firebase-tools 13.0.0 → 13.0.2

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 (37) hide show
  1. package/lib/api.js +2 -2
  2. package/lib/commands/{frameworks-backends-create.js → apphosting-backends-create.js} +6 -3
  3. package/lib/commands/{frameworks-backends-delete.js → apphosting-backends-delete.js} +9 -7
  4. package/lib/commands/{frameworks-backends-get.js → apphosting-backends-get.js} +16 -27
  5. package/lib/commands/{frameworks-backends-list.js → apphosting-backends-list.js} +9 -19
  6. package/lib/commands/apphosting-builds-create.js +31 -0
  7. package/lib/commands/apphosting-builds-get.js +18 -0
  8. package/lib/commands/apphosting-rollouts-create.js +26 -0
  9. package/lib/commands/apphosting-rollouts-list.js +18 -0
  10. package/lib/commands/index.js +12 -6
  11. package/lib/deploy/functions/services/firestore.js +11 -1
  12. package/lib/frameworks/angular/index.js +5 -3
  13. package/lib/frameworks/angular/utils.js +19 -2
  14. package/lib/frameworks/astro/index.js +5 -2
  15. package/lib/frameworks/astro/utils.js +3 -2
  16. package/lib/frameworks/constants.js +31 -7
  17. package/lib/frameworks/index.js +12 -7
  18. package/lib/frameworks/next/index.js +24 -8
  19. package/lib/frameworks/next/utils.js +1 -1
  20. package/lib/frameworks/nuxt/index.js +15 -5
  21. package/lib/frameworks/nuxt2/index.js +5 -4
  22. package/lib/frameworks/sveltekit/index.js +2 -1
  23. package/lib/frameworks/utils.js +13 -9
  24. package/lib/frameworks/vite/index.js +19 -5
  25. package/lib/gcp/apphosting.js +89 -0
  26. package/lib/gcp/cloudbuild.js +5 -1
  27. package/lib/hosting/api.js +19 -1
  28. package/lib/init/features/{frameworks → apphosting}/constants.js +1 -2
  29. package/lib/init/features/apphosting/index.js +135 -0
  30. package/lib/init/features/{frameworks → apphosting}/repo.js +53 -28
  31. package/lib/init/features/hosting/index.js +1 -1
  32. package/lib/init/features/index.js +3 -3
  33. package/lib/init/index.js +0 -4
  34. package/lib/utils.js +26 -4
  35. package/package.json +1 -1
  36. package/lib/gcp/frameworks.js +0 -40
  37. package/lib/init/features/frameworks/index.js +0 -116
package/lib/api.js CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.githubApiOrigin = exports.githubOrigin = exports.frameworksOrigin = exports.serviceUsageOrigin = exports.cloudRunApiOrigin = exports.hostingApiOrigin = exports.firebaseStorageOrigin = exports.storageOrigin = exports.runtimeconfigOrigin = exports.rulesOrigin = exports.resourceManagerOrigin = exports.remoteConfigApiOrigin = exports.rtdbMetadataOrigin = exports.rtdbManagementOrigin = exports.realtimeOrigin = exports.extensionsTOSOrigin = exports.extensionsPublisherOrigin = exports.extensionsOrigin = exports.iamOrigin = exports.identityOrigin = exports.hostingOrigin = exports.googleOrigin = exports.pubsubOrigin = exports.cloudTasksOrigin = exports.cloudschedulerOrigin = exports.cloudbuildOrigin = exports.functionsDefaultRegion = exports.runOrigin = exports.functionsV2Origin = exports.functionsOrigin = exports.firestoreOrigin = exports.firestoreOriginOrEmulator = exports.firedataOrigin = exports.firebaseExtensionsRegistryOrigin = exports.firebaseApiOrigin = exports.eventarcOrigin = exports.dynamicLinksKey = exports.dynamicLinksOrigin = exports.deployOrigin = exports.consoleOrigin = exports.authOrigin = exports.appDistributionOrigin = exports.artifactRegistryDomain = exports.containerRegistryDomain = exports.cloudMonitoringOrigin = exports.cloudloggingOrigin = exports.cloudbillingOrigin = exports.clientSecret = exports.clientId = exports.authProxyOrigin = void 0;
3
+ exports.githubApiOrigin = exports.githubOrigin = exports.apphostingOrigin = exports.serviceUsageOrigin = exports.cloudRunApiOrigin = exports.hostingApiOrigin = exports.firebaseStorageOrigin = exports.storageOrigin = exports.runtimeconfigOrigin = exports.rulesOrigin = exports.resourceManagerOrigin = exports.remoteConfigApiOrigin = exports.rtdbMetadataOrigin = exports.rtdbManagementOrigin = exports.realtimeOrigin = exports.extensionsTOSOrigin = exports.extensionsPublisherOrigin = exports.extensionsOrigin = exports.iamOrigin = exports.identityOrigin = exports.hostingOrigin = exports.googleOrigin = exports.pubsubOrigin = exports.cloudTasksOrigin = exports.cloudschedulerOrigin = exports.cloudbuildOrigin = exports.functionsDefaultRegion = exports.runOrigin = exports.functionsV2Origin = exports.functionsOrigin = exports.firestoreOrigin = exports.firestoreOriginOrEmulator = exports.firedataOrigin = exports.firebaseExtensionsRegistryOrigin = exports.firebaseApiOrigin = exports.eventarcOrigin = exports.dynamicLinksKey = exports.dynamicLinksOrigin = exports.deployOrigin = exports.consoleOrigin = exports.authOrigin = exports.appDistributionOrigin = exports.artifactRegistryDomain = exports.containerRegistryDomain = exports.cloudMonitoringOrigin = exports.cloudloggingOrigin = exports.cloudbillingOrigin = exports.clientSecret = exports.clientId = exports.authProxyOrigin = void 0;
4
4
  exports.setScopes = exports.getScopes = exports.githubClientSecret = exports.githubClientId = exports.secretManagerOrigin = void 0;
