diff --git a/frontend/src/app/components/protected/create/hyper-ide/components/ide-tree/ide-tree.component.ts b/frontend/src/app/components/protected/create/hyper-ide/components/ide-tree/ide-tree.component.ts index 61ec790b1d..b8e23307ac 100644 --- a/frontend/src/app/components/protected/create/hyper-ide/components/ide-tree/ide-tree.component.ts +++ b/frontend/src/app/components/protected/create/hyper-ide/components/ide-tree/ide-tree.component.ts @@ -207,7 +207,8 @@ export class IdeTreeComponent implements OnInit { next: (result: any) => { this.dialog.open(ParametriseActionDialog, { - width: '550px', + width: '750px', + maxWidth: '80vw', disableClose: true, data: { input: result.input, diff --git a/frontend/src/app/components/protected/create/hyper-ide/components/parametrise-action-dialog/components/codemirror-sql-formly.component.ts b/frontend/src/app/components/protected/create/hyper-ide/components/parametrise-action-dialog/components/codemirror-sql-formly.component.ts index 30620b2379..1bcb3b16d2 100644 --- a/frontend/src/app/components/protected/create/hyper-ide/components/parametrise-action-dialog/components/codemirror-sql-formly.component.ts +++ b/frontend/src/app/components/protected/create/hyper-ide/components/parametrise-action-dialog/components/codemirror-sql-formly.component.ts @@ -7,7 +7,10 @@ import { ChangeDetectorRef, Component, OnInit, ViewChild } from '@angular/core'; import { CodemirrorComponent } from '@ctrl/ngx-codemirror'; import { FieldType, FieldTypeConfig } from '@ngx-formly/core'; +import { Databases } from 'src/app/models/databases.model'; import { CodemirrorActionsService } from 'src/app/services/codemirror-actions.service'; +import { GeneralService } from 'src/app/services/general.service'; +import { SqlService } from 'src/app/services/sql.service'; /** * CodeMirror Formly extension field. @@ -18,13 +21,17 @@ import { CodemirrorActionsService } from 'src/app/services/codemirror-actions.se }) export class CodemirrorSqlFormlyComponent extends FieldType implements OnInit { + private databases: Databases = null; @ViewChild('editor') private editor: CodemirrorComponent; cmOptions: any = null; ready: boolean = false; constructor( - private codemirrorActionsService: CodemirrorActionsService, - private cdn: ChangeDetectorRef) { + private sqlService: SqlService, + private cdn: ChangeDetectorRef, + private generalService: GeneralService, + private codemirrorActionsService: CodemirrorActionsService) { + super(); } @@ -44,9 +51,79 @@ export class CodemirrorSqlFormlyComponent extends FieldType imp // Waiting until CodeMirror is displayed, and cleaning history. setTimeout(() => { + + // Cleaning out history and marking editor as clean. this.editor.codeMirror.getDoc().markClean(); this.editor.codeMirror.getDoc().clearHistory(); + + // Verifying we've got database type, connection string, and database values. + if (this.form.controls['database-type'] && + this.form.controls['connection-string'] && + this.form.controls['database']) { + + // Retrieving tables for autocomplete. + this.getDatabaseTables(); + + // Making sure we listen to changes in model. + this.form.controls['database-type'].valueChanges.subscribe({ + next : () => { + this.getDatabaseTables(); + } + }); + this.form.controls['connection-string'].valueChanges.subscribe({ + next : () => { + this.getDatabaseTables(); + } + }); + this.form.controls['database'].valueChanges.subscribe({ + next : () => { + this.databaseChanged(); + } + }); + } }, 1); }, 250); } + + /* + * Private helpers. + */ + + private getDatabaseTables() { + + // Verifying we've got a "well known type" that allows us to retrieve database meta information. + if (this.model['database-type'] === '' || + this.model['connection-string'] === '' || + this.model['database'] === '') { + + // No valid database is selected. + return; + } + + this.generalService.showLoading(); + this.sqlService.getDatabaseMetaInfo(this.model['database-type'], this.model['connection-string']).subscribe({ + + next: (result: Databases) => { + + this.databases = result; + this.generalService.hideLoading(); + this.databaseChanged(); + }, + + error: (error: any) => { + + this.generalService.hideLoading(); + this.generalService.showFeedback(error?.error?.message ?? error, 'errorMessage'); + } + }); + } + + private databaseChanged() { + + let hintTables = (this.databases.databases || []).find((db: any) => db.name === this.model['database'])?.tables || []; + const hints = Object.fromEntries(hintTables.map((x: any) => [x.name, x.columns.map((y: any) => y.name)])); + this.cmOptions.hintOptions = { + tables: hints, + }; +} }