opex792's picture
Upload 2 files
8c3c2a2 verified
import express from 'express';
import cors from 'cors';
import cron from 'node-cron';
import { initializeDatabase, refreshData, searchByName } from './database.js';
// --- Константы ---
const PORT = process.env.PORT || 7860;
const API_VERSION = "1.4";
// --- Настройка приложения Express ---
const app = express();
app.use(cors());
app.use(express.json());
let isReady = false;
// --- Middleware для проверки готовности ---
app.use((req, res, next) => {
if (!isReady && req.path !== '/health') {
return res.status(503).json({ message: 'Сервис временно недоступен, идет инициализация данных.', statusCode: 503 });
}
next();
});
// --- API Эндпоинты ---
app.get('/health', (req, res) => {
res.status(200).json({ status: isReady ? 'UP' : 'DOWN', message: isReady ? 'Сервис готов к работе' : 'Идет инициализация' });
});
app.get(`/v${API_VERSION}/movie/search`, async (req, res) => {
const { query, page, limit } = req.query;
if (!query) {
return res.status(400).json({ message: 'Параметр "query" является обязательным.', statusCode: 400 });
}
const pageNum = parseInt(page, 10) || 1;
const limitNum = Math.min(parseInt(limit, 10) || 10, 250);
try {
const { docs, total } = await searchByName(query, pageNum, limitNum);
const pages = Math.ceil(total / limitNum);
res.json({ docs, total, limit: limitNum, page: pageNum, pages });
} catch (e) {
console.error(`Ошибка при поиске по запросу "${query}":`, e);
res.status(500).json({ message: 'Внутренняя ошибка сервера при поиске.', error: e.message });
}
});
// --- Логика запуска сервера ---
(async () => {
try {
// ИСПРАВЛЕНИЕ: Получаем объект 'db' после инициализации.
const db = await initializeDatabase();
const needsRebuild = process.argv.includes('--rebuild-index');
// ИСПРАВЛЕНИЕ: Используем полученный 'db' для запроса.
const result = await db.get('SELECT COUNT(*) as count FROM movies');
const moviesCount = result.count;
if (needsRebuild || moviesCount === 0) {
if (needsRebuild) console.log('Обнаружен флаг --rebuild-index. Запуск принудительной переиндексации.');
if (moviesCount === 0) console.log('База данных пуста. Запуск первоначальной загрузки.');
await refreshData();
} else {
console.log(`В базе уже есть ${moviesCount} фильмов. Запуск в штатном режиме.`);
}
isReady = true;
console.log('✅ Сервис готов к приему запросов!');
app.listen(PORT, () => {
console.log(`🚀 Сервер поиска запущен на порту ${PORT}`);
console.log(`URL для поиска: http://localhost:${PORT}/v${API_VERSION}/movie/search`);
});
cron.schedule('0 3 * * *', async () => {
console.log('Начало планового ежедневного обновления данных...');
isReady = false;
try {
await refreshData();
} catch (error) {
console.error('Критическая ошибка во время планового обновления:', error);
}
isReady = true;
console.log('Плановое обновление завершено. Сервис снова готов к работе.');
}, { scheduled: true, timezone: "Europe/Moscow" });
} catch (e) {
console.error("❌ Критическая ошибка при запуске сервера:", e);
process.exit(1);
}
})();