Skip to content

Commit

Permalink
improve module imports #264 (#338)
Browse files Browse the repository at this point in the history
  • Loading branch information
mateomorris authored Aug 23, 2023
1 parent ea98900 commit 084090b
Show file tree
Hide file tree
Showing 10 changed files with 734 additions and 338 deletions.
52 changes: 52 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,15 @@
"@fontsource/fira-code": "^5.0.5",
"@iconify/svelte": "^2.2.1",
"@primocms/builder": "^0.1.10",
"@rollup/browser": "^3.28.0",
"@supabase/auth-helpers-sveltekit": "^0.10.2",
"@supabase/supabase-js": "^2.31.0",
"axios": "^0.26.0",
"estree-walker": "^3.0.3",
"lodash-es": "^4.17.21",
"nanoid": "^3.1.23",
"promise-worker": "^2.0.1",
"resolve.exports": "^2.0.2",
"timeago.js": "^4.0.2"
},
"devDependencies": {
Expand Down
25 changes: 0 additions & 25 deletions src/compiler/lib/rollup-browser.js

This file was deleted.

233 changes: 120 additions & 113 deletions src/compiler/processors.js
Original file line number Diff line number Diff line change
@@ -1,129 +1,136 @@
import _ from 'lodash-es'
import _ from 'lodash-es';
import PromiseWorker from 'promise-worker';
import {get} from 'svelte/store'
import {site} from '@primocms/builder'
import {locale} from '@primocms/builder'
import rollupWorker from './workers/rollup.worker.js?worker'
import postCSSWorker from './workers/postcss.worker.js?worker'
import { get } from 'svelte/store';
import { site } from '@primocms/builder';
import { locale } from '@primocms/builder';
import rollupWorker from './workers/rollup.worker.js?worker';
import postCSSWorker from './workers/postcss.worker.js?worker';

const cssPromiseWorker = new PromiseWorker(new postCSSWorker());
const htmlPromiseWorker = new PromiseWorker(new rollupWorker());
const postcss_worker = new PromiseWorker(new postCSSWorker());
const rollup_worker = new PromiseWorker(new rollupWorker());

const componentsMap = new Map();
const COMPILED_COMPONENTS_CACHE = new Map();

export async function html({ component, buildStatic = true, format = 'esm'}) {
/**
* Compiles and renders a given component or page, caching the result.
* @async
* @param {Object} options - The options for rendering.
* @param {Object|Object[]} options.component - The component(s) to be rendered. Can be a single component or an array of components for a page.
* @param {boolean} [options.buildStatic=true] - Indicates whether to build the component statically or not.
* @param {string} [options.format='esm'] - The module format to use, such as 'esm' for ES Modules.
* @returns {Promise<Object>} Returns a payload containing the rendered HTML, CSS, JS, and other relevant data.
* @throws {Error} Throws an error if the compilation or rendering fails.
*/
export async function html({ component, buildStatic = true, format = 'esm' }) {
let cache_key;
if (!buildStatic) {
cache_key = JSON.stringify({
component,
format
});
if (COMPILED_COMPONENTS_CACHE.has(cache_key)) {
return COMPILED_COMPONENTS_CACHE.get(cache_key);
}
}

// return {
// error: 'none'
// }
const compile_page = Array.isArray(component);

let cacheKey
if (!buildStatic) {
cacheKey = JSON.stringify({
component,
format
})
if (componentsMap.has(cacheKey)) {
const cached = componentsMap.get(cacheKey)
return cached
}
}
let res;
try {
const has_js = compile_page ? component.some((s) => s.js) : !!component.js;
res = await rollup_worker.postMessage({
component,
hydrated: buildStatic && has_js,
buildStatic,
format,
site: get(site),
locale: get(locale)
});
} catch (e) {
console.log('error', e);
res = {
error: e.toString()
};
}

let res
try {
const has_js = Array.isArray(component) ? component.some(s => s.js) : !!component.js
res = await htmlPromiseWorker.postMessage({
component,
hydrated: buildStatic && has_js,
buildStatic,
format,
site: get(site),
locale: get(locale)
})
} catch(e) {
console.log('error', e)
res = {
error: e.toString()
}
}
let payload;

let final
if (!res) {
payload = {
html: '<h1 style="text-align: center">could not render</h1>'
};
res = {};
} else if (res.error) {
console.error(res.error);
payload = {
error: escapeHtml(res.error)
};
function escapeHtml(unsafe) {
return unsafe
.replace(/&/g, '&amp;')
.replace(/</g, '&lt;')
.replace(/>/g, '&gt;')
.replace(/"/g, '&quot;')
.replace(/'/g, '&#039;');
}
} else if (buildStatic) {
const blob = new Blob([res.ssr], { type: 'text/javascript' });
const url = URL.createObjectURL(blob);
const { default: App } = await import(url /* @vite-ignore */);
URL.revokeObjectURL(url);

if (!res) {
final = {
html: '<h1 style="text-align: center">could not render</h1>'
}
res = {}
} else if (res.error) {
console.error(res.error)
final = {
error: escapeHtml(res.error)
}
function escapeHtml(unsafe) {
return unsafe
.replace(/&/g, "&amp;")
.replace(/</g, "&lt;")
.replace(/>/g, "&gt;")
.replace(/"/g, "&quot;")
.replace(/'/g, "&#039;");
}
} else if (buildStatic) {
const blob = new Blob([res.ssr], { type: 'text/javascript' });
const url = URL.createObjectURL(blob);
const {default:App} = await import(url/* @vite-ignore */)
let component_data;
if (compile_page) {
// get the component data for the page
component_data = component.reduce((accumulator, item, i) => {
if (!_.isEmpty(item.data)) {
accumulator[`component_${i}_props`] = item.data;
}
return accumulator;
}, {});
} else {
component_data = component.data;
}

let component_data
if (Array.isArray(component)) {
component_data = component.reduce((accumulator, item, i) => {
if (!_.isEmpty(item.data)) {
accumulator[`component_${i}_props`] = item.data
}
return accumulator;
}, {});
} else {
component_data = component.data
}
const rendered = App.render(component_data);

const rendered = App.render(component_data)
payload = {
head: rendered.head,
html: rendered.html,
css: rendered.css.code,
js: res.dom
};
} else {
payload = {
js: res.dom
};
}

final = {
head: rendered.head,
html: rendered.html,
css: rendered.css.code,
js: res.dom
}
} else {
final = {
js: res.dom
}
}
if (!buildStatic) {
COMPILED_COMPONENTS_CACHE.set(cache_key, payload);
}

if (!buildStatic) {
componentsMap.set(cacheKey, final)
}

return final
return payload;
}


const cssMap = new Map()
const cssMap = new Map();
export async function css(raw) {
// return {
// css: ''
// }
if (cssMap.has(raw)) {
return ({ css: cssMap.get(raw) })
}
const processed = await cssPromiseWorker.postMessage({
css: raw
})
if (processed.message) {
return {
error: processed.message
}
}
cssMap.set(raw, processed)
return {
css: processed
}
}
// return {
// css: ''
// }
if (cssMap.has(raw)) {
return { css: cssMap.get(raw) };
}
const processed = await postcss_worker.postMessage({
css: raw
});
if (processed.message) {
return {
error: processed.message
};
}
cssMap.set(raw, processed);
return {
css: processed
};
}
Loading

0 comments on commit 084090b

Please sign in to comment.