Ahmad Kholid 2 gadi atpakaļ
vecāks
revīzija
49e37eeddc

+ 1 - 1
package.json

@@ -1,6 +1,6 @@
 {
   "name": "automa",
-  "version": "1.21.4",
+  "version": "1.21.6",
   "description": "An extension for automating your browser by connecting blocks",
   "repository": {
     "type": "git",

+ 53 - 32
src/background/index.js

@@ -256,7 +256,8 @@ async function checkVisitWebTriggers(tabId, tabUrl) {
     }
 
     const workflowData = await workflow.get(workflowId);
-    if (workflowData) workflow.execute(workflowData, { tabId });
+    if (workflowData && !workflow.isDisabled)
+      workflow.execute(workflowData, { tabId });
   }
 }
 async function checkRecordingWorkflow(tabId, tabUrl) {
@@ -270,7 +271,7 @@ async function checkRecordingWorkflow(tabId, tabUrl) {
     file: 'recordWorkflow.bundle.js',
   });
 }
-browser.webNavigation.onHistoryStateUpdated.addListener(
+browser.webNavigation.onCompleted.addListener(
   async ({ tabId, url, frameId }) => {
     if (frameId > 0) return;
 
@@ -528,43 +529,63 @@ browser.runtime.onInstalled.addListener(async ({ reason }) => {
   }
 });
 browser.runtime.onStartup.addListener(async () => {
-  const { workflows, workflowHosts, teamWorkflows } =
-    await browser.storage.local.get([
-      'workflows',
-      'workflowHosts',
-      'teamWorkflows',
-    ]);
-  const convertToArr = (value) =>
-    Array.isArray(value) ? value : Object.values(value);
-
-  const workflowsArr = convertToArr(workflows);
+  try {
+    const { workflows, workflowHosts, teamWorkflows } =
+      await browser.storage.local.get([
+        'workflows',
+        'workflowHosts',
+        'teamWorkflows',
+      ]);
+    const convertToArr = (value) =>
+      Array.isArray(value) ? value : Object.values(value);
+
+    const workflowsArr = convertToArr(workflows);
+
+    if (workflowHosts) {
+      workflowsArr.push(...convertToArr(workflowHosts));
+    }
+    if (teamWorkflows) {
+      workflowsArr.push(...flattenTeamWorkflows(teamWorkflows));
+    }
 
-  if (workflowHosts) {
-    workflowsArr.push(...convertToArr(workflowHosts));
-  }
-  if (teamWorkflows) {
-    workflowsArr.push(...flattenTeamWorkflows(teamWorkflows));
-  }
+    for (const currWorkflow of workflowsArr) {
+      let triggerBlock = currWorkflow.trigger;
 
-  for (const currWorkflow of workflowsArr) {
-    let triggerBlock = currWorkflow.trigger;
+      if (!triggerBlock) {
+        const flow =
+          typeof currWorkflow.drawflow === 'string'
+            ? parseJSON(currWorkflow.drawflow, {})
+            : currWorkflow.drawflow;
 
-    if (!triggerBlock) {
-      const flow =
-        typeof currWorkflow.drawflow === 'string'
-          ? parseJSON(currWorkflow.drawflow, {})
-          : currWorkflow.drawflow;
+        triggerBlock = findTriggerBlock(flow)?.data;
+      }
 
-      triggerBlock = findTriggerBlock(flow)?.data;
-    }
+      const executeWorkflow = async (trigger, triggerData) => {
+        if (trigger.type === 'on-startup') {
+          workflow.execute(currWorkflow);
+        } else if (trigger.type !== 'manual') {
+          await registerWorkflowTrigger(currWorkflow.id, triggerData);
+        }
+      };
+
+      if (triggerBlock) {
+        if (triggerBlock.triggers) {
+          for (const trigger of triggerBlock.triggers) {
+            if (trigger.type === 'on-startup') {
+              workflow.execute(currWorkflow);
+            }
+          }
 
-    if (triggerBlock) {
-      if (triggerBlock.type === 'on-startup') {
-        workflow.execute(currWorkflow);
-      } else {
-        await registerWorkflowTrigger(currWorkflow.id, { data: triggerBlock });
+          await registerWorkflowTrigger(currWorkflow.id, {
+            data: triggerBlock,
+          });
+        } else {
+          await executeWorkflow(triggerBlock, { data: triggerBlock });
+        }
       }
     }
+  } catch (error) {
+    console.error(error);
   }
 });
 

+ 12 - 5
src/background/workflowEngine/blocksHandler/handlerGoogleSheets.js

@@ -64,16 +64,23 @@ async function updateSpreadsheetValues(
     if (keysAsFirstRow) {
       values = convertArrObjTo2DArr(columns);
     } else {
-      values = columns.map((item) =>
-        Object.values(item).map((value) =>
-          typeof value === 'object' ? JSON.stringify(value) : value
-        )
-      );
+      values = columns.map((item) => Object.values(item));
     }
   } else if (dataFrom === 'custom') {
     values = parseJSON(customData, customData);
   }
 
+  if (Array.isArray(values)) {
+    const validTypes = ['boolean', 'string', 'number'];
+    values.forEach((row, rowIndex) => {
+      row.forEach((column, colIndex) => {
+        if (column && validTypes.includes(typeof column)) return;
+
+        values[rowIndex][colIndex] = ' ';
+      });
+    });
+  }
+
   const queries = {
     valueInputOption: valueInputOption || 'RAW',
   };

+ 15 - 0
src/background/workflowEngine/blocksHandler/handlerWebhook.js

@@ -3,6 +3,16 @@ import { isWhitespace } from '@/utils/helper';
 import { executeWebhook } from '@/utils/webhookUtil';
 import mustacheReplacer from '@/utils/referenceData/mustacheReplacer';
 
+function fileReader(blob) {
+  return new Promise((resolve) => {
+    const reader = new FileReader();
+    reader.onload = () => {
+      resolve(reader.result);
+    };
+    reader.readAsDataURL(blob);
+  });
+}
+
 export async function webhook({ data, id }, { refData }) {
   const nextBlockId = this.getBlockConnections(id);
   const fallbackOutput = this.getBlockConnections(id, 'fallback');
@@ -49,6 +59,11 @@ export async function webhook({ data, id }, { refData }) {
       const jsonRes = await response.json();
 
       returnData = objectPath.get(jsonRes, data.dataPath);
+    } else if (data.responseType === 'base64') {
+      const blob = await response.blob();
+      const base64 = await fileReader(blob);
+
+      returnData = base64;
     } else {
       returnData = await response.text();
     }

+ 2 - 5
src/components/newtab/workflow/edit/EditWebhook.vue

@@ -86,11 +86,7 @@
             <v-remixicon name="riCloseCircleLine" size="20" />
           </button>
         </template>
-        <ui-button
-          class="col-span-4 mt-4 block w-full"
-          variant="accent"
-          @click="addHeader"
-        >
+        <ui-button class="col-span-4 mt-4 block w-full" @click="addHeader">
           <span> {{ t('workflow.blocks.webhook.buttons.header') }} </span>
         </ui-button>
       </ui-tab-panel>
@@ -111,6 +107,7 @@
         >
           <option value="json">JSON</option>
           <option value="text">Text</option>
+          <option value="base64">Base64</option>
         </ui-select>
         <ui-input
           v-if="data.responseType === 'json'"

+ 19 - 0
src/components/newtab/workflows/WorkflowsFolder.vue

@@ -50,6 +50,16 @@
             />
           </template>
           <ui-list class="w-36 space-y-1">
+            <ui-list-item
+              v-close-popover
+              class="cursor-pointer"
+              @click="exportFolderWorkflows(folder.id)"
+            >
+              <v-remixicon name="riDownloadLine" class="mr-2 -ml-1" />
+              <span>
+                {{ t('common.export') }}
+              </span>
+            </ui-list-item>
             <ui-list-item
               v-close-popover
               class="cursor-pointer"
@@ -83,6 +93,7 @@ import { useDialog } from '@/composable/dialog';
 import { parseJSON } from '@/utils/helper';
 import { useFolderStore } from '@/stores/folder';
 import { useWorkflowStore } from '@/stores/workflow';
+import { exportWorkflow } from '@/utils/workflowData';
 
 defineProps({
   modelValue: {
@@ -99,6 +110,14 @@ const workflowStore = useWorkflowStore();
 
 const folders = computed(() => folderStore.items);
 
+function exportFolderWorkflows(folderId) {
+  const workflows = workflowStore.getWorkflows.filter(
+    (item) => item.folderId === folderId
+  );
+  workflows.forEach((workflow) => {
+    exportWorkflow(workflow);
+  });
+}
 function onDragover(event, toggle) {
   const parent = event.target.closest('.ui-list-item');
   if (!parent) return;

+ 0 - 4
src/components/ui/UiModal.vue

@@ -78,9 +78,6 @@ export default {
     const show = ref(false);
     const modalContent = ref(null);
 
-    function onClickOverlay(event) {
-      console.log(event);
-    }
     function toggleBodyOverflow(value) {
       document.body.classList.toggle('overflow-hidden', value);
     }
@@ -115,7 +112,6 @@ export default {
       show,
       closeModal,
       modalContent,
-      onClickOverlay,
     };
   },
 };

+ 19 - 1
src/content/commandPalette/App.vue

@@ -150,10 +150,10 @@ import {
   inject,
 } from 'vue';
 import browser from 'webextension-polyfill';
-import { getReadableShortcut } from '@/composable/shortcut';
 import { sendMessage } from '@/utils/message';
 import { debounce } from '@/utils/helper';
 
+const os = navigator.appVersion.indexOf('Mac') !== -1 ? 'mac' : 'win';
 const defaultPlaceholders = {
   string: 'Text',
   number: '123123',
@@ -185,6 +185,24 @@ const workflows = computed(() =>
   )
 );
 
+function getReadableShortcut(str) {
+  const list = {
+    option: {
+      win: 'alt',
+      mac: 'option',
+    },
+    mod: {
+      win: 'ctrl',
+      mac: '⌘',
+    },
+  };
+  const regex = /option|mod/g;
+  const replacedStr = str.replace(regex, (match) => {
+    return list[match][os];
+  });
+
+  return replacedStr;
+}
 function clearParamsState() {
   Object.assign(paramsState, {
     items: [],

+ 13 - 16
src/content/services/shortcutListener.js

@@ -64,18 +64,21 @@ function workflowShortcutsListener(findWorkflow, shortcutsObj) {
   });
 }
 async function getWorkflows() {
-  const { workflows, workflowHosts } = await browser.storage.local.get([
+  const {
+    workflows: localWorkflows,
+    workflowHosts,
+    teamWorkflows,
+  } = await browser.storage.local.get([
     'workflows',
     'workflowHosts',
+    'teamWorkflows',
   ]);
-  const localWorkflows = Array.isArray(workflows)
-    ? workflows
-    : Object.values(workflows);
-
-  return {
-    local: localWorkflows,
-    hosted: Object.values(workflowHosts || {}),
-  };
+
+  return [
+    ...Object.values(workflowHosts || {}),
+    ...Object.values(localWorkflows || {}),
+    ...Object.values(Object.values(teamWorkflows || {})[0] || {}),
+  ];
 }
 
 export default async function () {
@@ -84,7 +87,7 @@ export default async function () {
     let workflows = await getWorkflows();
 
     const findWorkflow = (id, publicId = false) => {
-      let workflow = workflows.local.find((item) => {
+      const workflow = workflows.find((item) => {
         if (publicId) {
           return item.settings.publicId === id;
         }
@@ -92,12 +95,6 @@ export default async function () {
         return item.id === id;
       });
 
-      if (!workflow) {
-        workflow = workflows.hosted.find(({ hostId }) => hostId === id);
-
-        if (workflow) workflow.id = workflow.hostId;
-      }
-
       return workflow;
     };
 

+ 4 - 4
src/newtab/pages/workflows/[id].vue

@@ -697,10 +697,10 @@ function onClickEditor({ target }) {
     if (!connectionExist) {
       editor.value.addEdges([
         {
-          source: nodeid,
-          sourceHandle: handleid,
-          target: nodeTargetHandle.nodeId,
-          targetHandle: nodeTargetHandle.handleId,
+          target: nodeid,
+          targetHandle: handleid,
+          source: nodeTargetHandle.nodeId,
+          sourceHandle: nodeTargetHandle.handleId,
         },
       ]);
     }

+ 15 - 3
src/utils/workflowData.js

@@ -1,6 +1,12 @@
 import browser from 'webextension-polyfill';
 import { useWorkflowStore } from '@/stores/workflow';
-import { parseJSON, fileSaver, openFilePicker } from './helper';
+import { registerWorkflowTrigger } from './workflowTrigger';
+import {
+  parseJSON,
+  fileSaver,
+  openFilePicker,
+  findTriggerBlock,
+} from './helper';
 
 const contextMenuPermission =
   BROWSER_TYPE === 'firefox' ? 'menus' : 'contextMenus';
@@ -109,15 +115,21 @@ export function importWorkflow(attrs = {}) {
           workflow.table = workflow.table || workflow.dataColumns;
           delete workflow.dataColumns;
 
-          if (typeof workflow.drawflow === 'string')
+          if (typeof workflow.drawflow === 'string') {
             workflow.drawflow = parseJSON(workflow.drawflow, {});
+          }
 
           workflowStore
             .insert({
               ...workflow,
               createdAt: Date.now(),
             })
-            .then(resolve);
+            .then((result) => {
+              const triggerBlock = findTriggerBlock(result.drawflow);
+              registerWorkflowTrigger(result.id, triggerBlock);
+
+              resolve(result);
+            });
         };
 
         files.forEach((file) => {

+ 1 - 1
src/utils/workflowTrigger.js

@@ -281,7 +281,7 @@ export const workflowTriggersMap = {
 
 export async function registerWorkflowTrigger(workflowId, { data }) {
   try {
-    await cleanWorkflowTriggers(workflowId, data.triggers);
+    await cleanWorkflowTriggers(workflowId, data && data?.triggers);
 
     if (data.triggers) {
       for (const trigger of data.triggers) {

Failā izmaiņas netiks attēlotas, jo tās ir par lielu
+ 296 - 354
yarn.lock


Daži faili netika attēloti, jo izmaiņu fails ir pārāk liels