mesela yani

This commit is contained in:
salvacybersec
2025-11-11 14:05:20 +03:00
parent 9f53a34cfb
commit 7582813f20
3 changed files with 47 additions and 3 deletions

View File

@@ -14,7 +14,7 @@ RUN npm install
COPY frontend/ ./
# Build frontend (output will be in dist/)
RUN npm run build
RUN npm run build && test -f dist/index.html
# Stage 2: Backend + Runtime
FROM node:20-alpine

View File

@@ -15,6 +15,26 @@ const PORT = process.env.PORT || 3000;
// Security middleware - Helmet'i tamamen kaldır (CORS ve mixed content sorunları için)
// app.use(helmet()); // Geçici olarak devre dışı
// Basic CSP for SPA and assets to avoid white page due to blocked module scripts
// Allow self assets, inline/eval for Vite-built bundles, blobs/data, and API/websocket connections
app.use((req, res, next) => {
// Only set CSP for HTML responses later, but keeping a permissive default helps some browsers on preload
res.setHeader(
'Content-Security-Policy',
[
"default-src 'self' data: blob:;",
"script-src 'self' 'unsafe-inline' 'unsafe-eval' blob:;",
"style-src 'self' 'unsafe-inline';",
"img-src 'self' data: blob:;",
"font-src 'self' data:;",
"connect-src 'self' http: https: ws: wss:;",
"frame-ancestors 'self';",
'base-uri \'self\';',
].join(' ')
);
next();
});
// CORS - Her yerden erişime izin ver (tüm route'larda)
app.use((req, res, next) => {
res.header('Access-Control-Allow-Origin', '*');
@@ -51,12 +71,21 @@ app.use(express.static(path.join(__dirname, 'public'), {
res.set('Access-Control-Allow-Methods', 'GET, OPTIONS');
res.set('Access-Control-Allow-Headers', 'Content-Type, Accept, Origin');
res.set('Access-Control-Allow-Credentials', 'true');
// Ensure CSP also present on static (mainly harmless for non-HTML)
res.set('Content-Security-Policy',
"default-src 'self' data: blob:; script-src 'self' 'unsafe-inline' 'unsafe-eval' blob:; style-src 'self' 'unsafe-inline'; img-src 'self' data: blob:; font-src 'self' data:; connect-src 'self' http: https: ws: wss:; frame-ancestors 'self'; base-uri 'self';"
);
// Content-Type header'larını doğru ayarla
if (filePath.endsWith('.js')) {
// Serve ES modules correctly
res.set('Content-Type', 'application/javascript; charset=utf-8');
} else if (filePath.endsWith('.css')) {
res.set('Content-Type', 'text/css; charset=utf-8');
} else if (filePath.endsWith('.mjs')) {
res.set('Content-Type', 'application/javascript; charset=utf-8');
} else if (filePath.endsWith('.svg')) {
res.set('Content-Type', 'image/svg+xml');
}
}
}));
@@ -113,13 +142,20 @@ app.get('*', (req, res, next) => {
res.header('Access-Control-Allow-Origin', '*');
res.header('Access-Control-Allow-Methods', 'GET, OPTIONS');
res.header('Access-Control-Allow-Headers', 'Content-Type');
// Explicit CSP for HTML documents
res.setHeader(
'Content-Security-Policy',
"default-src 'self' data: blob:; script-src 'self' 'unsafe-inline' 'unsafe-eval' blob:; style-src 'self' 'unsafe-inline'; img-src 'self' data: blob:; font-src 'self' data:; connect-src 'self' http: https: ws: wss:; frame-ancestors 'self'; base-uri 'self';"
);
// Serve frontend index.html for all other routes
const frontendPath = path.join(__dirname, 'public', 'dist', 'index.html');
res.sendFile(frontendPath, (err) => {
if (err) {
// If frontend build doesn't exist, return 404
next();
// If frontend build doesn't exist, inform clearly
res.status(503).send(
'Frontend build not found. Please build the frontend (npm run build) and ensure dist is copied to backend/src/public/dist.'
);
}
});
});

View File

@@ -42,6 +42,14 @@ else
fi
fi
# Ensure frontend build exists before starting server
FRONTEND_INDEX="src/public/dist/index.html"
if [ ! -f "$FRONTEND_INDEX" ]; then
echo "❌ Frontend build not found at $FRONTEND_INDEX"
echo " Please run 'npm run build' in the frontend (or rebuild the Docker image) so the dist assets are available."
exit 1
fi
# Start the application
echo "✨ Starting server..."
exec "$@"