firebase-tools 11.17.0 → 11.19.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.
- package/lib/api.js +3 -2
- package/lib/commands/index.js +5 -0
- package/lib/commands/internaltesting-functions-discover.js +25 -0
- package/lib/deploy/extensions/prepare.js +6 -1
- package/lib/deploy/extensions/v2FunctionHelper.js +53 -0
- package/lib/deploy/functions/build.js +17 -2
- package/lib/deploy/functions/cel.js +90 -13
- package/lib/deploy/functions/params.js +141 -6
- package/lib/deploy/functions/prepare.js +40 -25
- package/lib/deploy/functions/release/fabricator.js +27 -1
- package/lib/deploy/functions/runtimes/discovery/parsing.js +7 -1
- package/lib/deploy/functions/runtimes/discovery/v1alpha1.js +1 -1
- package/lib/deploy/functions/runtimes/index.js +2 -1
- package/lib/deploy/functions/runtimes/node/index.js +2 -2
- package/lib/deploy/functions/runtimes/node/parseRuntimeAndValidateSDK.js +1 -0
- package/lib/deploy/functions/runtimes/node/versioning.js +30 -14
- package/lib/emulator/commandUtils.js +2 -1
- package/lib/emulator/downloadableEmulators.js +3 -3
- package/lib/emulator/env.js +29 -27
- package/lib/emulator/extensions/validation.js +2 -0
- package/lib/emulator/extensionsEmulator.js +1 -1
- package/lib/emulator/functionsEmulator.js +44 -32
- package/lib/emulator/storage/rules/runtime.js +2 -2
- package/lib/emulator/workQueue.js +11 -6
- package/lib/experiments.js +6 -0
- package/lib/extensions/billingMigrationHelper.js +2 -1
- package/lib/extensions/displayExtensionInfo.js +2 -1
- package/lib/extensions/emulator/specHelper.js +4 -3
- package/lib/extensions/emulator/triggerHelper.js +64 -20
- package/lib/extensions/extensionsHelper.js +1 -4
- package/lib/extensions/types.js +2 -1
- package/lib/extensions/utils.js +14 -1
- package/lib/firestore/indexes-api.js +7 -1
- package/lib/firestore/indexes-sort.js +4 -0
- package/lib/firestore/indexes.js +31 -5
- package/lib/firestore/util.js +5 -1
- package/lib/firestore/validator.js +7 -1
- package/lib/frameworks/angular/index.js +3 -0
- package/lib/frameworks/index.js +7 -1
- package/lib/frameworks/next/constants.js +10 -0
- package/lib/frameworks/next/index.js +170 -127
- package/lib/frameworks/next/interfaces.js +2 -0
- package/lib/frameworks/next/utils.js +92 -0
- package/lib/frameworks/nuxt/index.js +3 -0
- package/lib/frameworks/utils.js +24 -0
- package/lib/frameworks/vite/index.js +4 -1
- package/lib/gcp/eventarc.js +42 -0
- package/lib/init/features/emulators.js +1 -1
- package/npm-shrinkwrap.json +2 -93
- package/package.json +1 -4
- package/schema/firebase-config.json +4 -2
|
@@ -7,16 +7,22 @@ const path_1 = require("path");
|
|
|
7
7
|
const fs_extra_1 = require("fs-extra");
|
|
8
8
|
const url_1 = require("url");
|
|
9
9
|
const fs_1 = require("fs");
|
|
10
|
+
const semver_1 = require("semver");
|
|
11
|
+
const clc = require("colorette");
|
|
10
12
|
const __1 = require("..");
|
|
11
13
|
const prompt_1 = require("../../prompt");
|
|
12
|
-
const semver_1 = require("semver");
|
|
13
|
-
const logger_1 = require("../../logger");
|
|
14
14
|
const error_1 = require("../../error");
|
|
15
|
-
const
|
|
16
|
-
const
|
|
15
|
+
const utils_1 = require("./utils");
|
|
16
|
+
const utils_2 = require("../utils");
|
|
17
|
+
const utils_3 = require("../utils");
|
|
18
|
+
const utils_4 = require("./utils");
|
|
19
|
+
const constants_1 = require("./constants");
|
|
20
|
+
const DEFAULT_BUILD_SCRIPT = ["next build"];
|
|
21
|
+
const PUBLIC_DIR = "public";
|
|
17
22
|
exports.name = "Next.js";
|
|
18
23
|
exports.support = "experimental";
|
|
19
24
|
exports.type = 2;
|
|
25
|
+
const DEFAULT_NUMBER_OF_REASONS_TO_LIST = 5;
|
|
20
26
|
function getNextVersion(cwd) {
|
|
21
27
|
var _a;
|
|
22
28
|
return (_a = (0, __1.findDependency)("next", { cwd, depth: 0, omitDev: false })) === null || _a === void 0 ? void 0 : _a.version;
|
|
@@ -30,11 +36,13 @@ async function discover(dir) {
|
|
|
30
36
|
return;
|
|
31
37
|
if (!(await (0, fs_extra_1.pathExists)("next.config.js")) && !getNextVersion(dir))
|
|
32
38
|
return;
|
|
33
|
-
return { mayWantBackend: true, publicDirectory: (0, path_1.join)(dir,
|
|
39
|
+
return { mayWantBackend: true, publicDirectory: (0, path_1.join)(dir, PUBLIC_DIR) };
|
|
34
40
|
}
|
|
35
41
|
exports.discover = discover;
|
|
36
42
|
async function build(dir) {
|
|
43
|
+
var _a, _b;
|
|
37
44
|
const { default: nextBuild } = (0, __1.relativeRequire)(dir, "next/dist/build");
|
|
45
|
+
await (0, utils_3.warnIfCustomBuildScript)(dir, exports.name, DEFAULT_BUILD_SCRIPT);
|
|
38
46
|
const reactVersion = getReactVersion(dir);
|
|
39
47
|
if (reactVersion && (0, semver_1.gte)(reactVersion, "18.0.0")) {
|
|
40
48
|
process.env.__NEXT_REACT_ROOT = "true";
|
|
@@ -43,54 +51,89 @@ async function build(dir) {
|
|
|
43
51
|
console.error(e.message);
|
|
44
52
|
throw e;
|
|
45
53
|
});
|
|
46
|
-
|
|
47
|
-
|
|
54
|
+
const reasonsForBackend = [];
|
|
55
|
+
const { distDir } = await getConfig(dir);
|
|
56
|
+
if (await (0, utils_1.isUsingMiddleware)((0, path_1.join)(dir, distDir), false)) {
|
|
57
|
+
reasonsForBackend.push("middleware");
|
|
48
58
|
}
|
|
49
|
-
|
|
59
|
+
if (await (0, utils_1.isUsingImageOptimization)((0, path_1.join)(dir, distDir))) {
|
|
60
|
+
reasonsForBackend.push(`Image Optimization`);
|
|
50
61
|
}
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
const
|
|
55
|
-
const
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
const
|
|
64
|
-
|
|
65
|
-
const prerenderedRoutes = Object.keys(prerenderManifestJSON.routes);
|
|
66
|
-
const dynamicRoutes = Object.keys(prerenderManifestJSON.dynamicRoutes);
|
|
67
|
-
const unrenderedPages = [
|
|
68
|
-
...Object.keys(pagesManifestJSON),
|
|
69
|
-
...Object.values(appPathRoutesManifestJSON),
|
|
70
|
-
].filter((it) => !(["/_app", "/", "/_error", "/_document", "/404"].includes(it) ||
|
|
71
|
-
prerenderedRoutes.includes(it) ||
|
|
72
|
-
dynamicRoutes.includes(it)));
|
|
73
|
-
if (!anyDynamicRouteFallbacks && unrenderedPages.length === 0) {
|
|
74
|
-
wantsBackend = false;
|
|
62
|
+
if ((0, utils_1.isUsingAppDirectory)((0, path_1.join)(dir, distDir))) {
|
|
63
|
+
reasonsForBackend.push("app directory (unstable)");
|
|
64
|
+
}
|
|
65
|
+
const prerenderManifest = await (0, utils_2.readJSON)((0, path_1.join)(dir, distDir, constants_1.PRERENDER_MANIFEST));
|
|
66
|
+
const dynamicRoutesWithFallback = Object.entries(prerenderManifest.dynamicRoutes || {}).filter(([, it]) => it.fallback !== false);
|
|
67
|
+
if (dynamicRoutesWithFallback.length > 0) {
|
|
68
|
+
for (const [key] of dynamicRoutesWithFallback) {
|
|
69
|
+
reasonsForBackend.push(`use of fallback ${key}`);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
const routesWithRevalidate = Object.entries(prerenderManifest.routes).filter(([, it]) => it.initialRevalidateSeconds);
|
|
73
|
+
if (routesWithRevalidate.length > 0) {
|
|
74
|
+
for (const [key] of routesWithRevalidate) {
|
|
75
|
+
reasonsForBackend.push(`use of revalidate ${key}`);
|
|
75
76
|
}
|
|
76
77
|
}
|
|
77
|
-
const
|
|
78
|
-
const
|
|
78
|
+
const pagesManifestJSON = await (0, utils_2.readJSON)((0, path_1.join)(dir, distDir, "server", constants_1.PAGES_MANIFEST));
|
|
79
|
+
const prerenderedRoutes = Object.keys(prerenderManifest.routes);
|
|
80
|
+
const dynamicRoutes = Object.keys(prerenderManifest.dynamicRoutes);
|
|
81
|
+
const unrenderedPages = Object.keys(pagesManifestJSON).filter((it) => !(["/_app", "/", "/_error", "/_document", "/404"].includes(it) ||
|
|
82
|
+
prerenderedRoutes.includes(it) ||
|
|
83
|
+
dynamicRoutes.includes(it)));
|
|
84
|
+
if (unrenderedPages.length > 0) {
|
|
85
|
+
for (const key of unrenderedPages) {
|
|
86
|
+
reasonsForBackend.push(`non-static route ${key}`);
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
const manifest = await (0, utils_2.readJSON)((0, path_1.join)(dir, distDir, constants_1.ROUTES_MANIFEST));
|
|
79
90
|
const { headers: nextJsHeaders = [], redirects: nextJsRedirects = [], rewrites: nextJsRewrites = [], } = manifest;
|
|
80
|
-
const
|
|
91
|
+
const isEveryHeaderSupported = nextJsHeaders.every(utils_1.isHeaderSupportedByHosting);
|
|
92
|
+
if (!isEveryHeaderSupported) {
|
|
93
|
+
reasonsForBackend.push("advanced headers");
|
|
94
|
+
}
|
|
95
|
+
const headers = nextJsHeaders.filter(utils_1.isHeaderSupportedByHosting).map(({ source, headers }) => ({
|
|
96
|
+
source: (0, utils_1.cleanEscapedChars)(source),
|
|
97
|
+
headers,
|
|
98
|
+
}));
|
|
99
|
+
const isEveryRedirectSupported = nextJsRedirects.every(utils_1.isRedirectSupportedByHosting);
|
|
100
|
+
if (!isEveryRedirectSupported) {
|
|
101
|
+
reasonsForBackend.push("advanced redirects");
|
|
102
|
+
}
|
|
81
103
|
const redirects = nextJsRedirects
|
|
82
|
-
.filter(
|
|
83
|
-
.map(({ source, destination, statusCode: type }) => ({
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
104
|
+
.filter(utils_1.isRedirectSupportedByHosting)
|
|
105
|
+
.map(({ source, destination, statusCode: type }) => ({
|
|
106
|
+
source: (0, utils_1.cleanEscapedChars)(source),
|
|
107
|
+
destination,
|
|
108
|
+
type,
|
|
109
|
+
}));
|
|
110
|
+
const nextJsRewritesToUse = (0, utils_1.getNextjsRewritesToUse)(nextJsRewrites);
|
|
111
|
+
if (!Array.isArray(nextJsRewrites) &&
|
|
112
|
+
(((_a = nextJsRewrites.afterFiles) === null || _a === void 0 ? void 0 : _a.length) || ((_b = nextJsRewrites.fallback) === null || _b === void 0 ? void 0 : _b.length))) {
|
|
113
|
+
reasonsForBackend.push("advanced rewrites");
|
|
114
|
+
}
|
|
115
|
+
const isEveryRewriteSupported = nextJsRewritesToUse.every(utils_1.isRewriteSupportedByHosting);
|
|
116
|
+
if (!isEveryRewriteSupported) {
|
|
117
|
+
reasonsForBackend.push("advanced rewrites");
|
|
118
|
+
}
|
|
87
119
|
const rewrites = nextJsRewritesToUse
|
|
88
|
-
.
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
})
|
|
93
|
-
|
|
120
|
+
.filter(utils_1.isRewriteSupportedByHosting)
|
|
121
|
+
.map(({ source, destination }) => ({
|
|
122
|
+
source: (0, utils_1.cleanEscapedChars)(source),
|
|
123
|
+
destination,
|
|
124
|
+
}));
|
|
125
|
+
const wantsBackend = reasonsForBackend.length > 0;
|
|
126
|
+
if (wantsBackend) {
|
|
127
|
+
const numberOfReasonsToList = process.env.DEBUG ? Infinity : DEFAULT_NUMBER_OF_REASONS_TO_LIST;
|
|
128
|
+
console.log("Building a Cloud Function to run this application. This is needed due to:");
|
|
129
|
+
for (const reason of reasonsForBackend.slice(0, numberOfReasonsToList)) {
|
|
130
|
+
console.log(` • ${reason}`);
|
|
131
|
+
}
|
|
132
|
+
if (reasonsForBackend.length > numberOfReasonsToList) {
|
|
133
|
+
console.log(` • and ${reasonsForBackend.length - numberOfReasonsToList} other reasons, use --debug to see more`);
|
|
134
|
+
}
|
|
135
|
+
console.log("");
|
|
136
|
+
}
|
|
94
137
|
return { wantsBackend, headers, redirects, rewrites };
|
|
95
138
|
}
|
|
96
139
|
exports.build = build;
|
|
@@ -106,111 +149,111 @@ async function init(setup) {
|
|
|
106
149
|
exports.init = init;
|
|
107
150
|
async function ɵcodegenPublicDirectory(sourceDir, destDir) {
|
|
108
151
|
const { distDir } = await getConfig(sourceDir);
|
|
109
|
-
const
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
await (0, fs_extra_1.copy)(publicPath, destDir);
|
|
152
|
+
const publicPath = (0, path_1.join)(sourceDir, "public");
|
|
153
|
+
await (0, promises_1.mkdir)((0, path_1.join)(destDir, "_next", "static"), { recursive: true });
|
|
154
|
+
if (await (0, fs_extra_1.pathExists)(publicPath)) {
|
|
155
|
+
await (0, fs_extra_1.copy)(publicPath, destDir);
|
|
156
|
+
}
|
|
157
|
+
await (0, fs_extra_1.copy)((0, path_1.join)(sourceDir, distDir, "static"), (0, path_1.join)(destDir, "_next", "static"));
|
|
158
|
+
for (const file of ["index.html", "404.html", "500.html"]) {
|
|
159
|
+
const pagesPath = (0, path_1.join)(sourceDir, distDir, "server", "pages", file);
|
|
160
|
+
if (await (0, fs_extra_1.pathExists)(pagesPath)) {
|
|
161
|
+
await (0, promises_1.copyFile)(pagesPath, (0, path_1.join)(destDir, file));
|
|
162
|
+
continue;
|
|
121
163
|
}
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
if (await (0, fs_extra_1.pathExists)(pagesPath)) {
|
|
126
|
-
await (0, promises_1.copyFile)(pagesPath, (0, path_1.join)(destDir, file));
|
|
127
|
-
continue;
|
|
128
|
-
}
|
|
129
|
-
const appPath = (0, path_1.join)(sourceDir, distDir, "server", "app", file);
|
|
130
|
-
if (await (0, fs_extra_1.pathExists)(appPath)) {
|
|
131
|
-
await (0, promises_1.copyFile)(appPath, (0, path_1.join)(destDir, file));
|
|
132
|
-
}
|
|
164
|
+
const appPath = (0, path_1.join)(sourceDir, distDir, "server", "app", file);
|
|
165
|
+
if (await (0, fs_extra_1.pathExists)(appPath)) {
|
|
166
|
+
await (0, promises_1.copyFile)(appPath, (0, path_1.join)(destDir, file));
|
|
133
167
|
}
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
168
|
+
}
|
|
169
|
+
const [middlewareManifest, prerenderManifest, routesManifest] = await Promise.all([
|
|
170
|
+
(0, utils_2.readJSON)((0, path_1.join)(sourceDir, distDir, "server", constants_1.MIDDLEWARE_MANIFEST)),
|
|
171
|
+
(0, utils_2.readJSON)((0, path_1.join)(sourceDir, distDir, constants_1.PRERENDER_MANIFEST)),
|
|
172
|
+
(0, utils_2.readJSON)((0, path_1.join)(sourceDir, distDir, constants_1.ROUTES_MANIFEST)),
|
|
173
|
+
]);
|
|
174
|
+
const middlewareMatcherRegexes = Object.values(middlewareManifest.middleware)
|
|
175
|
+
.map((it) => it.matchers)
|
|
176
|
+
.flat()
|
|
177
|
+
.map((it) => new RegExp(it.regexp));
|
|
178
|
+
const { redirects = [], rewrites = [], headers = [] } = routesManifest;
|
|
179
|
+
const rewritesRegexesNotSupportedByHosting = (0, utils_1.getNextjsRewritesToUse)(rewrites)
|
|
180
|
+
.filter((rewrite) => !(0, utils_1.isRewriteSupportedByHosting)(rewrite))
|
|
181
|
+
.map((rewrite) => new RegExp(rewrite.regex));
|
|
182
|
+
const redirectsRegexesNotSupportedByHosting = redirects
|
|
183
|
+
.filter((redirect) => !(0, utils_1.isRedirectSupportedByHosting)(redirect))
|
|
184
|
+
.map((redirect) => new RegExp(redirect.regex));
|
|
185
|
+
const headersRegexesNotSupportedByHosting = headers
|
|
186
|
+
.filter((header) => !(0, utils_1.isHeaderSupportedByHosting)(header))
|
|
187
|
+
.map((header) => new RegExp(header.regex));
|
|
188
|
+
const pathsUsingsFeaturesNotSupportedByHosting = [
|
|
189
|
+
...middlewareMatcherRegexes,
|
|
190
|
+
...rewritesRegexesNotSupportedByHosting,
|
|
191
|
+
...redirectsRegexesNotSupportedByHosting,
|
|
192
|
+
...headersRegexesNotSupportedByHosting,
|
|
193
|
+
];
|
|
194
|
+
for (const [path, route] of Object.entries(prerenderManifest.routes)) {
|
|
195
|
+
if (route.initialRevalidateSeconds ||
|
|
196
|
+
pathsUsingsFeaturesNotSupportedByHosting.some((it) => path.match(it))) {
|
|
197
|
+
continue;
|
|
198
|
+
}
|
|
199
|
+
const isReactServerComponent = route.dataRoute.endsWith(".rsc");
|
|
200
|
+
const contentDist = (0, path_1.join)(sourceDir, distDir, "server", isReactServerComponent ? "app" : "pages");
|
|
201
|
+
const parts = path.split("/").filter((it) => !!it);
|
|
202
|
+
const partsOrIndex = parts.length > 0 ? parts : ["index"];
|
|
203
|
+
const htmlPath = `${(0, path_1.join)(...partsOrIndex)}.html`;
|
|
204
|
+
await (0, promises_1.mkdir)((0, path_1.join)(destDir, (0, path_1.dirname)(htmlPath)), { recursive: true });
|
|
205
|
+
await (0, promises_1.copyFile)((0, path_1.join)(contentDist, htmlPath), (0, path_1.join)(destDir, htmlPath));
|
|
206
|
+
if (!isReactServerComponent) {
|
|
207
|
+
const dataPath = `${(0, path_1.join)(...partsOrIndex)}.json`;
|
|
208
|
+
await (0, promises_1.mkdir)((0, path_1.join)(destDir, (0, path_1.dirname)(route.dataRoute)), { recursive: true });
|
|
209
|
+
await (0, promises_1.copyFile)((0, path_1.join)(contentDist, dataPath), (0, path_1.join)(destDir, route.dataRoute));
|
|
173
210
|
}
|
|
174
211
|
}
|
|
175
212
|
}
|
|
176
213
|
exports.ɵcodegenPublicDirectory = ɵcodegenPublicDirectory;
|
|
177
214
|
async function ɵcodegenFunctionsDirectory(sourceDir, destDir) {
|
|
178
215
|
const { distDir } = await getConfig(sourceDir);
|
|
179
|
-
const
|
|
180
|
-
const packageJson = JSON.parse(packageJsonBuffer.toString());
|
|
216
|
+
const packageJson = await (0, utils_2.readJSON)((0, path_1.join)(sourceDir, "package.json"));
|
|
181
217
|
if ((0, fs_1.existsSync)((0, path_1.join)(sourceDir, "next.config.js"))) {
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
await esbuild.build({
|
|
191
|
-
bundle: true,
|
|
192
|
-
external: Object.keys(packageJson.dependencies),
|
|
193
|
-
absWorkingDir: sourceDir,
|
|
194
|
-
entryPoints: ["next.config.js"],
|
|
195
|
-
outfile: (0, path_1.join)(destDir, "next.config.js"),
|
|
196
|
-
target: `node${__1.NODE_VERSION}`,
|
|
197
|
-
platform: "node",
|
|
218
|
+
const dependencyTree = JSON.parse((0, child_process_1.spawnSync)("npm", ["ls", "--omit=dev", "--all", "--json"], {
|
|
219
|
+
cwd: sourceDir,
|
|
220
|
+
}).stdout.toString());
|
|
221
|
+
const esbuildArgs = (0, utils_1.allDependencyNames)(dependencyTree)
|
|
222
|
+
.map((it) => `--external:${it}`)
|
|
223
|
+
.concat("--bundle", "--platform=node", `--target=node${__1.NODE_VERSION}`, `--outdir=${destDir}`, "--log-level=error");
|
|
224
|
+
const bundle = (0, child_process_1.spawnSync)("npx", ["--yes", "esbuild", "next.config.js", ...esbuildArgs], {
|
|
225
|
+
cwd: sourceDir,
|
|
198
226
|
});
|
|
227
|
+
if (bundle.status) {
|
|
228
|
+
console.error(bundle.stderr.toString());
|
|
229
|
+
throw new error_1.FirebaseError("Unable to bundle next.config.js for use in Cloud Functions");
|
|
230
|
+
}
|
|
199
231
|
}
|
|
200
232
|
if (await (0, fs_extra_1.pathExists)((0, path_1.join)(sourceDir, "public"))) {
|
|
201
233
|
await (0, promises_1.mkdir)((0, path_1.join)(destDir, "public"));
|
|
202
234
|
await (0, fs_extra_1.copy)((0, path_1.join)(sourceDir, "public"), (0, path_1.join)(destDir, "public"));
|
|
203
235
|
}
|
|
236
|
+
if (!(await (0, utils_4.hasUnoptimizedImage)(sourceDir, distDir)) &&
|
|
237
|
+
((0, utils_4.usesAppDirRouter)(sourceDir) || (await (0, utils_4.usesNextImage)(sourceDir, distDir)))) {
|
|
238
|
+
packageJson.dependencies["sharp"] = "latest";
|
|
239
|
+
}
|
|
204
240
|
await (0, fs_extra_1.mkdirp)((0, path_1.join)(destDir, distDir));
|
|
205
241
|
await (0, fs_extra_1.copy)((0, path_1.join)(sourceDir, distDir), (0, path_1.join)(destDir, distDir));
|
|
206
242
|
return { packageJson, frameworksEntry: "next.js" };
|
|
207
243
|
}
|
|
208
244
|
exports.ɵcodegenFunctionsDirectory = ɵcodegenFunctionsDirectory;
|
|
209
|
-
async function getDevModeHandle(dir) {
|
|
245
|
+
async function getDevModeHandle(dir, hostingEmulatorInfo) {
|
|
246
|
+
if (!hostingEmulatorInfo) {
|
|
247
|
+
if (await (0, utils_1.isUsingMiddleware)(dir, true)) {
|
|
248
|
+
throw new error_1.FirebaseError(`${clc.bold("firebase serve")} does not support Next.js Middleware. Please use ${clc.bold("firebase emulators:start")} instead.`);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
210
251
|
const { default: next } = (0, __1.relativeRequire)(dir, "next");
|
|
211
252
|
const nextApp = next({
|
|
212
253
|
dev: true,
|
|
213
254
|
dir,
|
|
255
|
+
hostname: hostingEmulatorInfo === null || hostingEmulatorInfo === void 0 ? void 0 : hostingEmulatorInfo.host,
|
|
256
|
+
port: hostingEmulatorInfo === null || hostingEmulatorInfo === void 0 ? void 0 : hostingEmulatorInfo.port,
|
|
214
257
|
});
|
|
215
258
|
const handler = nextApp.getRequestHandler();
|
|
216
259
|
await nextApp.prepare();
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.allDependencyNames = exports.isUsingAppDirectory = exports.isUsingImageOptimization = exports.isUsingMiddleware = exports.hasUnoptimizedImage = exports.usesNextImage = exports.usesAppDirRouter = exports.getNextjsRewritesToUse = exports.isHeaderSupportedByHosting = exports.isRedirectSupportedByHosting = exports.isRewriteSupportedByHosting = exports.cleanEscapedChars = exports.pathHasRegex = void 0;
|
|
4
|
+
const fs_1 = require("fs");
|
|
5
|
+
const fs_extra_1 = require("fs-extra");
|
|
6
|
+
const path_1 = require("path");
|
|
7
|
+
const utils_1 = require("../utils");
|
|
8
|
+
const constants_1 = require("./constants");
|
|
9
|
+
const fsutils_1 = require("../../fsutils");
|
|
10
|
+
function pathHasRegex(path) {
|
|
11
|
+
return /(?<!\\)\(/.test(path);
|
|
12
|
+
}
|
|
13
|
+
exports.pathHasRegex = pathHasRegex;
|
|
14
|
+
function cleanEscapedChars(path) {
|
|
15
|
+
return path.replace(/\\([(){}:+?*])/g, (a, b) => b);
|
|
16
|
+
}
|
|
17
|
+
exports.cleanEscapedChars = cleanEscapedChars;
|
|
18
|
+
function isRewriteSupportedByHosting(rewrite) {
|
|
19
|
+
return !("has" in rewrite || pathHasRegex(rewrite.source) || (0, utils_1.isUrl)(rewrite.destination));
|
|
20
|
+
}
|
|
21
|
+
exports.isRewriteSupportedByHosting = isRewriteSupportedByHosting;
|
|
22
|
+
function isRedirectSupportedByHosting(redirect) {
|
|
23
|
+
return !("has" in redirect || pathHasRegex(redirect.source) || "internal" in redirect);
|
|
24
|
+
}
|
|
25
|
+
exports.isRedirectSupportedByHosting = isRedirectSupportedByHosting;
|
|
26
|
+
function isHeaderSupportedByHosting(header) {
|
|
27
|
+
return !("has" in header || pathHasRegex(header.source));
|
|
28
|
+
}
|
|
29
|
+
exports.isHeaderSupportedByHosting = isHeaderSupportedByHosting;
|
|
30
|
+
function getNextjsRewritesToUse(nextJsRewrites) {
|
|
31
|
+
if (Array.isArray(nextJsRewrites)) {
|
|
32
|
+
return nextJsRewrites;
|
|
33
|
+
}
|
|
34
|
+
if (nextJsRewrites === null || nextJsRewrites === void 0 ? void 0 : nextJsRewrites.beforeFiles) {
|
|
35
|
+
return nextJsRewrites.beforeFiles;
|
|
36
|
+
}
|
|
37
|
+
return [];
|
|
38
|
+
}
|
|
39
|
+
exports.getNextjsRewritesToUse = getNextjsRewritesToUse;
|
|
40
|
+
function usesAppDirRouter(sourceDir) {
|
|
41
|
+
const appPathRoutesManifestPath = (0, path_1.join)(sourceDir, constants_1.APP_PATH_ROUTES_MANIFEST);
|
|
42
|
+
return (0, fs_1.existsSync)(appPathRoutesManifestPath);
|
|
43
|
+
}
|
|
44
|
+
exports.usesAppDirRouter = usesAppDirRouter;
|
|
45
|
+
async function usesNextImage(sourceDir, distDir) {
|
|
46
|
+
const exportMarker = await (0, utils_1.readJSON)((0, path_1.join)(sourceDir, distDir, constants_1.EXPORT_MARKER));
|
|
47
|
+
return exportMarker.isNextImageImported;
|
|
48
|
+
}
|
|
49
|
+
exports.usesNextImage = usesNextImage;
|
|
50
|
+
async function hasUnoptimizedImage(sourceDir, distDir) {
|
|
51
|
+
const imagesManifest = await (0, utils_1.readJSON)((0, path_1.join)(sourceDir, distDir, constants_1.IMAGES_MANIFEST));
|
|
52
|
+
return imagesManifest.images.unoptimized;
|
|
53
|
+
}
|
|
54
|
+
exports.hasUnoptimizedImage = hasUnoptimizedImage;
|
|
55
|
+
async function isUsingMiddleware(dir, isDevMode) {
|
|
56
|
+
if (isDevMode) {
|
|
57
|
+
const [middlewareJs, middlewareTs] = await Promise.all([
|
|
58
|
+
(0, fs_extra_1.pathExists)((0, path_1.join)(dir, "middleware.js")),
|
|
59
|
+
(0, fs_extra_1.pathExists)((0, path_1.join)(dir, "middleware.ts")),
|
|
60
|
+
]);
|
|
61
|
+
return middlewareJs || middlewareTs;
|
|
62
|
+
}
|
|
63
|
+
else {
|
|
64
|
+
const middlewareManifest = await (0, utils_1.readJSON)((0, path_1.join)(dir, "server", constants_1.MIDDLEWARE_MANIFEST));
|
|
65
|
+
return Object.keys(middlewareManifest.middleware).length > 0;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
exports.isUsingMiddleware = isUsingMiddleware;
|
|
69
|
+
async function isUsingImageOptimization(dir) {
|
|
70
|
+
const { isNextImageImported } = await (0, utils_1.readJSON)((0, path_1.join)(dir, constants_1.EXPORT_MARKER));
|
|
71
|
+
if (isNextImageImported) {
|
|
72
|
+
const imagesManifest = await (0, utils_1.readJSON)((0, path_1.join)(dir, constants_1.IMAGES_MANIFEST));
|
|
73
|
+
const usingImageOptimization = imagesManifest.images.unoptimized === false;
|
|
74
|
+
if (usingImageOptimization) {
|
|
75
|
+
return true;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
return false;
|
|
79
|
+
}
|
|
80
|
+
exports.isUsingImageOptimization = isUsingImageOptimization;
|
|
81
|
+
function isUsingAppDirectory(dir) {
|
|
82
|
+
const appPathRoutesManifestPath = (0, path_1.join)(dir, constants_1.APP_PATH_ROUTES_MANIFEST);
|
|
83
|
+
return (0, fsutils_1.fileExistsSync)(appPathRoutesManifestPath);
|
|
84
|
+
}
|
|
85
|
+
exports.isUsingAppDirectory = isUsingAppDirectory;
|
|
86
|
+
function allDependencyNames(mod) {
|
|
87
|
+
if (!mod.dependencies)
|
|
88
|
+
return [];
|
|
89
|
+
const dependencyNames = Object.keys(mod.dependencies).reduce((acc, it) => [...acc, it, ...allDependencyNames(mod.dependencies[it])], []);
|
|
90
|
+
return [...new Set(dependencyNames)];
|
|
91
|
+
}
|
|
92
|
+
exports.allDependencyNames = allDependencyNames;
|
|
@@ -6,9 +6,11 @@ const promises_1 = require("fs/promises");
|
|
|
6
6
|
const path_1 = require("path");
|
|
7
7
|
const semver_1 = require("semver");
|
|
8
8
|
const __1 = require("..");
|
|
9
|
+
const utils_1 = require("../utils");
|
|
9
10
|
exports.name = "Nuxt";
|
|
10
11
|
exports.support = "experimental";
|
|
11
12
|
exports.type = 4;
|
|
13
|
+
const DEFAULT_BUILD_SCRIPT = ["nuxt build"];
|
|
12
14
|
async function discover(dir) {
|
|
13
15
|
if (!(await (0, fs_extra_1.pathExists)((0, path_1.join)(dir, "package.json"))))
|
|
14
16
|
return;
|
|
@@ -26,6 +28,7 @@ exports.discover = discover;
|
|
|
26
28
|
async function build(root) {
|
|
27
29
|
const { buildNuxt } = await (0, __1.relativeRequire)(root, "@nuxt/kit");
|
|
28
30
|
const nuxtApp = await getNuxtApp(root);
|
|
31
|
+
await (0, utils_1.warnIfCustomBuildScript)(root, exports.name, DEFAULT_BUILD_SCRIPT);
|
|
29
32
|
await buildNuxt(nuxtApp);
|
|
30
33
|
return { wantsBackend: true };
|
|
31
34
|
}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.warnIfCustomBuildScript = exports.readJSON = exports.isUrl = void 0;
|
|
4
|
+
const fs_extra_1 = require("fs-extra");
|
|
5
|
+
const path_1 = require("path");
|
|
6
|
+
const promises_1 = require("fs/promises");
|
|
7
|
+
function isUrl(url) {
|
|
8
|
+
return /^https?:\/\//.test(url);
|
|
9
|
+
}
|
|
10
|
+
exports.isUrl = isUrl;
|
|
11
|
+
function readJSON(file, options) {
|
|
12
|
+
return (0, fs_extra_1.readJSON)(file, options);
|
|
13
|
+
}
|
|
14
|
+
exports.readJSON = readJSON;
|
|
15
|
+
async function warnIfCustomBuildScript(dir, framework, defaultBuildScripts) {
|
|
16
|
+
var _a;
|
|
17
|
+
const packageJsonBuffer = await (0, promises_1.readFile)((0, path_1.join)(dir, "package.json"));
|
|
18
|
+
const packageJson = JSON.parse(packageJsonBuffer.toString());
|
|
19
|
+
const buildScript = (_a = packageJson.scripts) === null || _a === void 0 ? void 0 : _a.build;
|
|
20
|
+
if (buildScript && !defaultBuildScripts.includes(buildScript)) {
|
|
21
|
+
console.warn(`\nWARNING: Your package.json contains a custom build that is being ignored. Only the ${framework} default build script (e.g, "${defaultBuildScripts[0]}") is respected. If you have a more advanced build process you should build a custom integration https://firebase.google.com/docs/hosting/express\n`);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
exports.warnIfCustomBuildScript = warnIfCustomBuildScript;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.getDevModeHandle = exports.ɵcodegenPublicDirectory = exports.build = exports.discover = exports.vitePluginDiscover = exports.viteDiscoverWithNpmDependency = exports.init = exports.initViteTemplate = exports.type = exports.support = exports.name = void 0;
|
|
3
|
+
exports.getDevModeHandle = exports.ɵcodegenPublicDirectory = exports.build = exports.discover = exports.vitePluginDiscover = exports.viteDiscoverWithNpmDependency = exports.init = exports.initViteTemplate = exports.DEFAULT_BUILD_SCRIPT = exports.type = exports.support = exports.name = void 0;
|
|
4
4
|
const child_process_1 = require("child_process");
|
|
5
5
|
const fs_1 = require("fs");
|
|
6
6
|
const fs_extra_1 = require("fs-extra");
|
|
@@ -8,10 +8,12 @@ const path_1 = require("path");
|
|
|
8
8
|
const __1 = require("..");
|
|
9
9
|
const proxy_1 = require("../../hosting/proxy");
|
|
10
10
|
const prompt_1 = require("../../prompt");
|
|
11
|
+
const utils_1 = require("../utils");
|
|
11
12
|
exports.name = "Vite";
|
|
12
13
|
exports.support = "experimental";
|
|
13
14
|
exports.type = 4;
|
|
14
15
|
const CLI_COMMAND = (0, path_1.join)("node_modules", ".bin", process.platform === "win32" ? "vite.cmd" : "vite");
|
|
16
|
+
exports.DEFAULT_BUILD_SCRIPT = ["vite build", "tsc && vite build"];
|
|
15
17
|
const initViteTemplate = (template) => async (setup) => await init(setup, template);
|
|
16
18
|
exports.initViteTemplate = initViteTemplate;
|
|
17
19
|
async function init(setup, baseTemplate = "vanilla") {
|
|
@@ -56,6 +58,7 @@ async function discover(dir, plugin, npmDependency) {
|
|
|
56
58
|
exports.discover = discover;
|
|
57
59
|
async function build(root) {
|
|
58
60
|
const { build } = (0, __1.relativeRequire)(root, "vite");
|
|
61
|
+
await (0, utils_1.warnIfCustomBuildScript)(root, exports.name, exports.DEFAULT_BUILD_SCRIPT);
|
|
59
62
|
await build({ root });
|
|
60
63
|
}
|
|
61
64
|
exports.build = build;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.deleteChannel = exports.updateChannel = exports.createChannel = exports.getChannel = exports.API_VERSION = void 0;
|
|
4
|
+
const apiv2_1 = require("../apiv2");
|
|
5
|
+
const api_1 = require("../api");
|
|
6
|
+
const lodash_1 = require("lodash");
|
|
7
|
+
const proto_1 = require("./proto");
|
|
8
|
+
exports.API_VERSION = "v1";
|
|
9
|
+
const client = new apiv2_1.Client({
|
|
10
|
+
urlPrefix: api_1.eventarcOrigin,
|
|
11
|
+
auth: true,
|
|
12
|
+
apiVersion: exports.API_VERSION,
|
|
13
|
+
});
|
|
14
|
+
async function getChannel(name) {
|
|
15
|
+
const res = await client.get(name);
|
|
16
|
+
if (res.status === 404) {
|
|
17
|
+
return undefined;
|
|
18
|
+
}
|
|
19
|
+
return res.body;
|
|
20
|
+
}
|
|
21
|
+
exports.getChannel = getChannel;
|
|
22
|
+
async function createChannel(channel) {
|
|
23
|
+
const pathParts = channel.name.split("/");
|
|
24
|
+
const res = await client.post(pathParts.slice(0, -1).join("/"), channel, {
|
|
25
|
+
queryParams: { channelId: (0, lodash_1.last)(pathParts) },
|
|
26
|
+
});
|
|
27
|
+
return res.body;
|
|
28
|
+
}
|
|
29
|
+
exports.createChannel = createChannel;
|
|
30
|
+
async function updateChannel(channel) {
|
|
31
|
+
const res = await client.put(channel.name, channel, {
|
|
32
|
+
queryParams: {
|
|
33
|
+
updateMask: (0, proto_1.fieldMasks)(channel).join(","),
|
|
34
|
+
},
|
|
35
|
+
});
|
|
36
|
+
return res.body;
|
|
37
|
+
}
|
|
38
|
+
exports.updateChannel = updateChannel;
|
|
39
|
+
async function deleteChannel(name) {
|
|
40
|
+
await client.delete(name);
|
|
41
|
+
}
|
|
42
|
+
exports.deleteChannel = deleteChannel;
|