Watching config change; update over MessageChannel

Co-authored-by: Jack Palmer <UsainBloot@users.noreply.github.com>
Co-authored-by: Patrik Oldsberg <poldsberg@gmail.com>
Co-authored-by: Vincenzo Scamporlino <vincenzos@spotify.com>
Signed-off-by: Philipp Hugenroth <philipph@spotify.com>
This commit is contained in:
Philipp Hugenroth
2023-07-12 14:57:54 +02:00
parent cc17a45e28
commit 2a56c3d075
5 changed files with 40 additions and 8 deletions
@@ -91,11 +91,16 @@ export async function startFrontend(options: StartAppOptions) {
checkReactVersion();
const configChannel = new MessageChannel();
const { name } = await fs.readJson(paths.resolveTarget('package.json'));
const config = await loadCliConfig({
args: options.configPaths,
fromPackage: name,
withFilteredKeys: true,
watch(appConfigs) {
configChannel.port1.postMessage(appConfigs);
},
});
const appBaseUrl = config.frontendConfig.getString('app.baseUrl');
@@ -119,6 +124,7 @@ export async function startFrontend(options: StartAppOptions) {
const waitForExit = await serveBundle({
entry: options.entry,
checksEnabled: options.checksEnabled,
configChannel,
...config,
});
+4 -6
View File
@@ -117,12 +117,6 @@ export async function createConfig(
}),
);
plugins.push(
new webpack.EnvironmentPlugin({
APP_CONFIG: options.frontendAppConfigs,
}),
);
plugins.push(
new HtmlWebpackPlugin({
template: paths.targetHtml,
@@ -137,6 +131,10 @@ export async function createConfig(
plugins.push(
new webpack.DefinePlugin({
'process.env.BUILD_INFO': JSON.stringify(buildInfo),
'process.env.APP_CONFIG': webpack.DefinePlugin.runtimeValue(
() => JSON.stringify(options.getFrontendAppConfigs()),
true,
),
}),
);
+13
View File
@@ -21,6 +21,7 @@ import openBrowser from 'react-dev-utils/openBrowser';
import { createConfig, resolveBaseUrl } from './config';
import { ServeOptions } from './types';
import { resolveBundlingPaths } from './paths';
import { AppConfig } from '@backstage/config';
export async function serveBundle(options: ServeOptions) {
const url = resolveBaseUrl(options.frontendConfig);
@@ -32,6 +33,8 @@ export async function serveBundle(options: ServeOptions) {
Number(url.port) ||
(url.protocol === 'https:' ? 443 : 80);
let latestFrontendAppConfigs = options.frontendAppConfigs;
const paths = resolveBundlingPaths(options);
const pkgPath = paths.targetPackageJson;
const pkg = await fs.readJson(pkgPath);
@@ -39,6 +42,9 @@ export async function serveBundle(options: ServeOptions) {
...options,
isDev: true,
baseUrl: url,
getFrontendAppConfigs: () => {
return latestFrontendAppConfigs;
},
});
const compiler = webpack(config);
@@ -95,6 +101,13 @@ export async function serveBundle(options: ServeOptions) {
});
});
options.configChannel.port2.onmessage = ({
data,
}: MessageEvent<AppConfig[]>) => {
latestFrontendAppConfigs = data;
server.invalidate();
};
const waitForExit = async () => {
for (const signal of ['SIGINT', 'SIGTERM'] as const) {
process.on(signal, () => {
+2 -1
View File
@@ -22,7 +22,7 @@ export type BundlingOptions = {
checksEnabled: boolean;
isDev: boolean;
frontendConfig: Config;
frontendAppConfigs: AppConfig[];
getFrontendAppConfigs(): AppConfig[];
baseUrl: URL;
parallelism?: number;
};
@@ -32,6 +32,7 @@ export type ServeOptions = BundlingPathsOptions & {
frontendConfig: Config;
frontendAppConfigs: AppConfig[];
fullConfig: Config;
configChannel: MessageChannel;
};
export type BuildOptions = BundlingPathsOptions & {
+15 -1
View File
@@ -19,7 +19,7 @@ import {
loadConfig,
loadConfigSchema,
} from '@backstage/config-loader';
import { ConfigReader } from '@backstage/config';
import { AppConfig, ConfigReader } from '@backstage/config';
import { paths } from './paths';
import { isValidUrl } from './urls';
import { getPackages } from '@manypkg/get-packages';
@@ -33,6 +33,7 @@ type Options = {
withDeprecatedKeys?: boolean;
fullVisibility?: boolean;
strict?: boolean;
watch?: (newFrontendAppConfigs: AppConfig[]) => void;
};
export async function loadCliConfig(options: Options) {
@@ -80,6 +81,19 @@ export async function loadCliConfig(options: Options) {
: undefined,
configRoot: paths.targetRoot,
configTargets: configTargets,
watch: options.watch && {
onChange(newAppConfigs) {
const newFrontendAppConfigs = schema.process(newAppConfigs, {
visibility: options.fullVisibility
? ['frontend', 'backend', 'secret']
: ['frontend'],
withFilteredKeys: options.withFilteredKeys,
withDeprecatedKeys: options.withDeprecatedKeys,
ignoreSchemaErrors: !options.strict,
});
options.watch!(newFrontendAppConfigs);
},
},
});
// printing to stderr to not clobber stdout in case the cli command