new features, bookstack

This commit is contained in:
Matthias Hochmeister
2026-03-03 21:30:38 +01:00
parent 817329db70
commit d3561c1109
32 changed files with 1923 additions and 207 deletions

View File

@@ -0,0 +1,41 @@
import { Request, Response } from 'express';
import bookstackService from '../services/bookstack.service';
import environment from '../config/environment';
import logger from '../utils/logger';
class BookStackController {
async getRecent(_req: Request, res: Response): Promise<void> {
if (!environment.bookstack.url) {
res.status(200).json({ success: true, data: [], configured: false });
return;
}
try {
const pages = await bookstackService.getRecentPages();
res.status(200).json({ success: true, data: pages, configured: true });
} catch (error) {
logger.error('BookStackController.getRecent error', { error });
res.status(500).json({ success: false, message: 'BookStack konnte nicht abgefragt werden' });
}
}
async search(req: Request, res: Response): Promise<void> {
if (!environment.bookstack.url) {
res.status(200).json({ success: true, data: [], configured: false });
return;
}
const query = req.query.query as string | undefined;
if (!query || query.trim().length === 0) {
res.status(400).json({ success: false, message: 'Suchbegriff fehlt' });
return;
}
try {
const results = await bookstackService.searchPages(query.trim());
res.status(200).json({ success: true, data: results, configured: true });
} catch (error) {
logger.error('BookStackController.search error', { error });
res.status(500).json({ success: false, message: 'BookStack-Suche fehlgeschlagen' });
}
}
}
export default new BookStackController();

View File

@@ -325,6 +325,43 @@ class EventsController {
res.status(500).json({ success: false, message: 'Fehler beim Erstellen des Kalender-Exports' });
}
};
// -------------------------------------------------------------------------
// POST /api/events/import
// -------------------------------------------------------------------------
importEvents = async (req: Request, res: Response): Promise<void> => {
try {
const { events } = req.body as { events: unknown[] };
if (!Array.isArray(events) || events.length === 0) {
res.status(400).json({ success: false, message: 'Keine Ereignisse zum Importieren' });
return;
}
const userId = (req.user as any)?.id ?? 'unknown';
const created: number[] = [];
const errors: string[] = [];
for (let i = 0; i < events.length; i++) {
try {
const parsed = CreateVeranstaltungSchema.safeParse(events[i]);
if (!parsed.success) {
errors.push(`Zeile ${i + 2}: ${parsed.error.issues.map((e) => e.message).join(', ')}`);
continue;
}
await eventsService.createEvent(parsed.data, userId);
created.push(i);
} catch (e) {
errors.push(`Zeile ${i + 2}: ${e instanceof Error ? e.message : 'Unbekannter Fehler'}`);
}
}
res.status(200).json({
success: true,
data: { created: created.length, errors },
});
} catch (error) {
logger.error('importEvents error', { error });
res.status(500).json({ success: false, message: 'Import fehlgeschlagen' });
}
};
}
export default new EventsController();