Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions src/cli/domain/ocConfig.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,10 @@ export interface OpenComponentsConfig {
registries?: string[];
/** Development-specific configuration settings */
development?: {
/** JavaScript code to be included in the preview HTML's <head> section.
* Can be either a filepath to a JS script or inline JavaScript code.
*/
preload?: string;
/** Fallback configuration for when components cannot be found locally */
fallback?: {
/** URL of the fallback registry to use when components cannot be found locally */
Expand Down Expand Up @@ -41,6 +45,7 @@ type ParsedConfig = {
sourcePath?: string;
registries: string[];
development: {
preload?: string;
plugins: {
dynamic?: Record<string, string>;
static?: Record<string, string>;
Expand Down Expand Up @@ -84,6 +89,7 @@ function parseConfig(config: OpenComponentsConfig): ParsedConfig {
...config,
registries: config.registries || [],
development: {
preload: config.development?.preload,
plugins,
fallback: config.development?.fallback
}
Expand Down
5 changes: 3 additions & 2 deletions src/cli/facade/dev.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,9 @@ const dev = ({ local, logger }: { logger: Logger; local: Local }) =>

let fallbackRegistryUrl = opts.fallbackRegistryUrl;
let fallbackClient = false;
const localConfig = getOcConfig(componentsDir);
if (!fallbackRegistryUrl) {
try {
const localConfig = getOcConfig(componentsDir);
if (
!fallbackRegistryUrl &&
typeof localConfig.development?.fallback?.url === 'string'
Expand Down Expand Up @@ -207,7 +207,8 @@ const dev = ({ local, logger }: { logger: Logger; local: Local }) =>
path: path.resolve(componentsDir),
port,
templates: dependencies.templates,
verbosity: 1
verbosity: 1,
preload: localConfig.development?.preload
});

registerPlugins(registry);
Expand Down
25 changes: 25 additions & 0 deletions src/registry/domain/options-sanitiser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,31 @@ export default function optionsSanitiser(input: RegistryOptions): Config {
options.templates = [];
}

// Handle preload script - if it's a filepath, read the file content
if (
options.preload &&
!options.preload.includes(';') &&
!options.preload.includes('{')
) {
try {
const fs = require('node:fs');
const path = require('node:path');
const preloadPath = path.isAbsolute(options.preload)
? options.preload
: path.resolve(process.cwd(), options.preload);

if (fs.existsSync(preloadPath)) {
options.preload = fs.readFileSync(preloadPath, 'utf8');
}
} catch (error) {
// If file reading fails, keep the original value (might be inline JS)
console.warn(
`Warning: Could not read preload file "${options.preload}":`,
(error as Error).message
);
}
}

if (options.compileClient || options.compileClient !== false) {
const clientOptions =
typeof options.compileClient === 'boolean'
Expand Down
1 change: 1 addition & 0 deletions src/registry/routes/component-preview.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ function componentPreview(
: undefined,
href: res.conf.baseUrl,
liveReload,
preload: res.conf.preload,
qs: urlBuilder.queryString(req.query as any),
templates
})
Expand Down
2 changes: 2 additions & 0 deletions src/registry/views/preview.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export default function preview(vm: {
qs: string;
liveReload: string;
templates: TemplateInfo[];
preload?: string;
}): string {
const baseUrl = vm.href.replace('http://', '//').replace('https://', '//');
const { name, version } = vm.component;
Expand All @@ -18,6 +19,7 @@ export default function preview(vm: {
return `<!DOCTYPE html>
<html>
<head>
${vm.preload ? `<script>${vm.preload}</script>` : ''}
<style>
html, body {
width: 100%;
Expand Down
8 changes: 8 additions & 0 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -242,6 +242,14 @@ export interface Config<T = any> {
* If omitted there is no execution timeout.
*/
executionTimeout?: number;
/**
* JavaScript code to be included in the preview HTML's <head> section.
* Can be either a filepath to a JS script or inline JavaScript code.
*
* @example "path/to/script.js"
* @example "console.log('Hello from preload script');"
*/
preload?: string;
/**
* URL of a secondary registry that will be queried if a component cannot
* be found on this instance. A trailing slash is appended automatically.
Expand Down