Skip to content

Commit

Permalink
patching with greenwood super css
Browse files Browse the repository at this point in the history
  • Loading branch information
thescientist13 committed Jul 21, 2024
1 parent 0e73a76 commit 329a2d8
Showing 1 changed file with 101 additions and 102 deletions.
203 changes: 101 additions & 102 deletions patches/@greenwood+cli+0.30.0-alpha.4.patch
Original file line number Diff line number Diff line change
@@ -1,51 +1,74 @@
diff --git a/node_modules/@greenwood/cli/src/config/rollup.config.js b/node_modules/@greenwood/cli/src/config/rollup.config.js
index 7771d11..9c09c47 100644
index 7771d11..5d48e0c 100644
--- a/node_modules/@greenwood/cli/src/config/rollup.config.js
+++ b/node_modules/@greenwood/cli/src/config/rollup.config.js
@@ -21,7 +21,7 @@ function greenwoodResourceLoader (compilation) {
@@ -12,7 +12,9 @@ function cleanRollupId(id) {
return id.replace('\x00', '').replace('?commonjs-proxy', '');
}

-function greenwoodResourceLoader (compilation) {
+function greenwoodResourceLoader (compilation, browser = false) {
+ // ConstructableStylesheets, JSON Modules
+ const externalizedResources = ['css', 'json'];
const resourcePlugins = compilation.config.plugins.filter((plugin) => {
return plugin.type === 'resource';
}).map((plugin) => {
@@ -21,16 +23,29 @@ function greenwoodResourceLoader (compilation) {

return {
name: 'greenwood-resource-loader',
- async resolveId(id) {
- const normalizedId = cleanRollupId(id); // idUrl.pathname;
- const { projectDirectory, userWorkspace } = compilation.context;
-
- if (normalizedId.startsWith('.') && !normalizedId.startsWith(projectDirectory.pathname)) {
+ async resolveId(id, importer) {
const normalizedId = cleanRollupId(id); // idUrl.pathname;
const { projectDirectory, userWorkspace } = compilation.context;

@@ -29,8 +29,15 @@ function greenwoodResourceLoader (compilation) {
+ const normalizedId = cleanRollupId(id);
+ const { userWorkspace } = compilation.context;
+
+ // check for non bare paths and resolve them to the user's workspace
+ // or Greenwood's scratch dir, like when bundling inline <script> tags
+ if (normalizedId.startsWith('.')) {
+ const importerUrl = new URL(normalizedId, `file://${importer}`);
+ const extension = importerUrl.pathname.split('.').pop();
+ const external = externalizedResources.includes(extension) && browser && !importerUrl.searchParams.has('type');
+ const isUserWorkspaceUrl = importerUrl.pathname.startsWith(userWorkspace.pathname);
const prefix = normalizedId.startsWith('..') ? './' : '';
const userWorkspaceUrl = new URL(`${prefix}${normalizedId.replace(/\.\.\//g, '')}`, userWorkspace);
- const userWorkspaceUrl = new URL(`${prefix}${normalizedId.replace(/\.\.\//g, '')}`, userWorkspace);
-
- if (await checkResourceExists(userWorkspaceUrl)) {
- return normalizePathnameForWindows(userWorkspaceUrl);
+ // console.log('1111', { id, importer, userWorkspaceUrl });
+ if (await checkResourceExists(new URL(id, `file://${importer}`))) {
+ const external = userWorkspaceUrl.pathname.endsWith('.css') || userWorkspaceUrl.pathname.endsWith('.json');
+ // console.log({ external });
+ // if its not in the users workspace, we clean up the dot-dots and check that against the user's workspace
+ const resolvedUrl = isUserWorkspaceUrl
+ ? importerUrl
+ : new URL(`${prefix}${normalizedId.replace(/\.\.\//g, '')}`, userWorkspace);
+
+ // console.log({ normalizedId, importerUrl, external });
+ if (await checkResourceExists(resolvedUrl)) {
+ return {
+ id: normalizePathnameForWindows(new URL(id, `file://${importer}`)),
+ id: normalizePathnameForWindows(resolvedUrl),
+ external
+ };
}
}
},
@@ -364,6 +371,7 @@ function greenwoodImportMetaUrl(compilation) {
@@ -364,6 +379,7 @@ function greenwoodImportMetaUrl(compilation) {
};
},

+ // sync bundles from API routes to the corresponding API route's entry in the manifest (useful for adapters)
generateBundle(options, bundles) {
for (const bundle in bundles) {
const bundleExtension = bundle.split('.').pop();
@@ -398,6 +406,120 @@ function greenwoodImportMetaUrl(compilation) {
@@ -398,6 +414,120 @@ function greenwoodImportMetaUrl(compilation) {
};
}

+// sync externalized import attributes usages within browser scripts
+// to corresponding static bundles, instead of being bundled and shipped as JavaScript
+// e.g. import theme from './theme.css' with { type: 'css' }
+// -> import theme from './theme.ab345dcc.css' with { type: 'css' }
+//
+//
+// this includes:
+// - replace all instances of assert with with (until Rollup supports with keyword)
+// - sync externalized import attribute paths with bundled CSS paths
Expand All @@ -59,20 +82,20 @@ index 7771d11..9c09c47 100644
+ // TODO do we need to run all resource lifecycles here?
+ const that = this;
+ for (const bundle in bundles) {
+ // console.log({ bundle });
+ // console.log({ bundle });
+
+ if(!bundle.endsWith('.map')) {
+ console.log('sync import attributes', { bundle });
+ if (!bundle.endsWith('.map')) {
+ // console.log('sync import attributes', { bundle });
+ const { code } = bundles[bundle];
+ const ast = this.parse(code);
+
+
+ walk.simple(ast, {
+ // TOOO should really get import attributes through the actual AST, not sure if possible though...
+ ImportDeclaration(node) {
+ console.log('ImportDeclaration ########', node.source.raw);
+ const statement = code.slice(node.start, node.end);
+ // console.log('ImportDeclaration ########', node.source.raw);
+ // const statement = code.slice(node.start, node.end);
+ const { value } = node.source;
+ console.log({ value, statement });
+ // console.log({ value, statement });
+
+ // TODO will this also happen to module.css, need to filter somehow?
+ if (value.endsWith('.css') || value.endsWith('.json')) {
Expand All @@ -81,29 +104,29 @@ index 7771d11..9c09c47 100644
+ bundles[bundle].code = bundles[bundle].code.replace(/assert{/g, 'with{');
+
+ // check for app level assets, like say a shared theme.css
+ compilation.resources.forEach((resource, key) => {
+ compilation.resources.forEach((resource) => {
+ if (resource.sourcePathURL.pathname === new URL(value, compilation.context.projectDirectory).pathname) {
+ // console.log('$$$ found pre-bundled CSS!!!', resource.optimizedFileName);
+ // console.log('$$$ found pre-bundled CSS!!!', resource.optimizedFileName);
+ bundles[bundle].code = bundles[bundle].code.replace(value, `/${resource.optimizedFileName}`);
+ preBundled = true;
+ }
+ });
+
+ // otherwise emit "one-offs" as Rollup assets
+ if (!preBundled) {
+ console.log('#### not pre bundled', { value, bundle });
+ const source = fs.readFileSync(new URL(value, compilation.context.projectDirectory), 'utf-8')
+ // console.log('#### not pre bundled', { value, bundle });
+ const source = fs.readFileSync(new URL(value, compilation.context.projectDirectory), 'utf-8');
+ const type = 'asset';
+ const emitConfig = { type, name: value.split('/').pop(), source, needsCodeReference: true };
+ const ref = that.emitFile(emitConfig);
+ const importRef = `import.meta.ROLLUP_ASSET_URL_${ref}`;
+
+ console.log({ importRef });
+ // console.log({ importRef });
+ bundles[bundle].code = bundles[bundle].code.replace(value, `/${importRef}`);
+ if(!unbundledAssetsRefMapper[emitConfig.name]) {
+ if (!unbundledAssetsRefMapper[emitConfig.name]) {
+ unbundledAssetsRefMapper[emitConfig.name] = {
+ importers: [],
+ importRefs: [],
+ importRefs: []
+ };
+ }
+
Expand All @@ -123,50 +146,51 @@ index 7771d11..9c09c47 100644
+ // since it seems that Rollup will not do it after the bundling hook
+ // https://github.com/rollup/rollup/blob/v3.29.4/docs/plugin-development/index.md#generatebundle
+ writeBundle(options, bundles) {
+ console.log('WRITE BUNDLE', { unbundledAssetsRefMapper });
+ for(const asset in unbundledAssetsRefMapper) {
+ console.log({ asset });
+ const ext = asset.split('.').pop();
+ const key = asset.replace(`.${ext}`, '');
+ // console.log('WRITE BUNDLE', { unbundledAssetsRefMapper });
+ for (const asset in unbundledAssetsRefMapper) {
+ // console.log({ asset });
+ // const ext = asset.split('.').pop();
+ // const key = asset.replace(`.${ext}`, '');
+
+ for (const bundle in bundles) {
+ const { name, fileName } = bundles[bundle];
+ const { fileName } = bundles[bundle];
+ const hash = fileName.split('.')[fileName.split('.').length - 2];
+
+ // console.log(bundles[bundle])
+ console.log('CHECKING....', { bundle, fileName, name, key })
+ // console.log('CHECKING....', { bundle, fileName, name, key });
+
+ if(fileName.replace(`.${hash}`, '') === asset) {
+ console.log('MONEY!!!!!!', unbundledAssetsRefMapper[asset], fileName);
+ if (fileName.replace(`.${hash}`, '') === asset) {
+ // console.log('MONEY!!!!!!', unbundledAssetsRefMapper[asset], fileName);
+ unbundledAssetsRefMapper[asset].importers.forEach((importer, idx) => {
+ let contents = fs.readFileSync(new URL(`./${importer}`, compilation.context.outputDir), 'utf-8');
+
+ contents = contents.replace(unbundledAssetsRefMapper[asset].importRefs[idx], fileName);
+
+ fs.writeFileSync(new URL(`./${importer}`, compilation.context.outputDir), contents)
+ })
+
+ fs.writeFileSync(new URL(`./${importer}`, compilation.context.outputDir), contents);
+ });
+ }
+ }
+ console.log('====================')
+ // console.log('====================');
+ }
+ }
+ }
+
+ };
+
+}
+
+// TODO should rename this to something like getRollupConfigForBrowser
const getRollupConfigForScriptResources = async (compilation) => {
const { outputDir } = compilation.context;
const input = [...compilation.resources.values()]
@@ -416,11 +538,13 @@ const getRollupConfigForScriptResources = async (compilation) => {
@@ -416,11 +546,13 @@ const getRollupConfigForScriptResources = async (compilation) => {
dir: normalizePathnameForWindows(outputDir),
entryFileNames: '[name].[hash].js',
chunkFileNames: '[name].[hash].js',
+ assetFileNames: '[name].[hash].[ext]',
sourcemap: true
},
plugins: [
greenwoodResourceLoader(compilation),
- greenwoodResourceLoader(compilation),
+ greenwoodResourceLoader(compilation, true),
greenwoodSyncPageResourceBundlesPlugin(compilation),
+ greenwoodSyncImportAttributes(compilation),
greenwoodImportMetaUrl(compilation),
Expand Down Expand Up @@ -211,29 +235,21 @@ index e397396..8dbf281 100644

const finalBody = pageLayoutContents
diff --git a/node_modules/@greenwood/cli/src/lifecycles/bundle.js b/node_modules/@greenwood/cli/src/lifecycles/bundle.js
index 21636a9..b1b39a7 100644
index 21636a9..f3b814b 100644
--- a/node_modules/@greenwood/cli/src/lifecycles/bundle.js
+++ b/node_modules/@greenwood/cli/src/lifecycles/bundle.js
@@ -105,7 +105,7 @@ async function optimizeStaticPages(compilation, plugins) {
}

// clean up optimization markers
- const body = (await response.text()).replace(/data-gwd-opt=".*[a-z]"/g, '');
+ const body = (await response.text()).replace(/data-gwd-opt=".*?[a-z]"/g, '');

await fs.writeFile(new URL(`.${outputPath}`, outputDir), body);
})
@@ -353,10 +353,12 @@ const bundleCompilation = async (compilation) => {

console.info('bundling static assets...');

+ // need styles bundled first for usage with import attributes syncing in Rollup
+ await bundleStyleResources(compilation, optimizeResourcePlugins)
+ await bundleStyleResources(compilation, optimizeResourcePlugins);
+
await Promise.all([
await bundleApiRoutes(compilation),
await bundleScriptResources(compilation),
- await bundleScriptResources(compilation),
- await bundleStyleResources(compilation, optimizeResourcePlugins)
+ await bundleScriptResources(compilation)
]);

// bundleSsrPages depends on bundleScriptResources having run first
Expand All @@ -250,10 +266,10 @@ index 657ab4e..792f43c 100644
scratchDir: new URL(`file://${process.cwd()}/.greenwood/`)
},
diff --git a/node_modules/@greenwood/cli/src/plugins/resource/plugin-standard-css.js b/node_modules/@greenwood/cli/src/plugins/resource/plugin-standard-css.js
index b0cdbcb..deace8b 100644
index b0cdbcb..d8409ea 100644
--- a/node_modules/@greenwood/cli/src/plugins/resource/plugin-standard-css.js
+++ b/node_modules/@greenwood/cli/src/plugins/resource/plugin-standard-css.js
@@ -49,23 +49,27 @@ function bundleCss(body, url, compilation) {
@@ -49,23 +49,26 @@ function bundleCss(body, url, compilation) {
barePath = barePath.replace('/', '');
}

Expand All @@ -263,27 +279,24 @@ index b0cdbcb..deace8b 100644
: new URL(`./${barePath}`, userWorkspace);

if (fs.existsSync(locationUrl)) {
+ const isDev = process.env.__GWD_COMMAND__ === 'develop'; // eslint-disable-line no-underscore-dangle
const hash = hashString(fs.readFileSync(locationUrl, 'utf-8'));
const ext = barePath.split('.').pop();
- const hashedRoot = barePath.replace(`.${ext}`, `.${hash}.${ext}`);
-
+ const hashedRoot = isDev ? barePath : barePath.replace(`.${ext}`, `.${hash}.${ext}`);

- fs.mkdirSync(new URL(`./${path.dirname(barePath)}/`, outputDir), {
- recursive: true
- });
-
+ if (!isDev) {
+ fs.mkdirSync(new URL(`./${path.dirname(hashedRoot)}/`, outputDir), {
+ recursive: true
+ });

- fs.promises.copyFile(
- locationUrl,
- new URL(`./${hashedRoot}`, outputDir)
- );
+ const hashedRoot = process.env.__GWD_COMMAND__ === 'develop'
+ ? barePath
+ : barePath.replace(`.${ext}`, `.${hash}.${ext}`)
+
+ if (process.env.__GWD_COMMAND__ !== 'develop') {
+ fs.mkdirSync(new URL(`./${path.dirname(hashedRoot)}/`, outputDir), {
+ recursive: true
+ });
+
+ fs.promises.copyFile(
+ locationUrl,
+ new URL(`./${hashedRoot}`, outputDir)
Expand All @@ -292,11 +305,13 @@ index b0cdbcb..deace8b 100644

optimizedCss += `url('${basePath}${hashedRoot}')`;
} else {
@@ -304,39 +308,42 @@ class StandardCssResource extends ResourceInterface {
@@ -303,39 +306,25 @@ class StandardCssResource extends ResourceInterface {
});
}

async shouldIntercept(url, request) {
- async shouldIntercept(url, request) {
- const { pathname, searchParams } = url;
+ async shouldIntercept(url) {
+ const { pathname } = url;
const ext = pathname.split('.').pop();

Expand All @@ -307,53 +322,37 @@ index b0cdbcb..deace8b 100644
async intercept(url, request, response) {
- const contents = (await response.text()).replace(/\r?\n|\r/g, ' ').replace(/\\/g, '\\\\');
- const body = `const sheet = new CSSStyleSheet();sheet.replaceSync(\`${contents}\`);export default sheet;`;
+ let body = bundleCss(await response.text(), url, this.compilation);
+ let headers = {};

-
- return new Response(body, {
- headers: {
- 'Content-Type': 'text/javascript'
- }
- });
- }
+ if (request.headers.get('Accept')?.indexOf('text/javascript') >= 0 && !url.searchParams.has('type')) {
+ const contents = (body).replace(/\r?\n|\r/g, ' ').replace(/\\/g, '\\\\');
+ let body = bundleCss(await response.text(), url, this.compilation);
+ let headers = {};

- async shouldOptimize(url, response) {
- const { protocol, pathname, searchParams } = url;
- const isValidCss = pathname.split('.').pop() === this.extensions[0]
- && protocol === 'file:'
- && response.headers.get('Content-Type').indexOf(this.contentType) >= 0
- && searchParams.get('type') !== 'css';
+ body = `const sheet = new CSSStyleSheet();sheet.replaceSync(\`${contents}\`);export default sheet;`;
+ headers['Content-Type'] = 'text/javascript';
+ }
+ if (request.headers.get('Accept')?.indexOf('text/javascript') >= 0 && !url.searchParams.has('type')) {
+ const contents = body.replace(/\r?\n|\r/g, ' ').replace(/\\/g, '\\\\');

- return this.compilation.config.optimization !== 'none' && isValidCss;
+ return new Response(body, { headers });
}

- }
-
- async optimize(url, response) {
- const body = await response.text();
- const optimizedBody = bundleCss(body, url, this.compilation);
+ // async shouldOptimize(url, response) {
+ // const { protocol, pathname, searchParams } = url;
+ // const isValidCss = pathname.split('.').pop() === this.extensions[0]
+ // && protocol === 'file:'
+ // && response.headers.get('Content-Type').indexOf(this.contentType) >= 0
+ // && searchParams.get('type') !== 'css';
+ body = `const sheet = new CSSStyleSheet();sheet.replaceSync(\`${contents}\`);export default sheet;`;
+ headers['Content-Type'] = 'text/javascript';
+ }

- return new Response(optimizedBody);
- }
+ // return this.compilation.config.optimization !== 'none' && isValidCss;
+ // }
+
+ // async optimize(url, response) {
+ // const body = await response.text();
+ // const optimizedBody = bundleCss(body, url, this.compilation);
+
+ // return new Response(optimizedBody);
+ // }
+ return new Response(body, { headers });
}
}

const greenwoodPluginStandardCss = {

0 comments on commit 329a2d8

Please sign in to comment.