5
5
  const constants_1 = require("./emulator/constants");
6
6
  const logger_1 = require("./logger");
@@ -59,7 +59,7 @@ exports.firebaseStorageOrigin = utils.envOverride("FIREBASE_FIREBASESTORAGE_URL"
59
59
  exports.hostingApiOrigin = utils.envOverride("FIREBASE_HOSTING_API_URL", "https://firebasehosting.googleapis.com");
60
60
  exports.cloudRunApiOrigin = utils.envOverride("CLOUD_RUN_API_URL", "https://run.googleapis.com");
61
61
  exports.serviceUsageOrigin = utils.envOverride("FIREBASE_SERVICE_USAGE_URL", "https://serviceusage.googleapis.com");
62
- exports.frameworksOrigin = utils.envOverride("FRAMEWORKS_URL", "https://placeholder.googleapis.com");
62
+ exports.apphostingOrigin = utils.envOverride("APPHOSTING_URL", "https://firebaseapphosting.googleapis.com");
63
63
  exports.githubOrigin = utils.envOverride("GITHUB_URL", "https://github.com");
64
64
  exports.githubApiOrigin = utils.envOverride("GITHUB_API_URL", "https://api.github.com");
65
65
  exports.secretManagerOrigin = utils.envOverride("CLOUD_SECRET_MANAGER_URL", "https://secretmanager.googleapis.com");
@@ -4,11 +4,14 @@ exports.command = void 0;
4
4
  const command_1 = require("../command");
5
5
  const projectUtils_1 = require("../projectUtils");
6
6
  const requireInteractive_1 = require("../requireInteractive");
7
- const frameworks_1 = require("../init/features/frameworks");
8
- exports.command = new command_1.Command("backends:create")
7
+ const apphosting_1 = require("../init/features/apphosting");
8
+ const apphosting_2 = require("../gcp/apphosting");
9
+ exports.command = new command_1.Command("apphosting:backends:create")
9
10
  .description("Create a backend in a Firebase project")
11
+ .option("-l, --location <location>", "Specify the region of the backend", "")
12
+ .before(apphosting_2.ensureApiEnabled)
10
13
  .before(requireInteractive_1.default)
11
14
  .action(async (options) => {
12
15
  const projectId = (0, projectUtils_1.needProjectId)(options);
13
- await (0, frameworks_1.doSetup)(options, projectId);
16
+ await (0, apphosting_1.doSetup)(options, projectId);
14
17
  });
@@ -4,11 +4,11 @@ exports.command = void 0;
4
4
  const command_1 = require("../command");
5
5
  const projectUtils_1 = require("../projectUtils");
6
6
  const error_1 = require("../error");
7
- const gcp = require("../gcp/frameworks");
8
7
  const prompt_1 = require("../prompt");
9
- const utils = require("../utils");
10
8
  const logger_1 = require("../logger");
11
- const constants_1 = require("../init/features/frameworks/constants");
9
+ const constants_1 = require("../init/features/apphosting/constants");
10
+ const utils = require("../utils");
11
+ const apphosting = require("../gcp/apphosting");
12
12
  const Table = require("cli-table");
13
13
  const COLUMN_LENGTH = 20;
14
14
  const TABLE_HEAD = [
@@ -19,11 +19,12 @@ const TABLE_HEAD = [
19
19
  "Created Date",
20
20
  "Updated Date",
21
21
  ];
22
- exports.command = new command_1.Command("backends:delete")
22
+ exports.command = new command_1.Command("apphosting:backends:delete")
23
23
  .description("Delete a backend from a Firebase project")
24
24
  .option("-l, --location <location>", "App Backend location", "")
25
25
  .option("-s, --backend <backend>", "Backend Id", "")
26
26
  .withForce()
27
+ .before(apphosting.ensureApiEnabled)
27
28
  .action(async (options) => {
28
29
  const projectId = (0, projectUtils_1.needProjectId)(options);
29
30
  let location = options.location;
@@ -32,12 +33,13 @@ exports.command = new command_1.Command("backends:delete")
32
33
  throw new error_1.FirebaseError("Backend id can't be empty.");
33
34
  }
34
35
  if (!location) {
36
+ const allowedLocations = (await apphosting.listLocations(projectId)).map((loc) => loc.locationId);
35
37
  location = await (0, prompt_1.promptOnce)({
36
38
  name: "region",
37
39
  type: "list",
38
40
  default: constants_1.DEFAULT_REGION,
39
41
  message: "Please select the region of the backend you'd like to delete:",
40
- choices: constants_1.ALLOWED_REGIONS,
42
+ choices: allowedLocations,
41
43
  });
42
44
  }
43
45
  const table = new Table({
@@ -47,7 +49,7 @@ exports.command = new command_1.Command("backends:delete")
47
49
  table.colWidths = COLUMN_LENGTH;
48
50
  let backend;
49
51
  try {
50
- backend = await gcp.getBackend(projectId, location, backendId);
52
+ backend = await apphosting.getBackend(projectId, location, backendId);
51
53
  populateTable(backend, table);
52
54
  }
53
55
  catch (err) {
@@ -67,7 +69,7 @@ exports.command = new command_1.Command("backends:delete")
67
69
  throw new error_1.FirebaseError("Deletion Aborted");
68
70
  }
69
71
  try {
70
- await gcp.deleteBackend(projectId, location, backendId);
72
+ await apphosting.deleteBackend(projectId, location, backendId);
71
73
  utils.logSuccess(`Successfully deleted the backend: ${backendId}`);
72
74
  }
73
75
  catch (err) {
@@ -3,30 +3,20 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.command = void 0;
4
4
  const command_1 = require("../command");
5
5
  const projectUtils_1 = require("../projectUtils");
6
- const gcp = require("../gcp/frameworks");
7
6
  const error_1 = require("../error");
8
7
  const logger_1 = require("../logger");
8
+ const utils_1 = require("../utils");
9
+ const apphosting = require("../gcp/apphosting");
9
10
  const Table = require("cli-table");
10
11
  const COLUMN_LENGTH = 20;
11
- const TABLE_HEAD = [
12
- "Backend Id",
13
- "Repository Name",
14
- "Location",
15
- "URL",
16
- "Created Date",
17
- "Updated Date",
18
- ];
19
- exports.command = new command_1.Command("backends:get")
12
+ const TABLE_HEAD = ["Backend Id", "Repository", "Location", "URL", "Created Date", "Updated Date"];
13
+ exports.command = new command_1.Command("apphosting:backends:get <backendId>")
20
14
  .description("Get backend details of a Firebase project")
21
15
  .option("-l, --location <location>", "App Backend location", "-")
22
- .option("-b, --backend <backend>", "Backend Id", "")
23
- .action(async (options) => {
16
+ .before(apphosting.ensureApiEnabled)
17
+ .action(async (backendId, options) => {
24
18
  const projectId = (0, projectUtils_1.needProjectId)(options);
25
19
  const location = options.location;
26
- const backendId = options.backend;
27
- if (!backendId) {
28
- throw new error_1.FirebaseError("Backend id can't be empty.");
29
- }
30
20
  let backendsList = [];
31
21
  const table = new Table({
32
22
  head: TABLE_HEAD,
@@ -35,27 +25,26 @@ exports.command = new command_1.Command("backends:get")
35
25
  table.colWidths = COLUMN_LENGTH;
36
26
  try {
37
27
  if (location !== "-") {
38
- const backendInRegion = await gcp.getBackend(projectId, location, backendId);
28
+ const backendInRegion = await apphosting.getBackend(projectId, location, backendId);
39
29
  backendsList.push(backendInRegion);
40
30
  populateTable(backendInRegion, table);
41
31
  }
42
32
  else {
43
- const allBackend = await gcp.listBackends(projectId, location);
44
- backendsList = allBackend.backends.filter((bkd) => bkd.name.split("/").pop() === backendId);
33
+ const resp = await apphosting.listBackends(projectId, "-");
34
+ const allBackends = resp.backends || [];
35
+ backendsList = allBackends.filter((bkd) => bkd.name.split("/").pop() === backendId);
45
36
  backendsList.forEach((bkd) => populateTable(bkd, table));
46
37
  }
47
- if (backendsList.length !== 0) {
48
- logger_1.logger.info(table.toString());
49
- }
50
- else {
51
- logger_1.logger.info();
52
- logger_1.logger.info(`There are no backends with id: ${backendId}`);
53
- }
54
38
  }
55
39
  catch (err) {
56
40
  throw new error_1.FirebaseError(`Failed to get backend: ${backendId}. Please check the parameters you have provided.`, { original: err });
57
41
  }
58
- return backendsList;
42
+ if (backendsList.length === 0) {
43
+ (0, utils_1.logWarning)(`Found no backend with id: ${backendId}`);
44
+ return;
45
+ }
46
+ logger_1.logger.info(table.toString());
47
+ return backendsList[0];
59
48
  });
60
49
  function populateTable(backend, table) {
61
50
  var _a;
@@ -3,23 +3,16 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.command = void 0;
4
4
  const command_1 = require("../command");
5
5
  const projectUtils_1 = require("../projectUtils");
6
- const gcp = require("../gcp/frameworks");
7
6
  const error_1 = require("../error");
8
7
  const logger_1 = require("../logger");
9
- const colorette_1 = require("colorette");
8
+ const apphosting = require("../gcp/apphosting");
10
9
  const Table = require("cli-table");
11
10
  const COLUMN_LENGTH = 20;
12
- const TABLE_HEAD = [
13
- "Backend Id",
14
- "Repository Name",
15
- "Location",
16
- "URL",
17
- "Created Date",
18
- "Updated Date",
19
- ];
20
- exports.command = new command_1.Command("backends:list")
11
+ const TABLE_HEAD = ["Backend Id", "Repository", "Location", "URL", "Created Date", "Updated Date"];
12
+ exports.command = new command_1.Command("apphosting:backends:list")
21
13
  .description("List backends of a Firebase project.")
22
14
  .option("-l, --location <location>", "App Backend location", "-")
15
+ .before(apphosting.ensureApiEnabled)
23
16
  .action(async (options) => {
24
17
  const projectId = (0, projectUtils_1.needProjectId)(options);
25
18
  const location = options.location;
@@ -30,12 +23,9 @@ exports.command = new command_1.Command("backends:list")
30
23
  table.colWidths = COLUMN_LENGTH;
31
24
  const backendsList = [];
32
25
  try {
33
- const backendsPerRegion = await gcp.listBackends(projectId, location);
34
- backendsList.push(backendsPerRegion);
35
- populateTable(backendsPerRegion, location, table);
36
- logger_1.logger.info();
37
- logger_1.logger.info(`Backends for project ${(0, colorette_1.bold)(projectId)}`);
38
- logger_1.logger.info();
26
+ const backendsPerRegion = await apphosting.listBackends(projectId, location);
27
+ backendsList.push(...(backendsPerRegion.backends || []));
28
+ populateTable(backendsList, table);
39
29
  logger_1.logger.info(table.toString());
40
30
  }
41
31
  catch (err) {
@@ -43,9 +33,9 @@ exports.command = new command_1.Command("backends:list")
43
33
  }
44
34
  return backendsList;
45
35
  });
46
- function populateTable(backendsLists, location, table) {
36
+ function populateTable(backends, table) {
47
37
  var _a;
48
- for (const backend of backendsLists.backends) {
38
+ for (const backend of backends) {
49
39
  const [location, , backendId] = backend.name.split("/").slice(3, 6);
50
40
  const entry = [
51
41
  backendId,
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.command = void 0;
4
+ const apphosting = require("../gcp/apphosting");
5
+ const logger_1 = require("../logger");
6
+ const command_1 = require("../command");
7
+ const utils_1 = require("../utils");
8
+ const projectUtils_1 = require("../projectUtils");
9
+ exports.command = new command_1.Command("apphosting:builds:create <backendId>")
10
+ .description("Create a build for an App Hosting backend")
11
+ .option("-l, --location <location>", "Specify the region of the backend", "us-central1")
12
+ .option("-i, --id <buildId>", "Id of the build. If not present, autogenerate a random id", "")
13
+ .option("-b, --branch <branch>", "Repository branch to deploy. Defaults to 'main'", "main")
14
+ .before(apphosting.ensureApiEnabled)
15
+ .action(async (backendId, options) => {
16
+ const projectId = (0, projectUtils_1.needProjectId)(options);
17
+ const location = options.location;
18
+ const buildId = options.buildId || (0, utils_1.generateId)();
19
+ const branch = options.branch;
20
+ const op = await apphosting.createBuild(projectId, location, backendId, buildId, {
21
+ source: {
22
+ codebase: {
23
+ branch: "main",
24
+ },
25
+ },
26
+ });
27
+ logger_1.logger.info(`Started a build for backend ${backendId} on branch ${branch}.`);
28
+ logger_1.logger.info("Check status by running:");
29
+ logger_1.logger.info(`\tfirebase apphosting:builds:get ${backendId} ${buildId} --location ${location}`);
30
+ return op;
31
+ });
@@ -0,0 +1,18 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.command = void 0;
4
+ const apphosting = require("../gcp/apphosting");
5
+ const logger_1 = require("../logger");
6
+ const command_1 = require("../command");
7
+ const projectUtils_1 = require("../projectUtils");
8
+ exports.command = new command_1.Command("apphosting:builds:get <backendId> <buildId>")
9
+ .description("Create a build for an App Hosting backend")
10
+ .option("-l, --location <location>", "Specify the region of the backend", "us-central1")
11
+ .before(apphosting.ensureApiEnabled)
12
+ .action(async (backendId, buildId, options) => {
13
+ const projectId = (0, projectUtils_1.needProjectId)(options);
14
+ const location = options.location;
15
+ const build = await apphosting.getBuild(projectId, location, backendId, buildId);
16
+ logger_1.logger.info(JSON.stringify(build, null, 2));
17
+ return build;
18
+ });
@@ -0,0 +1,26 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.command = void 0;
4
+ const apphosting = require("../gcp/apphosting");
5
+ const logger_1 = require("../logger");
6
+ const command_1 = require("../command");
7
+ const projectUtils_1 = require("../projectUtils");
8
+ const utils_1 = require("../utils");
9
+ exports.command = new command_1.Command("apphosting:rollouts:create <backendId> <buildId>")
10
+ .description("Create a build for an App Hosting backend")
11
+ .option("-l, --location <location>", "Specify the region of the backend", "us-central1")
12
+ .option("-i, --id <rolloutId>", "Id of the rollout. If not present, autogenerate a random id", "")
13
+ .before(apphosting.ensureApiEnabled)
14
+ .action(async (backendId, buildId, options) => {
15
+ const projectId = (0, projectUtils_1.needProjectId)(options);
16
+ const location = options.location;
17
+ const rolloutId = options.buildId || (0, utils_1.generateId)();
18
+ const build = `projects/${projectId}/backends/${backendId}/builds/${buildId}`;
19
+ const op = await apphosting.createRollout(projectId, location, backendId, rolloutId, {
20
+ build,
21
+ });
22
+ logger_1.logger.info(`Started a rollout for backend ${backendId} with build ${buildId}.`);
23
+ logger_1.logger.info("Check status by running:");
24
+ logger_1.logger.info(`\tfirebase apphosting:rollouts:list --location ${location}`);
25
+ return op;
26
+ });
@@ -0,0 +1,18 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.command = void 0;
4
+ const apphosting = require("../gcp/apphosting");
5
+ const logger_1 = require("../logger");
6
+ const command_1 = require("../command");
7
+ const projectUtils_1 = require("../projectUtils");
8
+ exports.command = new command_1.Command("apphosting:rollouts:list <backendId>")
9
+ .description("List rollouts of an App Hosting backend")
10
+ .option("-l, --location <location>", "Rgion of the rollouts. Defaults to listing rollouts from all regions", "-")
11
+ .before(apphosting.ensureApiEnabled)
12
+ .action(async (backendId, options) => {
13
+ const projectId = (0, projectUtils_1.needProjectId)(options);
14
+ const location = options.location;
15
+ const rollouts = await apphosting.listRollouts(projectId, location, backendId);
16
+ logger_1.logger.info(JSON.stringify(rollouts, null, 2));
17
+ return rollouts;
18
+ });
@@ -145,12 +145,18 @@ function load(client) {
145
145
  client.internaltesting.functions.discover = loadCommand("internaltesting-functions-discover");
146
146
  }
147
147
  if (experiments.isEnabled("internalframeworks")) {
148
- client.frameworks = {};
149
- client.frameworks.backends = {};
150
- client.frameworks.backends.list = loadCommand("frameworks-backends-list");
151
- client.frameworks.backends.create = loadCommand("frameworks-backends-create");
152
- client.frameworks.backends.get = loadCommand("frameworks-backends-get");
153
- client.frameworks.backends.delete = loadCommand("frameworks-backends-delete");
148
+ client.apphosting = {};
149
+ client.apphosting.backends = {};
150
+ client.apphosting.backends.list = loadCommand("apphosting-backends-list");
151
+ client.apphosting.backends.create = loadCommand("apphosting-backends-create");
152
+ client.apphosting.backends.get = loadCommand("apphosting-backends-get");
153
+ client.apphosting.backends.delete = loadCommand("apphosting-backends-delete");
154
+ client.apphosting.builds = {};
155
+ client.apphosting.builds.get = loadCommand("apphosting-builds-get");
156
+ client.apphosting.builds.create = loadCommand("apphosting-builds-create");
157
+ client.apphosting.rollouts = {};
158
+ client.apphosting.rollouts.create = loadCommand("apphosting-rollouts-create");
159
+ client.apphosting.rollouts.list = loadCommand("apphosting-rollouts-list");
154
160
  }
155
161
  client.login = loadCommand("login");
156
162
  client.login.add = loadCommand("login-add");
@@ -3,9 +3,19 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ensureFirestoreTriggerRegion = void 0;
4
4
  const firestore = require("../../../gcp/firestore");
5
5
  const error_1 = require("../../../error");
6
+ const dbCache = new Map();
7
+ async function getDatabase(project, databaseId) {
8
+ const key = `${project}/${databaseId}`;
9
+ if (dbCache.has(key)) {
10
+ return dbCache.get(key);
11
+ }
12
+ const db = await firestore.getDatabase(project, databaseId);
13
+ dbCache.set(key, db);
14
+ return db;
15
+ }
6
16
  async function ensureFirestoreTriggerRegion(endpoint) {
7
17
  var _a;
8
- const db = await firestore.getDatabase(endpoint.project, ((_a = endpoint.eventTrigger.eventFilters) === null || _a === void 0 ? void 0 : _a.database) || "(default)");
18
+ const db = await getDatabase(endpoint.project, ((_a = endpoint.eventTrigger.eventFilters) === null || _a === void 0 ? void 0 : _a.database) || "(default)");
9
19
  const dbRegion = db.locationId;
10
20
  if (!endpoint.eventTrigger.region) {
11
21
  endpoint.eventTrigger.region = dbRegion;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.ɵcodegenFunctionsDirectory = exports.shouldUseDevModeHandle = exports.getValidBuildTargets = exports.ɵcodegenPublicDirectory = exports.getDevModeHandle = exports.build = exports.init = exports.discover = exports.docsUrl = exports.type = exports.support = exports.name = void 0;
3
+ exports.ɵcodegenFunctionsDirectory = exports.shouldUseDevModeHandle = exports.getValidBuildTargets = exports.ɵcodegenPublicDirectory = exports.getDevModeHandle = exports.build = exports.init = exports.discover = exports.supportedRange = exports.docsUrl = exports.type = exports.support = exports.name = void 0;
4
4
  const path_1 = require("path");
5
5
  const child_process_1 = require("child_process");
6
6
  const cross_spawn_1 = require("cross-spawn");
@@ -15,16 +15,18 @@ exports.support = "preview";
15
15
  exports.type = 3;
16
16
  exports.docsUrl = "https://firebase.google.com/docs/hosting/frameworks/angular";
17
17
  const DEFAULT_BUILD_SCRIPT = ["ng build"];
18
+ exports.supportedRange = "14 - 17";
18
19
  async function discover(dir) {
19
20
  if (!(await (0, fs_extra_1.pathExists)((0, path_1.join)(dir, "package.json"))))
20
21
  return;
21
22
  if (!(await (0, fs_extra_1.pathExists)((0, path_1.join)(dir, "angular.json"))))
22
23
  return;
23
- return { mayWantBackend: true, publicDirectory: (0, path_1.join)(dir, "src", "assets") };
24
+ const version = (0, utils_2.getAngularVersion)(dir);
25
+ return { mayWantBackend: true, publicDirectory: (0, path_1.join)(dir, "src", "assets"), version };
24
26
  }
25
27
  exports.discover = discover;
26
28
  function init(setup, config) {
27
- (0, child_process_1.execSync)(`npx --yes -p @angular/cli@latest ng new ${setup.projectId} --directory ${setup.hosting.source} --skip-git`, {
29
+ (0, child_process_1.execSync)(`npx --yes -p @angular/cli@"${exports.supportedRange}" ng new ${setup.projectId} --directory ${setup.hosting.source} --skip-git`, {
28
30
  stdio: "inherit",
29
31
  cwd: config.projectDir,
30
32
  });
@@ -1,11 +1,12 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getBuildConfig = exports.getServerConfig = exports.getBrowserConfig = exports.getContext = exports.getAllTargets = void 0;
3
+ exports.getAngularVersion = exports.getBuildConfig = exports.getServerConfig = exports.getBrowserConfig = exports.getContext = exports.getAllTargets = void 0;
4
4
  const utils_1 = require("../utils");
5
5
  const error_1 = require("../../error");
6
6
  const path_1 = require("path");
7
7
  const assert_1 = require("assert");
8
8
  const utils_2 = require("../../utils");
9
+ const semver_1 = require("semver");
9
10
  async function localesForTarget(dir, architectHost, target, workspaceProject) {
10
11
  var _a;
11
12
  const { targetStringFromTarget } = (0, utils_1.relativeRequire)(dir, "@angular-devkit/architect");
@@ -182,7 +183,9 @@ async function getContext(dir, targetOrConfiguration) {
182
183
  }
183
184
  }
184
185
  if (deployTarget) {
185
- const options = await architectHost.getOptionsForTarget(deployTarget);
186
+ const options = await architectHost
187
+ .getOptionsForTarget(deployTarget)
188
+ .catch(() => { var _a; return (_a = workspaceProject.targets.get(deployTarget.target)) === null || _a === void 0 ? void 0 : _a.options; });
186
189
  if (!options)
187
190
  throw new error_1.FirebaseError("Unable to get options for ng-deploy.");
188
191
  if (options.buildTarget) {
@@ -201,6 +204,10 @@ async function getContext(dir, targetOrConfiguration) {
201
204
  (0, utils_2.assertIsString)(options.serverTarget);
202
205
  serverTarget = targetFromTargetString(options.serverTarget);
203
206
  }
207
+ if (options.serveTarget) {
208
+ (0, utils_2.assertIsString)(options.serveTarget);
209
+ serveTarget = targetFromTargetString(options.serveTarget);
210
+ }
204
211
  if (options.serveOptimizedImages) {
205
212
  serveOptimizedImages = true;
206
213
  }
@@ -441,3 +448,13 @@ async function getBuildConfig(sourceDir, configuration) {
441
448
  };
442
449
  }
443
450
  exports.getBuildConfig = getBuildConfig;
451
+ function getAngularVersion(cwd) {
452
+ const dependency = (0, utils_1.findDependency)("@angular/core", { cwd, depth: 0, omitDev: false });
453
+ if (!dependency)
454
+ return undefined;
455
+ const angularVersionSemver = (0, semver_1.coerce)(dependency.version);
456
+ if (!angularVersionSemver)
457
+ return dependency.version;
458
+ return angularVersionSemver.toString();
459
+ }
460
+ exports.getAngularVersion = getAngularVersion;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getDevModeHandle = exports.ɵcodegenFunctionsDirectory = exports.ɵcodegenPublicDirectory = exports.build = exports.discover = exports.type = exports.support = exports.name = void 0;
3
+ exports.getDevModeHandle = exports.ɵcodegenFunctionsDirectory = exports.ɵcodegenPublicDirectory = exports.build = exports.discover = exports.supportedRange = exports.type = exports.support = exports.name = void 0;
4
4
  const cross_spawn_1 = require("cross-spawn");
5
5
  const fs_extra_1 = require("fs-extra");
6
6
  const path_1 = require("path");
@@ -10,15 +10,18 @@ const utils_2 = require("./utils");
10
10
  exports.name = "Astro";
11
11
  exports.support = "experimental";
12
12
  exports.type = 2;
13
+ exports.supportedRange = "2 - 3";
13
14
  async function discover(dir) {
14
15
  if (!(0, fs_extra_1.existsSync)((0, path_1.join)(dir, "package.json")))
15
16
  return;
16
- if (!(0, utils_2.getAstroVersion)(dir))
17
+ const version = (0, utils_2.getAstroVersion)(dir);
18
+ if (!version)
17
19
  return;
18
20
  const { output, publicDir: publicDirectory } = await (0, utils_2.getConfig)(dir);
19
21
  return {
20
22
  mayWantBackend: output !== "static",
21
23
  publicDirectory,
24
+ version,
22
25
  };
23
26
  }
24
27
  exports.discover = discover;
@@ -4,6 +4,7 @@ exports.getAstroVersion = exports.getConfig = exports.getBootstrapScript = void
4
4
  const path_1 = require("path");
5
5
  const utils_1 = require("../utils");
6
6
  const semver_1 = require("semver");
7
+ const url_1 = require("url");
7
8
  const { dynamicImport } = require(true && "../../dynamicImport");
8
9
  function getBootstrapScript() {
9
10
  return `const entry = import('./entry.mjs');\nexport const handle = async (req, res) => (await entry).handler(req, res)`;
@@ -26,8 +27,8 @@ async function getConfig(cwd) {
26
27
  config = astroConfig;
27
28
  }
28
29
  return {
29
- outDir: (0, path_1.relative)(cwd, config.outDir.pathname),
30
- publicDir: (0, path_1.relative)(cwd, config.publicDir.pathname),
30
+ outDir: (0, path_1.relative)(cwd, (0, url_1.fileURLToPath)(config.outDir)),
31
+ publicDir: (0, path_1.relative)(cwd, (0, url_1.fileURLToPath)(config.publicDir)),
31
32
  output: config.output,
32
33
  adapter: config.adapter,
33
34
  };
@@ -6,10 +6,10 @@ const experiments = require("../experiments");
6
6
  exports.NPM_COMMAND_TIMEOUT_MILLIES = 10000;
7
7
  exports.SupportLevelWarnings = {
8
8
  ["experimental"]: (framework) => `Thank you for trying our ${clc.italic("experimental")} support for ${framework} on Firebase Hosting.
9
- ${clc.yellow(`While this integration is maintained by Googlers it is not a supported Firebase product.
9
+ ${clc.red(`While this integration is maintained by Googlers it is not a supported Firebase product.
10
10
  Issues filed on GitHub will be addressed on a best-effort basis by maintainers and other community members.`)}`,
11
11
  ["preview"]: (framework) => `Thank you for trying our ${clc.italic("early preview")} of ${framework} support on Firebase Hosting.
12
- ${clc.yellow("During the preview, support is best-effort and breaking changes can be expected. Proceed with caution.")}`,
12
+ ${clc.red("During the preview, support is best-effort and breaking changes can be expected. Proceed with caution.")}`,
13
13
  };
14
14
  exports.DEFAULT_DOCS_URL = "https://firebase.google.com/docs/hosting/frameworks/frameworks-overview";
15
15
  exports.FILE_BUG_URL = "https://github.com/firebase/firebase-tools/issues/new?template=bug_report.md";
@@ -26,11 +26,35 @@ exports.VALID_ENGINES = { node: [16, 18, 20] };
26
26
  exports.VALID_LOCALE_FORMATS = [/^ALL_[a-z]+$/, /^[a-z]+_ALL$/, /^[a-z]+(_[a-z]+)?$/];
27
27
  exports.DEFAULT_REGION = "us-central1";
28
28
  exports.ALLOWED_SSR_REGIONS = [
29
- { name: "us-central1 (Iowa)", value: "us-central1" },
30
- { name: "us-west1 (Oregon)", value: "us-west1" },
31
- { name: "us-east1 (South Carolina)", value: "us-east1" },
32
- { name: "europe-west1 (Belgium)", value: "europe-west1" },
33
- { name: "asia-east1 (Taiwan)", value: "asia-east1" },
29
+ { name: "us-central1 (Iowa)", value: "us-central1", recommended: true },
30
+ { name: "us-east1 (South Carolina)", value: "us-east1", recommended: true },
31
+ { name: "us-east4 (Northern Virginia)", value: "us-east4" },
32
+ { name: "us-west1 (Oregon)", value: "us-west1", recommended: true },
33
+ { name: "us-west2 (Los Angeles)", value: "us-west2" },
34
+ { name: "us-west3 (Salt Lake City)", value: "us-west3" },
35
+ { name: "us-west4 (Las Vegas)", value: "us-west4" },
36
+ { name: "asia-east1 (Taiwan)", value: "asia-east1", recommended: true },
37
+ { name: "asia-east2 (Hong Kong)", value: "asia-east2" },
38
+ { name: "asia-northeast1 (Tokyo)", value: "asia-northeast1" },
39
+ { name: "asia-northeast2 (Osaka)", value: "asia-northeast2" },
40
+ { name: "asia-northeast3 (Seoul)", value: "asia-northeast3" },
41
+ { name: "asia-south1 (Mumbai)", value: "asia-south1" },
42
+ { name: "asia-south2 (Delhi)", value: "asia-south2" },
43
+ { name: "asia-southeast1 (Singapore)", value: "asia-southeast1" },
44
+ { name: "asia-southeast2 (Jakarta)", value: "asia-southeast2" },
45
+ { name: "australia-southeast1 (Sydney)", value: "australia-southeast1" },
46
+ { name: "australia-southeast2 (Melbourne)", value: "australia-southeast2" },
47
+ { name: "europe-central2 (Warsaw)", value: "europe-central2" },
48
+ { name: "europe-north1 (Finland)", value: "europe-north1" },
49
+ { name: "europe-west1 (Belgium)", value: "europe-west1", recommended: true },
50
+ { name: "europe-west2 (London)", value: "europe-west2" },
51
+ { name: "europe-west3 (Frankfurt)", value: "europe-west3" },
52
+ { name: "europe-west4 (Netherlands)", value: "europe-west4" },
53
+ { name: "europe-west6 (Zurich)", value: "europe-west6" },
54
+ { name: "northamerica-northeast1 (Montreal)", value: "northamerica-northeast1" },
55
+ { name: "northamerica-northeast2 (Toronto)", value: "northamerica-northeast2" },
56
+ { name: "southamerica-east1 (São Paulo)", value: "southamerica-east1" },
57
+ { name: "southamerica-west1 (Santiago)", value: "southamerica-west1" },
34
58
  ];
35
59
  exports.I18N_ROOT = "/";
36
60
  function GET_DEFAULT_BUILD_TARGETS() {
@@ -62,14 +62,14 @@ async function discover(dir, warn = true) {
62
62
  }
63
63
  exports.discover = discover;
64
64
  const BUILD_MEMO = new Map();
65
- function memoizeBuild(dir, build, deps, target) {
65
+ function memoizeBuild(dir, build, deps, target, context) {
66
66
  const key = [dir, ...deps];
67
67
  for (const existingKey of BUILD_MEMO.keys()) {
68
68
  if ((0, util_1.isDeepStrictEqual)(existingKey, key)) {
69
69
  return BUILD_MEMO.get(existingKey);
70
70
  }
71
71
  }
72
- const value = build(dir, target);
72
+ const value = build(dir, target, context);
73
73
  BUILD_MEMO.set(key, value);
74
74
  return value;
75
75
  }
@@ -119,7 +119,7 @@ async function prepareFrameworks(purpose, targetNames, context, options, emulato
119
119
  throw new error_1.FirebaseError(`Hosting config for site ${site} places server-side content in region ${ssrRegion} which is not known. Valid regions are ${validRegions}`);
120
120
  }
121
121
  const getProjectPath = (...args) => (0, path_1.join)(projectRoot, source, ...args);
122
- const functionId = `ssr${site.toLowerCase().replace(/-/g, "")}`;
122
+ const functionId = `ssr${site.toLowerCase().replace(/-/g, "").substring(0, 20)}`;
123
123
  const usesFirebaseAdminSdk = !!(0, utils_1.findDependency)("firebase-admin", { cwd: getProjectPath() });
124
124
  const usesFirebaseJsSdk = !!(0, utils_1.findDependency)("@firebase/app", { cwd: getProjectPath() });
125
125
  if (usesFirebaseAdminSdk) {
@@ -190,13 +190,18 @@ async function prepareFrameworks(purpose, targetNames, context, options, emulato
190
190
  throw new error_1.FirebaseError((0, utils_1.frameworksCallToAction)("Unable to detect the web framework in use, check firebase-debug.log for more info."));
191
191
  }
192
192
  const { framework, mayWantBackend, publicDirectory } = results;
193
- const { build, ɵcodegenPublicDirectory, ɵcodegenFunctionsDirectory: codegenProdModeFunctionsDirectory, getDevModeHandle, name, support, docsUrl, getValidBuildTargets = constants_2.GET_DEFAULT_BUILD_TARGETS, shouldUseDevModeHandle = constants_2.DEFAULT_SHOULD_USE_DEV_MODE_HANDLE, } = frameworks_1.WebFrameworks[framework];
194
- logger_1.logger.info(`\n${(0, utils_1.frameworksCallToAction)(constants_2.SupportLevelWarnings[support](name), docsUrl, " ")}\n`);
193
+ const { build, ɵcodegenPublicDirectory, ɵcodegenFunctionsDirectory: codegenProdModeFunctionsDirectory, getDevModeHandle, name, support, docsUrl, supportedRange, getValidBuildTargets = constants_2.GET_DEFAULT_BUILD_TARGETS, shouldUseDevModeHandle = constants_2.DEFAULT_SHOULD_USE_DEV_MODE_HANDLE, } = frameworks_1.WebFrameworks[framework];
194
+ logger_1.logger.info(`\n${(0, utils_1.frameworksCallToAction)(constants_2.SupportLevelWarnings[support](name), docsUrl, " ", name, results.version, supportedRange, results.vite)}\n`);
195
195
  const hostingEmulatorInfo = emulators.find((e) => e.name === types_1.Emulators.HOSTING);
196
196
  const validBuildTargets = await getValidBuildTargets(purpose, getProjectPath());
197
197
  const frameworksBuildTarget = (0, utils_1.getFrameworksBuildTarget)(purpose, validBuildTargets);
198
198
  const useDevModeHandle = purpose !== "deploy" &&
199
199
  (await shouldUseDevModeHandle(frameworksBuildTarget, getProjectPath()));
200
+ const frameworkContext = {
201
+ projectId: project,
202
+ site: options.site,
203
+ hostingChannel: context === null || context === void 0 ? void 0 : context.hostingChannel,
204
+ };
200
205
  let codegenFunctionsDirectory;
201
206
  let baseUrl = "";
202
207
  const rewrites = [];
@@ -213,7 +218,7 @@ async function prepareFrameworks(purpose, targetNames, context, options, emulato
213
218
  }
214
219
  }
215
220
  else {
216
- const buildResult = await memoizeBuild(getProjectPath(), build, [firebaseDefaults, frameworksBuildTarget], frameworksBuildTarget);
221
+ const buildResult = await memoizeBuild(getProjectPath(), build, [firebaseDefaults, frameworksBuildTarget], frameworksBuildTarget, frameworkContext);
217
222
  const { wantsBackend = false, trailingSlash, i18n = false } = buildResult || {};
218
223
  if (buildResult) {
219
224
  baseUrl = (_d = buildResult.baseUrl) !== null && _d !== void 0 ? _d : baseUrl;
@@ -282,7 +287,7 @@ async function prepareFrameworks(purpose, targetNames, context, options, emulato
282
287
  else {
283
288
  await (0, fs_extra_1.mkdirp)(functionsDist);
284
289
  }
285
- const { packageJson, bootstrapScript, frameworksEntry = framework, dotEnv = {}, rewriteSource, } = await codegenFunctionsDirectory(getProjectPath(), functionsDist, frameworksBuildTarget);
290
+ const { packageJson, bootstrapScript, frameworksEntry = framework, dotEnv = {}, rewriteSource, } = await codegenFunctionsDirectory(getProjectPath(), functionsDist, frameworksBuildTarget, frameworkContext);
286
291
  const rewrite = {
287
292
  source: rewriteSource || path_1.posix.join(baseUrl, "**"),
288
293
  function: {