const { Pool } = require('pg'); const dotenv = require('dotenv'); const uuid = require('uuid'); dotenv.config(); const pool = new Pool({ connectionString: process.env.DATABASE_URL, }); async function createNotificationTables() { const client = await pool.connect(); try { await client.query('BEGIN'); console.log('Creating UUID extension if not exists...'); await client.query(` CREATE EXTENSION IF NOT EXISTS "uuid-ossp"; `); // Проверяем существование таблицы notifications const notificationsExists = await client.query(` SELECT EXISTS ( SELECT FROM information_schema.tables WHERE table_name = 'notifications' ) as exists `); if (!notificationsExists.rows[0].exists) { console.log('Creating notifications table...'); await client.query(` CREATE TABLE notifications ( id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), user_id UUID NOT NULL REFERENCES users(id) ON DELETE CASCADE, type VARCHAR(50) NOT NULL, data JSONB, is_read BOOLEAN DEFAULT FALSE, created_at TIMESTAMP DEFAULT NOW() ) `); console.log('Creating index on notifications...'); await client.query(` CREATE INDEX idx_notifications_user_id ON notifications (user_id); CREATE INDEX idx_notifications_type ON notifications (type); CREATE INDEX idx_notifications_created_at ON notifications (created_at); `); } else { console.log('Notifications table already exists.'); } // Проверяем существование таблицы scheduled_notifications const scheduledExists = await client.query(` SELECT EXISTS ( SELECT FROM information_schema.tables WHERE table_name = 'scheduled_notifications' ) as exists `); if (!scheduledExists.rows[0].exists) { console.log('Creating scheduled_notifications table...'); await client.query(` CREATE TABLE scheduled_notifications ( id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), user_id UUID NOT NULL REFERENCES users(id) ON DELETE CASCADE, type VARCHAR(50) NOT NULL, data JSONB, scheduled_at TIMESTAMP NOT NULL, processed BOOLEAN DEFAULT FALSE, created_at TIMESTAMP DEFAULT NOW() ) `); console.log('Creating index on scheduled_notifications...'); await client.query(` CREATE INDEX idx_scheduled_notifications_user_id ON scheduled_notifications (user_id); CREATE INDEX idx_scheduled_notifications_scheduled_at ON scheduled_notifications (scheduled_at); CREATE INDEX idx_scheduled_notifications_processed ON scheduled_notifications (processed); `); } else { console.log('Scheduled_notifications table already exists.'); } // Проверяем существование таблицы notification_templates const templatesExists = await client.query(` SELECT EXISTS ( SELECT FROM information_schema.tables WHERE table_name = 'notification_templates' ) as exists `); if (!templatesExists.rows[0].exists) { console.log('Creating notification_templates table...'); await client.query(` CREATE TABLE notification_templates ( id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), type VARCHAR(50) NOT NULL UNIQUE, title TEXT NOT NULL, message_template TEXT NOT NULL, button_template JSONB, created_at TIMESTAMP DEFAULT NOW(), updated_at TIMESTAMP DEFAULT NOW() ) `); } else { console.log('Notification_templates table already exists.'); } // Проверяем наличие колонки notification_settings в таблице users const settingsColumnExists = await client.query(` SELECT EXISTS ( SELECT FROM information_schema.columns WHERE table_name = 'users' AND column_name = 'notification_settings' ) as exists `); if (!settingsColumnExists.rows[0].exists) { console.log('Adding notification_settings column to users table...'); await client.query(` ALTER TABLE users ADD COLUMN notification_settings JSONB DEFAULT '{ "newMatches": true, "newMessages": true, "newLikes": true, "reminders": true, "dailySummary": true, "timePreference": "evening", "doNotDisturb": false }'::jsonb `); } else { console.log('Notification_settings column already exists in users table.'); } // Заполнение таблицы шаблонов уведомлений базовыми шаблонами if (!templatesExists.rows[0].exists) { console.log('Populating notification templates...'); const templates = [ { type: 'new_like', title: 'Новый лайк!', message_template: '❤️ *{{name}}* поставил(а) вам лайк!\n\nВозраст: {{age}}\n{{city}}\n\nОтветьте взаимностью или посмотрите профиль.', button_template: { inline_keyboard: [ [{ text: '👀 Посмотреть профиль', callback_data: 'view_profile:{{userId}}' }], [ { text: '❤️ Лайк в ответ', callback_data: 'like_back:{{userId}}' }, { text: '⛔️ Пропустить', callback_data: 'dislike_profile:{{userId}}' } ], [{ text: '💕 Открыть все лайки', callback_data: 'view_likes' }] ] } }, { type: 'super_like', title: 'Супер-лайк!', message_template: '⭐️ *{{name}}* отправил(а) вам супер-лайк!\n\nВозраст: {{age}}\n{{city}}\n\nВы произвели особое впечатление! Ответьте взаимностью или посмотрите профиль.', button_template: { inline_keyboard: [ [{ text: '👀 Посмотреть профиль', callback_data: 'view_profile:{{userId}}' }], [ { text: '❤️ Лайк в ответ', callback_data: 'like_back:{{userId}}' }, { text: '⛔️ Пропустить', callback_data: 'dislike_profile:{{userId}}' } ], [{ text: '💕 Открыть все лайки', callback_data: 'view_likes' }] ] } }, { type: 'new_match', title: 'Новый матч!', message_template: '🎊 *Ура! Это взаимно!* 🎊\n\nВы и *{{name}}* понравились друг другу!\nВозраст: {{age}}\n{{city}}\n\nСделайте первый шаг - напишите сообщение!', button_template: { inline_keyboard: [ [{ text: '💬 Начать общение', callback_data: 'open_chat:{{matchId}}' }], [ { text: '👀 Посмотреть профиль', callback_data: 'view_profile:{{userId}}' }, { text: '📋 Все матчи', callback_data: 'view_matches' } ] ] } }, { type: 'new_message', title: 'Новое сообщение!', message_template: '💌 *Новое сообщение!*\n\nОт: *{{name}}*\n\n"{{message}}"\n\nОтветьте на сообщение прямо сейчас!', button_template: { inline_keyboard: [ [{ text: '📩 Ответить', callback_data: 'open_chat:{{matchId}}' }], [ { text: '👤 Профиль', callback_data: 'view_profile:{{userId}}' }, { text: '📋 Все чаты', callback_data: 'view_matches' } ] ] } }, { type: 'match_reminder', title: 'Напоминание о матче', message_template: '💕 У вас есть матч с *{{name}}*, но вы еще не начали общение!\n\nНе упустите шанс познакомиться поближе!', button_template: { inline_keyboard: [ [{ text: '💬 Начать общение', callback_data: 'open_chat:{{matchId}}' }], [{ text: '👀 Посмотреть профиль', callback_data: 'view_profile:{{userId}}' }] ] } }, { type: 'inactive_matches', title: 'Неактивные матчи', message_template: '⏰ У вас {{count}} неактивных матчей!\n\nПродолжите общение, чтобы не упустить интересные знакомства!', button_template: { inline_keyboard: [ [{ text: '📋 Открыть матчи', callback_data: 'view_matches' }], [{ text: '💕 Смотреть новые анкеты', callback_data: 'start_browsing' }] ] } }, { type: 'like_summary', title: 'Сводка лайков', message_template: '💖 У вас {{count}} новых лайков!\n\nПосмотрите, кто проявил к вам интерес сегодня!', button_template: { inline_keyboard: [ [{ text: '👀 Посмотреть лайки', callback_data: 'view_likes' }], [{ text: '💕 Начать знакомиться', callback_data: 'start_browsing' }] ] } } ]; for (const template of templates) { await client.query(` INSERT INTO notification_templates (id, type, title, message_template, button_template) VALUES ($1, $2, $3, $4, $5) `, [ uuid.v4(), template.type, template.title, template.message_template, JSON.stringify(template.button_template) ]); } } await client.query('COMMIT'); console.log('Successfully created notification tables'); } catch (err) { await client.query('ROLLBACK'); console.error('Error creating notification tables:', err); } finally { client.release(); pool.end(); } } createNotificationTables().catch(err => console.error('Failed to create notification tables:', err));