mirror of
				https://github.com/Fabio286/antares.git
				synced 2025-06-05 21:59:22 +02:00 
			
		
		
		
	feat(PostgreSQL): trigger rename and delete
This commit is contained in:
		@@ -115,7 +115,7 @@
 | 
			
		||||
    "electron-devtools-installer": "^3.2.0",
 | 
			
		||||
    "electron-webpack": "^2.8.2",
 | 
			
		||||
    "electron-webpack-vue": "^2.4.0",
 | 
			
		||||
    "eslint": "^7.27.0",
 | 
			
		||||
    "eslint": "^7.28.0",
 | 
			
		||||
    "eslint-config-standard": "^16.0.3",
 | 
			
		||||
    "eslint-plugin-import": "^2.23.4",
 | 
			
		||||
    "eslint-plugin-node": "^11.1.0",
 | 
			
		||||
@@ -127,8 +127,8 @@
 | 
			
		||||
    "stylelint": "^13.13.1",
 | 
			
		||||
    "stylelint-config-standard": "^22.0.0",
 | 
			
		||||
    "stylelint-scss": "^3.19.0",
 | 
			
		||||
    "vue": "^2.6.13",
 | 
			
		||||
    "vue-template-compiler": "^2.6.13",
 | 
			
		||||
    "vue": "^2.6.14",
 | 
			
		||||
    "vue-template-compiler": "^2.6.14",
 | 
			
		||||
    "webpack": "^4.46.0"
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -63,7 +63,9 @@ module.exports = {
 | 
			
		||||
   functionContext: false,
 | 
			
		||||
   functionLanguage: false,
 | 
			
		||||
   triggerMiltipleEvents: false,
 | 
			
		||||
   triggerTableInName: false,
 | 
			
		||||
   triggerUpdateColumns: false,
 | 
			
		||||
   triggerOnlyRename: false,
 | 
			
		||||
   parametersLength: false,
 | 
			
		||||
   languages: false
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -13,7 +13,7 @@ module.exports = {
 | 
			
		||||
   // Structure
 | 
			
		||||
   tables: true,
 | 
			
		||||
   views: true,
 | 
			
		||||
   triggers: false,
 | 
			
		||||
   triggers: true,
 | 
			
		||||
   routines: true,
 | 
			
		||||
   functions: true,
 | 
			
		||||
   // Settings
 | 
			
		||||
@@ -25,7 +25,7 @@ module.exports = {
 | 
			
		||||
   databaseEdit: false,
 | 
			
		||||
   tableSettings: true,
 | 
			
		||||
   viewSettings: true,
 | 
			
		||||
   triggerSettings: false,
 | 
			
		||||
   triggerSettings: true,
 | 
			
		||||
   routineSettings: true,
 | 
			
		||||
   functionSettings: true,
 | 
			
		||||
   indexes: true,
 | 
			
		||||
@@ -38,5 +38,8 @@ module.exports = {
 | 
			
		||||
   functionSql: '$BODY$\r\n\r\n$BODY$',
 | 
			
		||||
   functionContext: true,
 | 
			
		||||
   functionLanguage: true,
 | 
			
		||||
   triggerMultipleEvents: true,
 | 
			
		||||
   triggerTableInName: true,
 | 
			
		||||
   triggerOnlyRename: true,
 | 
			
		||||
   languages: ['sql', 'plpgsql', 'c', 'internal']
 | 
			
		||||
};
 | 
			
		||||
 
 | 
			
		||||
@@ -584,8 +584,8 @@ export class MySQLClient extends AntaresCore {
 | 
			
		||||
            sql: row['SQL Original Statement'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0],
 | 
			
		||||
            name: row.Trigger,
 | 
			
		||||
            table: row['SQL Original Statement'].match(/(?<=ON `).*?(?=`)/gs)[0],
 | 
			
		||||
            event1: row['SQL Original Statement'].match(/(BEFORE|AFTER)/gs)[0],
 | 
			
		||||
            event2: row['SQL Original Statement'].match(/(INSERT|UPDATE|DELETE)/gs)[0]
 | 
			
		||||
            activation: row['SQL Original Statement'].match(/(BEFORE|AFTER)/gs)[0],
 | 
			
		||||
            event: row['SQL Original Statement'].match(/(INSERT|UPDATE|DELETE)/gs)[0]
 | 
			
		||||
         };
 | 
			
		||||
      })[0];
 | 
			
		||||
   }
 | 
			
		||||
