firebase-tools 11.1.0 → 11.2.0

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.
Files changed (88) hide show
  1. package/lib/accountExporter.js +11 -4
  2. package/lib/accountImporter.js +5 -6
  3. package/lib/appdistribution/client.js +7 -9
  4. package/lib/auth.js +3 -5
  5. package/lib/checkValidTargetFilters.js +28 -18
  6. package/lib/commands/database-profile.js +2 -3
  7. package/lib/commands/database-push.js +2 -3
  8. package/lib/commands/database-remove.js +1 -2
  9. package/lib/commands/database-set.js +1 -2
  10. package/lib/commands/deploy.js +5 -6
  11. package/lib/commands/ext-dev-emulators-exec.js +1 -1
  12. package/lib/commands/ext-dev-emulators-start.js +1 -1
  13. package/lib/commands/ext-dev-list.js +6 -7
  14. package/lib/commands/ext-info.js +12 -13
  15. package/lib/commands/ext.js +2 -3
  16. package/lib/commands/functions-delete.js +1 -7
  17. package/lib/commands/open.js +5 -6
  18. package/lib/commands/serve.js +3 -5
  19. package/lib/commands/use.js +2 -3
  20. package/lib/config.js +4 -3
  21. package/lib/deploy/database/prepare.js +2 -3
  22. package/lib/deploy/extensions/secrets.js +3 -3
  23. package/lib/deploy/functions/build.js +3 -2
  24. package/lib/deploy/functions/ensure.js +1 -11
  25. package/lib/deploy/functions/prepare.js +3 -13
  26. package/lib/deploy/functions/prepareFunctionsUpload.js +2 -3
  27. package/lib/deploy/functions/release/fabricator.js +0 -1
  28. package/lib/deploy/functions/release/index.js +1 -5
  29. package/lib/deploy/functions/runtimes/discovery/index.js +18 -3
  30. package/lib/deploy/functions/runtimes/discovery/v1alpha1.js +3 -2
  31. package/lib/deploy/functions/runtimes/golang/index.js +2 -22
  32. package/lib/deploy/functions/runtimes/node/index.js +3 -7
  33. package/lib/deploy/functions/runtimes/node/parseTriggers.js +1 -1
  34. package/lib/deploy/lifecycleHooks.js +7 -10
  35. package/lib/deploy/storage/prepare.js +1 -1
  36. package/lib/emulator/auth/index.js +1 -1
  37. package/lib/emulator/auth/operations.js +336 -64
  38. package/lib/emulator/auth/server.js +2 -2
  39. package/lib/emulator/auth/state.js +32 -7
  40. package/lib/emulator/commandUtils.js +1 -1
  41. package/lib/emulator/constants.js +1 -1
  42. package/lib/emulator/controller.js +6 -5
  43. package/lib/emulator/databaseEmulator.js +2 -2
  44. package/lib/emulator/download.js +1 -1
  45. package/lib/emulator/events/types.js +2 -3
  46. package/lib/emulator/firestoreEmulator.js +2 -2
  47. package/lib/emulator/functionsEmulator.js +27 -37
  48. package/lib/emulator/functionsEmulatorRuntime.js +7 -7
  49. package/lib/emulator/hostingEmulator.js +1 -1
  50. package/lib/emulator/hub.js +1 -1
  51. package/lib/emulator/loggingEmulator.js +1 -1
  52. package/lib/emulator/pubsubEmulator.js +1 -1
  53. package/lib/emulator/storage/crc.js +4 -4
  54. package/lib/emulator/storage/index.js +1 -1
  55. package/lib/emulator/types.js +1 -1
  56. package/lib/extensions/askUserForConsent.js +1 -2
  57. package/lib/extensions/askUserForParam.js +15 -18
  58. package/lib/extensions/emulator/optionsHelper.js +4 -4
  59. package/lib/extensions/extensionsApi.js +1 -22
  60. package/lib/extensions/extensionsHelper.js +6 -6
  61. package/lib/extensions/listExtensions.js +9 -10
  62. package/lib/extensions/manifest.js +2 -2
  63. package/lib/extensions/resolveSource.js +11 -7
  64. package/lib/extensions/secretsUtils.js +3 -3
  65. package/lib/extensions/types.js +24 -0
  66. package/lib/extensions/updateHelper.js +1 -1
  67. package/lib/extensions/utils.js +1 -2
  68. package/lib/extensions/warnings.js +3 -3
  69. package/lib/firestore/encodeFirestoreValue.js +11 -8
  70. package/lib/fsAsync.js +3 -3
  71. package/lib/functionsConfig.js +17 -14
  72. package/lib/functionsConfigClone.js +10 -12
  73. package/lib/gcp/cloudfunctions.js +2 -15
  74. package/lib/gcp/rules.js +1 -1
  75. package/lib/gcp/runtimeconfig.js +2 -2
  76. package/lib/hosting/proxy.js +1 -1
  77. package/lib/init/features/hosting/github.js +1 -1
  78. package/lib/init/features/hosting/index.js +2 -2
  79. package/lib/localFunction.js +4 -4
  80. package/lib/previews.js +1 -1
  81. package/lib/profileReport.js +10 -10
  82. package/lib/prompt.js +1 -2
  83. package/lib/rc.js +1 -1
  84. package/lib/rulesDeploy.js +2 -2
  85. package/lib/serve/index.js +4 -5
  86. package/lib/utils.js +30 -6
  87. package/npm-shrinkwrap.json +2 -2
  88. package/package.json +10 -9
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getExtension = exports.deleteExtension = exports.unpublishExtension = exports.publishExtensionVersion = exports.undeprecateExtensionVersion = exports.deprecateExtensionVersion = exports.registerPublisherProfile = exports.getPublisherProfile = exports.listExtensionVersions = exports.listExtensions = exports.getExtensionVersion = exports.getSource = exports.createSource = exports.updateInstanceFromRegistry = exports.updateInstance = exports.configureInstance = exports.listInstances = exports.getInstance = exports.deleteInstance = exports.createInstance = exports.ParamType = exports.FUNCTIONS_RESOURCE_TYPE = exports.Visibility = exports.RegistryLaunchStage = void 0;
3
+ exports.getExtension = exports.deleteExtension = exports.unpublishExtension = exports.publishExtensionVersion = exports.undeprecateExtensionVersion = exports.deprecateExtensionVersion = exports.registerPublisherProfile = exports.getPublisherProfile = exports.listExtensionVersions = exports.listExtensions = exports.getExtensionVersion = exports.getSource = exports.createSource = exports.updateInstanceFromRegistry = exports.updateInstance = exports.configureInstance = exports.listInstances = exports.getInstance = exports.deleteInstance = exports.createInstance = void 0;
4
4
  const yaml = require("js-yaml");
