@budibase/server 2.7.20 → 2.7.21-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -946,6 +946,7 @@ var init_automation2 = __esm({
946
946
  AutomationIOType2["NUMBER"] = "number";
947
947
  AutomationIOType2["ARRAY"] = "array";
948
948
  AutomationIOType2["JSON"] = "json";
949
+ AutomationIOType2["DATE"] = "date";
949
950
  return AutomationIOType2;
950
951
  })(AutomationIOType || {});
951
952
  AutomationCustomIOType = /* @__PURE__ */ ((AutomationCustomIOType2) => {
@@ -5360,11 +5361,11 @@ function makeCacheItem(doc2, lastWrite = null) {
5360
5361
  return { doc: doc2, lastWrite: lastWrite || Date.now() };
5361
5362
  }
5362
5363
  async function put(db2, doc2, writeRateMs = DEFAULT_WRITE_RATE_MS) {
5363
- const cache2 = await getCache();
5364
+ const cache3 = await getCache();
5364
5365
  const key = doc2._id;
5365
5366
  let cacheItem;
5366
5367
  if (key) {
5367
- cacheItem = await cache2.get(makeCacheKey(db2, key));
5368
+ cacheItem = await cache3.get(makeCacheKey(db2, key));
5368
5369
  }
5369
5370
  const updateDb = !cacheItem || cacheItem.lastWrite < Date.now() - writeRateMs;
5370
5371
  let output = doc2;
@@ -5402,30 +5403,30 @@ async function put(db2, doc2, writeRateMs = DEFAULT_WRITE_RATE_MS) {
5402
5403
  }
5403
5404
  cacheItem = makeCacheItem(output, updateDb ? null : cacheItem == null ? void 0 : cacheItem.lastWrite);
5404
5405
  if (output._id) {
5405
- await cache2.store(makeCacheKey(db2, output._id), cacheItem);
5406
+ await cache3.store(makeCacheKey(db2, output._id), cacheItem);
5406
5407
  }
5407
5408
  return { ok: true, id: output._id, rev: output._rev };
5408
5409
  }
5409
5410
  async function get2(db2, id) {
5410
- const cache2 = await getCache();
5411
+ const cache3 = await getCache();
5411
5412
  const cacheKey = makeCacheKey(db2, id);
5412
- let cacheItem = await cache2.get(cacheKey);
5413
+ let cacheItem = await cache3.get(cacheKey);
5413
5414
  if (!cacheItem) {
5414
5415
  const doc2 = await db2.get(id);
5415
5416
  cacheItem = makeCacheItem(doc2);
5416
- await cache2.store(cacheKey, cacheItem);
5417
+ await cache3.store(cacheKey, cacheItem);
5417
5418
  }
5418
5419
  return cacheItem.doc;
5419
5420
  }
5420
5421
  async function remove(db2, docOrId, rev2) {
5421
- const cache2 = await getCache();
5422
+ const cache3 = await getCache();
5422
5423
  if (!docOrId) {
5423
5424
  throw new Error("No ID/Rev provided.");
5424
5425
  }
5425
5426
  const id = typeof docOrId === "string" ? docOrId : docOrId._id;
5426
5427
  rev2 = typeof docOrId === "string" ? rev2 : docOrId._rev;
5427
5428
  try {
5428
- await cache2.delete(makeCacheKey(db2, id));
5429
+ await cache3.delete(makeCacheKey(db2, id));
5429
5430
  } finally {
5430
5431
  await db2.remove(id, rev2);
5431
5432
  }
@@ -9028,7 +9029,7 @@ function lowerBuiltinRoleID(roleId1, roleId2) {
9028
9029
  }
9029
9030
  return builtinRoleToNumber(roleId1) > builtinRoleToNumber(roleId2) ? roleId2 : roleId1;
9030
9031
  }
9031
- async function getRole(roleId) {
9032
+ async function getRole(roleId, opts) {
9032
9033
  if (!roleId) {
9033
9034
  return void 0;
9034
9035
  }
@@ -9044,6 +9045,9 @@ async function getRole(roleId) {
9044
9045
  role = Object.assign(role, dbRole);
9045
9046
  role._id = getExternalRoleID(role._id);
9046
9047
  } catch (err) {
9048
+ if (!isBuiltin(roleId) && (opts == null ? void 0 : opts.defaultPublic)) {
9049
+ return cloneDeep2(BUILTIN_ROLES.PUBLIC);
9050
+ }
9047
9051
  if (Object.keys(role).length === 0) {
9048
9052
  throw err;
9049
9053
  }
@@ -9784,8 +9788,8 @@ async function preAuth(passport2, ctx, next) {
9784
9788
  callbackUrl,
9785
9789
  ssoSaveUserNoOp
9786
9790
  );
9787
- if (!ctx.query.appId || !ctx.query.datasourceId) {
9788
- ctx.throw(400, "appId and datasourceId query params not present.");
9791
+ if (!ctx.query.appId) {
9792
+ ctx.throw(400, "appId query param not present.");
9789
9793
  }
9790
9794
  return passport2.authenticate(strategy, {
9791
9795
  scope: ["profile", "email", "https://www.googleapis.com/auth/spreadsheets"],
@@ -9805,7 +9809,7 @@ async function postAuth(passport2, ctx, next) {
9805
9809
  clientSecret: config.clientSecret,
9806
9810
  callbackURL: callbackUrl
9807
9811
  },
9808
- (accessToken, refreshToken, profile, done) => {
9812
+ (accessToken, refreshToken, _profile, done) => {
9809
9813
  clearCookie(ctx, "budibase:datasourceauth" /* DatasourceAuth */);
9810
9814
  done(null, { accessToken, refreshToken });
9811
9815
  }
@@ -9813,22 +9817,14 @@ async function postAuth(passport2, ctx, next) {
9813
9817
  { successRedirect: "/", failureRedirect: "/error" },
9814
9818
  async (err, tokens) => {
9815
9819
  const baseUrl = `/builder/app/${authStateCookie.appId}/data`;
9816
- await doWithDB(authStateCookie.appId, async (db2) => {
9817
- let datasource2;
9818
- try {
9819
- datasource2 = await db2.get(authStateCookie.datasourceId);
9820
- } catch (err2) {
9821
- if (err2.status === 404) {
9822
- ctx.redirect(baseUrl);
9823
- }
9824
- }
9825
- if (!datasource2.config) {
9826
- datasource2.config = {};
9820
+ const id = newid();
9821
+ await store(
9822
+ `datasource:creation:${authStateCookie.appId}:google:${id}`,
9823
+ {
9824
+ tokens
9827
9825
  }
9828
- datasource2.config.auth = { type: "google", ...tokens };
9829
- await db2.put(datasource2);
9830
- ctx.redirect(`${baseUrl}/datasource/${authStateCookie.datasourceId}`);
9831
- });
9826
+ );
9827
+ ctx.redirect(`${baseUrl}/new?continue_google_setup=${id}`);
9832
9828
  }
9833
9829
  )(ctx, next);
9834
9830
  }
@@ -9837,9 +9833,9 @@ var init_google2 = __esm({
9837
9833
  "../backend-core/src/middleware/passport/datasource/google.ts"() {
9838
9834
  init_google();
9839
9835
  init_constants2();
9840
- init_utils5();
9841
- init_db5();
9842
9836
  init_configs3();
9837
+ init_cache();
9838
+ init_utils5();
9843
9839
  init_sso2();
9844
9840
  GoogleStrategy2 = require("passport-google-oauth").OAuth2Strategy;
9845
9841
  }
@@ -9889,7 +9885,9 @@ var encryption_exports = {};
9889
9885
  __export(encryption_exports, {
9890
9886
  SecretOption: () => SecretOption,
9891
9887
  decrypt: () => decrypt,
9888
+ decryptFile: () => decryptFile,
9892
9889
  encrypt: () => encrypt,
9890
+ encryptFile: () => encryptFile,
9893
9891
  getSecret: () => getSecret
9894
9892
  });
9895
9893
  function getSecret(secretOption) {
@@ -9910,11 +9908,11 @@ function getSecret(secretOption) {
9910
9908
  }
9911
9909
  return secret;
9912
9910
  }
9913
- function stretchString(string, salt) {
9914
- return import_crypto.default.pbkdf2Sync(string, salt, ITERATIONS, STRETCH_LENGTH, "sha512");
9911
+ function stretchString(secret, salt) {
9912
+ return import_crypto.default.pbkdf2Sync(secret, salt, ITERATIONS, STRETCH_LENGTH, "sha512");
9915
9913
  }
9916
9914
  function encrypt(input, secretOption = "api" /* API */) {
9917
- const salt = import_crypto.default.randomBytes(RANDOM_BYTES);
9915
+ const salt = import_crypto.default.randomBytes(SALT_LENGTH);
9918
9916
  const stretched = stretchString(getSecret(secretOption), salt);
9919
9917
  const cipher = import_crypto.default.createCipheriv(ALGO, stretched, salt);
9920
9918
  const base = cipher.update(input);
@@ -9931,16 +9929,101 @@ function decrypt(input, secretOption = "api" /* API */) {
9931
9929
  const final = decipher.final();
9932
9930
  return Buffer.concat([base, final]).toString();
9933
9931
  }
9934
- var import_crypto, ALGO, SEPARATOR3, ITERATIONS, RANDOM_BYTES, STRETCH_LENGTH, SecretOption;
9932
+ async function encryptFile({ dir, filename }, secret) {
9933
+ const outputFileName = `${filename}.enc`;
9934
+ const filePath = (0, import_path2.join)(dir, filename);
9935
+ const inputFile = import_fs2.default.createReadStream(filePath);
9936
+ const outputFile = import_fs2.default.createWriteStream((0, import_path2.join)(dir, outputFileName));
9937
+ const salt = import_crypto.default.randomBytes(SALT_LENGTH);
9938
+ const iv = import_crypto.default.randomBytes(IV_LENGTH);
9939
+ const stretched = stretchString(secret, salt);
9940
+ const cipher = import_crypto.default.createCipheriv(ALGO, stretched, iv);
9941
+ outputFile.write(salt);
9942
+ outputFile.write(iv);
9943
+ inputFile.pipe(import_zlib.default.createGzip()).pipe(cipher).pipe(outputFile);
9944
+ return new Promise((r) => {
9945
+ outputFile.on("finish", () => {
9946
+ r({
9947
+ filename: outputFileName,
9948
+ dir
9949
+ });
9950
+ });
9951
+ });
9952
+ }
9953
+ async function getSaltAndIV(path2) {
9954
+ const fileStream = import_fs2.default.createReadStream(path2);
9955
+ const salt = await readBytes(fileStream, SALT_LENGTH);
9956
+ const iv = await readBytes(fileStream, IV_LENGTH);
9957
+ fileStream.close();
9958
+ return { salt, iv };
9959
+ }
9960
+ async function decryptFile(inputPath, outputPath, secret) {
9961
+ const { salt, iv } = await getSaltAndIV(inputPath);
9962
+ const inputFile = import_fs2.default.createReadStream(inputPath, {
9963
+ start: SALT_LENGTH + IV_LENGTH
9964
+ });
9965
+ const outputFile = import_fs2.default.createWriteStream(outputPath);
9966
+ const stretched = stretchString(secret, salt);
9967
+ const decipher = import_crypto.default.createDecipheriv(ALGO, stretched, iv);
9968
+ const unzip = import_zlib.default.createGunzip();
9969
+ inputFile.pipe(decipher).pipe(unzip).pipe(outputFile);
9970
+ return new Promise((res, rej) => {
9971
+ outputFile.on("finish", () => {
9972
+ outputFile.close();
9973
+ res();
9974
+ });
9975
+ inputFile.on("error", (e) => {
9976
+ outputFile.close();
9977
+ rej(e);
9978
+ });
9979
+ decipher.on("error", (e) => {
9980
+ outputFile.close();
9981
+ rej(e);
9982
+ });
9983
+ unzip.on("error", (e) => {
9984
+ outputFile.close();
9985
+ rej(e);
9986
+ });
9987
+ outputFile.on("error", (e) => {
9988
+ outputFile.close();
9989
+ rej(e);
9990
+ });
9991
+ });
9992
+ }
9993
+ function readBytes(stream3, length) {
9994
+ return new Promise((resolve3, reject) => {
9995
+ let bytesRead = 0;
9996
+ const data2 = [];
9997
+ stream3.on("readable", () => {
9998
+ let chunk;
9999
+ while ((chunk = stream3.read(length - bytesRead)) !== null) {
10000
+ data2.push(chunk);
10001
+ bytesRead += chunk.length;
10002
+ }
10003
+ resolve3(Buffer.concat(data2));
10004
+ });
10005
+ stream3.on("end", () => {
10006
+ reject(new Error("Insufficient data in the stream."));
10007
+ });
10008
+ stream3.on("error", (error) => {
10009
+ reject(error);
10010
+ });
10011
+ });
10012
+ }
10013
+ var import_crypto, import_fs2, import_zlib, import_path2, ALGO, SEPARATOR3, ITERATIONS, STRETCH_LENGTH, SALT_LENGTH, IV_LENGTH, SecretOption;
9935
10014
  var init_encryption = __esm({
9936
10015
  "../backend-core/src/security/encryption.ts"() {
9937
10016
  import_crypto = __toESM(require("crypto"));
10017
+ import_fs2 = __toESM(require("fs"));
10018
+ import_zlib = __toESM(require("zlib"));
9938
10019
  init_environment3();
10020
+ import_path2 = require("path");
9939
10021
  ALGO = "aes-256-ctr";
9940
10022
  SEPARATOR3 = "-";
9941
10023
  ITERATIONS = 1e4;
9942
- RANDOM_BYTES = 16;
9943
10024
  STRETCH_LENGTH = 32;
10025
+ SALT_LENGTH = 16;
10026
+ IV_LENGTH = 16;
9944
10027
  SecretOption = /* @__PURE__ */ ((SecretOption2) => {
9945
10028
  SecretOption2["API"] = "api";
9946
10029
  SecretOption2["ENCRYPTION"] = "encryption";
@@ -10851,12 +10934,12 @@ var init_plugin4 = __esm({
10851
10934
  function budibaseTempDir() {
10852
10935
  return bbTmp;
10853
10936
  }
10854
- var import_path2, import_os, import_fs2, ObjectStoreBuckets, bbTmp;
10937
+ var import_path3, import_os, import_fs3, ObjectStoreBuckets, bbTmp;
10855
10938
  var init_utils8 = __esm({
10856
10939
  "../backend-core/src/objectStore/utils.ts"() {
10857
- import_path2 = require("path");
10940
+ import_path3 = require("path");
10858
10941
  import_os = require("os");
10859
- import_fs2 = __toESM(require("fs"));
10942
+ import_fs3 = __toESM(require("fs"));
10860
10943
  init_environment3();
10861
10944
  ObjectStoreBuckets = {
10862
10945
  BACKUPS: environment_default2.BACKUPS_BUCKET_NAME,
@@ -10865,9 +10948,9 @@ var init_utils8 = __esm({
10865
10948
  GLOBAL: environment_default2.GLOBAL_BUCKET_NAME,
10866
10949
  PLUGINS: environment_default2.PLUGIN_BUCKET_NAME
10867
10950
  };
10868
- bbTmp = (0, import_path2.join)((0, import_os.tmpdir)(), ".budibase");
10869
- if (!import_fs2.default.existsSync(bbTmp)) {
10870
- import_fs2.default.mkdirSync(bbTmp);
10951
+ bbTmp = (0, import_path3.join)((0, import_os.tmpdir)(), ".budibase");
10952
+ if (!import_fs3.default.existsSync(bbTmp)) {
10953
+ import_fs3.default.mkdirSync(bbTmp);
10871
10954
  }
10872
10955
  }
10873
10956
  });
@@ -10879,17 +10962,17 @@ function sanitizeKey(input) {
10879
10962
  function sanitizeBucket(input) {
10880
10963
  return input.replace(new RegExp(APP_DEV_PREFIX, "g"), APP_PREFIX);
10881
10964
  }
10882
- var import_aws_sdk, import_stream, import_node_fetch6, import_tar_fs, import_zlib, import_util, import_path3, import_fs3, import_uuid3, sanitize, streamPipeline, STATE, CONTENT_TYPE_MAP, STRING_CONTENT_TYPES, ObjectStore, makeSureBucketExists, upload, streamUpload, retrieve, listAllObjects, getPresignedUrl, retrieveToTmp, retrieveDirectory, deleteFile, deleteFiles, deleteFolder, uploadDirectory, downloadTarballDirect, downloadTarball;
10965
+ var import_aws_sdk, import_stream, import_node_fetch6, import_tar_fs, import_zlib2, import_util, import_path4, import_fs4, import_uuid3, sanitize, streamPipeline, STATE, CONTENT_TYPE_MAP, STRING_CONTENT_TYPES, ObjectStore, makeSureBucketExists, upload, streamUpload, retrieve, listAllObjects, getPresignedUrl, retrieveToTmp, retrieveDirectory, deleteFile, deleteFiles, deleteFolder, uploadDirectory, downloadTarballDirect, downloadTarball;
10883
10966
  var init_objectStore = __esm({
10884
10967
  "../backend-core/src/objectStore/objectStore.ts"() {
10885
10968
  import_aws_sdk = __toESM(require("aws-sdk"));
10886
10969
  import_stream = __toESM(require("stream"));
10887
10970
  import_node_fetch6 = __toESM(require("node-fetch"));
10888
10971
  import_tar_fs = __toESM(require("tar-fs"));
10889
- import_zlib = __toESM(require("zlib"));
10972
+ import_zlib2 = __toESM(require("zlib"));
10890
10973
  import_util = require("util");
10891
- import_path3 = require("path");
10892
- import_fs3 = __toESM(require("fs"));
10974
+ import_path4 = require("path");
10975
+ import_fs4 = __toESM(require("fs"));
10893
10976
  init_environment3();
10894
10977
  init_utils8();
10895
10978
  import_uuid3 = require("uuid");
@@ -10968,7 +11051,7 @@ var init_objectStore = __esm({
10968
11051
  metadata: metadata2
10969
11052
  }) => {
10970
11053
  const extension = filename.split(".").pop();
10971
- const fileBytes = import_fs3.default.readFileSync(path2);
11054
+ const fileBytes = import_fs4.default.readFileSync(path2);
10972
11055
  const objectStore = ObjectStore(bucketName);
10973
11056
  await makeSureBucketExists(objectStore, bucketName);
10974
11057
  let contentType = type;
@@ -11070,13 +11153,13 @@ var init_objectStore = __esm({
11070
11153
  bucketName = sanitizeBucket(bucketName);
11071
11154
  filepath = sanitizeKey(filepath);
11072
11155
  const data2 = await retrieve(bucketName, filepath);
11073
- const outputPath = (0, import_path3.join)(budibaseTempDir(), (0, import_uuid3.v4)());
11074
- import_fs3.default.writeFileSync(outputPath, data2);
11156
+ const outputPath = (0, import_path4.join)(budibaseTempDir(), (0, import_uuid3.v4)());
11157
+ import_fs4.default.writeFileSync(outputPath, data2);
11075
11158
  return outputPath;
11076
11159
  };
11077
11160
  retrieveDirectory = async (bucketName, path2) => {
11078
- let writePath = (0, import_path3.join)(budibaseTempDir(), (0, import_uuid3.v4)());
11079
- import_fs3.default.mkdirSync(writePath);
11161
+ let writePath = (0, import_path4.join)(budibaseTempDir(), (0, import_uuid3.v4)());
11162
+ import_fs4.default.mkdirSync(writePath);
11080
11163
  const objects = await listAllObjects(bucketName, path2);
11081
11164
  let fullObjects = await Promise.all(
11082
11165
  objects.map((obj) => retrieve(bucketName, obj.Key))
@@ -11088,9 +11171,9 @@ var init_objectStore = __esm({
11088
11171
  const possiblePath = filename.split("/");
11089
11172
  if (possiblePath.length > 1) {
11090
11173
  const dirs = possiblePath.slice(0, possiblePath.length - 1);
11091
- import_fs3.default.mkdirSync((0, import_path3.join)(writePath, ...dirs), { recursive: true });
11174
+ import_fs4.default.mkdirSync((0, import_path4.join)(writePath, ...dirs), { recursive: true });
11092
11175
  }
11093
- import_fs3.default.writeFileSync((0, import_path3.join)(writePath, ...possiblePath), data2);
11176
+ import_fs4.default.writeFileSync((0, import_path4.join)(writePath, ...possiblePath), data2);
11094
11177
  }
11095
11178
  return writePath;
11096
11179
  };
@@ -11144,14 +11227,14 @@ var init_objectStore = __esm({
11144
11227
  uploadDirectory = async (bucketName, localPath, bucketPath2) => {
11145
11228
  bucketName = sanitizeBucket(bucketName);
11146
11229
  let uploads = [];
11147
- const files2 = import_fs3.default.readdirSync(localPath, { withFileTypes: true });
11230
+ const files2 = import_fs4.default.readdirSync(localPath, { withFileTypes: true });
11148
11231
  for (let file of files2) {
11149
- const path2 = sanitizeKey((0, import_path3.join)(bucketPath2, file.name));
11150
- const local = (0, import_path3.join)(localPath, file.name);
11232
+ const path2 = sanitizeKey((0, import_path4.join)(bucketPath2, file.name));
11233
+ const local = (0, import_path4.join)(localPath, file.name);
11151
11234
  if (file.isDirectory()) {
11152
11235
  uploads.push(uploadDirectory(bucketName, local, path2));
11153
11236
  } else {
11154
- uploads.push(streamUpload(bucketName, path2, import_fs3.default.createReadStream(local)));
11237
+ uploads.push(streamUpload(bucketName, path2, import_fs4.default.createReadStream(local)));
11155
11238
  }
11156
11239
  }
11157
11240
  await Promise.all(uploads);
@@ -11163,7 +11246,7 @@ var init_objectStore = __esm({
11163
11246
  if (!response2.ok) {
11164
11247
  throw new Error(`unexpected response ${response2.statusText}`);
11165
11248
  }
11166
- await streamPipeline(response2.body, import_zlib.default.createUnzip(), import_tar_fs.default.extract(path2));
11249
+ await streamPipeline(response2.body, import_zlib2.default.createUnzip(), import_tar_fs.default.extract(path2));
11167
11250
  };
11168
11251
  downloadTarball = async (url, bucketName, path2) => {
11169
11252
  bucketName = sanitizeBucket(bucketName);
@@ -11172,8 +11255,8 @@ var init_objectStore = __esm({
11172
11255
  if (!response2.ok) {
11173
11256
  throw new Error(`unexpected response ${response2.statusText}`);
11174
11257
  }
11175
- const tmpPath = (0, import_path3.join)(budibaseTempDir(), path2);
11176
- await streamPipeline(response2.body, import_zlib.default.createUnzip(), import_tar_fs.default.extract(tmpPath));
11258
+ const tmpPath = (0, import_path4.join)(budibaseTempDir(), path2);
11259
+ await streamPipeline(response2.body, import_zlib2.default.createUnzip(), import_tar_fs.default.extract(tmpPath));
11177
11260
  if (!environment_default2.isTest() && environment_default2.SELF_HOSTED) {
11178
11261
  await uploadDirectory(bucketName, tmpPath, path2);
11179
11262
  }
@@ -12626,21 +12709,21 @@ __export(version_exports, {
12626
12709
  getLicenseVersion: () => getLicenseVersion,
12627
12710
  getProVersion: () => getProVersion
12628
12711
  });
12629
- var import_fs4, import_path4, getLicenseVersion, getProVersion;
12712
+ var import_fs5, import_path5, getLicenseVersion, getProVersion;
12630
12713
  var init_version2 = __esm({
12631
12714
  "../pro/packages/pro/src/constants/version.ts"() {
12632
12715
  init_src2();
12633
- import_fs4 = __toESM(require("fs"));
12634
- import_path4 = __toESM(require("path"));
12716
+ import_fs5 = __toESM(require("fs"));
12717
+ import_path5 = __toESM(require("path"));
12635
12718
  getLicenseVersion = () => {
12636
12719
  if (environment_default2.isDev()) {
12637
12720
  const DEV_VER_FILENAME = "dev-version.txt";
12638
- const verFile = import_path4.default.join(objectStore_exports2.budibaseTempDir(), DEV_VER_FILENAME);
12639
- if (import_fs4.default.existsSync(verFile)) {
12640
- return import_fs4.default.readFileSync(verFile, "utf8");
12721
+ const verFile = import_path5.default.join(objectStore_exports2.budibaseTempDir(), DEV_VER_FILENAME);
12722
+ if (import_fs5.default.existsSync(verFile)) {
12723
+ return import_fs5.default.readFileSync(verFile, "utf8");
12641
12724
  } else {
12642
12725
  const devVer = utils_exports2.newid();
12643
- import_fs4.default.writeFileSync(verFile, devVer);
12726
+ import_fs5.default.writeFileSync(verFile, devVer);
12644
12727
  return devVer;
12645
12728
  }
12646
12729
  } else {
@@ -13086,31 +13169,31 @@ function getOfflineLicense() {
13086
13169
  }
13087
13170
  }
13088
13171
  function getOfflineLicenseFromDisk() {
13089
- if (import_fs5.default.existsSync(LICENSE_FILE_PATH)) {
13090
- const token = import_fs5.default.readFileSync(LICENSE_FILE_PATH, { encoding: "utf-8" });
13172
+ if (import_fs6.default.existsSync(LICENSE_FILE_PATH)) {
13173
+ const token = import_fs6.default.readFileSync(LICENSE_FILE_PATH, { encoding: "utf-8" });
13091
13174
  return import_jsonwebtoken.default.verify(token, PUBLIC_KEY, { algorithms: ["RS256"] });
13092
13175
  }
13093
13176
  }
13094
13177
  function writeOfflineLicenseToDisk(signedLicense) {
13095
- import_fs5.default.writeFileSync(LICENSE_FILE_PATH, signedLicense, { encoding: "utf-8" });
13178
+ import_fs6.default.writeFileSync(LICENSE_FILE_PATH, signedLicense, { encoding: "utf-8" });
13096
13179
  }
13097
13180
  function deleteOfflineLicense() {
13098
- import_fs5.default.rmSync(LICENSE_FILE_PATH, { force: true });
13181
+ import_fs6.default.rmSync(LICENSE_FILE_PATH, { force: true });
13099
13182
  }
13100
- var import_fs5, import_path5, import_os2, import_jsonwebtoken, SUB_DIRECTORY, DIRECTORY, OFFLINE_LICENSE_FILE, LICENSE_FILE_PATH, PUBLIC_KEY;
13183
+ var import_fs6, import_path6, import_os2, import_jsonwebtoken, SUB_DIRECTORY, DIRECTORY, OFFLINE_LICENSE_FILE, LICENSE_FILE_PATH, PUBLIC_KEY;
13101
13184
  var init_offline = __esm({
13102
13185
  "../pro/packages/pro/src/sdk/licensing/licenses/offline.ts"() {
13103
- import_fs5 = __toESM(require("fs"));
13104
- import_path5 = require("path");
13186
+ import_fs6 = __toESM(require("fs"));
13187
+ import_path6 = require("path");
13105
13188
  import_os2 = require("os");
13106
13189
  import_jsonwebtoken = __toESM(require("jsonwebtoken"));
13107
13190
  init_src2();
13108
13191
  SUB_DIRECTORY = environment_default2.isTest() ? ".budibase-test" : ".budibase";
13109
- DIRECTORY = (0, import_path5.join)((0, import_os2.tmpdir)(), SUB_DIRECTORY);
13192
+ DIRECTORY = (0, import_path6.join)((0, import_os2.tmpdir)(), SUB_DIRECTORY);
13110
13193
  OFFLINE_LICENSE_FILE = "offline_license.txt";
13111
- LICENSE_FILE_PATH = (0, import_path5.join)(DIRECTORY, OFFLINE_LICENSE_FILE);
13112
- if (!import_fs5.default.existsSync(DIRECTORY)) {
13113
- import_fs5.default.mkdirSync(DIRECTORY);
13194
+ LICENSE_FILE_PATH = (0, import_path6.join)(DIRECTORY, OFFLINE_LICENSE_FILE);
13195
+ if (!import_fs6.default.existsSync(DIRECTORY)) {
13196
+ import_fs6.default.mkdirSync(DIRECTORY);
13114
13197
  }
13115
13198
  PUBLIC_KEY = "-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAvz3jePLCFBXZ19c8Dpkv\nXtSgOhKFOcvQdo/LV0KJRUzQWDPWuO4ILtBtnqhjtIzZH4CH0qCYBet5L6Qr4CM1\nl2HXiAD1Q2rlHNW9wDaYyKb1F5f+v4RyqCAyzlkwRdksmkLeECTboojNnmRCrE3C\n8suunQP5bEScqEY2kclqzSf8e6xqMzPUg3mL/pNa1iEv7TuLbU9nJfgR36l0WmZY\n94fWnSaT8OSXSqcxsaByf06gfS3HAoTJNc7eqz1Hf9fUORQGPUAnFK8cT3SfdA36\nd/o3ZWE1TTj1zYwlCLN5qRKr3hU8nC3xEYNEbkB9SfTRaOq9Q7P8WmfLkoCPm3pR\nmwIDAQAB\n-----END PUBLIC KEY-----\n";
13116
13199
  }
@@ -14567,13 +14650,13 @@ var init_groups6 = __esm({
14567
14650
 
14568
14651
  // ../pro/packages/pro/src/utilities/fileSystem.ts
14569
14652
  function loadJSFile(directory2, name2) {
14570
- return import_fs6.default.readFileSync((0, import_path6.join)(directory2, name2), "utf8");
14653
+ return import_fs7.default.readFileSync((0, import_path7.join)(directory2, name2), "utf8");
14571
14654
  }
14572
- var import_fs6, import_path6;
14655
+ var import_fs7, import_path7;
14573
14656
  var init_fileSystem = __esm({
14574
14657
  "../pro/packages/pro/src/utilities/fileSystem.ts"() {
14575
- import_fs6 = __toESM(require("fs"));
14576
- import_path6 = require("path");
14658
+ import_fs7 = __toESM(require("fs"));
14659
+ import_path7 = require("path");
14577
14660
  }
14578
14661
  });
14579
14662
 
@@ -17540,8 +17623,8 @@ async function runBackup(trigger, tenantId, appId, opts) {
17540
17623
  }
17541
17624
  });
17542
17625
  await updateMetadata2("complete" /* COMPLETE */, { filename, contents });
17543
- if (import_fs7.default.existsSync(tarPath)) {
17544
- import_fs7.default.rmSync(tarPath);
17626
+ if (import_fs8.default.existsSync(tarPath)) {
17627
+ import_fs8.default.rmSync(tarPath);
17545
17628
  }
17546
17629
  } catch (err) {
17547
17630
  logging_exports.logAlert("App backup error", err);
@@ -17599,14 +17682,14 @@ async function exportProcessor(job, opts) {
17599
17682
  });
17600
17683
  });
17601
17684
  }
17602
- var import_fs7;
17685
+ var import_fs8;
17603
17686
  var init_processing = __esm({
17604
17687
  "../pro/packages/pro/src/sdk/backups/processing.ts"() {
17605
17688
  init_src2();
17606
17689
  init_backup5();
17607
17690
  init_src();
17608
17691
  init_queue4();
17609
- import_fs7 = __toESM(require("fs"));
17692
+ import_fs8 = __toESM(require("fs"));
17610
17693
  }
17611
17694
  });
17612
17695
 
@@ -18247,15 +18330,15 @@ async function downloadBackup(ctx) {
18247
18330
  const backupId = ctx.params.backupId;
18248
18331
  const { metadata: metadata2, path: path2 } = await backups_default.downloadAppBackup(backupId);
18249
18332
  ctx.attachment(`backup-${metadata2.timestamp}.tar.gz`);
18250
- ctx.body = import_fs8.default.createReadStream(path2);
18333
+ ctx.body = import_fs9.default.createReadStream(path2);
18251
18334
  }
18252
- var import_fs8;
18335
+ var import_fs9;
18253
18336
  var init_backups3 = __esm({
18254
18337
  "../pro/packages/pro/src/api/controllers/apps/backups.ts"() {
18255
18338
  init_src();
18256
18339
  init_sdk2();
18257
18340
  init_src2();
18258
- import_fs8 = __toESM(require("fs"));
18341
+ import_fs9 = __toESM(require("fs"));
18259
18342
  }
18260
18343
  });
18261
18344
 
@@ -18891,11 +18974,39 @@ var init_filters = __esm({
18891
18974
  // ../shared-core/src/utils.ts
18892
18975
  var utils_exports5 = {};
18893
18976
  __export(utils_exports5, {
18977
+ parallelForeach: () => parallelForeach,
18894
18978
  unreachable: () => unreachable
18895
18979
  });
18896
18980
  function unreachable(value, message = `No such case in exhaustive switch: ${value}`) {
18897
18981
  throw new Error(message);
18898
18982
  }
18983
+ async function parallelForeach(items, task, maxConcurrency) {
18984
+ const promises = [];
18985
+ let index2 = 0;
18986
+ const processItem = async (item) => {
18987
+ try {
18988
+ await task(item);
18989
+ } finally {
18990
+ processNext();
18991
+ }
18992
+ };
18993
+ const processNext = () => {
18994
+ if (index2 >= items.length) {
18995
+ return;
18996
+ }
18997
+ const item = items[index2];
18998
+ index2++;
18999
+ const promise = processItem(item);
19000
+ promises.push(promise);
19001
+ if (promises.length >= maxConcurrency) {
19002
+ Promise.race(promises).then(processNext);
19003
+ } else {
19004
+ processNext();
19005
+ }
19006
+ };
19007
+ processNext();
19008
+ await Promise.all(promises);
19009
+ }
18899
19010
  var init_utils12 = __esm({
18900
19011
  "../shared-core/src/utils.ts"() {
18901
19012
  }
@@ -19519,32 +19630,32 @@ var init_centralPath = __esm({
19519
19630
  });
19520
19631
 
19521
19632
  // src/utilities/fileSystem/filesystem.ts
19522
- var import_fs9, import_path7, import_tar, uuid2, TOP_LEVEL_PATH, apiFileReturn, streamFile, createTempFolder, extractTarball;
19633
+ var import_fs10, import_path8, import_tar, uuid2, TOP_LEVEL_PATH, apiFileReturn, streamFile, createTempFolder, extractTarball;
19523
19634
  var init_filesystem = __esm({
19524
19635
  "src/utilities/fileSystem/filesystem.ts"() {
19525
- import_fs9 = __toESM(require("fs"));
19636
+ import_fs10 = __toESM(require("fs"));
19526
19637
  init_budibaseDir();
19527
- import_path7 = require("path");
19638
+ import_path8 = require("path");
19528
19639
  init_environment();
19529
19640
  import_tar = __toESM(require("tar"));
19530
19641
  init_environment();
19531
19642
  uuid2 = require("uuid/v4");
19532
- TOP_LEVEL_PATH = environment_default.TOP_LEVEL_PATH || (0, import_path7.resolve)((0, import_path7.join)(__dirname, "..", "..", ".."));
19643
+ TOP_LEVEL_PATH = environment_default.TOP_LEVEL_PATH || (0, import_path8.resolve)((0, import_path8.join)(__dirname, "..", "..", ".."));
19533
19644
  apiFileReturn = (contents) => {
19534
- const path2 = (0, import_path7.join)(budibaseTempDir2(), uuid2());
19535
- import_fs9.default.writeFileSync(path2, contents);
19536
- return import_fs9.default.createReadStream(path2);
19645
+ const path2 = (0, import_path8.join)(budibaseTempDir2(), uuid2());
19646
+ import_fs10.default.writeFileSync(path2, contents);
19647
+ return import_fs10.default.createReadStream(path2);
19537
19648
  };
19538
19649
  streamFile = (path2) => {
19539
- return import_fs9.default.createReadStream(path2);
19650
+ return import_fs10.default.createReadStream(path2);
19540
19651
  };
19541
19652
  createTempFolder = (item) => {
19542
- const path2 = (0, import_path7.join)(budibaseTempDir2(), item);
19653
+ const path2 = (0, import_path8.join)(budibaseTempDir2(), item);
19543
19654
  try {
19544
- if (import_fs9.default.existsSync(path2)) {
19545
- import_fs9.default.rmSync(path2, { recursive: true, force: true });
19655
+ if (import_fs10.default.existsSync(path2)) {
19656
+ import_fs10.default.rmSync(path2, { recursive: true, force: true });
19546
19657
  }
19547
- import_fs9.default.mkdirSync(path2);
19658
+ import_fs10.default.mkdirSync(path2);
19548
19659
  } catch (err) {
19549
19660
  throw new Error(`Path cannot be created: ${err.message}`);
19550
19661
  }
@@ -19571,17 +19682,17 @@ var init_clientLibrary = __esm({
19571
19682
  });
19572
19683
 
19573
19684
  // src/utilities/fileSystem/app.ts
19574
- var import_path8, NODE_MODULES_PATH;
19685
+ var import_path9, NODE_MODULES_PATH;
19575
19686
  var init_app7 = __esm({
19576
19687
  "src/utilities/fileSystem/app.ts"() {
19577
19688
  init_budibaseDir();
19578
- import_path8 = require("path");
19689
+ import_path9 = require("path");
19579
19690
  init_constants6();
19580
19691
  init_clientLibrary();
19581
19692
  init_environment();
19582
19693
  init_src2();
19583
19694
  init_filesystem();
19584
- NODE_MODULES_PATH = (0, import_path8.join)(TOP_LEVEL_PATH, "node_modules");
19695
+ NODE_MODULES_PATH = (0, import_path9.join)(TOP_LEVEL_PATH, "node_modules");
19585
19696
  }
19586
19697
  });
19587
19698
 
@@ -19589,19 +19700,19 @@ var init_app7 = __esm({
19589
19700
  async function getPluginImpl(path2, plugin) {
19590
19701
  var _a;
19591
19702
  const hash3 = (_a = plugin.schema) == null ? void 0 : _a.hash;
19592
- if (!import_fs10.default.existsSync(path2)) {
19593
- import_fs10.default.mkdirSync(path2);
19703
+ if (!import_fs11.default.existsSync(path2)) {
19704
+ import_fs11.default.mkdirSync(path2);
19594
19705
  }
19595
- const filename = (0, import_path9.join)(path2, plugin.name);
19706
+ const filename = (0, import_path10.join)(path2, plugin.name);
19596
19707
  const metadataName = `${filename}.bbmetadata`;
19597
- if (import_fs10.default.existsSync(filename)) {
19598
- const currentHash = import_fs10.default.readFileSync(metadataName, "utf8");
19708
+ if (import_fs11.default.existsSync(filename)) {
19709
+ const currentHash = import_fs11.default.readFileSync(metadataName, "utf8");
19599
19710
  if (currentHash === hash3) {
19600
19711
  return require(filename);
19601
19712
  } else {
19602
19713
  console.log(`Updating plugin: ${plugin.name}`);
19603
19714
  delete require.cache[require.resolve(filename)];
19604
- import_fs10.default.unlinkSync(filename);
19715
+ import_fs11.default.unlinkSync(filename);
19605
19716
  }
19606
19717
  }
19607
19718
  const pluginKey = objectStore_exports2.getPluginJSKey(plugin);
@@ -19609,24 +19720,24 @@ async function getPluginImpl(path2, plugin) {
19609
19720
  objectStore_exports2.ObjectStoreBuckets.PLUGINS,
19610
19721
  pluginKey
19611
19722
  );
19612
- import_fs10.default.writeFileSync(filename, pluginJs);
19613
- import_fs10.default.writeFileSync(metadataName, hash3);
19723
+ import_fs11.default.writeFileSync(filename, pluginJs);
19724
+ import_fs11.default.writeFileSync(metadataName, hash3);
19614
19725
  return require(filename);
19615
19726
  }
19616
- var import_fs10, import_path9, DATASOURCE_PATH, AUTOMATION_PATH, getPluginMetadata, getDatasourcePlugin, getAutomationPlugin;
19727
+ var import_fs11, import_path10, DATASOURCE_PATH, AUTOMATION_PATH, getPluginMetadata, getDatasourcePlugin, getAutomationPlugin;
19617
19728
  var init_plugin5 = __esm({
19618
19729
  "src/utilities/fileSystem/plugin.ts"() {
19619
19730
  init_budibaseDir();
19620
- import_fs10 = __toESM(require("fs"));
19621
- import_path9 = require("path");
19731
+ import_fs11 = __toESM(require("fs"));
19732
+ import_path10 = require("path");
19622
19733
  init_src2();
19623
- DATASOURCE_PATH = (0, import_path9.join)(budibaseTempDir2(), "datasource");
19624
- AUTOMATION_PATH = (0, import_path9.join)(budibaseTempDir2(), "automation");
19734
+ DATASOURCE_PATH = (0, import_path10.join)(budibaseTempDir2(), "datasource");
19735
+ AUTOMATION_PATH = (0, import_path10.join)(budibaseTempDir2(), "automation");
19625
19736
  getPluginMetadata = async (path2) => {
19626
19737
  let metadata2 = {};
19627
19738
  try {
19628
- const pkg2 = import_fs10.default.readFileSync((0, import_path9.join)(path2, "package.json"), "utf8");
19629
- const schema = import_fs10.default.readFileSync((0, import_path9.join)(path2, "schema.json"), "utf8");
19739
+ const pkg2 = import_fs11.default.readFileSync((0, import_path10.join)(path2, "package.json"), "utf8");
19740
+ const schema = import_fs11.default.readFileSync((0, import_path10.join)(path2, "schema.json"), "utf8");
19630
19741
  metadata2.schema = JSON.parse(schema);
19631
19742
  metadata2.package = JSON.parse(pkg2);
19632
19743
  if (!metadata2.package.name || !metadata2.package.version || !metadata2.package.description) {
@@ -19697,13 +19808,14 @@ __export(exports_exports, {
19697
19808
  streamExportApp: () => streamExportApp
19698
19809
  });
19699
19810
  function tarFilesToTmp(tmpDir, files2) {
19700
- const exportFile = (0, import_path10.join)(budibaseTempDir2(), `${uuid3()}.tar.gz`);
19701
- tar3.create(
19811
+ const fileName = `${uuid3()}.tar.gz`;
19812
+ const exportFile = (0, import_path11.join)(budibaseTempDir2(), fileName);
19813
+ import_tar2.default.create(
19702
19814
  {
19703
19815
  sync: true,
19704
19816
  gzip: true,
19705
19817
  file: exportFile,
19706
- recursive: true,
19818
+ noDirRecurse: false,
19707
19819
  cwd: tmpDir
19708
19820
  },
19709
19821
  files2
@@ -19720,7 +19832,7 @@ async function exportDB(dbName, opts = {}) {
19720
19832
  return db_exports.doWithDB(dbName, async (db2) => {
19721
19833
  if (opts == null ? void 0 : opts.exportPath) {
19722
19834
  const path2 = opts == null ? void 0 : opts.exportPath;
19723
- const writeStream = import_fs11.default.createWriteStream(path2);
19835
+ const writeStream = import_fs12.default.createWriteStream(path2);
19724
19836
  await db2.dump(writeStream, exportOpts);
19725
19837
  return path2;
19726
19838
  } else {
@@ -19753,9 +19865,9 @@ async function exportApp(appId, config) {
19753
19865
  for (let path2 of STATIC_APP_FILES) {
19754
19866
  const contents = await objectStore_exports2.retrieve(
19755
19867
  ObjectStoreBuckets2.APPS,
19756
- (0, import_path10.join)(appPath, path2)
19868
+ (0, import_path11.join)(appPath, path2)
19757
19869
  );
19758
- import_fs11.default.writeFileSync((0, import_path10.join)(tmpPath, path2), contents);
19870
+ import_fs12.default.writeFileSync((0, import_path11.join)(tmpPath, path2), contents);
19759
19871
  }
19760
19872
  } else {
19761
19873
  tmpPath = await objectStore_exports2.retrieveDirectory(
@@ -19764,37 +19876,52 @@ async function exportApp(appId, config) {
19764
19876
  );
19765
19877
  }
19766
19878
  }
19767
- const downloadedPath = (0, import_path10.join)(tmpPath, appPath);
19768
- if (import_fs11.default.existsSync(downloadedPath)) {
19769
- const allFiles = import_fs11.default.readdirSync(downloadedPath);
19879
+ const downloadedPath = (0, import_path11.join)(tmpPath, appPath);
19880
+ if (import_fs12.default.existsSync(downloadedPath)) {
19881
+ const allFiles = import_fs12.default.readdirSync(downloadedPath);
19770
19882
  for (let file of allFiles) {
19771
- const path2 = (0, import_path10.join)(downloadedPath, file);
19772
- import_fs11.default.renameSync(path2, (0, import_path10.join)(downloadedPath, "..", file));
19883
+ const path2 = (0, import_path11.join)(downloadedPath, file);
19884
+ import_fs12.default.renameSync(path2, (0, import_path11.join)(downloadedPath, "..", file));
19773
19885
  }
19774
- import_fs11.default.rmdirSync(downloadedPath);
19886
+ import_fs12.default.rmdirSync(downloadedPath);
19775
19887
  }
19776
- const dbPath = (0, import_path10.join)(tmpPath, DB_EXPORT_FILE);
19888
+ const dbPath = (0, import_path11.join)(tmpPath, DB_EXPORT_FILE);
19777
19889
  await exportDB(appId, {
19778
19890
  filter: defineFilter(config == null ? void 0 : config.excludeRows, config == null ? void 0 : config.excludeLogs),
19779
19891
  exportPath: dbPath
19780
19892
  });
19893
+ if (config == null ? void 0 : config.encryptPassword) {
19894
+ for (let file of import_fs12.default.readdirSync(tmpPath)) {
19895
+ const path2 = (0, import_path11.join)(tmpPath, file);
19896
+ await encryption_exports.encryptFile(
19897
+ { dir: tmpPath, filename: file },
19898
+ config.encryptPassword
19899
+ );
19900
+ import_fs12.default.rmSync(path2);
19901
+ }
19902
+ }
19781
19903
  if (config == null ? void 0 : config.tar) {
19782
- const tarPath = tarFilesToTmp(tmpPath, import_fs11.default.readdirSync(tmpPath));
19783
- import_fs11.default.rmSync(tmpPath, { recursive: true, force: true });
19904
+ const tarPath = tarFilesToTmp(tmpPath, import_fs12.default.readdirSync(tmpPath));
19905
+ import_fs12.default.rmSync(tmpPath, { recursive: true, force: true });
19784
19906
  return tarPath;
19785
19907
  } else {
19786
19908
  return tmpPath;
19787
19909
  }
19788
19910
  }
19789
- async function streamExportApp(appId, excludeRows) {
19911
+ async function streamExportApp({
19912
+ appId,
19913
+ excludeRows,
19914
+ encryptPassword
19915
+ }) {
19790
19916
  const tmpPath = await exportApp(appId, {
19791
19917
  excludeRows,
19792
19918
  excludeLogs: true,
19793
- tar: true
19919
+ tar: true,
19920
+ encryptPassword
19794
19921
  });
19795
19922
  return streamFile(tmpPath);
19796
19923
  }
19797
- var import_fs11, import_path10, uuid3, tar3, MemoryStream2;
19924
+ var import_fs12, import_path11, import_tar2, uuid3, MemoryStream2;
19798
19925
  var init_exports2 = __esm({
19799
19926
  "src/sdk/app/backups/exports.ts"() {
19800
19927
  init_src2();
@@ -19803,11 +19930,11 @@ var init_exports2 = __esm({
19803
19930
  init_constants6();
19804
19931
  init_utils13();
19805
19932
  init_constants7();
19806
- import_fs11 = __toESM(require("fs"));
19807
- import_path10 = require("path");
19933
+ import_fs12 = __toESM(require("fs"));
19934
+ import_path11 = require("path");
19808
19935
  init_environment();
19936
+ import_tar2 = __toESM(require("tar"));
19809
19937
  uuid3 = require("uuid/v4");
19810
- tar3 = require("tar");
19811
19938
  MemoryStream2 = require("memorystream");
19812
19939
  }
19813
19940
  });
@@ -19884,16 +20011,16 @@ async function getTemplateStream(template) {
19884
20011
  throw new Error("Cannot import a non-text based file.");
19885
20012
  }
19886
20013
  if (template.file) {
19887
- return import_fs12.default.createReadStream(template.file.path);
20014
+ return import_fs13.default.createReadStream(template.file.path);
19888
20015
  } else if (template.key) {
19889
20016
  const [type, name2] = template.key.split("/");
19890
20017
  const tmpPath = await downloadTemplate(type, name2);
19891
- return import_fs12.default.createReadStream((0, import_path11.join)(tmpPath, name2, "db", "dump.txt"));
20018
+ return import_fs13.default.createReadStream((0, import_path12.join)(tmpPath, name2, "db", "dump.txt"));
19892
20019
  }
19893
20020
  }
19894
20021
  function untarFile(file) {
19895
- const tmpPath = (0, import_path11.join)(budibaseTempDir2(), uuid4());
19896
- import_fs12.default.mkdirSync(tmpPath);
20022
+ const tmpPath = (0, import_path12.join)(budibaseTempDir2(), uuid4());
20023
+ import_fs13.default.mkdirSync(tmpPath);
19897
20024
  tar4.extract({
19898
20025
  sync: true,
19899
20026
  cwd: tmpPath,
@@ -19901,31 +20028,49 @@ function untarFile(file) {
19901
20028
  });
19902
20029
  return tmpPath;
19903
20030
  }
20031
+ async function decryptFiles(path2, password) {
20032
+ try {
20033
+ for (let file of import_fs13.default.readdirSync(path2)) {
20034
+ const inputPath = (0, import_path12.join)(path2, file);
20035
+ const outputPath = inputPath.replace(/\.enc$/, "");
20036
+ await encryption_exports.decryptFile(inputPath, outputPath, password);
20037
+ import_fs13.default.rmSync(inputPath);
20038
+ }
20039
+ } catch (err) {
20040
+ if (err.message === "incorrect header check") {
20041
+ throw new Error("File cannot be imported");
20042
+ }
20043
+ throw err;
20044
+ }
20045
+ }
19904
20046
  function getGlobalDBFile(tmpPath) {
19905
- return import_fs12.default.readFileSync((0, import_path11.join)(tmpPath, GLOBAL_DB_EXPORT_FILE), "utf8");
20047
+ return import_fs13.default.readFileSync((0, import_path12.join)(tmpPath, GLOBAL_DB_EXPORT_FILE), "utf8");
19906
20048
  }
19907
20049
  function getListOfAppsInMulti(tmpPath) {
19908
- return import_fs12.default.readdirSync(tmpPath).filter((dir) => dir !== GLOBAL_DB_EXPORT_FILE);
20050
+ return import_fs13.default.readdirSync(tmpPath).filter((dir) => dir !== GLOBAL_DB_EXPORT_FILE);
19909
20051
  }
19910
20052
  async function importApp(appId, db2, template) {
19911
20053
  var _a, _b;
19912
20054
  let prodAppId = db_exports.getProdAppID(appId);
19913
20055
  let dbStream;
19914
20056
  const isTar = template.file && ((_b = (_a = template == null ? void 0 : template.file) == null ? void 0 : _a.type) == null ? void 0 : _b.endsWith("gzip"));
19915
- const isDirectory = template.file && import_fs12.default.lstatSync(template.file.path).isDirectory();
20057
+ const isDirectory = template.file && import_fs13.default.lstatSync(template.file.path).isDirectory();
19916
20058
  if (template.file && (isTar || isDirectory)) {
19917
20059
  const tmpPath = isTar ? untarFile(template.file) : template.file.path;
19918
- const contents = import_fs12.default.readdirSync(tmpPath);
20060
+ if (isTar && template.file.password) {
20061
+ await decryptFiles(tmpPath, template.file.password);
20062
+ }
20063
+ const contents = import_fs13.default.readdirSync(tmpPath);
19919
20064
  if (contents.length) {
19920
20065
  let promises = [];
19921
20066
  let excludedFiles = [GLOBAL_DB_EXPORT_FILE, DB_EXPORT_FILE];
19922
20067
  for (let filename of contents) {
19923
- const path2 = (0, import_path11.join)(tmpPath, filename);
20068
+ const path2 = (0, import_path12.join)(tmpPath, filename);
19924
20069
  if (excludedFiles.includes(filename)) {
19925
20070
  continue;
19926
20071
  }
19927
- filename = (0, import_path11.join)(prodAppId, filename);
19928
- if (import_fs12.default.lstatSync(path2).isDirectory()) {
20072
+ filename = (0, import_path12.join)(prodAppId, filename);
20073
+ if (import_fs13.default.lstatSync(path2).isDirectory()) {
19929
20074
  promises.push(
19930
20075
  objectStore_exports2.uploadDirectory(ObjectStoreBuckets2.APPS, path2, filename)
19931
20076
  );
@@ -19941,7 +20086,7 @@ async function importApp(appId, db2, template) {
19941
20086
  }
19942
20087
  await Promise.all(promises);
19943
20088
  }
19944
- dbStream = import_fs12.default.createReadStream((0, import_path11.join)(tmpPath, DB_EXPORT_FILE));
20089
+ dbStream = import_fs13.default.createReadStream((0, import_path12.join)(tmpPath, DB_EXPORT_FILE));
19945
20090
  } else {
19946
20091
  dbStream = await getTemplateStream(template);
19947
20092
  }
@@ -19953,7 +20098,7 @@ async function importApp(appId, db2, template) {
19953
20098
  await updateAutomations(prodAppId, db2);
19954
20099
  return ok;
19955
20100
  }
19956
- var import_path11, import_fs12, uuid4, tar4;
20101
+ var import_path12, import_fs13, uuid4, tar4;
19957
20102
  var init_imports = __esm({
19958
20103
  "src/sdk/app/backups/imports.ts"() {
19959
20104
  init_src2();
@@ -19962,8 +20107,8 @@ var init_imports = __esm({
19962
20107
  init_constants7();
19963
20108
  init_fileSystem2();
19964
20109
  init_constants6();
19965
- import_path11 = require("path");
19966
- import_fs12 = __toESM(require("fs"));
20110
+ import_path12 = require("path");
20111
+ import_fs13 = __toESM(require("fs"));
19967
20112
  init_sdk3();
19968
20113
  init_src();
19969
20114
  uuid4 = require("uuid/v4");
@@ -21086,6 +21231,19 @@ var init_postgres = __esm({
21086
21231
  required: false
21087
21232
  },
21088
21233
  ca: {
21234
+ display: "Server CA",
21235
+ type: "longForm" /* LONGFORM */,
21236
+ default: false,
21237
+ required: false
21238
+ },
21239
+ clientKey: {
21240
+ display: "Client key",
21241
+ type: "longForm" /* LONGFORM */,
21242
+ default: false,
21243
+ required: false
21244
+ },
21245
+ clientCert: {
21246
+ display: "Client cert",
21089
21247
  type: "longForm" /* LONGFORM */,
21090
21248
  default: false,
21091
21249
  required: false
@@ -21127,7 +21285,9 @@ var init_postgres = __esm({
21127
21285
  ...this.config,
21128
21286
  ssl: this.config.ssl ? {
21129
21287
  rejectUnauthorized: this.config.rejectUnauthorized,
21130
- ca: this.config.ca
21288
+ ca: this.config.ca,
21289
+ key: this.config.clientKey,
21290
+ cert: this.config.clientCert
21131
21291
  } : void 0
21132
21292
  };
21133
21293
  this.client = new import_pg.Client(newConfig);
@@ -21270,7 +21430,8 @@ var init_postgres = __esm({
21270
21430
  try {
21271
21431
  await this.openConnection();
21272
21432
  const columnsResponse = await this.client.query(this.COLUMNS_SQL);
21273
- return columnsResponse.rows.map((row) => row.table_name);
21433
+ const names = columnsResponse.rows.map((row) => row.table_name);
21434
+ return [...new Set(names)];
21274
21435
  } finally {
21275
21436
  await this.closeConnection();
21276
21437
  }
@@ -21899,6 +22060,8 @@ var init_mongodb = __esm({
21899
22060
  response2.connected = true;
21900
22061
  } catch (e) {
21901
22062
  response2.error = e.message;
22063
+ } finally {
22064
+ await this.client.close();
21902
22065
  }
21903
22066
  return response2;
21904
22067
  }
@@ -23830,6 +23993,16 @@ var init_rest = __esm({
23830
23993
  });
23831
23994
 
23832
23995
  // src/integrations/googlesheets.ts
23996
+ async function setupCreationAuth(datasouce) {
23997
+ if (datasouce.continueSetupId) {
23998
+ const appId = context_exports.getAppId();
23999
+ const tokens = await cache_exports.get(
24000
+ `datasource:creation:${appId}:google:${datasouce.continueSetupId}`
24001
+ );
24002
+ datasouce.auth = tokens.tokens;
24003
+ delete datasouce.continueSetupId;
24004
+ }
24005
+ }
23833
24006
  var import_google_auth_library, import_google_spreadsheet, import_node_fetch9, ALLOWED_TYPES, SCHEMA12, GoogleSheetsIntegration, googlesheets_default;
23834
24007
  var init_googlesheets = __esm({
23835
24008
  "src/integrations/googlesheets.ts"() {
@@ -23867,7 +24040,7 @@ var init_googlesheets = __esm({
23867
24040
  },
23868
24041
  datasource: {
23869
24042
  spreadsheetId: {
23870
- display: "Google Sheet URL",
24043
+ display: "Spreadsheet URL",
23871
24044
  type: "string" /* STRING */,
23872
24045
  required: true
23873
24046
  }
@@ -23988,6 +24161,7 @@ var init_googlesheets = __esm({
23988
24161
  async connect() {
23989
24162
  var _a;
23990
24163
  try {
24164
+ await setupCreationAuth(this.config);
23991
24165
  let googleConfig = await configs_exports.getGoogleDatasourceConfig();
23992
24166
  if (!googleConfig) {
23993
24167
  throw new HTTPError("Google config not found", 400);
@@ -24038,21 +24212,22 @@ var init_googlesheets = __esm({
24038
24212
  return table;
24039
24213
  }
24040
24214
  async buildSchema(datasourceId, entities) {
24041
- if (!this.config.auth) {
24042
- return;
24043
- }
24044
24215
  await this.connect();
24045
24216
  const sheets = this.client.sheetsByIndex;
24046
24217
  const tables = {};
24047
- for (let sheet of sheets) {
24048
- await sheet.getRows();
24049
- const id = buildExternalTableId(datasourceId, sheet.title);
24050
- tables[sheet.title] = this.getTableSchema(
24051
- sheet.title,
24052
- sheet.headerValues,
24053
- id
24054
- );
24055
- }
24218
+ await utils_exports5.parallelForeach(
24219
+ sheets,
24220
+ async (sheet) => {
24221
+ await sheet.getRows({ limit: 0, offset: 0 });
24222
+ const id = buildExternalTableId(datasourceId, sheet.title);
24223
+ tables[sheet.title] = this.getTableSchema(
24224
+ sheet.title,
24225
+ sheet.headerValues,
24226
+ id
24227
+ );
24228
+ },
24229
+ 10
24230
+ );
24056
24231
  const final = finaliseExternalTables(tables, entities);
24057
24232
  this.tables = final.tables;
24058
24233
  this.schemaErrors = final.errors;
@@ -26908,22 +27083,22 @@ function threadSetup() {
26908
27083
  init8();
26909
27084
  }
26910
27085
  async function checkCacheForDynamicVariable(queryId, variable) {
26911
- const cache2 = await getClient2();
26912
- return cache2.get(makeVariableKey(queryId, variable));
27086
+ const cache3 = await getClient2();
27087
+ return cache3.get(makeVariableKey(queryId, variable));
26913
27088
  }
26914
27089
  async function invalidateDynamicVariables(cachedVars) {
26915
- const cache2 = await getClient2();
27090
+ const cache3 = await getClient2();
26916
27091
  let promises = [];
26917
27092
  for (let variable of cachedVars) {
26918
27093
  promises.push(
26919
- cache2.delete(makeVariableKey(variable.queryId, variable.name))
27094
+ cache3.delete(makeVariableKey(variable.queryId, variable.name))
26920
27095
  );
26921
27096
  }
26922
27097
  await Promise.all(promises);
26923
27098
  }
26924
27099
  async function storeDynamicVariable(queryId, variable, value) {
26925
- const cache2 = await getClient2();
26926
- await cache2.store(
27100
+ const cache3 = await getClient2();
27101
+ await cache3.store(
26927
27102
  makeVariableKey(queryId, variable),
26928
27103
  value,
26929
27104
  VARIABLE_TTL_SECONDS
@@ -27391,7 +27566,16 @@ async function checkResponse(response2, errorMsg, { ctx } = {}) {
27391
27566
  }
27392
27567
  return response2.json();
27393
27568
  }
27394
- async function sendSmtpEmail(to, from, subject, contents, cc, bcc, automation) {
27569
+ async function sendSmtpEmail({
27570
+ to,
27571
+ from,
27572
+ subject,
27573
+ contents,
27574
+ cc,
27575
+ bcc,
27576
+ automation,
27577
+ invite
27578
+ }) {
27395
27579
  const response2 = await (0, import_node_fetch10.default)(
27396
27580
  checkSlashesInUrl2(environment_default.WORKER_URL + `/api/global/email/send`),
27397
27581
  request(void 0, {
@@ -27404,7 +27588,8 @@ async function sendSmtpEmail(to, from, subject, contents, cc, bcc, automation) {
27404
27588
  cc,
27405
27589
  bcc,
27406
27590
  purpose: "custom",
27407
- automation
27591
+ automation,
27592
+ invite
27408
27593
  }
27409
27594
  })
27410
27595
  );
@@ -27452,6 +27637,35 @@ var definition7 = {
27452
27637
  contents: {
27453
27638
  type: "string" /* STRING */,
27454
27639
  title: "HTML Contents"
27640
+ },
27641
+ addInvite: {
27642
+ type: "boolean" /* BOOLEAN */,
27643
+ title: "Add calendar invite"
27644
+ },
27645
+ startTime: {
27646
+ type: "date" /* DATE */,
27647
+ title: "Start Time",
27648
+ dependsOn: "addInvite"
27649
+ },
27650
+ endTime: {
27651
+ type: "date" /* DATE */,
27652
+ title: "End Time",
27653
+ dependsOn: "addInvite"
27654
+ },
27655
+ summary: {
27656
+ type: "string" /* STRING */,
27657
+ title: "Meeting Summary",
27658
+ dependsOn: "addInvite"
27659
+ },
27660
+ location: {
27661
+ type: "string" /* STRING */,
27662
+ title: "Location",
27663
+ dependsOn: "addInvite"
27664
+ },
27665
+ url: {
27666
+ type: "string" /* STRING */,
27667
+ title: "URL",
27668
+ dependsOn: "addInvite"
27455
27669
  }
27456
27670
  },
27457
27671
  required: ["to", "from", "subject", "contents"]
@@ -27472,21 +27686,41 @@ var definition7 = {
27472
27686
  }
27473
27687
  };
27474
27688
  async function run3({ inputs }) {
27475
- let { to, from, subject, contents, cc, bcc } = inputs;
27689
+ let {
27690
+ to,
27691
+ from,
27692
+ subject,
27693
+ contents,
27694
+ cc,
27695
+ bcc,
27696
+ addInvite,
27697
+ startTime,
27698
+ endTime,
27699
+ summary,
27700
+ location,
27701
+ url
27702
+ } = inputs;
27476
27703
  if (!contents) {
27477
27704
  contents = "<h1>No content</h1>";
27478
27705
  }
27479
27706
  to = to || void 0;
27480
27707
  try {
27481
- let response2 = await sendSmtpEmail(
27708
+ let response2 = await sendSmtpEmail({
27482
27709
  to,
27483
27710
  from,
27484
27711
  subject,
27485
27712
  contents,
27486
27713
  cc,
27487
27714
  bcc,
27488
- true
27489
- );
27715
+ automation: true,
27716
+ invite: addInvite ? {
27717
+ startTime,
27718
+ endTime,
27719
+ summary,
27720
+ location,
27721
+ url
27722
+ } : void 0
27723
+ });
27490
27724
  return {
27491
27725
  success: true,
27492
27726
  response: response2
@@ -30710,8 +30944,15 @@ init_constants6();
30710
30944
  init_integrations2();
30711
30945
  init_utils20();
30712
30946
  init_src2();
30947
+ init_src();
30713
30948
  init_sdk3();
30714
30949
  init_websockets();
30950
+ init_googlesheets();
30951
+ var preSaveAction = {
30952
+ ["GOOGLE_SHEETS" /* GOOGLE_SHEETS */]: async (datasource2) => {
30953
+ await setupCreationAuth(datasource2.config);
30954
+ }
30955
+ };
30715
30956
 
30716
30957
  // src/api/controllers/query/validation.ts
30717
30958
  init_src2();