@@ -630,7 +630,7 @@ export class MySQLClient extends AntaresCore {
 | 
			
		||||
    * @memberof MySQLClient
 | 
			
		||||
    */
 | 
			
		||||
   async createTrigger (trigger) {
 | 
			
		||||
      const sql = `CREATE ${trigger.definer ? `DEFINER=${trigger.definer} ` : ''}TRIGGER \`${this._schema}\`.\`${trigger.name}\` ${trigger.event1} ${trigger.event2} ON \`${trigger.table}\` FOR EACH ROW ${trigger.sql}`;
 | 
			
		||||
      const sql = `CREATE ${trigger.definer ? `DEFINER=${trigger.definer} ` : ''}TRIGGER \`${this._schema}\`.\`${trigger.name}\` ${trigger.activation} ${trigger.event} ON \`${trigger.table}\` FOR EACH ROW ${trigger.sql}`;
 | 
			
		||||
      return await this.raw(sql, { split: false });
 | 
			
		||||
   }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -496,17 +496,33 @@ export class PostgreSQLClient extends AntaresCore {
 | 
			
		||||
    * @memberof PostgreSQLClient
 | 
			
		||||
    */
 | 
			
		||||
   async getTriggerInformations ({ schema, trigger }) {
 | 
			
		||||
      const sql = `SHOW CREATE TRIGGER \`${schema}\`.\`${trigger}\``;
 | 
			
		||||
      const results = await this.raw(sql);
 | 
			
		||||
      const [table, triggerName] = trigger.split('.');
 | 
			
		||||
 | 
			
		||||
      const results = await this.raw(`
 | 
			
		||||
         SELECT event_object_schema AS table_schema,
 | 
			
		||||
            event_object_table AS table_name,
 | 
			
		||||
            trigger_schema,
 | 
			
		||||
            trigger_name,
 | 
			
		||||
            string_agg(event_manipulation, ',') AS event,
 | 
			
		||||
            action_timing AS activation,
 | 
			
		||||
            action_condition AS condition,
 | 
			
		||||
            action_statement AS definition
 | 
			
		||||
         FROM information_schema.triggers
 | 
			
		||||
         WHERE trigger_schema = '${schema}'
 | 
			
		||||
         AND trigger_name = '${triggerName}'
 | 
			
		||||
         AND event_object_table = '${table}'
 | 
			
		||||
         GROUP BY 1,2,3,4,6,7,8
 | 
			
		||||
         ORDER BY table_schema,
 | 
			
		||||
                  table_name
 | 
			
		||||
      `);
 | 
			
		||||
 | 
			
		||||
      return results.rows.map(row => {
 | 
			
		||||
         return {
 | 
			
		||||
            definer: row['SQL Original Statement'].match(/(?<=DEFINER=).*?(?=\s)/gs)[0],
 | 
			
		||||
            sql: row['SQL Original Statement'].match(/(BEGIN|begin)(.*)(END|end)/gs)[0],
 | 
			
		||||
            name: row.Trigger,
 | 
			
		||||
            table: row['SQL Original Statement'].match(/(?<=ON `).*?(?=`)/gs)[0],
 | 
			
		||||
            event1: row['SQL Original Statement'].match(/(BEFORE|AFTER)/gs)[0],
 | 
			
		||||
            event2: row['SQL Original Statement'].match(/(INSERT|UPDATE|DELETE)/gs)[0]
 | 
			
		||||
            sql: row.definition,
 | 
			
		||||
            name: row.trigger_name,
 | 
			
		||||
            table: row.table_name,
 | 
			
		||||
            event: row.event.split(','),
 | 
			
		||||
            activation: row.activation
 | 
			
		||||
         };
 | 
			
		||||
      })[0];
 | 
			
		||||
   }
 | 
			
		||||
@@ -531,18 +547,21 @@ export class PostgreSQLClient extends AntaresCore {
 | 
			
		||||
    */
 | 
			
		||||
   async alterTrigger (params) {
 | 
			
		||||
      const { trigger } = params;
 | 
			
		||||
      const tempTrigger = Object.assign({}, trigger);
 | 
			
		||||
      tempTrigger.name = `Antares_${tempTrigger.name}_tmp`;
 | 
			
		||||
      // const tempTrigger = Object.assign({}, trigger);
 | 
			
		||||
      // tempTrigger.name = `Antares_${tempTrigger.name}_tmp`;
 | 
			
		||||
 | 
			
		||||
      try {
 | 
			
		||||
         await this.createTrigger(tempTrigger);
 | 
			
		||||
         await this.dropTrigger({ trigger: tempTrigger.name });
 | 
			
		||||
         await this.dropTrigger({ trigger: trigger.oldName });
 | 
			
		||||
         await this.createTrigger(trigger);
 | 
			
		||||
      }
 | 
			
		||||
      catch (err) {
 | 
			
		||||
         return Promise.reject(err);
 | 
			
		||||
      }
 | 
			
		||||
      // try {
 | 
			
		||||
      //    await this.createTrigger(tempTrigger);
 | 
			
		||||
      //    await this.dropTrigger({ trigger: tempTrigger.name });
 | 
			
		||||
      //    await this.dropTrigger({ trigger: trigger.oldName });
 | 
			
		||||
      //    await this.createTrigger(trigger);
 | 
			
		||||
      // }
 | 
			
		||||
      // catch (err) {
 | 
			
		||||
      //    return Promise.reject(err);
 | 
			
		||||
      // }
 | 
			
		||||
 | 
			
		||||
      const sql = `ALTER TRIGGER ${trigger.oldName} ON ${trigger.table} RENAME TO ${trigger.name}`;
 | 
			
		||||
      return await this.raw(sql);
 | 
			
		||||
   }
 | 
			
		||||
 | 
			
		||||
   /**
 | 
			
		||||
@@ -552,7 +571,7 @@ export class PostgreSQLClient extends AntaresCore {
 | 
			
		||||
    * @memberof PostgreSQLClient
 | 
			
		||||
    */
 | 
			
		||||
   async createTrigger (trigger) {
 | 
			
		||||
      const sql = `CREATE ${trigger.definer ? `DEFINER=${trigger.definer} ` : ''}TRIGGER \`${trigger.name}\` ${trigger.event1} ${trigger.event2} ON \`${trigger.table}\` FOR EACH ROW ${trigger.sql}`;
 | 
			
		||||
      const sql = `CREATE ${trigger.definer ? `DEFINER=${trigger.definer} ` : ''}TRIGGER \`${trigger.name}\` ${trigger.event} ${trigger.activation} ON \`${trigger.table}\` FOR EACH ROW ${trigger.sql}`;
 | 
			
		||||
      return await this.raw(sql, { split: false });
 | 
			
		||||
   }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -71,11 +71,11 @@
 | 
			
		||||
               </label>
 | 
			
		||||
               <div class="column">
 | 
			
		||||
                  <div class="input-group">
 | 
			
		||||
                     <select v-model="localTrigger.event1" class="form-select">
 | 
			
		||||
                     <select v-model="localTrigger.activation" class="form-select">
 | 
			
		||||
                        <option>BEFORE</option>
 | 
			
		||||
                        <option>AFTER</option>
 | 
			
		||||
                     </select>
 | 
			
		||||
                     <select v-model="localTrigger.event2" class="form-select">
 | 
			
		||||
                     <select v-model="localTrigger.event" class="form-select">
 | 
			
		||||
                        <option>INSERT</option>
 | 
			
		||||
                        <option>UPDATE</option>
 | 
			
		||||
                        <option>DELETE</option>
 | 
			
		||||
@@ -106,8 +106,8 @@ export default {
 | 
			
		||||
            sql: 'BEGIN\r\n\r\nEND',
 | 
			
		||||
            name: '',
 | 
			
		||||
            table: '',
 | 
			
		||||
            event1: 'BEFORE',
 | 
			
		||||
            event2: 'INSERT'
 | 
			
		||||
            activation: 'BEFORE',
 | 
			
		||||
            event: 'INSERT'
 | 
			
		||||
         },
 | 
			
		||||
         isOptionsChanging: false
 | 
			
		||||
      };
 | 
			
		||||
 
 | 
			
		||||
@@ -37,7 +37,7 @@
 | 
			
		||||
                  >
 | 
			
		||||
               </div>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="column col-auto">
 | 
			
		||||
            <div v-if="customizations.definer" class="column col-auto">
 | 
			
		||||
               <div class="form-group">
 | 
			
		||||
                  <label class="form-label">{{ $t('word.definer') }}</label>
 | 
			
		||||
                  <select
 | 
			
		||||
@@ -67,7 +67,7 @@
 | 
			
		||||
               </div>
 | 
			
		||||
            </div>
 | 
			
		||||
         </div>
 | 
			
		||||
         <div class="columns">
 | 
			
		||||
         <fieldset class="columns" :disabled="customizations.triggerOnlyRename">
 | 
			
		||||
            <div class="column col-auto">
 | 
			
		||||
               <div class="form-group">
 | 
			
		||||
                  <label class="form-label">{{ $t('word.table') }}</label>
 | 
			
		||||
@@ -82,19 +82,33 @@
 | 
			
		||||
               <div class="form-group">
 | 
			
		||||
                  <label class="form-label">{{ $t('word.event') }}</label>
 | 
			
		||||
                  <div class="input-group">
 | 
			
		||||
                     <select v-model="localTrigger.event1" class="form-select">
 | 
			
		||||
                     <select v-model="localTrigger.activation" class="form-select">
 | 
			
		||||
                        <option>BEFORE</option>
 | 
			
		||||
                        <option>AFTER</option>
 | 
			
		||||
                     </select>
 | 
			
		||||
                     <select v-model="localTrigger.event2" class="form-select">
 | 
			
		||||
                        <option>INSERT</option>
 | 
			
		||||
                        <option>UPDATE</option>
 | 
			
		||||
                        <option>DELETE</option>
 | 
			
		||||
                     <select
 | 
			
		||||
                        v-if="!customizations.triggerMultipleEvents"
 | 
			
		||||
                        v-model="localTrigger.event"
 | 
			
		||||
                        class="form-select"
 | 
			
		||||
                     >
 | 
			
		||||
                        <option v-for="event in Object.keys(localEvents)" :key="event">
 | 
			
		||||
                           {{ event }}
 | 
			
		||||
                        </option>
 | 
			
		||||
                     </select>
 | 
			
		||||
                     <div v-if="customizations.triggerMultipleEvents" class="px-4">
 | 
			
		||||
                        <label
 | 
			
		||||
                           v-for="event in Object.keys(localEvents)"
 | 
			
		||||
                           :key="event"
 | 
			
		||||
                           class="form-checkbox form-inline"
 | 
			
		||||
                           @change.prevent="changeEvents(event)"
 | 
			
		||||
                        >
 | 
			
		||||
                           <input :checked="localEvents[event]" type="checkbox"><i class="form-icon" /> {{ event }}
 | 
			
		||||
                        </label>
 | 
			
		||||
                     </div>
 | 
			
		||||
                  </div>
 | 
			
		||||
               </div>
 | 
			
		||||
            </div>
 | 
			
		||||
         </div>
 | 
			
		||||
         </fieldset>
 | 
			
		||||
      </div>
 | 
			
		||||
      <div class="workspace-query-results column col-12 mt-2 p-relative">
 | 
			
		||||
         <BaseLoader v-if="isLoading" />
 | 
			
		||||
@@ -136,7 +150,8 @@ export default {
 | 
			
		||||
         localTrigger: { sql: '' },
 | 
			
		||||
         lastTrigger: null,
 | 
			
		||||
         sqlProxy: '',
 | 
			
		||||
         editorHeight: 300
 | 
			
		||||
         editorHeight: 300,
 | 
			
		||||
         localEvents: { INSERT: false, UPDATE: false, DELETE: false }
 | 
			
		||||
      };
 | 
			
		||||
   },
 | 
			
		||||
   computed: {
 | 
			
		||||
@@ -147,6 +162,9 @@ export default {
 | 
			
		||||
      workspace () {
 | 
			
		||||
         return this.getWorkspace(this.connection.uid);
 | 
			
		||||
      },
 | 
			
		||||
      customizations () {
 | 
			
		||||
         return this.workspace.customizations;
 | 
			
		||||
      },
 | 
			
		||||
      isSelected () {
 | 
			
		||||
         return this.workspace.selected_tab === 'prop' && this.selectedWorkspace === this.workspace.uid && this.trigger;
 | 
			
		||||
      },
 | 
			
		||||
@@ -209,6 +227,10 @@ export default {
 | 
			
		||||
      async getTriggerData () {
 | 
			
		||||
         if (!this.trigger) return;
 | 
			
		||||
 | 
			
		||||
         Object.keys(this.localEvents).forEach(event => {
 | 
			
		||||
            this.localEvents[event] = false;
 | 
			
		||||
         });
 | 
			
		||||
 | 
			
		||||
         this.localTrigger = { sql: '' };
 | 
			
		||||
         this.isLoading = true;
 | 
			
		||||
 | 
			
		||||
@@ -224,6 +246,12 @@ export default {
 | 
			
		||||
               this.originalTrigger = response;
 | 
			
		||||
               this.localTrigger = JSON.parse(JSON.stringify(this.originalTrigger));
 | 
			
		||||
               this.sqlProxy = this.localTrigger.sql;
 | 
			
		||||
 | 
			
		||||
               if (this.customizations.triggerMultipleEvents) {
 | 
			
		||||
                  this.originalTrigger.event.forEach(e => {
 | 
			
		||||
                     this.localEvents[e] = true;
 | 
			
		||||
                  });
 | 
			
		||||
               }
 | 
			
		||||
            }
 | 
			
		||||
            else
 | 
			
		||||
               this.addNotification({ status: 'error', message: response });
 | 
			
		||||
@@ -235,6 +263,16 @@ export default {
 | 
			
		||||
         this.resizeQueryEditor();
 | 
			
		||||
         this.isLoading = false;
 | 
			
		||||
      },
 | 
			
		||||
      changeEvents (event) {
 | 
			
		||||
         if (this.customizations.triggerMultipleEvents) {
 | 
			
		||||
            this.localEvents[event] = !this.localEvents[event];
 | 
			
		||||
            this.localTrigger.event = [];
 | 
			
		||||
            for (const key in this.localEvents) {
 | 
			
		||||
               if (this.localEvents[key])
 | 
			
		||||
                  this.localTrigger.event.push(key);
 | 
			
		||||
            }
 | 
			
		||||
         }
 | 
			
		||||
      },
 | 
			
		||||
      async saveChanges () {
 | 
			
		||||
         if (this.isSaving) return;
 | 
			
		||||
         this.isSaving = true;
 | 
			
		||||
@@ -257,7 +295,8 @@ export default {
 | 
			
		||||
 | 
			
		||||
               if (oldName !== this.localTrigger.name) {
 | 
			
		||||
                  this.setUnsavedChanges(false);
 | 
			
		||||
                  this.changeBreadcrumbs({ schema: this.schema, trigger: this.localTrigger.name });
 | 
			
		||||
                  const triggerName = this.customizations.triggerTableInName ? `${this.localTrigger.table}.${this.localTrigger.name}` : this.localTrigger.name;
 | 
			
		||||
                  this.changeBreadcrumbs({ schema: this.schema, trigger: triggerName });
 | 
			
		||||
               }
 | 
			
		||||
 | 
			
		||||
               this.getTriggerData();
 | 
			
		||||
@@ -274,6 +313,16 @@ export default {
 | 
			
		||||
      clearChanges () {
 | 
			
		||||
         this.localTrigger = JSON.parse(JSON.stringify(this.originalTrigger));
 | 
			
		||||
         this.$refs.queryEditor.editor.session.setValue(this.localTrigger.sql);
 | 
			
		||||
 | 
			
		||||
         Object.keys(this.localEvents).forEach(event => {
 | 
			
		||||
            this.localEvents[event] = false;
 | 
			
		||||
         });
 | 
			
		||||
 | 
			
		||||
         if (this.customizations.triggerMultipleEvents) {
 | 
			
		||||
            this.originalTrigger.event.forEach(e => {
 | 
			
		||||
               this.localEvents[e] = true;
 | 
			
		||||
            });
 | 
			
		||||
         }
 | 
			
		||||
      },
 | 
			
		||||
      resizeQueryEditor () {
 | 
			
		||||
         if (this.$refs.queryEditor) {
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user