diff --git a/packages/backend/src/apps/monday/actions/create-board/index.js b/packages/backend/src/apps/monday/actions/create-board/index.js new file mode 100644 index 00000000..2afd0d85 --- /dev/null +++ b/packages/backend/src/apps/monday/actions/create-board/index.js @@ -0,0 +1,70 @@ +import defineAction from '../../../../helpers/define-action.js'; + +export default defineAction({ + name: 'Create board', + key: 'createBoard', + description: 'Creates a new board.', + arguments: [ + { + label: 'Board Name', + key: 'boardName', + type: 'string', + required: true, + description: 'Title for the board.', + variables: true, + }, + { + label: 'Board Kind', + key: 'boardKind', + type: 'dropdown', + required: true, + description: '', + variables: true, + options: [ + { + label: 'Main', + value: 'public', + }, + { + label: 'Private', + value: 'private', + }, + { + label: 'Shareable', + value: 'share', + }, + ], + }, + { + label: 'Template ID', + key: 'templateId', + type: 'string', + required: false, + description: + "When you switch on developer mode, you'll spot the template IDs in your template store. Additionally, you have the option to utilize the Board ID from any board you've saved as a template.", + variables: true, + }, + ], + + async run($) { + const { boardName, boardKind, templateId } = $.step.parameters; + + const body = { + query: `mutation { + create_board (board_name: "${boardName}", board_kind: ${boardKind}${ + templateId ? `, template_id: ${templateId}` : '' + }) { + id + name + board_kind + } + }`, + }; + + const { data } = await $.http.post('/', body); + + $.setActionItem({ + raw: data, + }); + }, +}); diff --git a/packages/backend/src/apps/monday/actions/create-column/index.js b/packages/backend/src/apps/monday/actions/create-column/index.js new file mode 100644 index 00000000..2ea3d0ae --- /dev/null +++ b/packages/backend/src/apps/monday/actions/create-column/index.js @@ -0,0 +1,98 @@ +import defineAction from '../../../../helpers/define-action.js'; + +export default defineAction({ + name: 'Create column', + key: 'createColumn', + description: 'Creates a new column in a board.', + arguments: [ + { + label: 'Board', + key: 'boardId', + type: 'dropdown', + required: true, + description: '', + variables: true, + source: { + type: 'query', + name: 'getDynamicData', + arguments: [ + { + name: 'key', + value: 'listBoards', + }, + ], + }, + }, + { + label: 'Column Title', + key: 'columnTitle', + type: 'string', + required: true, + description: '', + variables: true, + }, + { + label: 'Column Type', + key: 'columnType', + type: 'dropdown', + required: true, + description: '', + variables: true, + options: [ + { label: 'Button', value: 'button' }, + { label: 'Checkbox', value: 'checkbox' }, + { label: 'Color Picker', value: 'color_picker' }, + { label: 'Connect Boards', value: 'board_relation' }, + { label: 'Country', value: 'country' }, + { label: 'Creation Log', value: 'creation_log' }, + { label: 'Date', value: 'date' }, + { label: 'Dependency', value: 'dependency' }, + { label: 'Dropdown', value: 'dropdown' }, + { label: 'Email', value: 'email' }, + { label: 'Files', value: 'file' }, + { label: 'Formula', value: 'formula' }, + { label: 'Hour', value: 'hour' }, + { label: 'Item ID', value: 'item_id' }, + { label: 'Last Updated', value: 'last_updated' }, + { label: 'Link', value: 'link' }, + { label: 'Location', value: 'location' }, + { label: 'Long Text', value: 'long_text' }, + { label: 'Mirror', value: 'mirror' }, + { label: 'monday Doc', value: 'doc' }, + { label: 'Name', value: 'name' }, + { label: 'Numbers', value: 'numbers' }, + { label: 'People', value: 'people' }, + { label: 'Phone', value: 'phone' }, + { label: 'Rating', value: 'rating' }, + { label: 'Status', value: 'status' }, + { label: 'Tags', value: 'tags' }, + { label: 'Text', value: 'text' }, + { label: 'Timeline', value: 'timeline' }, + { label: 'Time Tracking', value: 'time_tracking' }, + { label: 'Vote', value: 'vote' }, + { label: 'Week', value: 'week' }, + { label: 'World Clock', value: 'world_clock' }, + ], + }, + ], + + async run($) { + const { boardId, columnTitle, columnType } = $.step.parameters; + + const body = { + query: ` + mutation{ + create_column (board_id: ${boardId}, title: "${columnTitle}", column_type: ${columnType}) { + id + title + } + }`, + }; + + const { data } = await $.http.post('/', body); + + $.setActionItem({ + raw: data, + }); + }, +}); diff --git a/packages/backend/src/apps/monday/actions/create-item/index.js b/packages/backend/src/apps/monday/actions/create-item/index.js new file mode 100644 index 00000000..605148ee --- /dev/null +++ b/packages/backend/src/apps/monday/actions/create-item/index.js @@ -0,0 +1,112 @@ +import defineAction from '../../../../helpers/define-action.js'; + +export default defineAction({ + name: 'Create item', + key: 'createItem', + description: 'Creates a new item in a board.', + arguments: [ + { + label: 'Board', + key: 'boardId', + type: 'dropdown', + required: true, + description: '', + variables: true, + source: { + type: 'query', + name: 'getDynamicData', + arguments: [ + { + name: 'key', + value: 'listBoards', + }, + ], + }, + }, + { + label: 'Group', + key: 'groupId', + type: 'dropdown', + required: false, + description: '', + dependsOn: ['parameters.boardId'], + variables: true, + source: { + type: 'query', + name: 'getDynamicData', + arguments: [ + { + name: 'key', + value: 'listGroups', + }, + { + name: 'parameters.boardId', + value: '{parameters.boardId}', + }, + ], + }, + }, + { + label: 'Item Name', + key: 'itemName', + type: 'string', + required: true, + description: '', + variables: true, + }, + { + label: 'Subitem Names', + key: 'subitemNames', + type: 'dynamic', + required: false, + description: '', + fields: [ + { + label: 'Subitem Name', + key: 'subitemName', + type: 'string', + required: false, + description: '', + variables: true, + }, + ], + }, + ], + + async run($) { + const { boardId, groupId, itemName, subitemNames } = $.step.parameters; + const allSubitems = subitemNames.map((entry) => entry.subitemName); + + const body = { + query: ` + mutation { + create_item (board_id: ${boardId}${ + groupId ? `, group_id: "${groupId}"` : '' + }, item_name: "${itemName}") { + id + } + }`, + }; + + const { data } = await $.http.post('/', body); + + const itemId = data.data.create_item.id; + + for (let subitemName of allSubitems) { + let body = { + query: ` + mutation { + create_subitem (parent_item_id:${itemId}, item_name:"${subitemName}") { + id + } + }`, + }; + + await $.http.post('/', body); + } + + $.setActionItem({ + raw: data, + }); + }, +}); diff --git a/packages/backend/src/apps/monday/actions/index.js b/packages/backend/src/apps/monday/actions/index.js new file mode 100644 index 00000000..8f12938e --- /dev/null +++ b/packages/backend/src/apps/monday/actions/index.js @@ -0,0 +1,5 @@ +import createBoard from './create-board/index.js'; +import createColumn from './create-column/index.js'; +import createItem from './create-item/index.js'; + +export default [createBoard, createColumn, createItem]; diff --git a/packages/backend/src/apps/monday/dynamic-data/index.js b/packages/backend/src/apps/monday/dynamic-data/index.js new file mode 100644 index 00000000..c686d52a --- /dev/null +++ b/packages/backend/src/apps/monday/dynamic-data/index.js @@ -0,0 +1,4 @@ +import listBoards from './list-boards/index.js'; +import listGroups from './list-groups/index.js'; + +export default [listBoards, listGroups]; diff --git a/packages/backend/src/apps/monday/dynamic-data/list-boards/index.js b/packages/backend/src/apps/monday/dynamic-data/list-boards/index.js new file mode 100644 index 00000000..b804d447 --- /dev/null +++ b/packages/backend/src/apps/monday/dynamic-data/list-boards/index.js @@ -0,0 +1,37 @@ +export default { + name: 'List boards', + key: 'listBoards', + + async run($) { + const boards = { + data: [], + }; + + const body = { + query: ` + query { + boards { + id + name + type + } + } + `, + }; + + const { data } = await $.http.post('/', body); + + if (data.data.boards?.length) { + for (const board of data.data.boards) { + if (board.type === 'board') { + boards.data.push({ + value: board.id, + name: board.name, + }); + } + } + } + + return boards; + }, +}; diff --git a/packages/backend/src/apps/monday/dynamic-data/list-groups/index.js b/packages/backend/src/apps/monday/dynamic-data/list-groups/index.js new file mode 100644 index 00000000..19f4db46 --- /dev/null +++ b/packages/backend/src/apps/monday/dynamic-data/list-groups/index.js @@ -0,0 +1,40 @@ +export default { + name: 'List groups', + key: 'listGroups', + + async run($) { + const groups = { + data: [], + }; + const boardId = $.step.parameters.boardId; + + if (!boardId) { + return groups; + } + + const body = { + query: `query { + boards (ids: ${boardId}) { + groups { + title + id + } + } + } + `, + }; + + const { data } = await $.http.post('/', body); + + if (data.data.boards[0]?.groups.length) { + for (const group of data.data.boards[0].groups) { + groups.data.push({ + value: group.id, + name: group.title, + }); + } + } + + return groups; + }, +}; diff --git a/packages/backend/src/apps/monday/index.js b/packages/backend/src/apps/monday/index.js index efed1eae..2ee81ebb 100644 --- a/packages/backend/src/apps/monday/index.js +++ b/packages/backend/src/apps/monday/index.js @@ -1,6 +1,9 @@ import defineApp from '../../helpers/define-app.js'; import addAuthHeader from './common/add-auth-header.js'; import auth from './auth/index.js'; +import triggers from './triggers/index.js'; +import actions from './actions/index.js'; +import dynamicData from './dynamic-data/index.js'; export default defineApp({ name: 'Monday', @@ -13,4 +16,7 @@ export default defineApp({ primaryColor: 'F62B54', beforeRequest: [addAuthHeader], auth, + triggers, + actions, + dynamicData, }); diff --git a/packages/backend/src/apps/monday/triggers/index.js b/packages/backend/src/apps/monday/triggers/index.js new file mode 100644 index 00000000..6ffc8710 --- /dev/null +++ b/packages/backend/src/apps/monday/triggers/index.js @@ -0,0 +1,4 @@ +import newBoards from './new-boards/index.js'; +import newUsers from './new-users/index.js'; + +export default [newBoards, newUsers]; diff --git a/packages/backend/src/apps/monday/triggers/new-boards/index.js b/packages/backend/src/apps/monday/triggers/new-boards/index.js new file mode 100644 index 00000000..599d7d2e --- /dev/null +++ b/packages/backend/src/apps/monday/triggers/new-boards/index.js @@ -0,0 +1,31 @@ +import defineTrigger from '../../../../helpers/define-trigger.js'; + +export default defineTrigger({ + name: 'New board', + key: 'newBoard', + pollInterval: 15, + description: 'Triggers when a new board is created.', + + async run($) { + const body = { + query: 'query { boards { id, name, type } }', + }; + + const { data } = await $.http.post('/', body); + + if (!data?.data?.boards?.length) { + return; + } + + for (const board of data.data.boards) { + if (board.type === 'board') { + $.pushTriggerItem({ + raw: board, + meta: { + internalId: board.id, + }, + }); + } + } + }, +}); diff --git a/packages/backend/src/apps/monday/triggers/new-users/index.js b/packages/backend/src/apps/monday/triggers/new-users/index.js new file mode 100644 index 00000000..aa0e474b --- /dev/null +++ b/packages/backend/src/apps/monday/triggers/new-users/index.js @@ -0,0 +1,29 @@ +import defineTrigger from '../../../../helpers/define-trigger.js'; + +export default defineTrigger({ + name: 'New users', + key: 'newUsers', + pollInterval: 15, + description: 'Triggers when a new user joins your account.', + + async run($) { + const body = { + query: 'query { users { id name } }', + }; + + const { data } = await $.http.post('/', body); + + if (!data.data?.users?.length) { + return; + } + + for (const user of data.data.users.reverse()) { + $.pushTriggerItem({ + raw: user, + meta: { + internalId: user.id, + }, + }); + } + }, +}); diff --git a/packages/backend/src/models/__snapshots__/app.test.js.snap b/packages/backend/src/models/__snapshots__/app.test.js.snap index 624194aa..33000024 100644 --- a/packages/backend/src/models/__snapshots__/app.test.js.snap +++ b/packages/backend/src/models/__snapshots__/app.test.js.snap @@ -40,6 +40,7 @@ exports[`App model > list should have list of applications keys 1`] = ` "mattermost", "miro", "mistral-ai", + "monday", "notion", "ntfy", "odoo", diff --git a/packages/docs/pages/.vitepress/config.js b/packages/docs/pages/.vitepress/config.js index a8026f02..dde76d78 100644 --- a/packages/docs/pages/.vitepress/config.js +++ b/packages/docs/pages/.vitepress/config.js @@ -344,7 +344,11 @@ export default defineConfig({ text: 'Monday', collapsible: true, collapsed: true, - items: [{ text: 'Connection', link: '/apps/monday/connection' }], + items: [ + { text: 'Triggers', link: '/apps/monday/triggers' }, + { text: 'Actions', link: '/apps/monday/actions' }, + { text: 'Connection', link: '/apps/monday/connection' }, + ], }, { text: 'Notion', diff --git a/packages/docs/pages/apps/monday/actions.md b/packages/docs/pages/apps/monday/actions.md new file mode 100644 index 00000000..f2034ed2 --- /dev/null +++ b/packages/docs/pages/apps/monday/actions.md @@ -0,0 +1,16 @@ +--- +favicon: /favicons/monday.svg +items: + - name: Create board + desc: Creates a new board. + - name: Create column + desc: Creates a new column in a board. + - name: Create item + desc: Creates a new item in a board. +--- + + + + diff --git a/packages/docs/pages/apps/monday/triggers.md b/packages/docs/pages/apps/monday/triggers.md new file mode 100644 index 00000000..f1b79fb8 --- /dev/null +++ b/packages/docs/pages/apps/monday/triggers.md @@ -0,0 +1,14 @@ +--- +favicon: /favicons/monday.svg +items: + - name: New board + desc: Triggers when a new board is created. + - name: New users + desc: Triggers when a new user joins your account. +--- + + + + diff --git a/packages/docs/pages/guide/available-apps.md b/packages/docs/pages/guide/available-apps.md index 5f0271ad..037e9ac2 100644 --- a/packages/docs/pages/guide/available-apps.md +++ b/packages/docs/pages/guide/available-apps.md @@ -34,6 +34,7 @@ The following integrations are currently supported by Automatisch. - [Mattermost](/apps/mattermost/actions) - [Miro](/apps/miro/actions) - [Mistral AI](/apps/mistral-ai/actions) +- [Monday](/apps/monday/triggers) - [Notion](/apps/notion/triggers) - [Ntfy](/apps/ntfy/actions) - [Odoo](/apps/odoo/actions)