wesl-plugin 0.6.69 → 0.6.71
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/README.md +3 -3
- package/dist/{PluginExtension-N4JBtncl.d.mts → PluginExtension-CHxUB0-8.d.mts} +19 -3
- package/dist/{StaticExtension-BvgvwnkI.mjs → StaticExtension-Q8HMuFJa.mjs} +57 -66
- package/dist/WeslPlugin-CajtfXHH.mjs +7344 -0
- package/dist/{WeslPluginOptions-DHLy1_Dm.d.mts → WeslPluginOptions-kd-CXSl9.d.mts} +1 -1
- package/dist/pluginIndex.d.mts +11 -12
- package/dist/pluginIndex.mjs +31 -2
- package/dist/plugins/astro.d.mts +1 -2
- package/dist/plugins/astro.mjs +3 -3
- package/dist/plugins/esbuild.d.mts +3 -4
- package/dist/plugins/esbuild.mjs +2 -2
- package/dist/plugins/farm.d.mts +1 -2
- package/dist/plugins/farm.mjs +2 -2
- package/dist/plugins/nuxt.d.mts +1 -2
- package/dist/plugins/nuxt.mjs +2 -2
- package/dist/plugins/rollup.d.mts +3 -4
- package/dist/plugins/rollup.mjs +2 -2
- package/dist/plugins/rspack.d.mts +1 -2
- package/dist/plugins/rspack.mjs +2 -2
- package/dist/plugins/vite.d.mts +3 -4
- package/dist/plugins/vite.mjs +2 -2
- package/dist/plugins/webpack.d.mts +3 -4
- package/dist/plugins/webpack.mjs +2 -2
- package/package.json +3 -2
- package/src/PluginApi.ts +111 -53
- package/src/PluginExtension.ts +21 -2
- package/src/WeslPlugin.ts +96 -146
- package/src/defaultSuffixTypes.d.ts +6 -0
- package/src/extensions/LinkExtension.ts +9 -16
- package/src/extensions/ReflectExtension.ts +53 -0
- package/src/extensions/StaticExtension.ts +16 -30
- package/src/pluginIndex.ts +1 -0
- package/dist/WeslPlugin-C1pAE34o.mjs +0 -10077
package/README.md
CHANGED
|
@@ -96,10 +96,10 @@ export default {
|
|
|
96
96
|
|
|
97
97
|
### Conditions in Import Path
|
|
98
98
|
|
|
99
|
-
For `?static`, you can specify conditions
|
|
99
|
+
For `?static`, you can specify conditions as query parameters:
|
|
100
100
|
|
|
101
101
|
```ts
|
|
102
|
-
import wgsl from "./app.wesl
|
|
102
|
+
import wgsl from "./app.wesl?MOBILE=true&DEBUG=false&static";
|
|
103
103
|
```
|
|
104
104
|
|
|
105
105
|
## Configuration (wesl.toml)
|
|
@@ -124,7 +124,7 @@ import type { PluginExtension } from "wesl-plugin";
|
|
|
124
124
|
|
|
125
125
|
const myExtension: PluginExtension = {
|
|
126
126
|
extensionName: "myfeature", // enables ?myfeature imports
|
|
127
|
-
emitFn: async (shaderPath, api, conditions) => {
|
|
127
|
+
emitFn: async (shaderPath, api, conditions, options) => {
|
|
128
128
|
const sources = await api.weslSrc();
|
|
129
129
|
// Return JavaScript code as a string
|
|
130
130
|
return `export default ${JSON.stringify(sources)};`;
|
|
@@ -31,10 +31,16 @@ interface WeslTomlInfo {
|
|
|
31
31
|
}
|
|
32
32
|
//#endregion
|
|
33
33
|
//#region src/PluginExtension.d.ts
|
|
34
|
-
/** function type required for
|
|
34
|
+
/** function type required for emit extensions */
|
|
35
35
|
type ExtensionEmitFn = (/** absolute path to the shader to which the extension is attached */
|
|
36
|
+
|
|
36
37
|
shaderPath: string, /** support functions available to plugin extensions */
|
|
37
|
-
|
|
38
|
+
|
|
39
|
+
pluginApi: PluginExtensionApi, /** static conditions specified on the js import */
|
|
40
|
+
|
|
41
|
+
conditions?: Record<string, boolean>, /** plugin-level options from query params (e.g., { include: "all" }) */
|
|
42
|
+
|
|
43
|
+
options?: Record<string, string>) => Promise<string>;
|
|
38
44
|
/** an extension that runs inside the wesl-js build plugin */
|
|
39
45
|
interface PluginExtension extends WeslJsPlugin {
|
|
40
46
|
/** javascript imports with this suffix will trigger the plugin */
|
|
@@ -43,6 +49,10 @@ interface PluginExtension extends WeslJsPlugin {
|
|
|
43
49
|
* e.g. import myPluginJs from "./foo.wesl?myPlugin"; */
|
|
44
50
|
emitFn: ExtensionEmitFn;
|
|
45
51
|
}
|
|
52
|
+
interface ProjectSources {
|
|
53
|
+
weslSrc: Record<string, string>;
|
|
54
|
+
dependencies: string[];
|
|
55
|
+
}
|
|
46
56
|
/** api supplied to plugin extensions */
|
|
47
57
|
interface PluginExtensionApi {
|
|
48
58
|
weslToml: () => Promise<WeslTomlInfo>;
|
|
@@ -50,6 +60,12 @@ interface PluginExtensionApi {
|
|
|
50
60
|
weslRegistry: () => Promise<BatchModuleResolver>;
|
|
51
61
|
weslMain: (baseId: string) => Promise<string>;
|
|
52
62
|
weslDependencies: () => Promise<string[]>;
|
|
63
|
+
/** weslRoot relative to tomlDir, with forward slashes. */
|
|
64
|
+
debugWeslRoot: () => Promise<string>;
|
|
65
|
+
/** Get weslSrc scoped to modules reachable from a root, plus their deps. */
|
|
66
|
+
scopedProject: (rootModuleName: string) => Promise<ProjectSources>;
|
|
67
|
+
/** Fetch project sources, either all or scoped to reachable modules. */
|
|
68
|
+
fetchProject: (rootModuleName: string, options?: Record<string, string>) => Promise<ProjectSources>;
|
|
53
69
|
}
|
|
54
70
|
//#endregion
|
|
55
|
-
export { PluginExtension as n, PluginExtensionApi as r, ExtensionEmitFn as t };
|
|
71
|
+
export { ProjectSources as i, PluginExtension as n, PluginExtensionApi as r, ExtensionEmitFn as t };
|
|
@@ -14,12 +14,9 @@ const linkBuildExtension = {
|
|
|
14
14
|
emitFn: emitLinkJs
|
|
15
15
|
};
|
|
16
16
|
/** Emit a JavaScript LinkParams structure, ready for linking at runtime. */
|
|
17
|
-
async function emitLinkJs(baseId, api) {
|
|
18
|
-
const { resolvedRoot, tomlDir } = await api.weslToml();
|
|
19
|
-
const weslSrc = await api.weslSrc();
|
|
17
|
+
async function emitLinkJs(baseId, api, _conditions, options) {
|
|
20
18
|
const rootModuleName = noSuffix(await api.weslMain(baseId));
|
|
21
|
-
const debugWeslRoot =
|
|
22
|
-
const autoDeps = await api.weslDependencies();
|
|
19
|
+
const [{ weslSrc, dependencies: autoDeps }, debugWeslRoot] = await Promise.all([api.fetchProject(rootModuleName, options), api.debugWeslRoot()]);
|
|
23
20
|
const sanitizedDeps = autoDeps.map((dep) => dep.replaceAll("/", "_"));
|
|
24
21
|
const bundleImports = autoDeps.map((p, i) => `import ${sanitizedDeps[i]} from "${p}";`).join("\n");
|
|
25
22
|
const paramsName = `link${path.basename(rootModuleName).replace(/\W/g, "_")}Config`;
|
|
@@ -165,8 +162,8 @@ codes.ERR_INVALID_PACKAGE_CONFIG = createError(
|
|
|
165
162
|
* @param {string} [base]
|
|
166
163
|
* @param {string} [message]
|
|
167
164
|
*/
|
|
168
|
-
(path
|
|
169
|
-
return `Invalid package config ${path
|
|
165
|
+
(path, base, message) => {
|
|
166
|
+
return `Invalid package config ${path}${base ? ` while importing ${base}` : ""}${message ? `. ${message}` : ""}`;
|
|
170
167
|
},
|
|
171
168
|
Error
|
|
172
169
|
);
|
|
@@ -196,8 +193,8 @@ codes.ERR_MODULE_NOT_FOUND = createError(
|
|
|
196
193
|
* @param {string} base
|
|
197
194
|
* @param {boolean} [exactUrl]
|
|
198
195
|
*/
|
|
199
|
-
(path
|
|
200
|
-
return `Cannot find ${exactUrl ? "module" : "package"} '${path
|
|
196
|
+
(path, base, exactUrl = false) => {
|
|
197
|
+
return `Cannot find ${exactUrl ? "module" : "package"} '${path}' imported from ${base}`;
|
|
201
198
|
},
|
|
202
199
|
Error
|
|
203
200
|
);
|
|
@@ -235,8 +232,8 @@ codes.ERR_UNKNOWN_FILE_EXTENSION = createError(
|
|
|
235
232
|
* @param {string} extension
|
|
236
233
|
* @param {string} path
|
|
237
234
|
*/
|
|
238
|
-
(extension, path
|
|
239
|
-
return `Unknown file extension "${extension}" for ${path
|
|
235
|
+
(extension, path) => {
|
|
236
|
+
return `Unknown file extension "${extension}" for ${path}`;
|
|
240
237
|
},
|
|
241
238
|
TypeError
|
|
242
239
|
);
|
|
@@ -471,8 +468,8 @@ function getPackageScopeConfig(resolved) {
|
|
|
471
468
|
* @param {URL} url - The URL to get the package type for.
|
|
472
469
|
* @returns {PackageType}
|
|
473
470
|
*/
|
|
474
|
-
function getPackageType(url
|
|
475
|
-
return getPackageScopeConfig(url
|
|
471
|
+
function getPackageType(url) {
|
|
472
|
+
return getPackageScopeConfig(url).type;
|
|
476
473
|
}
|
|
477
474
|
|
|
478
475
|
//#endregion
|
|
@@ -537,8 +534,8 @@ function getDataProtocolModuleFormat(parsed) {
|
|
|
537
534
|
* @param {URL} url
|
|
538
535
|
* @returns {string}
|
|
539
536
|
*/
|
|
540
|
-
function extname(url
|
|
541
|
-
const pathname = url
|
|
537
|
+
function extname(url) {
|
|
538
|
+
const pathname = url.pathname;
|
|
542
539
|
let index = pathname.length;
|
|
543
540
|
while (index--) {
|
|
544
541
|
const code = pathname.codePointAt(index);
|
|
@@ -550,22 +547,22 @@ function extname(url$1) {
|
|
|
550
547
|
/**
|
|
551
548
|
* @type {ProtocolHandler}
|
|
552
549
|
*/
|
|
553
|
-
function getFileProtocolModuleFormat(url
|
|
554
|
-
const value = extname(url
|
|
550
|
+
function getFileProtocolModuleFormat(url, _context, ignoreErrors) {
|
|
551
|
+
const value = extname(url);
|
|
555
552
|
if (value === ".js") {
|
|
556
|
-
const packageType = getPackageType(url
|
|
553
|
+
const packageType = getPackageType(url);
|
|
557
554
|
if (packageType !== "none") return packageType;
|
|
558
555
|
return "commonjs";
|
|
559
556
|
}
|
|
560
557
|
if (value === "") {
|
|
561
|
-
const packageType = getPackageType(url
|
|
558
|
+
const packageType = getPackageType(url);
|
|
562
559
|
if (packageType === "none" || packageType === "commonjs") return "commonjs";
|
|
563
560
|
return "module";
|
|
564
561
|
}
|
|
565
|
-
const format
|
|
566
|
-
if (format
|
|
562
|
+
const format = extensionFormatMap[value];
|
|
563
|
+
if (format) return format;
|
|
567
564
|
if (ignoreErrors) return;
|
|
568
|
-
throw new ERR_UNKNOWN_FILE_EXTENSION(value, fileURLToPath(url
|
|
565
|
+
throw new ERR_UNKNOWN_FILE_EXTENSION(value, fileURLToPath(url));
|
|
569
566
|
}
|
|
570
567
|
function getHttpProtocolModuleFormat() {}
|
|
571
568
|
/**
|
|
@@ -573,10 +570,10 @@ function getHttpProtocolModuleFormat() {}
|
|
|
573
570
|
* @param {{parentURL: string}} context
|
|
574
571
|
* @returns {string | null}
|
|
575
572
|
*/
|
|
576
|
-
function defaultGetFormatWithoutErrors(url
|
|
577
|
-
const protocol = url
|
|
573
|
+
function defaultGetFormatWithoutErrors(url, context) {
|
|
574
|
+
const protocol = url.protocol;
|
|
578
575
|
if (!hasOwnProperty.call(protocolHandlers, protocol)) return null;
|
|
579
|
-
return protocolHandlers[protocol](url
|
|
576
|
+
return protocolHandlers[protocol](url, context, true) || null;
|
|
580
577
|
}
|
|
581
578
|
|
|
582
579
|
//#endregion
|
|
@@ -649,10 +646,10 @@ function emitInvalidSegmentDeprecation(target, request, match, packageJsonUrl, i
|
|
|
649
646
|
* @param {string} [main]
|
|
650
647
|
* @returns {void}
|
|
651
648
|
*/
|
|
652
|
-
function emitLegacyIndexDeprecation(url
|
|
649
|
+
function emitLegacyIndexDeprecation(url, packageJsonUrl, base, main) {
|
|
653
650
|
if (process.noDeprecation) return;
|
|
654
|
-
if (defaultGetFormatWithoutErrors(url
|
|
655
|
-
const urlPath = fileURLToPath(url
|
|
651
|
+
if (defaultGetFormatWithoutErrors(url, { parentURL: base.href }) !== "module") return;
|
|
652
|
+
const urlPath = fileURLToPath(url.href);
|
|
656
653
|
const packagePath = fileURLToPath(new URL$1(".", packageJsonUrl));
|
|
657
654
|
const basePath = fileURLToPath(base);
|
|
658
655
|
if (!main) process.emitWarning(`No "main" or "exports" field defined in the package.json for ${packagePath} resolving the main entry point "${urlPath.slice(packagePath.length)}", imported from ${basePath}.\nDefault "index" lookups for the main are deprecated for ES modules.`, "DeprecationWarning", "DEP0151");
|
|
@@ -662,9 +659,9 @@ function emitLegacyIndexDeprecation(url$1, packageJsonUrl, base, main) {
|
|
|
662
659
|
* @param {string} path
|
|
663
660
|
* @returns {Stats | undefined}
|
|
664
661
|
*/
|
|
665
|
-
function tryStatSync(path
|
|
662
|
+
function tryStatSync(path) {
|
|
666
663
|
try {
|
|
667
|
-
return statSync(path
|
|
664
|
+
return statSync(path);
|
|
668
665
|
} catch {}
|
|
669
666
|
}
|
|
670
667
|
/**
|
|
@@ -678,8 +675,8 @@ function tryStatSync(path$1) {
|
|
|
678
675
|
* @param {URL} url
|
|
679
676
|
* @returns {boolean}
|
|
680
677
|
*/
|
|
681
|
-
function fileExists(url
|
|
682
|
-
const stats = statSync(url
|
|
678
|
+
function fileExists(url) {
|
|
679
|
+
const stats = statSync(url, { throwIfNoEntry: false });
|
|
683
680
|
const isFile = stats ? stats.isFile() : void 0;
|
|
684
681
|
return isFile === null || isFile === void 0 ? false : isFile;
|
|
685
682
|
}
|
|
@@ -695,7 +692,7 @@ function legacyMainResolve(packageJsonUrl, packageConfig, base) {
|
|
|
695
692
|
if (packageConfig.main !== void 0) {
|
|
696
693
|
guess = new URL$1(packageConfig.main, packageJsonUrl);
|
|
697
694
|
if (fileExists(guess)) return guess;
|
|
698
|
-
const tries
|
|
695
|
+
const tries = [
|
|
699
696
|
`./${packageConfig.main}.js`,
|
|
700
697
|
`./${packageConfig.main}.json`,
|
|
701
698
|
`./${packageConfig.main}.node`,
|
|
@@ -703,9 +700,9 @@ function legacyMainResolve(packageJsonUrl, packageConfig, base) {
|
|
|
703
700
|
`./${packageConfig.main}/index.json`,
|
|
704
701
|
`./${packageConfig.main}/index.node`
|
|
705
702
|
];
|
|
706
|
-
let i
|
|
707
|
-
while (++i
|
|
708
|
-
guess = new URL$1(tries
|
|
703
|
+
let i = -1;
|
|
704
|
+
while (++i < tries.length) {
|
|
705
|
+
guess = new URL$1(tries[i], packageJsonUrl);
|
|
709
706
|
if (fileExists(guess)) break;
|
|
710
707
|
guess = void 0;
|
|
711
708
|
}
|
|
@@ -826,12 +823,12 @@ function resolvePackageTargetString(target, subpath, match, packageJsonUrl, base
|
|
|
826
823
|
if (subpath !== "" && !pattern && target[target.length - 1] !== "/") throw invalidPackageTarget(match, target, packageJsonUrl, internal, base);
|
|
827
824
|
if (!target.startsWith("./")) {
|
|
828
825
|
if (internal && !target.startsWith("../") && !target.startsWith("/")) {
|
|
829
|
-
let isURL
|
|
826
|
+
let isURL = false;
|
|
830
827
|
try {
|
|
831
828
|
new URL$1(target);
|
|
832
|
-
isURL
|
|
829
|
+
isURL = true;
|
|
833
830
|
} catch {}
|
|
834
|
-
if (!isURL
|
|
831
|
+
if (!isURL) return packageResolve(pattern ? RegExpPrototypeSymbolReplace.call(patternRegEx, target, () => subpath) : target + subpath, packageJsonUrl, conditions);
|
|
835
832
|
}
|
|
836
833
|
throw invalidPackageTarget(match, target, packageJsonUrl, internal, base);
|
|
837
834
|
}
|
|
@@ -1096,8 +1093,8 @@ function packageResolve(specifier, base, conditions) {
|
|
|
1096
1093
|
const packageConfig = getPackageScopeConfig(base);
|
|
1097
1094
|
/* c8 ignore next 16 */
|
|
1098
1095
|
if (packageConfig.exists) {
|
|
1099
|
-
const packageJsonUrl
|
|
1100
|
-
if (packageConfig.name === packageName && packageConfig.exports !== void 0 && packageConfig.exports !== null) return packageExportsResolve(packageJsonUrl
|
|
1096
|
+
const packageJsonUrl = pathToFileURL(packageConfig.pjsonPath);
|
|
1097
|
+
if (packageConfig.name === packageName && packageConfig.exports !== void 0 && packageConfig.exports !== null) return packageExportsResolve(packageJsonUrl, packageSubpath, packageConfig, base, conditions);
|
|
1101
1098
|
}
|
|
1102
1099
|
let packageJsonUrl = new URL$1("./node_modules/" + packageName + "/package.json", base);
|
|
1103
1100
|
let packageJsonPath = fileURLToPath(packageJsonUrl);
|
|
@@ -1111,12 +1108,12 @@ function packageResolve(specifier, base, conditions) {
|
|
|
1111
1108
|
packageJsonPath = fileURLToPath(packageJsonUrl);
|
|
1112
1109
|
continue;
|
|
1113
1110
|
}
|
|
1114
|
-
const packageConfig
|
|
1111
|
+
const packageConfig = read(packageJsonPath, {
|
|
1115
1112
|
base,
|
|
1116
1113
|
specifier
|
|
1117
1114
|
});
|
|
1118
|
-
if (packageConfig
|
|
1119
|
-
if (packageSubpath === ".") return legacyMainResolve(packageJsonUrl, packageConfig
|
|
1115
|
+
if (packageConfig.exports !== void 0 && packageConfig.exports !== null) return packageExportsResolve(packageJsonUrl, packageSubpath, packageConfig, base, conditions);
|
|
1116
|
+
if (packageSubpath === ".") return legacyMainResolve(packageJsonUrl, packageConfig, base);
|
|
1120
1117
|
return new URL$1(packageSubpath, packageJsonUrl);
|
|
1121
1118
|
} while (packageJsonPath.length !== lastPath.length);
|
|
1122
1119
|
throw new ERR_MODULE_NOT_FOUND(packageName, fileURLToPath(base), false);
|
|
@@ -1261,10 +1258,10 @@ function defaultResolve(specifier, context = {}) {
|
|
|
1261
1258
|
if (protocol === "node:") return { url: specifier };
|
|
1262
1259
|
if (parsed && parsed.protocol === "node:") return { url: specifier };
|
|
1263
1260
|
const conditions = getConditionsSet(context.conditions);
|
|
1264
|
-
const url
|
|
1261
|
+
const url = moduleResolve(specifier, new URL$1(parentURL), conditions, false);
|
|
1265
1262
|
return {
|
|
1266
|
-
url: url
|
|
1267
|
-
format: defaultGetFormatWithoutErrors(url
|
|
1263
|
+
url: url.href,
|
|
1264
|
+
format: defaultGetFormatWithoutErrors(url, { parentURL })
|
|
1268
1265
|
};
|
|
1269
1266
|
}
|
|
1270
1267
|
|
|
@@ -1301,34 +1298,28 @@ function resolve(specifier, parent) {
|
|
|
1301
1298
|
|
|
1302
1299
|
//#endregion
|
|
1303
1300
|
//#region src/extensions/StaticExtension.ts
|
|
1304
|
-
/**
|
|
1305
|
-
* a wesl-js ?static build extension that statically links from the root file
|
|
1306
|
-
* and emits a JavaScript file containing the linked wgsl string.
|
|
1307
|
-
*
|
|
1308
|
-
* use it like this:
|
|
1309
|
-
* import wgsl from "./shaders/app.wesl?static";
|
|
1310
|
-
*
|
|
1311
|
-
* or with conditions, like this:
|
|
1312
|
-
* import wgsl from "../shaders/foo/app.wesl MOBILE=true FUN SAFE=false ?static";
|
|
1313
|
-
*/
|
|
1301
|
+
/** Build extension for ?static imports: links WESL at build time, emits WGSL string. */
|
|
1314
1302
|
const staticBuildExtension = {
|
|
1315
1303
|
extensionName: "static",
|
|
1316
1304
|
emitFn: emitStaticJs
|
|
1317
1305
|
};
|
|
1318
|
-
/** Emit a
|
|
1319
|
-
async function emitStaticJs(baseId, api, conditions) {
|
|
1306
|
+
/** Emit a JS module exporting the statically linked WGSL string. */
|
|
1307
|
+
async function emitStaticJs(baseId, api, conditions, _options) {
|
|
1320
1308
|
const { resolvedRoot, tomlDir } = await api.weslToml();
|
|
1321
1309
|
const parentModule = url.pathToFileURL(path.join(tomlDir, "wesl.toml")).toString();
|
|
1322
|
-
const
|
|
1323
|
-
const
|
|
1324
|
-
|
|
1325
|
-
|
|
1326
|
-
|
|
1327
|
-
|
|
1310
|
+
const rootModuleName = noSuffix(await api.weslMain(baseId));
|
|
1311
|
+
const [weslSrc, dependencies] = await Promise.all([api.weslSrc(), api.weslDependencies()]);
|
|
1312
|
+
const libFileUrls = dependencies.map((d) => resolve(d, parentModule));
|
|
1313
|
+
const libs = (await Promise.all(libFileUrls.map((f) => import(f)))).map((m) => m.default);
|
|
1314
|
+
const { dest: wgsl } = await link({
|
|
1315
|
+
weslSrc,
|
|
1316
|
+
rootModuleName,
|
|
1328
1317
|
debugWeslRoot: path.relative(tomlDir, resolvedRoot).replaceAll(path.sep, "/"),
|
|
1329
1318
|
libs,
|
|
1330
1319
|
conditions
|
|
1331
|
-
})
|
|
1320
|
+
});
|
|
1321
|
+
return `
|
|
1322
|
+
export const wgsl = \`${wgsl}\`;
|
|
1332
1323
|
export default wgsl;
|
|
1333
1324
|
`;
|
|
1334
1325
|
}
|