Files
Dimension-47/server/src/main.ts
Alexander Zielonka 94335ecd12 feat: Charaktere-Modul mit Pathbuilder Import
Backend:
- Characters-Modul (CRUD, HP-Tracking, Conditions)
- Pathbuilder 2e JSON Import Service
- Claude API Integration für automatische Übersetzungen
- Translations-Modul mit Datenbank-Caching
- Prisma Schema erweitert (Character, Abilities, Skills, Feats, Items, Resources)

Frontend:
- Kampagnen-Detailseite mit Mitglieder- und Charakterverwaltung
- Charakter erstellen Modal
- Pathbuilder Import Modal (Datei-Upload + JSON-Paste)
- Logo-Integration (Dimension 47 + Zeasy)
- Cinzel Font für Branding

Weitere Änderungen:
- Auth 401 Redirect Fix für Login-Seite
- PROGRESS.md mit Projektfortschritt

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-18 20:36:44 +01:00

75 lines
2.3 KiB
TypeScript

import { NestFactory } from '@nestjs/core';
import { ValidationPipe } from '@nestjs/common';
import { SwaggerModule, DocumentBuilder } from '@nestjs/swagger';
import { ConfigService } from '@nestjs/config';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
const configService = app.get(ConfigService);
// Global prefix
app.setGlobalPrefix('api');
// Validation
app.useGlobalPipes(
new ValidationPipe({
whitelist: true,
forbidNonWhitelisted: true,
transform: true,
transformOptions: {
enableImplicitConversion: true,
},
}),
);
// CORS
const nodeEnv = configService.get<string>('NODE_ENV', 'development');
app.enableCors({
origin: (origin, callback) => {
// Allow requests with no origin (mobile apps, curl, etc.)
if (!origin) return callback(null, true);
// In development, allow all localhost origins
if (nodeEnv === 'development' && /^https?:\/\/localhost(:\d+)?$/.test(origin)) {
return callback(null, true);
}
// Check against configured origins
const corsOrigins = configService.get<string>('CORS_ORIGINS', 'http://localhost:3000,http://localhost:5173');
if (corsOrigins.split(',').includes(origin)) {
return callback(null, true);
}
callback(new Error('Not allowed by CORS'));
},
credentials: true,
});
// Swagger API Documentation
const config = new DocumentBuilder()
.setTitle('Dimension47 API')
.setDescription('TTRPG Campaign Management Platform API')
.setVersion('1.0')
.addBearerAuth()
.addTag('Auth', 'Authentication endpoints')
.addTag('Campaigns', 'Campaign management')
.addTag('Characters', 'Character management')
.addTag('Battle', 'Battle screen and combat')
.addTag('Documents', 'Document management')
.addTag('Library', 'Combatants and maps library')
.build();
const document = SwaggerModule.createDocument(app, config);
SwaggerModule.setup('api/docs', app, document);
// Start server
const port = configService.get<number>('PORT', 5000);
await app.listen(port);
console.log(`🚀 Dimension47 Server running on http://localhost:${port}`);
console.log(`📚 API Documentation: http://localhost:${port}/api/docs`);
}
bootstrap();