@solidjs/start 2.0.0-alpha.2 → 2.0.0-beta.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/CHANGELOG.md +35 -0
- package/dist/config/constants.d.ts +3 -3
- package/dist/config/constants.js +1 -1
- package/dist/config/dev-server.js +9 -1
- package/dist/config/env.d.ts +19 -0
- package/dist/config/env.js +81 -0
- package/dist/config/fs-routes/fs-watcher.js +32 -28
- package/dist/config/fs-routes/index.js +2 -2
- package/dist/config/fs-routes/router.d.ts +8 -3
- package/dist/config/fs-routes/router.js +26 -13
- package/dist/config/fs-routes/tree-shake.js +0 -43
- package/dist/config/index.d.ts +16 -1
- package/dist/config/index.js +31 -31
- package/dist/config/lazy.js +4 -2
- package/dist/config/manifest.js +41 -7
- package/dist/config/vite-utils.d.ts +1 -1
- package/dist/directives/bubble-function-declaration.d.ts +3 -0
- package/dist/directives/bubble-function-declaration.js +23 -0
- package/dist/directives/compile.d.ts +9 -0
- package/dist/directives/compile.js +40 -0
- package/dist/directives/generate-unique-name.d.ts +3 -0
- package/dist/directives/generate-unique-name.js +16 -0
- package/dist/directives/get-descriptive-name.d.ts +2 -0
- package/dist/directives/get-descriptive-name.js +37 -0
- package/dist/directives/get-import-identifier.d.ts +4 -0
- package/dist/directives/get-import-identifier.js +19 -0
- package/dist/directives/get-root-statement-path.d.ts +2 -0
- package/dist/directives/get-root-statement-path.js +12 -0
- package/dist/directives/index.d.ts +14 -0
- package/dist/directives/index.js +170 -0
- package/dist/directives/is-statement-top-level.d.ts +3 -0
- package/dist/directives/is-statement-top-level.js +9 -0
- package/dist/directives/paths.d.ts +9 -0
- package/dist/directives/paths.js +36 -0
- package/dist/directives/plugin.d.ts +21 -0
- package/dist/directives/plugin.js +302 -0
- package/dist/directives/remove-unused-variables.d.ts +3 -0
- package/dist/directives/remove-unused-variables.js +66 -0
- package/dist/directives/types.d.ts +10 -0
- package/dist/directives/xxhash32.d.ts +6 -0
- package/dist/directives/xxhash32.js +193 -0
- package/dist/{server/server-runtime.d.ts → fns/client.d.ts} +1 -1
- package/dist/fns/client.js +106 -0
- package/dist/fns/handler.d.ts +5 -0
- package/dist/{server/server-functions-handler.js → fns/handler.js} +55 -96
- package/dist/fns/registration.d.ts +2 -0
- package/dist/fns/registration.js +12 -0
- package/dist/fns/serialization.d.ts +6 -0
- package/dist/fns/serialization.js +208 -0
- package/dist/fns/server.d.ts +7 -0
- package/dist/{server/server-fns-runtime.js → fns/server.js} +7 -1
- package/dist/fns/shared.d.ts +17 -0
- package/dist/fns/shared.js +105 -0
- package/dist/http/index.d.ts +1 -1
- package/dist/middleware/index.d.ts +17 -0
- package/dist/middleware/index.js +15 -0
- package/dist/server/handler.d.ts +61 -3
- package/dist/server/handler.js +18 -16
- package/dist/server/spa/handler.d.ts +30 -1
- package/dist/server/types.d.ts +1 -1
- package/dist/shared/dev-overlay/CodeView.jsx +4 -4
- package/dist/shared/dev-overlay/DevOverlayDialog.jsx +34 -34
- package/dist/shared/dev-overlay/index.jsx +2 -2
- package/dist/shared/dev-overlay/styles.css +40 -40
- package/dist/utils/debounce.d.ts +4 -0
- package/dist/utils/debounce.js +10 -0
- package/package.json +28 -21
- package/src/config/constants.ts +3 -3
- package/src/config/env.ts +105 -0
- package/src/config/fs-routes/fs-watcher.ts +38 -49
- package/src/config/fs-routes/index.ts +2 -2
- package/src/config/fs-routes/router.ts +29 -13
- package/src/config/fs-routes/tree-shake.ts +1 -48
- package/src/config/index.ts +45 -41
- package/src/config/lazy.ts +3 -2
- package/src/config/manifest.ts +45 -10
- package/src/config/vite-utils.ts +1 -1
- package/src/directives/bubble-function-declaration.ts +33 -0
- package/src/directives/compile.ts +54 -0
- package/src/directives/generate-unique-name.ts +22 -0
- package/src/directives/get-descriptive-name.ts +39 -0
- package/src/directives/get-import-identifier.ts +34 -0
- package/src/directives/get-root-statement-path.ts +14 -0
- package/src/directives/index.ts +233 -0
- package/src/directives/is-statement-top-level.ts +13 -0
- package/src/directives/paths.ts +63 -0
- package/src/directives/plugin.ts +389 -0
- package/src/directives/remove-unused-variables.ts +70 -0
- package/src/directives/types.ts +12 -0
- package/src/directives/xxhash32.ts +214 -0
- package/src/env.d.ts +1 -1
- package/src/fns/client.ts +141 -0
- package/src/fns/handler.spec.ts +85 -0
- package/src/{server/server-functions-handler.ts → fns/handler.ts} +65 -117
- package/src/fns/registration.ts +19 -0
- package/src/fns/serialization.ts +250 -0
- package/src/{server/server-fns-runtime.ts → fns/server.ts} +17 -2
- package/src/fns/shared.ts +116 -0
- package/src/middleware/index.ts +17 -0
- package/src/server/handler.ts +19 -17
- package/src/server/types.ts +1 -1
- package/src/shared/dev-overlay/CodeView.tsx +5 -7
- package/src/shared/dev-overlay/DevOverlayDialog.tsx +34 -34
- package/src/shared/dev-overlay/get-source-map.ts +1 -1
- package/src/shared/dev-overlay/index.tsx +4 -4
- package/src/shared/dev-overlay/styles.css +40 -40
- package/src/utils/debounce.ts +10 -0
- package/tsconfig.json +1 -0
- package/dist/server/fetchEvent.spec.js +0 -65
- package/dist/server/server-fns-runtime.d.ts +0 -1
- package/dist/server/server-functions-handler.d.ts +0 -2
- package/dist/server/server-runtime.js +0 -194
- package/src/server/server-runtime.ts +0 -240
- /package/dist/{server/fetchEvent.spec.d.ts → directives/types.js} +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,40 @@
|
|
|
1
1
|
# @solidjs/start
|
|
2
2
|
|
|
3
|
+
## 2.0.0-beta.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- 0a9fdc3: fix cloudflare
|
|
8
|
+
|
|
9
|
+
### Patch Changes
|
|
10
|
+
|
|
11
|
+
- 0c95804: Fix URL to path conversion in manifest resolver
|
|
12
|
+
- 6011e5a: Fixed changes in route files resulting in a reload instead of hot module replace. Reloads now only are triggered when adding or removing routes.
|
|
13
|
+
- 8fb81e6: Fixed niche edge cases in the server functions dead code removal (DCE) logic:
|
|
14
|
+
- Server functions only referenced in event handlers (e.g. `onClick`) now aren't considered unused and work properly.
|
|
15
|
+
- Unused variables in server functions no longer lead to compilation errors.
|
|
16
|
+
- 8d12d6a: Fixed tailwind class changes not getting applied via HMR in filesystem routes.
|
|
17
|
+
- ec1b82b: Included Vite 8 in the peer dependency range.
|
|
18
|
+
|
|
19
|
+
## 2.0.0-alpha.3
|
|
20
|
+
|
|
21
|
+
### Minor Changes
|
|
22
|
+
|
|
23
|
+
- 798b285: Updated dependencies.
|
|
24
|
+
- f6f0452: seroval json mode
|
|
25
|
+
- d4be1b6: Add new directives plugin with shorter function IDs and inner declaration support
|
|
26
|
+
- b9c4ade: feat: add `env:*` runtime environment variables support
|
|
27
|
+
|
|
28
|
+
### Patch Changes
|
|
29
|
+
|
|
30
|
+
- ff9607c: import DevEnvironment and Rollup as type from vite
|
|
31
|
+
- 6da636b: The server function directives runtime is now internally accessed via package.json exports instead of relative paths, fixing inconsistencies in the file resolution. Also the server functions file inclusion/exclusion patterns can now be configured in the start plugin options via `serverFunctions`.
|
|
32
|
+
- 2885905: fix: clone request headers in single-flight to avoid mutating immutable headers
|
|
33
|
+
- abe3979: reload ssr server when new route files are created in dev
|
|
34
|
+
- 7c288f6: Sanitize Location header value in streaming redirect script
|
|
35
|
+
- 6c83886: update seroval to 1.5.4
|
|
36
|
+
- 9d5d783: Add support for Vite 8 asset manifest loading
|
|
37
|
+
|
|
3
38
|
## 2.0.0-alpha.2
|
|
4
39
|
|
|
5
40
|
### Minor Changes
|
|
@@ -5,12 +5,12 @@ export declare const VIRTUAL_MODULES: {
|
|
|
5
5
|
readonly getClientManifest: "solid-start:get-client-manifest";
|
|
6
6
|
readonly getManifest: "solid-start:get-manifest";
|
|
7
7
|
readonly middleware: "solid-start:middleware";
|
|
8
|
-
readonly serverFnManifest: "
|
|
8
|
+
readonly serverFnManifest: "solid-start:server-fn-manifest";
|
|
9
9
|
readonly clientEntry: "solid-start:client-entry";
|
|
10
10
|
readonly serverEntry: "solid-start:server-entry";
|
|
11
11
|
readonly app: "solid-start:app";
|
|
12
12
|
};
|
|
13
13
|
export declare const VITE_ENVIRONMENTS: {
|
|
14
|
-
client:
|
|
15
|
-
server:
|
|
14
|
+
client: "client";
|
|
15
|
+
server: "ssr";
|
|
16
16
|
};
|
package/dist/config/constants.js
CHANGED
|
@@ -5,7 +5,7 @@ export const VIRTUAL_MODULES = {
|
|
|
5
5
|
getClientManifest: "solid-start:get-client-manifest",
|
|
6
6
|
getManifest: "solid-start:get-manifest",
|
|
7
7
|
middleware: "solid-start:middleware",
|
|
8
|
-
serverFnManifest: "
|
|
8
|
+
serverFnManifest: "solid-start:server-fn-manifest",
|
|
9
9
|
clientEntry: "solid-start:client-entry",
|
|
10
10
|
serverEntry: "solid-start:server-entry",
|
|
11
11
|
app: "solid-start:app",
|
|
@@ -1,3 +1,11 @@
|
|
|
1
|
+
var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExtension) || function (path, preserveJsx) {
|
|
2
|
+
if (typeof path === "string" && /^\.\.?\//.test(path)) {
|
|
3
|
+
return path.replace(/\.(tsx)$|((?:\.d)?)((?:\.[^./]+?)?)\.([cm]?)ts$/i, function (m, tsx, d, ext, cm) {
|
|
4
|
+
return tsx ? preserveJsx ? ".jsx" : ".js" : d && (!ext || !cm) ? m : (d + ext + "." + cm.toLowerCase() + "js");
|
|
5
|
+
});
|
|
6
|
+
}
|
|
7
|
+
return path;
|
|
8
|
+
};
|
|
1
9
|
import { NodeRequest, sendNodeResponse } from "srvx/node";
|
|
2
10
|
import { isRunnableDevEnvironment, } from "vite";
|
|
3
11
|
import { VITE_ENVIRONMENTS } from "./constants.js";
|
|
@@ -10,7 +18,7 @@ export function devServer() {
|
|
|
10
18
|
server.middlewares.use(async (req, res) => {
|
|
11
19
|
res.setHeader("content-encoding", "identity");
|
|
12
20
|
const webReq = new NodeRequest({ req, res });
|
|
13
|
-
const def = await import(process.cwd() + "/dist/server/entry-server.js");
|
|
21
|
+
const def = await import(__rewriteRelativeImportExtension(process.cwd() + "/dist/server/entry-server.js", true));
|
|
14
22
|
sendNodeResponse(res, await def.default.fetch(webReq));
|
|
15
23
|
});
|
|
16
24
|
};
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { type Plugin } from "vite";
|
|
2
|
+
declare const LOADERS: {
|
|
3
|
+
node: string;
|
|
4
|
+
"cloudflare-workers": string;
|
|
5
|
+
"netlify-edge": string;
|
|
6
|
+
};
|
|
7
|
+
export interface EnvPluginOptions {
|
|
8
|
+
server?: {
|
|
9
|
+
runtime?: keyof typeof LOADERS | (string & {});
|
|
10
|
+
load?: (mode: string) => Record<string, string>;
|
|
11
|
+
prefix?: string;
|
|
12
|
+
};
|
|
13
|
+
client?: {
|
|
14
|
+
load?: (mode: string) => Record<string, string>;
|
|
15
|
+
prefix?: string;
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
export declare function envPlugin(options?: EnvPluginOptions): Plugin;
|
|
19
|
+
export {};
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import { loadEnv } from "vite";
|
|
2
|
+
const LOADERS = {
|
|
3
|
+
node: `export default key => process.env[key];`,
|
|
4
|
+
"cloudflare-workers": `import { env } from 'cloudflare:workers';export default key => env[key];`,
|
|
5
|
+
"netlify-edge": `export default key => Netlify.env.get(key);`,
|
|
6
|
+
};
|
|
7
|
+
const SERVER_ENV = "env:server";
|
|
8
|
+
const CLIENT_ENV = "env:client";
|
|
9
|
+
const SERVER_RUNTIME_ENV = `${SERVER_ENV}/runtime`;
|
|
10
|
+
const SERVER_RUNTIME_LOADER = `${SERVER_RUNTIME_ENV}/loader`;
|
|
11
|
+
const DEFAULT_SERVER_PREFIX = "SERVER_";
|
|
12
|
+
const DEFAULT_CLIENT_PREFIX = "CLIENT_";
|
|
13
|
+
const SERVER_ONLY_MODULE = `throw new Error('Attempt to load server-only environment variables in client runtime.');`;
|
|
14
|
+
const SERVER_RUNTIME_CODE = `import load from '${SERVER_RUNTIME_LOADER}';
|
|
15
|
+
|
|
16
|
+
export default new Proxy({}, {
|
|
17
|
+
get(_, key) {
|
|
18
|
+
return load(key);
|
|
19
|
+
},
|
|
20
|
+
})`;
|
|
21
|
+
function convertObjectToModule(object) {
|
|
22
|
+
let result = "";
|
|
23
|
+
for (const key in object) {
|
|
24
|
+
result += `export const ${key} = ${JSON.stringify(object[key])};`;
|
|
25
|
+
}
|
|
26
|
+
return result;
|
|
27
|
+
}
|
|
28
|
+
export function envPlugin(options) {
|
|
29
|
+
const currentOptions = options ?? {};
|
|
30
|
+
let env;
|
|
31
|
+
const serverPrefix = currentOptions.server?.prefix ?? DEFAULT_SERVER_PREFIX;
|
|
32
|
+
const clientPrefix = currentOptions.client?.prefix ?? DEFAULT_CLIENT_PREFIX;
|
|
33
|
+
const runtime = options?.server?.runtime ?? "node";
|
|
34
|
+
const runtimeCode = runtime in LOADERS ? LOADERS[runtime] : runtime;
|
|
35
|
+
return {
|
|
36
|
+
name: "solid-start:env",
|
|
37
|
+
enforce: "pre",
|
|
38
|
+
configResolved(config) {
|
|
39
|
+
env = config.mode !== "production" ? "development" : "production";
|
|
40
|
+
},
|
|
41
|
+
resolveId(id) {
|
|
42
|
+
if (id === SERVER_ENV ||
|
|
43
|
+
id === CLIENT_ENV ||
|
|
44
|
+
id === SERVER_RUNTIME_ENV ||
|
|
45
|
+
id === SERVER_RUNTIME_LOADER) {
|
|
46
|
+
return id;
|
|
47
|
+
}
|
|
48
|
+
return undefined;
|
|
49
|
+
},
|
|
50
|
+
load(id, opts) {
|
|
51
|
+
if (id === SERVER_ENV) {
|
|
52
|
+
if (!opts?.ssr) {
|
|
53
|
+
return SERVER_ONLY_MODULE;
|
|
54
|
+
}
|
|
55
|
+
const vars = currentOptions.server?.load
|
|
56
|
+
? currentOptions.server.load(env)
|
|
57
|
+
: loadEnv(env, '.', serverPrefix);
|
|
58
|
+
return convertObjectToModule(vars);
|
|
59
|
+
}
|
|
60
|
+
if (id === CLIENT_ENV) {
|
|
61
|
+
const vars = currentOptions.client?.load
|
|
62
|
+
? currentOptions.client.load(env)
|
|
63
|
+
: loadEnv(env, '.', clientPrefix);
|
|
64
|
+
return convertObjectToModule(vars);
|
|
65
|
+
}
|
|
66
|
+
if (id === SERVER_RUNTIME_LOADER) {
|
|
67
|
+
if (!opts?.ssr) {
|
|
68
|
+
return SERVER_ONLY_MODULE;
|
|
69
|
+
}
|
|
70
|
+
return runtimeCode;
|
|
71
|
+
}
|
|
72
|
+
if (id === SERVER_RUNTIME_ENV) {
|
|
73
|
+
if (!opts?.ssr) {
|
|
74
|
+
return SERVER_ONLY_MODULE;
|
|
75
|
+
}
|
|
76
|
+
return SERVER_RUNTIME_CODE;
|
|
77
|
+
}
|
|
78
|
+
return undefined;
|
|
79
|
+
},
|
|
80
|
+
};
|
|
81
|
+
}
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { debounce } from "../../utils/debounce.js";
|
|
2
|
+
import { VITE_ENVIRONMENTS } from "../constants.js";
|
|
1
3
|
import { moduleId } from "./index.js";
|
|
2
4
|
function setupWatcher(watcher, routes) {
|
|
3
5
|
watcher.on("unlink", path => routes.removeRoute(path));
|
|
@@ -5,44 +7,46 @@ function setupWatcher(watcher, routes) {
|
|
|
5
7
|
watcher.on("change", path => routes.updateRoute(path));
|
|
6
8
|
}
|
|
7
9
|
function createRoutesReloader(server, routes, environment) {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
10
|
+
const devEnv = server.environments[environment];
|
|
11
|
+
if (!devEnv?.moduleGraph)
|
|
12
|
+
return;
|
|
13
|
+
/**
|
|
14
|
+
* Debounce catches multiple route changes in a row
|
|
15
|
+
* Short timeout for inexpensive invalidations
|
|
16
|
+
*/
|
|
17
|
+
const invalidateModule = debounce((mod) => {
|
|
18
|
+
devEnv.moduleGraph.invalidateModule(mod);
|
|
19
|
+
}, 0);
|
|
20
|
+
/**
|
|
21
|
+
* Long debounce timeout for expensive reloads
|
|
22
|
+
*/
|
|
23
|
+
const reloadModule = debounce((mod) => {
|
|
24
|
+
devEnv.reloadModule(mod);
|
|
25
|
+
}, 200);
|
|
26
|
+
return routes.on("reload", function handleRoutesReload(evt) {
|
|
27
|
+
const mod = devEnv.moduleGraph.getModuleById(moduleId);
|
|
28
|
+
if (!mod) {
|
|
29
|
+
devEnv.hot.send({ type: "full-reload" });
|
|
30
|
+
return;
|
|
21
31
|
}
|
|
22
|
-
|
|
23
|
-
//
|
|
24
|
-
|
|
25
|
-
const mod = moduleGraph.getModuleById(moduleId);
|
|
26
|
-
if (mod) {
|
|
27
|
-
const seen = new Set();
|
|
28
|
-
moduleGraph.invalidateModule(mod, seen);
|
|
29
|
-
server.reloadModule(mod);
|
|
30
|
-
}
|
|
32
|
+
if (environment === VITE_ENVIRONMENTS.client && evt.detail.type !== "update") {
|
|
33
|
+
// Client has to be reloaded when routes are added or removed
|
|
34
|
+
reloadModule(mod);
|
|
31
35
|
}
|
|
32
|
-
|
|
33
|
-
|
|
36
|
+
else {
|
|
37
|
+
invalidateModule(mod);
|
|
34
38
|
}
|
|
35
|
-
}
|
|
39
|
+
});
|
|
36
40
|
}
|
|
37
41
|
export const fileSystemWatcher = (routers) => {
|
|
38
42
|
const plugin = {
|
|
39
43
|
name: "fs-watcher",
|
|
40
44
|
async configureServer(server) {
|
|
41
|
-
|
|
42
|
-
const router =
|
|
45
|
+
for (const environment of [VITE_ENVIRONMENTS.server, VITE_ENVIRONMENTS.client]) {
|
|
46
|
+
const router = routers[environment];
|
|
43
47
|
setupWatcher(server.watcher, router);
|
|
44
48
|
createRoutesReloader(server, router, environment);
|
|
45
|
-
}
|
|
49
|
+
}
|
|
46
50
|
},
|
|
47
51
|
};
|
|
48
52
|
return plugin;
|
|
@@ -43,8 +43,8 @@ export function fsRoutes({ routers }) {
|
|
|
43
43
|
const buildId = `${v.src}?${v.pick.map((p) => `pick=${p}`).join("&")}`;
|
|
44
44
|
return {
|
|
45
45
|
src: relative(root, buildId),
|
|
46
|
-
build: isBuild ? `_$() => import(
|
|
47
|
-
import: `_$() => import(
|
|
46
|
+
build: isBuild ? `_$() => import('${buildId}')$_` : undefined,
|
|
47
|
+
import: `_$() => import('${buildId}')$_`,
|
|
48
48
|
};
|
|
49
49
|
}
|
|
50
50
|
return v;
|
|
@@ -10,6 +10,10 @@ type Route = {
|
|
|
10
10
|
} & Record<string, any>;
|
|
11
11
|
export declare function cleanPath(src: string, config: FileSystemRouterConfig): string;
|
|
12
12
|
export declare function analyzeModule(src: string): readonly [imports: readonly import("es-module-lexer").ImportSpecifier[], exports: readonly import("es-module-lexer").ExportSpecifier[], facade: boolean, hasModuleSyntax: boolean];
|
|
13
|
+
type RouterEvent = CustomEvent<{
|
|
14
|
+
route: string;
|
|
15
|
+
type: "update" | "remove" | "add";
|
|
16
|
+
}>;
|
|
13
17
|
export declare class BaseFileSystemRouter extends EventTarget {
|
|
14
18
|
routes: Route[];
|
|
15
19
|
config: FileSystemRouterConfig;
|
|
@@ -27,11 +31,12 @@ export declare class BaseFileSystemRouter extends EventTarget {
|
|
|
27
31
|
* To be attached by vite plugin to the vite dev server
|
|
28
32
|
*/
|
|
29
33
|
update: undefined;
|
|
30
|
-
_addRoute(route: Route):
|
|
34
|
+
_addRoute(route: Route): boolean;
|
|
31
35
|
addRoute(src: string): Promise<void>;
|
|
32
|
-
reload(route: string): void;
|
|
33
|
-
updateRoute(
|
|
36
|
+
reload(route: string, type: "update" | "remove" | "add"): void;
|
|
37
|
+
updateRoute(src_: string): Promise<void>;
|
|
34
38
|
removeRoute(src: string): void;
|
|
39
|
+
on(type: string, cb: (evt: RouterEvent) => void): () => void;
|
|
35
40
|
buildRoutesPromise?: Promise<any[]>;
|
|
36
41
|
getRoutes(): Promise<Route[]>;
|
|
37
42
|
}
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { init, parse } from "es-module-lexer";
|
|
2
2
|
import esbuild from "esbuild";
|
|
3
3
|
import fg from "fast-glob";
|
|
4
|
-
import fs from "fs";
|
|
4
|
+
import fs from "node:fs";
|
|
5
5
|
import micromatch from "micromatch";
|
|
6
|
-
import { posix } from "path";
|
|
6
|
+
import { posix } from "node:path";
|
|
7
7
|
import { pathToRegexp } from "path-to-regexp";
|
|
8
8
|
import { normalizePath } from "vite";
|
|
9
9
|
export { pathToRegexp };
|
|
@@ -71,8 +71,11 @@ export class BaseFileSystemRouter extends EventTarget {
|
|
|
71
71
|
*/
|
|
72
72
|
update = undefined;
|
|
73
73
|
_addRoute(route) {
|
|
74
|
-
|
|
74
|
+
const idx = this.routes.findIndex(r => r.path === route.path);
|
|
75
|
+
if (idx >= 0)
|
|
76
|
+
this.routes.splice(idx, 1);
|
|
75
77
|
this.routes.push(route);
|
|
78
|
+
return idx >= 0;
|
|
76
79
|
}
|
|
77
80
|
async addRoute(src) {
|
|
78
81
|
src = normalizePath(src);
|
|
@@ -81,7 +84,7 @@ export class BaseFileSystemRouter extends EventTarget {
|
|
|
81
84
|
const route = this.toRoute(src);
|
|
82
85
|
if (route) {
|
|
83
86
|
this._addRoute(route);
|
|
84
|
-
this.reload(route.path);
|
|
87
|
+
this.reload(route.path, "add");
|
|
85
88
|
}
|
|
86
89
|
}
|
|
87
90
|
catch (e) {
|
|
@@ -89,22 +92,25 @@ export class BaseFileSystemRouter extends EventTarget {
|
|
|
89
92
|
}
|
|
90
93
|
}
|
|
91
94
|
}
|
|
92
|
-
reload(route) {
|
|
93
|
-
this.dispatchEvent(new
|
|
94
|
-
// @ts-ignore
|
|
95
|
+
reload(route, type) {
|
|
96
|
+
this.dispatchEvent(new CustomEvent("reload", {
|
|
95
97
|
detail: {
|
|
96
98
|
route,
|
|
99
|
+
type,
|
|
97
100
|
},
|
|
98
101
|
}));
|
|
99
102
|
}
|
|
100
|
-
async updateRoute(
|
|
101
|
-
src = normalizePath(
|
|
103
|
+
async updateRoute(src_) {
|
|
104
|
+
const src = normalizePath(src_);
|
|
102
105
|
if (this.isRoute(src)) {
|
|
103
106
|
try {
|
|
104
107
|
const route = this.toRoute(src);
|
|
105
108
|
if (route) {
|
|
106
|
-
this._addRoute(route);
|
|
107
|
-
this.reload(route.path);
|
|
109
|
+
const updated = this._addRoute(route);
|
|
110
|
+
this.reload(route.path, updated ? "update" : "add");
|
|
111
|
+
}
|
|
112
|
+
else {
|
|
113
|
+
this.removeRoute(src_);
|
|
108
114
|
}
|
|
109
115
|
}
|
|
110
116
|
catch (e) {
|
|
@@ -120,10 +126,17 @@ export class BaseFileSystemRouter extends EventTarget {
|
|
|
120
126
|
if (path === undefined) {
|
|
121
127
|
return;
|
|
122
128
|
}
|
|
123
|
-
|
|
124
|
-
|
|
129
|
+
const idx = this.routes.findIndex(r => r.path === path);
|
|
130
|
+
if (idx === -1)
|
|
131
|
+
return;
|
|
132
|
+
this.routes.splice(idx, 1);
|
|
133
|
+
this.reload(path, "remove");
|
|
125
134
|
}
|
|
126
135
|
}
|
|
136
|
+
on(type, cb) {
|
|
137
|
+
this.addEventListener(type, cb);
|
|
138
|
+
return () => this.removeEventListener(type, cb);
|
|
139
|
+
}
|
|
127
140
|
buildRoutesPromise;
|
|
128
141
|
async getRoutes() {
|
|
129
142
|
if (!this.buildRoutesPromise) {
|
|
@@ -260,9 +260,6 @@ function treeShakeTransform({ types: t }) {
|
|
|
260
260
|
};
|
|
261
261
|
}
|
|
262
262
|
export function treeShake() {
|
|
263
|
-
let config;
|
|
264
|
-
const cache = {};
|
|
265
|
-
let server;
|
|
266
263
|
async function transform(id, code) {
|
|
267
264
|
const [path, queryString] = id.split("?");
|
|
268
265
|
const query = new URLSearchParams(queryString);
|
|
@@ -286,44 +283,6 @@ export function treeShake() {
|
|
|
286
283
|
return {
|
|
287
284
|
name: "tree-shake",
|
|
288
285
|
enforce: "pre",
|
|
289
|
-
configResolved(resolvedConfig) {
|
|
290
|
-
config = resolvedConfig;
|
|
291
|
-
},
|
|
292
|
-
configureServer(s) {
|
|
293
|
-
server = s;
|
|
294
|
-
},
|
|
295
|
-
async handleHotUpdate(ctx) {
|
|
296
|
-
if (cache[ctx.file]) {
|
|
297
|
-
const mods = [];
|
|
298
|
-
const newCode = await ctx.read();
|
|
299
|
-
for (const [id, code] of Object.entries(cache[ctx.file])) {
|
|
300
|
-
const transformed = await transform(id, newCode);
|
|
301
|
-
if (!transformed)
|
|
302
|
-
continue;
|
|
303
|
-
const { code: transformedCode } = transformed;
|
|
304
|
-
if (transformedCode !== code) {
|
|
305
|
-
const mod = server.moduleGraph.getModuleById(id);
|
|
306
|
-
if (mod)
|
|
307
|
-
mods.push(mod);
|
|
308
|
-
}
|
|
309
|
-
cache[ctx.file] ??= {};
|
|
310
|
-
cache[ctx.file][id] = transformedCode;
|
|
311
|
-
// server.moduleGraph.setModuleSource(id, code);
|
|
312
|
-
}
|
|
313
|
-
return mods;
|
|
314
|
-
}
|
|
315
|
-
// const mods = [];
|
|
316
|
-
// [...server.moduleGraph.urlToModuleMap.entries()].forEach(([url, m]) => {
|
|
317
|
-
// if (m.file === ctx.file && m.id.includes("pick=")) {
|
|
318
|
-
// if (!m.id.includes("pick=loader")) {
|
|
319
|
-
// mods.push(m);
|
|
320
|
-
// }
|
|
321
|
-
// }
|
|
322
|
-
// });
|
|
323
|
-
// return mods;
|
|
324
|
-
// // this.router.updateRoute(ctx.path);
|
|
325
|
-
// }
|
|
326
|
-
},
|
|
327
286
|
async transform(code, id) {
|
|
328
287
|
const [path, queryString] = id.split("?");
|
|
329
288
|
if (!path)
|
|
@@ -336,8 +295,6 @@ export function treeShake() {
|
|
|
336
295
|
const transformed = await transform(id, code);
|
|
337
296
|
if (!transformed?.code)
|
|
338
297
|
return;
|
|
339
|
-
cache[path] ??= {};
|
|
340
|
-
cache[path][id] = transformed.code;
|
|
341
298
|
return {
|
|
342
299
|
code: transformed.code,
|
|
343
300
|
map: transformed.map,
|
package/dist/config/index.d.ts
CHANGED
|
@@ -1,10 +1,25 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import type { PluginOption } from "vite";
|
|
2
2
|
import { type Options as SolidOptions } from "vite-plugin-solid";
|
|
3
|
+
import { type ServerFunctionsOptions } from "../directives/index.ts";
|
|
4
|
+
import { type EnvPluginOptions } from "./env.ts";
|
|
3
5
|
export interface SolidStartOptions {
|
|
4
6
|
solid?: Partial<SolidOptions>;
|
|
5
7
|
ssr?: boolean;
|
|
6
8
|
routeDir?: string;
|
|
7
9
|
extensions?: string[];
|
|
8
10
|
middleware?: string;
|
|
11
|
+
serialization?: {
|
|
12
|
+
/**
|
|
13
|
+
* The serialization mode to use for server functions/actions.
|
|
14
|
+
* The "js" mode uses a custom binary format that is more efficient than JSON, but requires a custom deserializer (with `eval()`) on the client.
|
|
15
|
+
* A strong CSP should block `eval()` executions, which would prevent the "js" mode from working.
|
|
16
|
+
* The "json" mode uses JSON for serialization, which is less efficient but can be deserialized with `JSON.parse` on the client.
|
|
17
|
+
*
|
|
18
|
+
* @default "json"
|
|
19
|
+
*/
|
|
20
|
+
mode?: "js" | "json";
|
|
21
|
+
};
|
|
22
|
+
env?: EnvPluginOptions;
|
|
23
|
+
serverFunctions?: Pick<ServerFunctionsOptions, "filter">;
|
|
9
24
|
}
|
|
10
25
|
export declare function solidStart(options?: SolidStartOptions): Array<PluginOption>;
|
package/dist/config/index.js
CHANGED
|
@@ -1,12 +1,11 @@
|
|
|
1
|
-
import { TanStackServerFnPlugin } from "@tanstack/server-functions-plugin";
|
|
2
1
|
import { defu } from "defu";
|
|
3
2
|
import { globSync } from "node:fs";
|
|
4
3
|
import { extname, isAbsolute, join } from "node:path";
|
|
5
|
-
import { fileURLToPath } from "node:url";
|
|
6
|
-
import { normalizePath } from "vite";
|
|
7
4
|
import solid from "vite-plugin-solid";
|
|
5
|
+
import { serverFunctionsPlugin } from "../directives/index.js";
|
|
8
6
|
import { DEFAULT_EXTENSIONS, VIRTUAL_MODULES, VITE_ENVIRONMENTS } from "./constants.js";
|
|
9
7
|
import { devServer } from "./dev-server.js";
|
|
8
|
+
import { envPlugin } from "./env.js";
|
|
10
9
|
import { SolidStartClientFileRouter, SolidStartServerFileRouter } from "./fs-router.js";
|
|
11
10
|
import { fsRoutes } from "./fs-routes/index.js";
|
|
12
11
|
import lazy from "./lazy.js";
|
|
@@ -38,6 +37,18 @@ export function solidStart(options) {
|
|
|
38
37
|
server: `${start.appRoot}/entry-server${entryExtension}`,
|
|
39
38
|
};
|
|
40
39
|
return [
|
|
40
|
+
// TODO (Alexis): check if the comment below is still relevant
|
|
41
|
+
//
|
|
42
|
+
// Must be placed after fsRoutes, as treeShake will remove the
|
|
43
|
+
// server fn exports added in by this plugin
|
|
44
|
+
serverFunctionsPlugin({
|
|
45
|
+
manifest: VIRTUAL_MODULES.serverFnManifest,
|
|
46
|
+
runtime: {
|
|
47
|
+
server: '@solidjs/start/fns/server',
|
|
48
|
+
client: '@solidjs/start/fns/client',
|
|
49
|
+
},
|
|
50
|
+
filter: options?.serverFunctions?.filter,
|
|
51
|
+
}),
|
|
41
52
|
{
|
|
42
53
|
name: "solid-start:config",
|
|
43
54
|
enforce: "pre",
|
|
@@ -67,6 +78,16 @@ export function solidStart(options) {
|
|
|
67
78
|
return {
|
|
68
79
|
appType: "custom",
|
|
69
80
|
build: { assetsDir: "_build/assets" },
|
|
81
|
+
optimizeDeps: {
|
|
82
|
+
// Suppress TS errors from Vite 7 types when configuring Vite 8's Rolldown
|
|
83
|
+
...{
|
|
84
|
+
rolldownOptions: {
|
|
85
|
+
transform: {
|
|
86
|
+
jsx: "react",
|
|
87
|
+
},
|
|
88
|
+
},
|
|
89
|
+
},
|
|
90
|
+
},
|
|
70
91
|
environments: {
|
|
71
92
|
[VITE_ENVIRONMENTS.client]: {
|
|
72
93
|
consumer: "client",
|
|
@@ -109,6 +130,9 @@ export function solidStart(options) {
|
|
|
109
130
|
}
|
|
110
131
|
: {}),
|
|
111
132
|
},
|
|
133
|
+
// Depending on the package manager and dependency structure Vite externalizes @solidjs/start
|
|
134
|
+
// This makes sure that @solidjs/start goes through the Vite build process
|
|
135
|
+
noExternal: ["@solidjs/start"],
|
|
112
136
|
},
|
|
113
137
|
define: {
|
|
114
138
|
"import.meta.env.MANIFEST": `globalThis.MANIFEST`,
|
|
@@ -118,6 +142,7 @@ export function solidStart(options) {
|
|
|
118
142
|
"import.meta.env.START_APP_ENTRY": JSON.stringify(appEntryPath),
|
|
119
143
|
"import.meta.env.START_CLIENT_ENTRY": JSON.stringify(handlers.client),
|
|
120
144
|
"import.meta.env.START_DEV_OVERLAY": JSON.stringify(start.devOverlay),
|
|
145
|
+
"import.meta.env.SEROVAL_MODE": JSON.stringify(start.serialization?.mode || "json"),
|
|
121
146
|
},
|
|
122
147
|
builder: {
|
|
123
148
|
sharedPlugins: true,
|
|
@@ -152,33 +177,7 @@ export function solidStart(options) {
|
|
|
152
177
|
},
|
|
153
178
|
}),
|
|
154
179
|
lazy(),
|
|
155
|
-
|
|
156
|
-
// server fn exports added in by this plugin
|
|
157
|
-
TanStackServerFnPlugin({
|
|
158
|
-
// This is the ID that will be available to look up and import
|
|
159
|
-
// our server function manifest and resolve its module
|
|
160
|
-
manifestVirtualImportId: VIRTUAL_MODULES.serverFnManifest,
|
|
161
|
-
directive: "use server",
|
|
162
|
-
callers: [
|
|
163
|
-
{
|
|
164
|
-
envConsumer: "client",
|
|
165
|
-
envName: VITE_ENVIRONMENTS.client,
|
|
166
|
-
getRuntimeCode: () => `import { createServerReference } from "${normalizePath(fileURLToPath(new URL("../server/server-runtime", import.meta.url)))}"`,
|
|
167
|
-
replacer: opts => `createServerReference('${opts.functionId}')`,
|
|
168
|
-
},
|
|
169
|
-
{
|
|
170
|
-
envConsumer: "server",
|
|
171
|
-
envName: VITE_ENVIRONMENTS.server,
|
|
172
|
-
getRuntimeCode: () => `import { createServerReference } from '${normalizePath(fileURLToPath(new URL("../server/server-fns-runtime", import.meta.url)))}'`,
|
|
173
|
-
replacer: opts => `createServerReference(${opts.fn}, '${opts.functionId}')`,
|
|
174
|
-
},
|
|
175
|
-
],
|
|
176
|
-
provider: {
|
|
177
|
-
envName: VITE_ENVIRONMENTS.server,
|
|
178
|
-
getRuntimeCode: () => `import { createServerReference } from '${normalizePath(fileURLToPath(new URL("../server/server-fns-runtime", import.meta.url)))}'`,
|
|
179
|
-
replacer: opts => `createServerReference(${opts.fn}, '${opts.functionId}')`,
|
|
180
|
-
},
|
|
181
|
-
}),
|
|
180
|
+
envPlugin(options?.env),
|
|
182
181
|
{
|
|
183
182
|
name: "solid-start:virtual-modules",
|
|
184
183
|
async resolveId(id) {
|
|
@@ -203,8 +202,9 @@ export function solidStart(options) {
|
|
|
203
202
|
{
|
|
204
203
|
name: "solid-start:capture-client-bundle",
|
|
205
204
|
enforce: "post",
|
|
206
|
-
generateBundle(
|
|
205
|
+
generateBundle(options, bundle) {
|
|
207
206
|
globalThis.START_CLIENT_BUNDLE = bundle;
|
|
207
|
+
globalThis.START_CLIENT_OUT_DIR = options.dir;
|
|
208
208
|
},
|
|
209
209
|
},
|
|
210
210
|
devServer(),
|
package/dist/config/lazy.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import babel from "@babel/core";
|
|
2
2
|
import * as t from "@babel/types";
|
|
3
|
-
import { sep as osSep } from "path";
|
|
4
|
-
import { basename, relative, sep } from "path/posix";
|
|
3
|
+
import { sep as osSep } from "node:path";
|
|
4
|
+
import { basename, relative, sep } from "node:path/posix";
|
|
5
5
|
import { VITE_ENVIRONMENTS } from "./constants.js";
|
|
6
6
|
const idTransform = (id) => {
|
|
7
7
|
return {
|
|
@@ -77,6 +77,8 @@ const lazy = () => {
|
|
|
77
77
|
// Therefore we skip, if the src doesn't have any import
|
|
78
78
|
if (src.indexOf("import") === -1)
|
|
79
79
|
return;
|
|
80
|
+
if (id.includes("entry-server"))
|
|
81
|
+
return;
|
|
80
82
|
const plugins = [];
|
|
81
83
|
const hasDefaultExport = src.indexOf("export default") !== -1;
|
|
82
84
|
if (hasDefaultExport) {
|