- Add wechat-mp.service.ts for MP web authorization - Add wechat-mp.routes.ts with /api/mp endpoints - Update EntryQRCode.vue to show H5 URL QR code - Update HomeView.vue with WeChat auth detection Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
88 lines
2.3 KiB
TypeScript
88 lines
2.3 KiB
TypeScript
import express, { Application } from 'express';
|
|
import cors from 'cors';
|
|
import helmet from 'helmet';
|
|
import compression from 'compression';
|
|
import path from 'path';
|
|
import { fileURLToPath } from 'url';
|
|
import { dirname } from 'path';
|
|
import { config } from './config';
|
|
import { logger } from './utils/logger';
|
|
import { errorHandler } from './middleware/errorHandler';
|
|
import { requestLogger } from './middleware/requestLogger';
|
|
import voteRoutes from './routes/vote.routes';
|
|
import adminRoutes from './routes/admin.routes';
|
|
import scanRoutes from './routes/scan.routes';
|
|
import wechatRoutes from './routes/wechat.routes';
|
|
import wechatMpRoutes from './routes/wechat-mp.routes';
|
|
import publicRoutes from './routes/public.routes';
|
|
|
|
// ES Module __dirname equivalent
|
|
const __filename = fileURLToPath(import.meta.url);
|
|
const __dirname = dirname(__filename);
|
|
|
|
export const app: Application = express();
|
|
|
|
// CORS - must be before helmet
|
|
app.use(
|
|
cors({
|
|
origin: function (origin, callback) {
|
|
// Allow requests with no origin (like mobile apps or curl)
|
|
if (!origin) return callback(null, true);
|
|
|
|
const allowedOrigins = [
|
|
'http://localhost:5173',
|
|
'http://localhost:5174',
|
|
'http://192.168.1.5:5173',
|
|
'http://192.168.1.5:5174',
|
|
];
|
|
|
|
if (allowedOrigins.includes(origin)) {
|
|
callback(null, true);
|
|
} else {
|
|
console.log('CORS blocked origin:', origin);
|
|
callback(null, true); // Allow all for development
|
|
}
|
|
},
|
|
credentials: true,
|
|
})
|
|
);
|
|
|
|
// Security middleware
|
|
app.use(helmet());
|
|
|
|
// Compression
|
|
app.use(compression());
|
|
|
|
// Body parsing
|
|
app.use(express.json({ limit: '1mb' }));
|
|
app.use(express.urlencoded({ extended: true }));
|
|
|
|
// Request logging
|
|
app.use(requestLogger);
|
|
|
|
// Static files (for WeChat domain verification, etc.)
|
|
app.use(express.static(path.join(__dirname, '../public')));
|
|
|
|
// Health check
|
|
app.get('/health', (_req, res) => {
|
|
res.json({ status: 'ok', timestamp: new Date().toISOString() });
|
|
});
|
|
|
|
// API routes
|
|
app.use('/api/vote', voteRoutes);
|
|
app.use('/api/admin', adminRoutes);
|
|
app.use('/api/scan', scanRoutes);
|
|
app.use('/api/wechat', wechatRoutes);
|
|
app.use('/api/mp', wechatMpRoutes);
|
|
app.use('/api/public', publicRoutes);
|
|
|
|
// 404 handler
|
|
app.use((_req, res) => {
|
|
res.status(404).json({ error: 'Not Found' });
|
|
});
|
|
|
|
// Error handler
|
|
app.use(errorHandler);
|
|
|
|
export { logger };
|