UNPKG

gethue

Version:

Hue is an Open source SQL Query Editor for Databases/Warehouses

121 lines (105 loc) 4.44 kB
// Licensed to Cloudera, Inc. under one // or more contributor license agreements. See the NOTICE file // distributed with this work for additional information // regarding copyright ownership. Cloudera, Inc. licenses this file // to you under the Apache License, Version 2.0 (the // "License"); you may not use this file except in compliance // with the License. You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. import huePubSub from '../../../utils/huePubSub'; import { ACTIVE_STATEMENT_CHANGED_EVENT } from '../../../ko/bindings/ace/aceLocationHandler'; import AceAnchoredRange from '../../../ko/bindings/ace/aceAnchoredRange'; import { EXECUTABLE_UPDATED_TOPIC } from '../../../apps/editor/execution/events'; // TODO: depends on Ace const LINE_BREAK_REGEX = /(\r\n)|(\n)|(\r)/g; const LEADING_WHITE_SPACE_REGEX = /^\s+/; const ACTIVE_CSS = 'ace-active-gutter-decoration'; const COMPLETED_CSS = 'ace-completed-gutter-decoration'; const EXECUTING_CSS = 'ace-executing-gutter-decoration'; const FAILED_CSS = 'ace-failed-gutter-decoration'; const FAILED_MARKER_CSS = 'ace-failed-marker'; const getLeadingEmptyLineCount = parsedStatement => { let leadingEmptyLineCount = 0; const leadingWhiteSpace = parsedStatement.statement.match(LEADING_WHITE_SPACE_REGEX); if (leadingWhiteSpace) { const lineBreakMatch = leadingWhiteSpace[0].match(LINE_BREAK_REGEX); if (lineBreakMatch) { leadingEmptyLineCount = lineBreakMatch.length; } } return leadingEmptyLineCount; }; export default class AceGutterHandler { constructor(options) { this.editor = options.editor; this.editorId = options.editorId; this.executor = options.executor; this.disposals = []; const activeStatementAnchor = new AceAnchoredRange(this.editor); activeStatementAnchor.addGutterCss(ACTIVE_CSS); const changedSubscription = huePubSub.subscribe( ACTIVE_STATEMENT_CHANGED_EVENT, statementDetails => { if (statementDetails.id !== this.editorId || !statementDetails.activeStatement) { return; } const leadingEmptyLineCount = getLeadingEmptyLineCount(statementDetails.activeStatement); activeStatementAnchor.move( statementDetails.activeStatement.location, leadingEmptyLineCount ); } ); this.disposals.push(() => { changedSubscription.remove(); activeStatementAnchor.dispose(); }); if (this.executor) { const executableSub = huePubSub.subscribe(EXECUTABLE_UPDATED_TOPIC, executable => { if (executable.executor === this.executor) { if (executable.lost) { if (executable.observerState.aceAnchor) { executable.observerState.aceAnchor.dispose(); delete executable.observerState.aceAnchor; } return; } const statement = executable.parsedStatement; if (!executable.observerState.aceAnchor) { executable.observerState.aceAnchor = new AceAnchoredRange(this.editor); } const leadingEmptyLineCount = getLeadingEmptyLineCount(statement); executable.observerState.aceAnchor.move(statement.location, leadingEmptyLineCount); const anchoredRange = executable.observerState.aceAnchor; anchoredRange.removeGutterCss(COMPLETED_CSS); anchoredRange.removeGutterCss(EXECUTING_CSS); anchoredRange.removeGutterCss(FAILED_CSS); anchoredRange.removeMarkerCss(FAILED_MARKER_CSS); if (executable.isRunning()) { anchoredRange.addGutterCss(EXECUTING_CSS); } else if (executable.isSuccess()) { anchoredRange.addGutterCss(COMPLETED_CSS); } else if (executable.isFailed()) { anchoredRange.addMarkerCss(FAILED_MARKER_CSS); anchoredRange.addGutterCss(FAILED_CSS); } } }); this.disposals.push(() => { executableSub.remove(); }); } } dispose() { while (this.disposals.length) { this.disposals.pop()(); } } }