5
5
  const clc = require("cli-color");
6
6
  const { marked } = require("marked");
@@ -13,27 +13,6 @@ const refs = require("./refs");
13
13
  const VERSION = "v1beta";
14
14
  const PAGE_SIZE_MAX = 100;
15
15
  const apiClient = new apiv2_1.Client({ urlPrefix: api_1.extensionsOrigin, apiVersion: VERSION });
16
- var RegistryLaunchStage;
17
- (function (RegistryLaunchStage) {
18
- RegistryLaunchStage["EXPERIMENTAL"] = "EXPERIMENTAL";
19
- RegistryLaunchStage["BETA"] = "BETA";
20
- RegistryLaunchStage["GA"] = "GA";
21
- RegistryLaunchStage["DEPRECATED"] = "DEPRECATED";
22
- RegistryLaunchStage["REGISTRY_LAUNCH_STAGE_UNSPECIFIED"] = "REGISTRY_LAUNCH_STAGE_UNSPECIFIED";
23
- })(RegistryLaunchStage = exports.RegistryLaunchStage || (exports.RegistryLaunchStage = {}));
24
- var Visibility;
25
- (function (Visibility) {
26
- Visibility["UNLISTED"] = "unlisted";
27
- Visibility["PUBLIC"] = "public";
28
- })(Visibility = exports.Visibility || (exports.Visibility = {}));
29
- exports.FUNCTIONS_RESOURCE_TYPE = "firebaseextensions.v1beta.function";
30
- var ParamType;
31
- (function (ParamType) {
32
- ParamType["STRING"] = "STRING";
33
- ParamType["SELECT"] = "SELECT";
34
- ParamType["MULTISELECT"] = "MULTISELECT";
35
- ParamType["SECRET"] = "SECRET";
36
- })(ParamType = exports.ParamType || (exports.ParamType = {}));
37
16
  async function createInstanceHelper(projectId, instanceId, config, validateOnly = false) {
38
17
  const createRes = await apiClient.post(`/projects/${projectId}/instances/`, {
39
18
  name: `projects/${projectId}/instances/${instanceId}`,
@@ -1,7 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.canonicalizeRefInput = exports.diagnoseAndFixProject = exports.confirm = exports.getSourceOrigin = exports.isLocalOrURLPath = exports.isLocalPath = exports.isUrlPath = exports.instanceIdExists = exports.promptForRepeatInstance = exports.promptForOfficialExtension = exports.displayReleaseNotes = exports.getPublisherProjectFromName = exports.createSourceFromLocation = exports.publishExtensionVersionFromLocalSource = exports.ensureExtensionsApiEnabled = exports.promptForValidInstanceId = exports.validateSpec = exports.validateCommandLineParams = exports.populateDefaultParams = exports.substituteParams = exports.getFirebaseProjectParams = exports.getDBInstanceFromURL = exports.resourceTypeToNiceName = exports.AUTOPOULATED_PARAM_PLACEHOLDERS = exports.EXTENSIONS_BUCKET_NAME = exports.URL_REGEX = exports.logPrefix = exports.SourceOrigin = exports.SpecParamType = void 0;
4
- const _ = require("lodash");
5
4
  const clc = require("cli-color");
6
5
  const ora = require("ora");
7
6
  const semver = require("semver");
@@ -116,9 +115,10 @@ function substituteParams(original, params) {
116
115
  const substituteRegexMatches = (unsubstituted, regex) => {
117
116
  return unsubstituted.replace(regex, paramVal);
118
117
  };
119
- return _.reduce(regexes, substituteRegexMatches, str);
118
+ return regexes.reduce(substituteRegexMatches, str);
120
119
  };
121
- return JSON.parse(_.reduce(params, applySubstitution, startingString));
120
+ const s = Object.entries(params).reduce((str, [key, val]) => applySubstitution(str, val, key), startingString);
121
+ return JSON.parse(s);
122
122
  }
123
123
  exports.substituteParams = substituteParams;
124
124
  function populateDefaultParams(paramVars, paramSpecs) {
@@ -207,8 +207,8 @@ function validateSpec(spec) {
207
207
  if (!param.label) {
208
208
  errors.push(`Param${param.param ? ` ${param.param}` : ""} is missing required field: label`);
209
209
  }
210
- if (param.type && !_.includes(SpecParamType, param.type)) {
211
- errors.push(`Invalid type ${param.type} for param${param.param ? ` ${param.param}` : ""}. Valid types are ${_.values(SpecParamType).join(", ")}`);
210
+ if (param.type && !Object.values(SpecParamType).includes(param.type)) {
211
+ errors.push(`Invalid type ${param.type} for param${param.param ? ` ${param.param}` : ""}. Valid types are ${Object.values(SpecParamType).join(", ")}`);
212
212
  }
213
213
  if (!param.type || param.type === SpecParamType.STRING) {
214
214
  if (param.options) {
@@ -422,7 +422,7 @@ async function promptForOfficialExtension(message) {
422
422
  type: "list",
423
423
  message,
424
424
  choices: (0, utils_1.convertOfficialExtensionsToList)(officialExts),
425
- pageSize: _.size(officialExts),
425
+ pageSize: Object.keys(officialExts).length,
426
426
  });
427
427
  }
428
428
  exports.promptForOfficialExtension = promptForOfficialExtension;
@@ -1,40 +1,39 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.listExtensions = void 0;
4
- const _ = require("lodash");
5
4
  const clc = require("cli-color");
6
5
  const Table = require("cli-table");
7
6
  const extensionsApi_1 = require("./extensionsApi");
7
+ const logger_1 = require("../logger");
8
+ const utils_1 = require("../utils");
8
9
  const extensionsHelper_1 = require("./extensionsHelper");
9
- const utils = require("../utils");
10
10
  const extensionsUtils = require("./utils");
11
- const logger_1 = require("../logger");
12
11
  async function listExtensions(projectId) {
13
12
  const instances = await (0, extensionsApi_1.listInstances)(projectId);
14
13
  if (instances.length < 1) {
15
- utils.logLabeledBullet(extensionsHelper_1.logPrefix, `there are no extensions installed on project ${clc.bold(projectId)}.`);
14
+ (0, utils_1.logLabeledBullet)(extensionsHelper_1.logPrefix, `there are no extensions installed on project ${clc.bold(projectId)}.`);
16
15
  return [];
17
16
  }
18
17
  const table = new Table({
19
18
  head: ["Extension", "Publisher", "Instance ID", "State", "Version", "Your last update"],
20
19
  style: { head: ["yellow"] },
21
20
  });
22
- const sorted = _.sortBy(instances, "createTime", "asc").reverse();
21
+ const sorted = instances.sort((a, b) => new Date(b.createTime).valueOf() - new Date(a.createTime).valueOf());
23
22
  const formatted = [];
24
23
  sorted.forEach((instance) => {
25
24
  var _a, _b, _c, _d;
26
- let extension = _.get(instance, "config.extensionRef", "");
25
+ let extension = instance.config.extensionRef || "";
27
26
  let publisher;
28
27
  if (extension === "") {
29
- extension = _.get(instance, "config.source.spec.name", "");
28
+ extension = instance.config.source.spec.name || "";
30
29
  publisher = "N/A";
31
30
  }
32
31
  else {
33
32
  publisher = extension.split("/")[0];
34
33
  }
35
- const instanceId = (_a = _.last(instance.name.split("/"))) !== null && _a !== void 0 ? _a : "";
34
+ const instanceId = (_a = (0, utils_1.last)(instance.name.split("/"))) !== null && _a !== void 0 ? _a : "";
36
35
  const state = instance.state +
37
- (_.get(instance, "config.source.state", "ACTIVE") === "DELETED" ? " (UNPUBLISHED)" : "");
36
+ ((instance.config.source.state || "ACTIVE") === "DELETED" ? " (UNPUBLISHED)" : "");
38
37
  const version = (_d = (_c = (_b = instance === null || instance === void 0 ? void 0 : instance.config) === null || _b === void 0 ? void 0 : _b.source) === null || _c === void 0 ? void 0 : _c.spec) === null || _d === void 0 ? void 0 : _d.version;
39
38
  const updateTime = extensionsUtils.formatTimestamp(instance.updateTime);
40
39
  table.push([extension, publisher, instanceId, state, version, updateTime]);
@@ -47,7 +46,7 @@ async function listExtensions(projectId) {
47
46
  updateTime,
48
47
  });
49
48
  });
50
- utils.logLabeledBullet(extensionsHelper_1.logPrefix, `list of extensions installed in ${clc.bold(projectId)}:`);
49
+ (0, utils_1.logLabeledBullet)(extensionsHelper_1.logPrefix, `list of extensions installed in ${clc.bold(projectId)}:`);
51
50
  logger_1.logger.info(table.toString());
52
51
  return formatted;
53
52
  }
@@ -12,7 +12,7 @@ const paramHelper_1 = require("./paramHelper");
12
12
  const error_1 = require("../error");
13
13
  const utils = require("../utils");
14
14
  const extensionsHelper_1 = require("./extensionsHelper");
15
- const extensionsApi_1 = require("./extensionsApi");
15
+ const types_1 = require("./types");
16
16
  exports.ENV_DIRECTORY = "extensions";
17
17
  async function writeToManifest(specs, config, options, allowOverwrite = false) {
18
18
  if (config.has("extensions") &&
@@ -48,7 +48,7 @@ async function writeLocalSecrets(specs, config, force) {
48
48
  continue;
49
49
  }
50
50
  const writeBuffer = {};
51
- const locallyOverridenSecretParams = extensionSpec.params.filter((p) => { var _a; return p.type === extensionsApi_1.ParamType.SECRET && ((_a = spec.params[p.param]) === null || _a === void 0 ? void 0 : _a.local); });
51
+ const locallyOverridenSecretParams = extensionSpec.params.filter((p) => { var _a; return p.type === types_1.ParamType.SECRET && ((_a = spec.params[p.param]) === null || _a === void 0 ? void 0 : _a.local); });
52
52
  for (const paramSpec of locallyOverridenSecretParams) {
53
53
  const key = paramSpec.param;
54
54
  const localValue = spec.params[key].local;
@@ -1,20 +1,24 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.getTrustedPublishers = exports.getExtensionRegistry = void 0;
4
- const _ = require("lodash");
5
4
  const logger_1 = require("../logger");
6
5
  const apiv2_1 = require("../apiv2");
7
6
  const api_1 = require("../api");
8
7
  const EXTENSIONS_REGISTRY_ENDPOINT = "/extensions.json";
9
- async function getExtensionRegistry(onlyFeatured) {
8
+ async function getExtensionRegistry(onlyFeatured = false) {
9
+ var _a;
10
10
  const client = new apiv2_1.Client({ urlPrefix: api_1.firebaseExtensionsRegistryOrigin });
11
11
  const res = await client.get(EXTENSIONS_REGISTRY_ENDPOINT);
12
- const extensions = _.get(res, "body.mods");
12
+ const extensions = res.body.mods || {};
13
13
  if (onlyFeatured) {
14
- const featuredList = _.get(res, "body.featured.discover");
15
- return _.pickBy(extensions, (_entry, extensionName) => {
16
- return _.includes(featuredList, extensionName);
17
- });
14
+ const featuredList = new Set(((_a = res.body.featured) === null || _a === void 0 ? void 0 : _a.discover) || []);
15
+ const filteredExtensions = {};
16
+ for (const [name, extension] of Object.entries(extensions)) {
17
+ if (featuredList.has(name)) {
18
+ filteredExtensions[name] = extension;
19
+ }
20
+ }
21
+ return filteredExtensions;
18
22
  }
19
23
  return extensions;
20
24
  }
@@ -5,7 +5,7 @@ const getProjectNumber_1 = require("../getProjectNumber");
5
5
  const utils = require("../utils");
6
6
  const ensureApiEnabled_1 = require("../ensureApiEnabled");
7
7
  const projectUtils_1 = require("../projectUtils");
8
- const extensionsApi = require("./extensionsApi");
8
+ const types_1 = require("./types");
9
9
  const secretManagerApi = require("../gcp/secretManager");
10
10
  const logger_1 = require("../logger");
11
11
  exports.SECRET_LABEL = "firebase-extensions-managed";
@@ -15,7 +15,7 @@ async function ensureSecretManagerApiEnabled(options) {
15
15
  }
16
16
  exports.ensureSecretManagerApiEnabled = ensureSecretManagerApiEnabled;
17
17
  function usesSecrets(spec) {
18
- return spec.params && !!spec.params.find((p) => p.type === extensionsApi.ParamType.SECRET);
18
+ return spec.params && !!spec.params.find((p) => p.type === types_1.ParamType.SECRET);
19
19
  }
20
20
  exports.usesSecrets = usesSecrets;
21
21
  async function grantFirexServiceAgentSecretAdminRole(secret) {
@@ -38,7 +38,7 @@ async function getManagedSecrets(instance) {
38
38
  exports.getManagedSecrets = getManagedSecrets;
39
39
  function getActiveSecrets(spec, params) {
40
40
  return spec.params
41
- .map((p) => (p.type === extensionsApi.ParamType.SECRET ? params[p.param] : ""))
41
+ .map((p) => (p.type === types_1.ParamType.SECRET ? params[p.param] : ""))
42
42
  .filter((pv) => !!pv);
43
43
  }
44
44
  exports.getActiveSecrets = getActiveSecrets;
@@ -0,0 +1,24 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ParamType = exports.FUNCTIONS_RESOURCE_TYPE = exports.Visibility = exports.RegistryLaunchStage = void 0;
4
+ var RegistryLaunchStage;
5
+ (function (RegistryLaunchStage) {
6
+ RegistryLaunchStage["EXPERIMENTAL"] = "EXPERIMENTAL";
7
+ RegistryLaunchStage["BETA"] = "BETA";
8
+ RegistryLaunchStage["GA"] = "GA";
9
+ RegistryLaunchStage["DEPRECATED"] = "DEPRECATED";
10
+ RegistryLaunchStage["REGISTRY_LAUNCH_STAGE_UNSPECIFIED"] = "REGISTRY_LAUNCH_STAGE_UNSPECIFIED";
11
+ })(RegistryLaunchStage = exports.RegistryLaunchStage || (exports.RegistryLaunchStage = {}));
12
+ var Visibility;
13
+ (function (Visibility) {
14
+ Visibility["UNLISTED"] = "unlisted";
15
+ Visibility["PUBLIC"] = "public";
16
+ })(Visibility = exports.Visibility || (exports.Visibility = {}));
17
+ exports.FUNCTIONS_RESOURCE_TYPE = "firebaseextensions.v1beta.function";
18
+ var ParamType;
19
+ (function (ParamType) {
20
+ ParamType["STRING"] = "STRING";
21
+ ParamType["SELECT"] = "SELECT";
22
+ ParamType["MULTISELECT"] = "MULTISELECT";
23
+ ParamType["SECRET"] = "SECRET";
24
+ })(ParamType = exports.ParamType || (exports.ParamType = {}));
@@ -17,7 +17,7 @@ function invalidSourceErrMsgTemplate(instanceId, source) {
17
17
  - Run \`${clc.bold("firebase ext:update " + instanceId)}\` to update from the published source.\n
18
18
  - Check your directory path or URL, then run \`${clc.bold("firebase ext:update " + instanceId + " <otherSource>")}\` to update from a local directory or URL source.`;
19
19
  }
20
- async function getExistingSourceOrigin(projectId, instanceId, extensionName, existingSource) {
20
+ async function getExistingSourceOrigin(projectId, instanceId) {
21
21
  const instance = await extensionsApi.getInstance(projectId, instanceId);
22
22
  return instance && instance.config.extensionRef
23
23
  ? extensionsHelper_1.SourceOrigin.PUBLISHED_EXTENSION
@@ -1,7 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.formatTimestamp = exports.getRandomString = exports.convertOfficialExtensionsToList = exports.convertExtensionOptionToLabeledList = exports.onceWithJoin = void 0;
4
- const _ = require("lodash");
5
4
  const prompt_1 = require("../prompt");
6
5
  async function onceWithJoin(question) {
7
6
  const response = await (0, prompt_1.promptOnce)(question);
@@ -22,7 +21,7 @@ function convertExtensionOptionToLabeledList(options) {
22
21
  }
23
22
  exports.convertExtensionOptionToLabeledList = convertExtensionOptionToLabeledList;
24
23
  function convertOfficialExtensionsToList(officialExts) {
25
- const l = _.map(officialExts, (entry, key) => {
24
+ const l = Object.entries(officialExts).map(([key, entry]) => {
26
25
  return {
27
26
  checked: false,
28
27
  value: `${entry.publisher}/${key}`,
@@ -3,7 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.paramsFlagDeprecationWarning = exports.displayWarningsForDeploy = exports.displayWarningPrompts = void 0;
4
4
  const { marked } = require("marked");
5
5
  const clc = require("cli-color");
6
- const extensionsApi_1 = require("./extensionsApi");
6
+ const types_1 = require("./types");
7
7
  const displayExtensionInfo_1 = require("./displayExtensionInfo");
8
8
  const extensionsHelper_1 = require("./extensionsHelper");
9
9
  const resolveSource_1 = require("./resolveSource");
@@ -31,7 +31,7 @@ async function displayWarningPrompts(publisherId, launchStage, extensionVersion)
31
31
  githubLink: extensionVersion.spec.sourceUrl,
32
32
  });
33
33
  }
34
- else if (launchStage === extensionsApi_1.RegistryLaunchStage.EXPERIMENTAL) {
34
+ else if (launchStage === types_1.RegistryLaunchStage.EXPERIMENTAL) {
35
35
  displayExperimentalWarning();
36
36
  }
37
37
  else {
@@ -55,7 +55,7 @@ async function displayWarningsForDeploy(instancesToCreate) {
55
55
  await (0, planner_1.getExtension)(i);
56
56
  }
57
57
  const [eapExtensions, nonEapExtensions] = (0, functional_1.partition)(publishedExtensionInstances, (i) => { var _a, _b; return !trustedPublishers.includes((_b = (_a = i.ref) === null || _a === void 0 ? void 0 : _a.publisherId) !== null && _b !== void 0 ? _b : ""); });
58
- const experimental = nonEapExtensions.filter((i) => i.extension.registryLaunchStage === extensionsApi_1.RegistryLaunchStage.EXPERIMENTAL);
58
+ const experimental = nonEapExtensions.filter((i) => i.extension.registryLaunchStage === types_1.RegistryLaunchStage.EXPERIMENTAL);
59
59
  if (experimental.length) {
60
60
  const humanReadableList = experimental.map((i) => `\t${(0, deploymentSummary_1.humanReadable)(i)}`).join("\n");
61
61
  utils.logLabeledBullet(extensionsHelper_1.logPrefix, marked(`The following are instances of ${clc.bold("experimental")} extensions.They may not be production-ready. Their functionality may change in backward-incompatible ways before their official release, or they may be discontinued.\n${humanReadableList}\n`, { gfm: false }));
@@ -9,22 +9,22 @@ function isPlainObject(input) {
9
9
  _.isEqual(Object.getPrototypeOf(input), Object.prototype));
10
10
  }
11
11
  function encodeHelper(val) {
12
- if (_.isString(val)) {
12
+ if (typeof val === "string") {
13
13
  return { stringValue: val };
14
14
  }
15
- if (_.isBoolean(val)) {
15
+ if (val === !!val) {
16
16
  return { booleanValue: val };
17
17
  }
18
- if (_.isInteger(val)) {
18
+ if (Number.isInteger(val)) {
19
19
  return { integerValue: val };
20
20
  }
21
- if (_.isNumber(val)) {
21
+ if (typeof val === "number") {
22
22
  return { doubleValue: val };
23
23
  }
24
- if (_.isDate(val)) {
24
+ if (val instanceof Date && !Number.isNaN(val)) {
25
25
  return { timestampValue: val.toISOString() };
26
26
  }
27
- if (_.isArray(val)) {
27
+ if (Array.isArray(val)) {
28
28
  const encodedElements = [];
29
29
  for (const v of val) {
30
30
  const enc = encodeHelper(v);
@@ -36,7 +36,7 @@ function encodeHelper(val) {
36
36
  arrayValue: { values: encodedElements },
37
37
  };
38
38
  }
39
- if (_.isNull(val)) {
39
+ if (val === null) {
40
40
  return { nullValue: "NULL_VALUE" };
41
41
  }
42
42
  if (val instanceof Buffer || val instanceof Uint8Array) {
@@ -51,6 +51,9 @@ function encodeHelper(val) {
51
51
  "The emulator does not yet support Firestore document reference values or geo points.");
52
52
  }
53
53
  function encodeFirestoreValue(data) {
54
- return _.mapValues(data, encodeHelper);
54
+ return Object.entries(data).reduce((acc, [key, val]) => {
55
+ acc[key] = encodeHelper(val);
56
+ return acc;
57
+ }, {});
55
58
  }
56
59
  exports.encodeFirestoreValue = encodeFirestoreValue;
package/lib/fsAsync.js CHANGED
@@ -8,7 +8,7 @@ const minimatch = require("minimatch");
8
8
  async function readdirRecursiveHelper(options) {
9
9
  const dirContents = (0, fs_extra_1.readdirSync)(options.path);
10
10
  const fullPaths = dirContents.map((n) => (0, path_1.join)(options.path, n));
11
- const filteredPaths = _.reject(fullPaths, options.filter);
11
+ const filteredPaths = fullPaths.filter((p) => !options.filter(p));
12
12
  const filePromises = [];
13
13
  for (const p of filteredPaths) {
14
14
  const fstat = (0, fs_extra_1.statSync)(p);
@@ -22,12 +22,12 @@ async function readdirRecursiveHelper(options) {
22
22
  }
23
23
  const files = await Promise.all(filePromises);
24
24
  let flatFiles = _.flattenDeep(files);
25
- flatFiles = _.reject(flatFiles, (f) => _.isNull(f));
25
+ flatFiles = flatFiles.filter((f) => f !== null);
26
26
  return flatFiles;
27
27
  }
28
28
  async function readdirRecursive(options) {
29
29
  const mmopts = { matchBase: true, dot: true };
30
- const rules = _.map(options.ignore || [], (glob) => {
30
+ const rules = (options.ignore || []).map((glob) => {
31
31
  return (p) => minimatch(p, glob, mmopts);
32
32
  });
33
33
  const filter = (t) => {
@@ -27,7 +27,7 @@ function setVariable(projectId, configId, varPath, val) {
27
27
  return runtimeconfig.variables.set(projectId, configId, varPath, val);
28
28
  }
29
29
  function isReservedNamespace(id) {
30
- return _.some(exports.RESERVED_NAMESPACES, (reserved) => {
30
+ return exports.RESERVED_NAMESPACES.some((reserved) => {
31
31
  return id.config.toLowerCase().startsWith(reserved);
32
32
  });
33
33
  }
@@ -44,7 +44,7 @@ function varNameToIds(varName) {
44
44
  }
45
45
  exports.varNameToIds = varNameToIds;
46
46
  function idsToVarName(projectId, configId, varId) {
47
- return _.join(["projects", projectId, "configs", configId, "variables", varId], "/");
47
+ return ["projects", projectId, "configs", configId, "variables", varId].join("/");
48
48
  }
49
49
  exports.idsToVarName = idsToVarName;
50
50
  function getAppEngineLocation(config) {
@@ -63,7 +63,7 @@ async function getFirebaseConfig(options) {
63
63
  exports.getFirebaseConfig = getFirebaseConfig;
64
64
  async function setVariablesRecursive(projectId, configId, varPath, val) {
65
65
  let parsed = val;
66
- if (_.isString(val)) {
66
+ if (typeof val === "string") {
67
67
  try {
68
68
  parsed = JSON.parse(val);
69
69
  }
@@ -71,8 +71,8 @@ async function setVariablesRecursive(projectId, configId, varPath, val) {
71
71
  }
72
72
  }
73
73
  if (_.isPlainObject(parsed)) {
74
- return Promise.all(_.map(parsed, (item, key) => {
75
- const newVarPath = varPath ? _.join([varPath, key], "/") : key;
74
+ return Promise.all(Object.entries(parsed).map(([key, item]) => {
75
+ const newVarPath = varPath ? [varPath, key].join("/") : key;
76
76
  return setVariablesRecursive(projectId, configId, newVarPath, item);
77
77
  }));
78
78
  }
@@ -87,7 +87,7 @@ async function materializeConfig(configName, output) {
87
87
  _.set(output, key, variable.text);
88
88
  };
89
89
  const traverseVariables = async function (variables) {
90
- return Promise.all(_.map(variables, (variable) => {
90
+ return Promise.all(variables.map((variable) => {
91
91
  return materializeVariable(variable.name);
92
92
  }));
93
93
  };
@@ -99,7 +99,10 @@ exports.materializeConfig = materializeConfig;
99
99
  async function materializeAll(projectId) {
100
100
  const output = {};
101
101
  const configs = await runtimeconfig.configs.list(projectId);
102
- await Promise.all(_.map(configs, (config) => {
102
+ if (!Array.isArray(configs) || !configs.length) {
103
+ return output;
104
+ }
105
+ await Promise.all(configs.map((config) => {
103
106
  if (config.name.match(new RegExp("configs/firebase"))) {
104
107
  return;
105
108
  }
@@ -110,7 +113,7 @@ async function materializeAll(projectId) {
110
113
  exports.materializeAll = materializeAll;
111
114
  function parseSetArgs(args) {
112
115
  const parsed = [];
113
- _.forEach(args, (arg) => {
116
+ for (const arg of args) {
114
117
  const parts = arg.split("=");
115
118
  const key = parts[0];
116
119
  if (parts.length < 2) {
@@ -129,17 +132,17 @@ function parseSetArgs(args) {
129
132
  varId: id.variable,
130
133
  val: val,
131
134
  });
132
- });
135
+ }
133
136
  return parsed;
134
137
  }
135
138
  exports.parseSetArgs = parseSetArgs;
136
139
  function parseUnsetArgs(args) {
137
140
  const parsed = [];
138
141
  let splitArgs = [];
139
- _.forEach(args, (arg) => {
140
- splitArgs = _.union(splitArgs, arg.split(","));
141
- });
142
- _.forEach(splitArgs, (key) => {
142
+ for (const arg of args) {
143
+ splitArgs = Array.from(new Set([...splitArgs, ...arg.split(",")]));
144
+ }
145
+ for (const key of splitArgs) {
143
146
  const id = keyToIds(key);
144
147
  if (isReservedNamespace(id)) {
145
148
  throw new error_1.FirebaseError("Cannot unset reserved namespace " + clc.bold(id.config));
@@ -148,7 +151,7 @@ function parseUnsetArgs(args) {
148
151
  configId: id.config,
149
152
  varId: id.variable,
150
153
  });
151
- });
154
+ }
152
155
  return parsed;
153
156
  }
154
157
  exports.parseUnsetArgs = parseUnsetArgs;
@@ -10,14 +10,12 @@ function matchPrefix(short, long) {
10
10
  if (short.length > long.length) {
11
11
  return false;
12
12
  }
13
- return _.reduce(short, (accum, x, i) => {
14
- return accum && x === long[i];
15
- }, true);
13
+ return short.reduce((accum, x, i) => accum && x === long[i], true);
16
14
  }
17
15
  function applyExcept(json, except) {
18
- _.forEach(except, (key) => {
16
+ for (const key of except) {
19
17
  _.unset(json, key);
20
- });
18
+ }
21
19
  }
22
20
  function cloneVariable(varName, toProject) {
23
21
  return runtimeconfig.variables.get(varName).then((variable) => {
@@ -27,42 +25,42 @@ function cloneVariable(varName, toProject) {
27
25
  }
28
26
  function cloneConfig(configName, toProject) {
29
27
  return runtimeconfig.variables.list(configName).then((variables) => {
30
- return Promise.all(_.map(variables, (variable) => {
28
+ return Promise.all(variables.map((variable) => {
31
29
  return cloneVariable(variable.name, toProject);
32
30
  }));
33
31
  });
34
32
  }
35
33
  async function cloneConfigOrVariable(key, fromProject, toProject) {
36
34
  const parts = key.split(".");
37
- if (_.includes(functionsConfig.RESERVED_NAMESPACES, parts[0])) {
35
+ if (functionsConfig.RESERVED_NAMESPACES.includes(parts[0])) {
38
36
  throw new error_1.FirebaseError("Cannot clone reserved namespace " + clc.bold(parts[0]));
39
37
  }
40
- const configName = _.join(["projects", fromProject, "configs", parts[0]], "/");
38
+ const configName = ["projects", fromProject, "configs", parts[0]].join("/");
41
39
  if (parts.length === 1) {
42
40
  return cloneConfig(configName, toProject);
43
41
  }
44
42
  return runtimeconfig.variables.list(configName).then((variables) => {
45
43
  const promises = [];
46
- _.forEach(variables, (variable) => {
44
+ for (const variable of variables) {
47
45
  const varId = functionsConfig.varNameToIds(variable.name).variable;
48
46
  const variablePrefixFilter = parts.slice(1);
49
47
  if (matchPrefix(variablePrefixFilter, varId.split("/"))) {
50
48
  promises.push(cloneVariable(variable.name, toProject));
51
49
  }
52
- });
50
+ }
53
51
  return Promise.all(promises);
54
52
  });
55
53
  }
56
54
  async function functionsConfigClone(fromProject, toProject, only, except = []) {
57
55
  if (only) {
58
- return Promise.all(_.map(only, (key) => {
56
+ return Promise.all(only.map((key) => {
59
57
  return cloneConfigOrVariable(key, fromProject, toProject);
60
58
  }));
61
59
  }
62
60
  return functionsConfig.materializeAll(fromProject).then((toClone) => {
63
61
  _.unset(toClone, "firebase");
64
62
  applyExcept(toClone, except);
65
- return Promise.all(_.map(toClone, (val, configId) => {
63
+ return Promise.all(Object.entries(toClone).map(([configId, val]) => {
66
64
  return functionsConfig.setVariablesRecursive(toProject, configId, "", val);
67
65
  }));
68
66
  });
@@ -4,7 +4,6 @@ exports.functionFromEndpoint = exports.endpointFromFunction = exports.listAllFun
4
4
  const clc = require("cli-color");
5
5
  const error_1 = require("../error");
6
6
  const logger_1 = require("../logger");
7
- const previews_1 = require("../previews");
8
7
  const backend = require("../deploy/functions/backend");
9
8
  const utils = require("../utils");
10
9
  const proto = require("./proto");
@@ -24,10 +23,6 @@ const BLOCKING_EVENT_TO_LABEL_KEY = {
24
23
  "providers/cloud.auth/eventTypes/user.beforeCreate": "before-create",
25
24
  "providers/cloud.auth/eventTypes/user.beforeSignIn": "before-sign-in",
26
25
  };
27
- function validateFunction(func) {
28
- proto.assertOneOf("Cloud Function", func, "sourceCode", "sourceArchiveUrl", "sourceRepository", "sourceUploadUrl");
29
- proto.assertOneOf("Cloud Function", func, "trigger", "httpsTrigger", "eventTrigger");
30
- }
31
26
  function functionsOpLogReject(funcName, type, err) {
32
27
  var _a, _b;
33
28
  if (((_b = (_a = err === null || err === void 0 ? void 0 : err.context) === null || _a === void 0 ? void 0 : _a.response) === null || _b === void 0 ? void 0 : _b.statusCode) === 429) {
@@ -58,11 +53,7 @@ async function createFunction(cloudFunction) {
58
53
  const apiPath = cloudFunction.name.substring(0, cloudFunction.name.lastIndexOf("/"));
59
54
  const endpoint = `/${apiPath}`;
60
55
  try {
61
- const headers = {};
62
- if (previews_1.previews.artifactregistry) {
63
- headers["X-Firebase-Artifact-Registry"] = "optin";
64
- }
65
- const res = await client.post(endpoint, cloudFunction, { headers });
56
+ const res = await client.post(endpoint, cloudFunction);
66
57
  return {
67
58
  name: res.body.name,
68
59
  type: "create",
@@ -147,12 +138,7 @@ async function updateFunction(cloudFunction) {
147
138
  const endpoint = `/${cloudFunction.name}`;
148
139
  const fieldMasks = proto.fieldMasks(cloudFunction, "labels", "environmentVariables", "secretEnvironmentVariables");
149
140
  try {
150
- const headers = {};
151
- if (previews_1.previews.artifactregistry) {
152
- headers["X-Firebase-Artifact-Registry"] = "optin";
153
- }
154
141
  const res = await client.patch(endpoint, cloudFunction, {
155
- headers,
156
142
  queryParams: {
157
143
  updateMask: fieldMasks.join(","),
158
144
  },
@@ -293,6 +279,7 @@ function functionFromEndpoint(endpoint, sourceUploadUrl) {
293
279
  sourceUploadUrl: sourceUploadUrl,
294
280
  entryPoint: endpoint.entryPoint,
295
281
  runtime: endpoint.runtime,
282
+ dockerRegistry: "ARTIFACT_REGISTRY",
296
283
  };
297
284
  proto.copyIfPresent(gcfFunction, endpoint, "labels");
298
285
  if (backend.isEventTriggered(endpoint)) {
package/lib/gcp/rules.js CHANGED
@@ -20,7 +20,7 @@ function _handleErrorResponse(response) {
20
20
  async function getLatestRulesetName(projectId, service) {
21
21
  const releases = await listAllReleases(projectId);
22
22
  const prefix = `projects/${projectId}/releases/${service}`;
23
- const release = _.find(releases, (r) => r.name.startsWith(prefix));
23
+ const release = releases.find((r) => r.name.startsWith(prefix));
24
24
  if (!release) {
25
25
  return null;
26
26
  }
@@ -15,7 +15,7 @@ function listConfigs(projectId) {
15
15
  .then((resp) => resp.body.configs);
16
16
  }
17
17
  function createConfig(projectId, configId) {
18
- const path = _.join(["projects", projectId, "configs"], "/");
18
+ const path = ["projects", projectId, "configs"].join("/");
19
19
  return apiClient
20
20
  .post(`/projects/${projectId}/configs`, {
21
21
  name: path + "/" + configId,
@@ -88,7 +88,7 @@ function updateVariable(projectId, configId, varId, value) {
88
88
  });
89
89
  }
90
90
  function setVariable(projectId, configId, varId, value) {
91
- const path = _.join(["projects", projectId, "configs", configId, "variables", varId], "/");
91
+ const path = ["projects", projectId, "configs", configId, "variables", varId].join("/");
92
92
  return getVariable(path)
93
93
  .then(() => {
94
94
  return updateVariable(projectId, configId, varId, value);
@@ -133,7 +133,7 @@ function proxyRequestHandler(url, rewriteIdentifier) {
133
133
  }
134
134
  exports.proxyRequestHandler = proxyRequestHandler;
135
135
  function errorRequestHandler(error) {
136
- return (req, res, next) => {
136
+ return (req, res) => {
137
137
  res.statusCode = 500;
138
138
  const out = `A problem occurred while trying to handle a proxied rewrite: ${error}`;
139
139
  logger_1.logger.error(out);
@@ -27,7 +27,7 @@ const YML_MERGE_FILENAME = "firebase-hosting-merge.yml";
27
27
  const CHECKOUT_GITHUB_ACTION_NAME = "actions/checkout@v2";
28
28
  const HOSTING_GITHUB_ACTION_NAME = "FirebaseExtended/action-hosting-deploy@v0";
29
29
  const githubApiClient = new apiv2_1.Client({ urlPrefix: api_1.githubApiOrigin, auth: false });
30
- async function initGitHub(setup, config, options) {
30
+ async function initGitHub(setup) {
31
31
  if (!setup.projectId) {
32
32
  return (0, utils_1.reject)("Could not determine Project ID, can't set up GitHub workflow.", { exit: 1 });
33
33
  }