From 856a9dbefcd1d334b18d381aa7ec5df5867eeafc Mon Sep 17 00:00:00 2001 From: ChanHo Lee Date: Mon, 25 Nov 2024 12:20:12 +0900 Subject: [PATCH] [ZEPPELIN-6151] Remove AngularJS -> Angular Code Migration Suggestion Feature ### What is this PR for? I propose removing the feature in Zeppelin's new UI that converts AngularJS code to Angular code. This feature currently prompts users when they run code with the `%angular` prefix, asking whether to migrate AngularJS code to Angular, and performs the migration if confirmed. The reasons for suggesting its removal are as follows: - The library supporting this feature is not compatible with the latest Angular versions due to peer dependency issues, making it difficult to upgrade Angular. - It is likely that this feature is not widely used by the community. Removing this feature will reduce unnecessary library dependencies, which will help streamline future updates to the latest Angular versions. If you have any other opinions, please feel free to share them. ### What type of PR is it? Removing Feature ### Todos * [ ] - Task ### What is the Jira issue? https://issues.apache.org/jira/browse/ZEPPELIN-6151 ### How should this be tested? * Strongly recommended: add automated unit tests for any new or changed behavior * Outline any manual steps to test the PR here. ### Screenshots (if appropriate) ### Questions: * Does the license files need to update? No * Is there breaking changes for older versions? No * Does this needs documentation? No Closes #4900 from tbonelee/remove-ng1-migration. Signed-off-by: Cheng Pan (cherry picked from commit ae48f71a564f5cb3e54759c9fcc214c4d8069517) Signed-off-by: Cheng Pan --- zeppelin-web-angular/package-lock.json | 18 -- zeppelin-web-angular/package.json | 1 - .../notebook/paragraph/paragraph.component.ts | 43 +--- .../services/ng-template-adapter.service.ts | 65 ------ .../ng1-migration.component.html | 65 ------ .../ng1-migration.component.less | 88 --------- .../ng1-migration/ng1-migration.component.ts | 185 ------------------ .../src/app/share/share.module.ts | 6 +- 8 files changed, 11 insertions(+), 460 deletions(-) delete mode 100644 zeppelin-web-angular/src/app/services/ng-template-adapter.service.ts delete mode 100644 zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.html delete mode 100644 zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.less delete mode 100644 zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.ts diff --git a/zeppelin-web-angular/package-lock.json b/zeppelin-web-angular/package-lock.json index acfe98974a0..2a6f4791e32 100644 --- a/zeppelin-web-angular/package-lock.json +++ b/zeppelin-web-angular/package-lock.json @@ -30,7 +30,6 @@ "mathjax": "2.7.5", "monaco-editor": "0.15.1", "ng-zorro-antd": "^8.4.0", - "ng1-template-updater": "0.0.4", "parse5": "^5.1.1", "rxjs": "~6.5.3", "systemjs": "^5.0.0", @@ -11535,17 +11534,6 @@ "rxjs": "^6.4.0" } }, - "node_modules/ng1-template-updater": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/ng1-template-updater/-/ng1-template-updater-0.0.4.tgz", - "integrity": "sha512-GgmAV7Zbj8ZLQ/IJGjjSi40bXTHFP/k5fhlxcH0V2fWaya5lu6y07Vh4LKvuUqNbkbKl28XW8Z1fhL5pwHxgsA==", - "peerDependencies": { - "@angular/common": "^8.0.0", - "@angular/core": "^8.0.0", - "parse5": "^5.1.1", - "tslib": "^1.10.0" - } - }, "node_modules/ngx-build-plus": { "version": "8.1.5", "resolved": "https://registry.npmjs.org/ngx-build-plus/-/ngx-build-plus-8.1.5.tgz", @@ -28153,12 +28141,6 @@ "tslib": "^1.9.0" } }, - "ng1-template-updater": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/ng1-template-updater/-/ng1-template-updater-0.0.4.tgz", - "integrity": "sha512-GgmAV7Zbj8ZLQ/IJGjjSi40bXTHFP/k5fhlxcH0V2fWaya5lu6y07Vh4LKvuUqNbkbKl28XW8Z1fhL5pwHxgsA==", - "requires": {} - }, "ngx-build-plus": { "version": "8.1.5", "resolved": "https://registry.npmjs.org/ngx-build-plus/-/ngx-build-plus-8.1.5.tgz", diff --git a/zeppelin-web-angular/package.json b/zeppelin-web-angular/package.json index 383fe3d3cec..d2b5d377ba5 100644 --- a/zeppelin-web-angular/package.json +++ b/zeppelin-web-angular/package.json @@ -41,7 +41,6 @@ "mathjax": "2.7.5", "monaco-editor": "0.15.1", "ng-zorro-antd": "^8.4.0", - "ng1-template-updater": "0.0.4", "parse5": "^5.1.1", "rxjs": "~6.5.3", "systemjs": "^5.0.0", diff --git a/zeppelin-web-angular/src/app/pages/workspace/notebook/paragraph/paragraph.component.ts b/zeppelin-web-angular/src/app/pages/workspace/notebook/paragraph/paragraph.component.ts index 3afdea13f6d..719877ad00d 100644 --- a/zeppelin-web-angular/src/app/pages/workspace/notebook/paragraph/paragraph.component.ts +++ b/zeppelin-web-angular/src/app/pages/workspace/notebook/paragraph/paragraph.component.ts @@ -46,7 +46,6 @@ import { } from '@zeppelin/services'; import { SpellResult } from '@zeppelin/spell/spell-result'; -import { NgTemplateAdapterService } from '@zeppelin/services/ng-template-adapter.service'; import { NzResizeEvent } from 'ng-zorro-antd/resizable'; import { NotebookParagraphResultComponent } from '../../share/result/result.component'; import { NotebookParagraphCodeEditorComponent } from './code-editor/code-editor.component'; @@ -301,31 +300,8 @@ export class NotebookParagraphComponent extends ParagraphBase implements OnInit, this.runParagraphUsingSpell(text, magic, propagated); this.runParagraphAfter(text); } else { - const check = this.ngTemplateAdapterService.preCheck(text); - if (!check) { - this.runParagraphUsingBackendInterpreter(text); - this.runParagraphAfter(text); - } else { - this.waitConfirmFromEdit = true; - this.nzModalService - .confirm({ - nzTitle: 'Do you want to migrate the Angular.js template?', - nzContent: - 'The Angular.js template has been deprecated, please upgrade to Angular template.' + - ' (more info)', - nzOnOk: () => { - this.switchMode('command'); - this.ngTemplateAdapterService - .openMigrationDialog(check) - .pipe(takeUntil(this.destroy$)) - .subscribe(newText => { - this.cloneParagraph('below', newText); - }); - } - }) - .afterClose.pipe(takeUntil(this.destroy$)) - .subscribe(() => (this.waitConfirmFromEdit = false)); - } + this.runParagraphUsingBackendInterpreter(text); + this.runParagraphAfter(text); } } } @@ -452,20 +428,17 @@ export class NotebookParagraphComponent extends ParagraphBase implements OnInit, private nzModalService: NzModalService, private noteVarShareService: NoteVarShareService, private shortcutService: ShortcutService, - private host: ElementRef, - private ngTemplateAdapterService: NgTemplateAdapterService + private host: ElementRef ) { super(messageService, noteStatusService, ngZService, cdr); } ngOnInit() { const shortcutService = this.shortcutService.forkByElement(this.host.nativeElement); - const observables: Array< - Observable<{ - action: ParagraphActions; - event: KeyboardEvent; - }> - > = []; + const observables: Array> = []; Object.entries(ShortcutsMap).forEach(([action, keys]) => { const keysArr: string[] = Array.isArray(keys) ? keys : [keys]; keysArr.forEach(key => { @@ -617,6 +590,7 @@ export class NotebookParagraphComponent extends ParagraphBase implements OnInit, }); } } + ngOnChanges(changes: SimpleChanges): void { const { index, select, scrolled } = changes; if ( @@ -637,6 +611,7 @@ export class NotebookParagraphComponent extends ParagraphBase implements OnInit, getElement(): HTMLElement { return this.host && this.host.nativeElement; } + ngAfterViewInit(): void { this.scrollIfNeeded(); } diff --git a/zeppelin-web-angular/src/app/services/ng-template-adapter.service.ts b/zeppelin-web-angular/src/app/services/ng-template-adapter.service.ts deleted file mode 100644 index f965e1dd8e9..00000000000 --- a/zeppelin-web-angular/src/app/services/ng-template-adapter.service.ts +++ /dev/null @@ -1,65 +0,0 @@ -/* - * Licensed 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 { Injectable } from '@angular/core'; -import { Ng1MigrationComponent } from '@zeppelin/share/ng1-migration/ng1-migration.component'; -import { NzModalService } from 'ng-zorro-antd/modal'; -import { Observable } from 'rxjs'; - -export interface NgTemplateCheckResult { - index: number; - match: string; - magic: string; - template: string; - origin: string; -} - -@Injectable({ - providedIn: 'root' -}) -export class NgTemplateAdapterService { - constructor(private nzModalService: NzModalService) {} - preCheck(origin: string): NgTemplateCheckResult | null { - const regexp = /(%angular)([\s\S]*<[\s\S]*>)/im; - const math = regexp.exec(origin); - if (math) { - const index = math.index; - const [output, magic, template] = math; - return { - index, - magic, - template, - origin, - match: output - }; - } - return null; - } - - openMigrationDialog(check: NgTemplateCheckResult): Observable { - const modalRef = this.nzModalService.create({ - nzTitle: 'Angular.js Templates Migration Tool', - nzContent: Ng1MigrationComponent, - nzComponentParams: check, - nzFooter: null, - nzWidth: '980px', - nzStyle: { - top: '45px' - }, - nzBodyStyle: { - padding: '0' - } - }); - - return modalRef.afterClose; - } -} diff --git a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.html b/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.html deleted file mode 100644 index da6ea8525ae..00000000000 --- a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.html +++ /dev/null @@ -1,65 +0,0 @@ - -
- - -
-
- -
- - - - - {{errorCount}} - - - - {{messageDetails.length - errorCount}} - - -
- -
- - - ({{(item.pos.line + 1) + ',' + (item.pos.character + 1)}}) - {{item.message}} - more -
-
- -
- - -
diff --git a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.less b/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.less deleted file mode 100644 index 107cfddcc2e..00000000000 --- a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.less +++ /dev/null @@ -1,88 +0,0 @@ -/* - * Licensed 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. - */ -:host { - height: 70vh; - display: flex; - - .code-editor { - flex: auto; - } - - .messages { - overflow: auto; - position: relative; - width: 240px; - border-left: 1px solid #e8e8e8; - - i { - &.error { - color: red; - } - &.close { - color: #1f8ffb; - } - } - - .fix-bar { - padding-right: 16px; - display: flex; - font-size: 12px; - border-bottom: 1px solid #e8e8e8; - height: 25px; - line-height: 25px; - .fix-btn { - flex: 0; - font-size: 12px; - } - .log-counts { - text-align: right; - flex: 1 auto; - } - } - - - .message { - font-family: Consolas, Verdana; - color: #1e1e1e; - padding: 8px 16px 8px 5px; - transition: background-color 0.3s; - word-break: break-all; - line-height: 17px; - cursor: pointer; - font-size: 12px; - .position { - color: #5d5d5d; - } - &:hover { - background-color: #ffb86c; - } - } - } -} - - -::ng-deep { - .monaco-editor { - .scroll-decoration { - box-shadow: none; - } - .decoration-link { - text-decoration-color: red; - text-decoration-line: underline; - text-decoration-style: wavy; - text-decoration-skip-ink: none; - } - .warn-content { - background: rgba(182, 182, 182, .3); - } - } -} diff --git a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.ts b/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.ts deleted file mode 100644 index 5eea0712f0c..00000000000 --- a/zeppelin-web-angular/src/app/share/ng1-migration/ng1-migration.component.ts +++ /dev/null @@ -1,185 +0,0 @@ -/* - * Licensed 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 { ChangeDetectionStrategy, ChangeDetectorRef, Component, Input, OnDestroy } from '@angular/core'; -import { editor, IDisposable, Range } from 'monaco-editor'; -import { NzModalRef } from 'ng-zorro-antd/modal'; -import { - defaultTemplateUpdaterRules, - LogLevel, - Message, - MessageDetail, - TemplateUpdater, - ValueChangeRule -} from 'ng1-template-updater'; -import { combineLatest, Subject } from 'rxjs'; -import IEditor = editor.IEditor; -import ITextModel = editor.ITextModel; -import IStandaloneCodeEditor = editor.IStandaloneCodeEditor; - -const zeppelinFunctionChangeRule: ValueChangeRule = (expression: string, start?: number) => { - let value = expression; - const messages: Message[] = []; - const funChanges = [ - { - regexp: /z\.angularBind/gm, - replace: 'z.set' - }, - { - regexp: /z\.angularUnbind/gm, - replace: 'z.unset' - }, - { - regexp: /z\.runParagraph/gm, - replace: 'z.run' - } - ]; - - funChanges.forEach(change => { - let match = change.regexp.exec(value); - while (match !== null) { - messages.push({ - position: start + match.index, - message: `${match[0]} has been deprecated, using ${change.replace} instead`, - length: match[0].length, - // url: 'https://angular.io/guide/ajs-quick-reference', - level: LogLevel.Info - }); - match = change.regexp.exec(value); - } - value = value.replace(change.regexp, change.replace); - }); - - return { - messages, - value - }; -}; - -@Component({ - selector: 'zeppelin-ng1-migration', - templateUrl: './ng1-migration.component.html', - styleUrls: ['./ng1-migration.component.less'], - changeDetection: ChangeDetectionStrategy.OnPush -}) -export class Ng1MigrationComponent implements OnDestroy { - @Input() origin: string; - @Input() index: number; - @Input() match: string; - @Input() template: string; - - messageDetails: MessageDetail[] = []; - templateUpdater: TemplateUpdater; - errorCount = 0; - decorations: string[] = []; - timeoutId = -1; - editor: IStandaloneCodeEditor; - editorModel: ITextModel; - editorInit$ = new Subject(); - editorChangeDisposable: IDisposable; - - constructor(private nzModalRef: NzModalRef, private cdr: ChangeDetectorRef) { - const updateRules = { - ...defaultTemplateUpdaterRules, - valueChangeRules: [...defaultTemplateUpdaterRules.valueChangeRules, zeppelinFunctionChangeRule] - }; - this.templateUpdater = new TemplateUpdater(updateRules); - combineLatest([this.nzModalRef.afterOpen, this.editorInit$]).subscribe(() => { - if (this.editor) { - this.editorModel = this.editor.getModel() as ITextModel; - this.editor.setValue(this.template); - this.editor.layout(); - this.bindEditorEvents(); - this.check(); - setTimeout(() => { - this.editor.focus(); - }, 150); - } - }); - } - - onEditorInit(_editor: IEditor) { - this.editorInit$.next(); - this.editorInit$.complete(); - this.editor = _editor as IStandaloneCodeEditor; - } - - bindEditorEvents() { - if (this.editorModel) { - this.editorChangeDisposable = this.editorModel.onDidChangeContent(() => { - clearTimeout(this.timeoutId); - this.timeoutId = setTimeout(() => { - this.check(); - }, 300); - }); - } - } - - scrollToLine(failure: MessageDetail) { - const line = failure.pos.line + 1; - const character = failure.pos.character + 1; - const range = new Range(line, character, line, character + failure.length); - this.editor.revealRangeAtTop(range); - this.editor.setSelection(range); - this.editor.focus(); - } - - check() { - const code = this.editor.getValue(); - const { messages } = this.templateUpdater.parse(code); - this.messageDetails = [...messages]; - this.errorCount = messages.filter(f => f.level === LogLevel.Error).length; - this.decorations = this.editor.deltaDecorations( - this.decorations, - messages.map(failure => { - const line = failure.pos.line + 1; - const character = failure.pos.character + 1; - return { - range: new Range(line, character, line, character + failure.length), - options: { - className: failure.level === LogLevel.Error ? '' : 'warn-content', - inlineClassName: failure.level === LogLevel.Error ? 'decoration-link' : '', - stickiness: 1, - hoverMessage: { - value: failure.message + (failure.url ? ` [more](${failure.url})` : '') - } - } - }; - }) - ); - this.cdr.markForCheck(); - } - - fix() { - const code = this.editor.getValue(); - const { template } = this.templateUpdater.parse(code); - this.editor.setValue(template); - } - - updateAndCopy() { - const code = this.editor.getValue(); - const newTemplate = this.origin.replace(this.match, `%ng\n${code}`); - this.nzModalRef.close(newTemplate); - } - - cancel() { - this.nzModalRef.destroy(); - } - - ngOnDestroy(): void { - if (this.editorChangeDisposable) { - this.editorChangeDisposable.dispose(); - } - if (this.editorModel) { - this.editorModel.dispose(); - } - } -} diff --git a/zeppelin-web-angular/src/app/share/share.module.ts b/zeppelin-web-angular/src/app/share/share.module.ts index 1070a7b83ad..ee6e8bda147 100644 --- a/zeppelin-web-angular/src/app/share/share.module.ts +++ b/zeppelin-web-angular/src/app/share/share.module.ts @@ -40,6 +40,7 @@ import { NzUploadModule } from 'ng-zorro-antd/upload'; import { AboutZeppelinComponent } from '@zeppelin/share/about-zeppelin/about-zeppelin.component'; import { CodeEditorModule } from '@zeppelin/share/code-editor'; +import { ExternalLinkDirective } from '@zeppelin/share/external-links/external-link.directive'; import { FolderRenameComponent } from '@zeppelin/share/folder-rename/folder-rename.component'; import { HeaderComponent } from '@zeppelin/share/header/header.component'; import { MathJaxDirective } from '@zeppelin/share/math-jax/math-jax.directive'; @@ -51,9 +52,7 @@ import { NoteTocComponent } from '@zeppelin/share/note-toc/note-toc.component'; import { PageHeaderComponent } from '@zeppelin/share/page-header/page-header.component'; import { HumanizeBytesPipe } from '@zeppelin/share/pipes'; import { RunScriptsDirective } from '@zeppelin/share/run-scripts/run-scripts.directive'; -import { ExternalLinkDirective } from "@zeppelin/share/external-links/external-link.directive"; import { SpinComponent } from '@zeppelin/share/spin/spin.component'; -import { Ng1MigrationComponent } from './ng1-migration/ng1-migration.component'; import { ResizeHandleComponent } from './resize-handle'; const MODAL_LIST = [ @@ -61,8 +60,7 @@ const MODAL_LIST = [ NoteImportComponent, NoteCreateComponent, NoteRenameComponent, - FolderRenameComponent, - Ng1MigrationComponent + FolderRenameComponent ]; const EXPORT_LIST = [ HeaderComponent,