From 7e3e0b4dce2cd5f16d63592ecaf0c5ef7330d58f Mon Sep 17 00:00:00 2001 From: michelle0927 Date: Thu, 18 Jul 2024 16:38:09 -0400 Subject: [PATCH 1/3] upload-multiple-files --- .../upload-multiple-files.mjs | 145 ++++++++++++++++++ components/dropbox/package.json | 2 +- 2 files changed, 146 insertions(+), 1 deletion(-) create mode 100644 components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs diff --git a/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs new file mode 100644 index 0000000000000..6be7b2224c0b9 --- /dev/null +++ b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs @@ -0,0 +1,145 @@ +import dropbox from "../../dropbox.app.mjs"; +import consts from "../../common/consts.mjs"; +import fs from "fs"; +import got from "got"; +import { ConfigurationError } from "@pipedream/platform"; + +export default { + name: "Upload Multiple Files", + description: "Uploads multiple file to a selected folder. [See the documentation](https://dropbox.github.io/dropbox-sdk-js/Dropbox.html#filesUpload__anchor)", + key: "dropbox-upload-multiple-files", + version: "0.0.1", + type: "action", + props: { + dropbox, + path: { + propDefinition: [ + dropbox, + "path", + () => ({ + filter: ({ metadata: { metadata: { [".tag"]: type } } }) => type === "folder", + }), + ], + description: "The folder to upload to. Type the folder name to search for it in the user's Dropbox.", + }, + fileUrls: { + type: "string[]", + label: "File URLs", + description: "The URLs of the files you want to upload to Dropbox. Must specify either File URLs or File Paths.", + optional: true, + reloadProps: true, + }, + filePaths: { + type: "string[]", + label: "File Paths", + description: "The paths to the files, e.g. /tmp/myFile.csv . Must specify either File URLs or File Paths.", + optional: true, + reloadProps: true, + }, + autorename: { + type: "boolean", + label: "Autorename", + description: "If there's a conflict, have Dropbox try to autorename the file to avoid the conflict.", + optional: true, + }, + mute: { + type: "boolean", + label: "Mute", + description: "Normally, users are made aware of any file modifications in their Dropbox account via notifications in the client software. If `true`, this will not result in a user notification.", + optional: true, + }, + strictConflict: { + type: "boolean", + label: "Strict Conflict", + description: "Be more strict about how each WriteMode detects conflict. For example, always return a conflict error when mode = WriteMode.update and the given \"rev\" doesn't match the existing file's \"rev\", even if the existing file has been deleted. This also forces a conflict even when the target path refers to a file with identical contents.", + optional: true, + }, + mode: { + type: "string", + label: "Mode", + description: "Selects what to do if the file already exists.", + options: consts.UPLOAD_FILE_MODE_OPTIONS, + optional: true, + }, + }, + async additionalProps() { + const props = {}; + if (this.fileUrls?.length) { + for (const url of this.fileUrls) { + props[`name_${url}`] = { + type: "string", + label: `New filename for "${url}"`, + description: "Make sure to include the file extension", + }; + } + } + if (this.filePaths?.length) { + for (const filePath of this.filePaths) { + props[`name_${filePath}`] = { + type: "string", + label: `New filename for "${filePath}"`, + description: "Make sure to include the file extension", + }; + } + } + return props; + }, + async run({ $ }) { + const { + path, + fileUrls, + filePaths, + autorename, + mute, + strictConflict, + mode, + ...fileProps + } = this; + + if (!fileUrls?.length && !filePaths?.length) { + throw new ConfigurationError("Must specify either File URLs or File Paths."); + } + + const fileInfo = []; + const normalizedPath = this.dropbox.getNormalizedPath(path, true); + + if (this.fileUrls?.length) { + for (const url of fileUrls) { + const filename = fileProps[`name_${url}`]; + fileInfo.push({ + contents: await got.stream(url), + path: `${normalizedPath}${filename}`, + }); + } + } + + if (this.filePaths?.length) { + for (const filePath of filePaths) { + const filename = fileProps[`name_${filePath}`]; + fileInfo.push({ + contents: fs.createReadStream(filePath), + path: `${normalizedPath}${filename}`, + }); + } + } + + const responses = []; + for (const file of fileInfo) { + const { result } = await this.dropbox.uploadFile({ + contents: file.contents, + autorename, + path: file.path, + mode: mode + ? { + ".tag": mode, + } + : undefined, + mute, + strict_conflict: strictConflict, + }); + responses.push(result); + } + $.export("$summary", "Files successfully uploaded"); + return responses; + }, +}; diff --git a/components/dropbox/package.json b/components/dropbox/package.json index c721ea8ddc7c5..9f56f31fb5a3c 100644 --- a/components/dropbox/package.json +++ b/components/dropbox/package.json @@ -1,6 +1,6 @@ { "name": "@pipedream/dropbox", - "version": "0.3.19", + "version": "0.4.0", "description": "Pipedream Dropbox Components", "main": "dropbox.app.mjs", "keywords": [ From 162725c5bc6f71dadad4c6b58ebf426cbfa83543 Mon Sep 17 00:00:00 2001 From: michelle0927 Date: Tue, 23 Jul 2024 11:19:35 -0400 Subject: [PATCH 2/3] fix additionalProp names --- .../upload-multiple-files.mjs | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs index 6be7b2224c0b9..1caf656fb28bf 100644 --- a/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs +++ b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs @@ -64,22 +64,25 @@ export default { }, async additionalProps() { const props = {}; + let i = 1; if (this.fileUrls?.length) { for (const url of this.fileUrls) { - props[`name_${url}`] = { + props[`name_${i}`] = { type: "string", label: `New filename for "${url}"`, description: "Make sure to include the file extension", }; + i++; } } if (this.filePaths?.length) { for (const filePath of this.filePaths) { - props[`name_${filePath}`] = { + props[`name_${i}`] = { type: "string", label: `New filename for "${filePath}"`, description: "Make sure to include the file extension", }; + i++; } } return props; @@ -102,24 +105,27 @@ export default { const fileInfo = []; const normalizedPath = this.dropbox.getNormalizedPath(path, true); + let i = 1; if (this.fileUrls?.length) { for (const url of fileUrls) { - const filename = fileProps[`name_${url}`]; + const filename = fileProps[`name_${i}`]; fileInfo.push({ contents: await got.stream(url), path: `${normalizedPath}${filename}`, }); + i++; } } if (this.filePaths?.length) { for (const filePath of filePaths) { - const filename = fileProps[`name_${filePath}`]; + const filename = fileProps[`name_${i}`]; fileInfo.push({ contents: fs.createReadStream(filePath), path: `${normalizedPath}${filename}`, }); + i++; } } From 5c36c9b4b115c1df6c9387190c65b9aaa7bc7fbf Mon Sep 17 00:00:00 2001 From: michelle0927 Date: Wed, 24 Jul 2024 11:13:19 -0400 Subject: [PATCH 3/3] filenames prop --- .../upload-multiple-files.mjs | 58 +++++++------------ 1 file changed, 21 insertions(+), 37 deletions(-) diff --git a/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs index 1caf656fb28bf..817b0b37b7321 100644 --- a/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs +++ b/components/dropbox/actions/upload-multiple-files/upload-multiple-files.mjs @@ -26,15 +26,20 @@ export default { type: "string[]", label: "File URLs", description: "The URLs of the files you want to upload to Dropbox. Must specify either File URLs or File Paths.", + default: [], optional: true, - reloadProps: true, }, filePaths: { type: "string[]", label: "File Paths", description: "The paths to the files, e.g. /tmp/myFile.csv . Must specify either File URLs or File Paths.", + default: [], optional: true, - reloadProps: true, + }, + filenames: { + type: "string[]", + label: "File Names", + description: "An array of filenames for the new files. Please provide a name for each URL and/or Path. Make sure to include the file extensions.", }, autorename: { type: "boolean", @@ -62,33 +67,9 @@ export default { optional: true, }, }, - async additionalProps() { - const props = {}; - let i = 1; - if (this.fileUrls?.length) { - for (const url of this.fileUrls) { - props[`name_${i}`] = { - type: "string", - label: `New filename for "${url}"`, - description: "Make sure to include the file extension", - }; - i++; - } - } - if (this.filePaths?.length) { - for (const filePath of this.filePaths) { - props[`name_${i}`] = { - type: "string", - label: `New filename for "${filePath}"`, - description: "Make sure to include the file extension", - }; - i++; - } - } - return props; - }, async run({ $ }) { const { + dropbox, path, fileUrls, filePaths, @@ -96,34 +77,37 @@ export default { mute, strictConflict, mode, - ...fileProps + filenames, } = this; if (!fileUrls?.length && !filePaths?.length) { throw new ConfigurationError("Must specify either File URLs or File Paths."); } + const numFiles = fileUrls.length + filePaths.length; + if (numFiles !== filenames.length) { + throw new ConfigurationError(`Number of filenames must match number of files. Detected ${numFiles} file(s) and ${filenames.length} filename(s)`); + } + const fileInfo = []; - const normalizedPath = this.dropbox.getNormalizedPath(path, true); - let i = 1; + const normalizedPath = dropbox.getNormalizedPath(path, true); + let i = 0; - if (this.fileUrls?.length) { + if (fileUrls?.length) { for (const url of fileUrls) { - const filename = fileProps[`name_${i}`]; fileInfo.push({ contents: await got.stream(url), - path: `${normalizedPath}${filename}`, + path: `${normalizedPath}${filenames[i]}`, }); i++; } } - if (this.filePaths?.length) { + if (filePaths?.length) { for (const filePath of filePaths) { - const filename = fileProps[`name_${i}`]; fileInfo.push({ contents: fs.createReadStream(filePath), - path: `${normalizedPath}${filename}`, + path: `${normalizedPath}${filenames[i]}`, }); i++; } @@ -131,7 +115,7 @@ export default { const responses = []; for (const file of fileInfo) { - const { result } = await this.dropbox.uploadFile({ + const { result } = await dropbox.uploadFile({ contents: file.contents, autorename, path: file.path,