mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-04 10:24:02 +00:00
A panel page loads the app with <base> pointing at the app's server, so addresses the app builds resolve against the document base instead of the page location, and hash updates stay on the page's own address. The dev server answers panel origins with CORS on the API routes too.
105 lines
3.5 KiB
JavaScript
105 lines
3.5 KiB
JavaScript
import { applicationHtmlPlugin } from './application-html.js';
|
|
import cesium from 'vite-plugin-cesium';
|
|
import { embedFramingPlugin } from './embed-framing.js';
|
|
|
|
/** Origins allowed to read the dev and preview servers' responses. */
|
|
export const PANEL_CORS_ORIGINS = Object.freeze([
|
|
/^https?:\/\/(?:(?:[^:]+\.)?localhost|127\.0\.0\.1|\[::1\])(?::\d+)?$/,
|
|
/^https:\/\/[a-z0-9]+\.claudemcpcontent\.com$/,
|
|
]);
|
|
|
|
/**
|
|
* Vite plugin answering cross-origin reads from PANEL_CORS_ORIGINS on every
|
|
* path. It runs ahead of the API middlewares, which Vite's own `cors` option
|
|
* would not cover.
|
|
*/
|
|
function panelCorsPlugin() {
|
|
const install = (server) => {
|
|
server.middlewares.use((req, res, next) => {
|
|
const origin = req.headers.origin;
|
|
if (
|
|
!origin ||
|
|
!PANEL_CORS_ORIGINS.some((allowed) => allowed.test(origin))
|
|
)
|
|
return next();
|
|
res.setHeader('Access-Control-Allow-Origin', origin);
|
|
res.setHeader('Vary', 'Origin');
|
|
if (req.method !== 'OPTIONS') return next();
|
|
res.setHeader('Access-Control-Allow-Methods', 'GET, HEAD, POST, OPTIONS');
|
|
res.setHeader(
|
|
'Access-Control-Allow-Headers',
|
|
req.headers['access-control-request-headers'] || '',
|
|
);
|
|
res.statusCode = 204;
|
|
res.end();
|
|
});
|
|
};
|
|
return {
|
|
name: 'panel-cors',
|
|
configureServer: install,
|
|
configurePreviewServer: install,
|
|
};
|
|
}
|
|
|
|
/** Build browser assets with explicit inputs; never load environment or providers. */
|
|
export function createBrowserViteConfig({
|
|
plugins = [],
|
|
publicDir,
|
|
googleApiKey,
|
|
cesiumToken,
|
|
host = 'localhost',
|
|
port = 4173,
|
|
command,
|
|
} = {}) {
|
|
return {
|
|
plugins: [
|
|
panelCorsPlugin(),
|
|
cesium(),
|
|
applicationHtmlPlugin(),
|
|
...plugins,
|
|
embedFramingPlugin(),
|
|
],
|
|
...(publicDir === undefined ? {} : { publicDir }),
|
|
// A production build must not clean the dependency cache a running dev
|
|
// server is still serving optimized module URLs from.
|
|
...(command === 'build' ? { cacheDir: 'node_modules/.vite-build' } : {}),
|
|
optimizeDeps: {
|
|
// First reached through the SDR worker or a dynamic import. Pre-bundle
|
|
// them at startup so first use cannot invalidate already-transformed
|
|
// URLs with Vite's "Outdated Optimize Dep" 504 response.
|
|
include: [
|
|
'@jtarrio/signals/demod/demodulator.js',
|
|
'@jtarrio/signals/demod/modes.js',
|
|
'@jtarrio/webrtlsdr/rtlsdr.js',
|
|
'egm96-universal',
|
|
],
|
|
},
|
|
server: {
|
|
host: host || 'localhost',
|
|
port: parseInt(port, 10) || 4173,
|
|
allowedHosts:
|
|
host === '0.0.0.0' || host === '::'
|
|
? true
|
|
: ['localhost', '127.0.0.1', '.local'],
|
|
fs: {
|
|
deny: ['.env', '.env.*', '*.{crt,pem}', '**/.git/**', '**/ENVIRONMENT'],
|
|
},
|
|
// Cross-origin reads: local pages, as Vite allows by default, plus the
|
|
// MCP Apps panels that load the app into a conversation (Claude's
|
|
// sandbox origins); see panelCorsPlugin. Development and preview only.
|
|
cors: { origin: PANEL_CORS_ORIGINS },
|
|
// These headers protect the document containing Provider Settings.
|
|
// Embed-mode documents are framable instead; see embed-framing.js.
|
|
headers: {
|
|
'X-Frame-Options': 'DENY',
|
|
'Content-Security-Policy': "frame-ancestors 'none'",
|
|
},
|
|
},
|
|
define: {
|
|
'import.meta.env.GOOGLE_MAPS_API_KEY': JSON.stringify(googleApiKey),
|
|
'import.meta.env.CESIUM_ION_TOKEN': JSON.stringify(cesiumToken),
|
|
},
|
|
build: { chunkSizeWarningLimit: 1500 },
|
|
};
|
|
}
|