186 lines
6.1 KiB
JavaScript
186 lines
6.1 KiB
JavaScript
const sqlite3 = require('sqlite3').verbose();
|
||
const path = require('path');
|
||
const fs = require('fs');
|
||
|
||
const dbPath = path.join(__dirname, 'data', 'school.db');
|
||
const dataDir = path.join(__dirname, 'data');
|
||
|
||
if (!fs.existsSync(dataDir)) {
|
||
fs.mkdirSync(dataDir);
|
||
}
|
||
|
||
const db = new sqlite3.Database(dbPath);
|
||
|
||
// Инициализация таблиц
|
||
db.serialize(() => {
|
||
db.run(`
|
||
CREATE TABLE IF NOT EXISTS lessons (
|
||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||
class_name TEXT NOT NULL,
|
||
parallel INTEGER NOT NULL,
|
||
subject TEXT NOT NULL,
|
||
teacher TEXT NOT NULL,
|
||
topic TEXT,
|
||
max_slots INTEGER NOT NULL DEFAULT 4,
|
||
current_slots INTEGER NOT NULL DEFAULT 0,
|
||
date TEXT NOT NULL,
|
||
time TEXT NOT NULL
|
||
)
|
||
`);
|
||
|
||
db.run(`
|
||
CREATE TABLE IF NOT EXISTS registrations (
|
||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||
lesson_id INTEGER NOT NULL,
|
||
parent_name TEXT NOT NULL,
|
||
parent_phone TEXT NOT NULL,
|
||
created_at TEXT DEFAULT CURRENT_TIMESTAMP,
|
||
FOREIGN KEY (lesson_id) REFERENCES lessons(id) ON DELETE CASCADE
|
||
)
|
||
`);
|
||
});
|
||
|
||
function runQuery(sql, params = []) {
|
||
return new Promise((resolve, reject) => {
|
||
db.run(sql, params, function(err) {
|
||
if (err) reject(err);
|
||
else resolve(this);
|
||
});
|
||
});
|
||
}
|
||
|
||
function getQuery(sql, params = []) {
|
||
return new Promise((resolve, reject) => {
|
||
db.get(sql, params, (err, row) => {
|
||
if (err) reject(err);
|
||
else resolve(row);
|
||
});
|
||
});
|
||
}
|
||
|
||
function allQuery(sql, params = []) {
|
||
return new Promise((resolve, reject) => {
|
||
db.all(sql, params, (err, rows) => {
|
||
if (err) reject(err);
|
||
else resolve(rows);
|
||
});
|
||
});
|
||
}
|
||
|
||
module.exports = {
|
||
db,
|
||
runQuery,
|
||
getQuery,
|
||
allQuery,
|
||
|
||
getLessons: (filter = {}) => {
|
||
let sql = 'SELECT * FROM lessons WHERE 1=1';
|
||
const params = [];
|
||
if (filter.class_name) {
|
||
sql += ' AND class_name LIKE ?';
|
||
params.push(`%${filter.class_name}%`);
|
||
}
|
||
if (filter.parallel) {
|
||
sql += ' AND parallel = ?';
|
||
params.push(filter.parallel);
|
||
}
|
||
if (filter.teacher) {
|
||
sql += ' AND teacher LIKE ?';
|
||
params.push(`%${filter.teacher}%`);
|
||
}
|
||
if (filter.topic) {
|
||
sql += ' AND topic LIKE ?';
|
||
params.push(`%${filter.topic}%`);
|
||
}
|
||
sql += ' ORDER BY parallel, class_name, time';
|
||
return allQuery(sql, params);
|
||
},
|
||
|
||
getLessonById: (id) => {
|
||
return getQuery('SELECT * FROM lessons WHERE id = ?', [id]);
|
||
},
|
||
|
||
createLesson: (lesson) => {
|
||
const { class_name, parallel, subject, teacher, topic, max_slots, date, time } = lesson;
|
||
return runQuery(
|
||
`INSERT INTO lessons (class_name, parallel, subject, teacher, topic, max_slots, current_slots, date, time)
|
||
VALUES (?, ?, ?, ?, ?, ?, 0, ?, ?)`,
|
||
[class_name, parallel, subject, teacher, topic || '', max_slots, date, time]
|
||
).then(result => result.lastID);
|
||
},
|
||
|
||
updateLesson: (id, lesson) => {
|
||
const { class_name, parallel, subject, teacher, topic, max_slots, date, time } = lesson;
|
||
return runQuery(
|
||
`UPDATE lessons SET class_name=?, parallel=?, subject=?, teacher=?, topic=?, max_slots=?, date=?, time=? WHERE id=?`,
|
||
[class_name, parallel, subject, teacher, topic || '', max_slots, date, time, id]
|
||
);
|
||
},
|
||
|
||
deleteLesson: (id) => {
|
||
return runQuery('DELETE FROM lessons WHERE id = ?', [id]);
|
||
},
|
||
|
||
incrementCurrentSlots: (lessonId) => {
|
||
return runQuery(
|
||
`UPDATE lessons SET current_slots = current_slots + 1 WHERE id = ? AND current_slots < max_slots`,
|
||
[lessonId]
|
||
);
|
||
},
|
||
|
||
addRegistration: (lessonId, parentName, parentPhone) => {
|
||
return runQuery(
|
||
`INSERT INTO registrations (lesson_id, parent_name, parent_phone) VALUES (?, ?, ?)`,
|
||
[lessonId, parentName, parentPhone]
|
||
);
|
||
},
|
||
|
||
getRegistrationsByLesson: (lessonId) => {
|
||
return allQuery('SELECT * FROM registrations WHERE lesson_id = ? ORDER BY created_at DESC', [lessonId]);
|
||
},
|
||
|
||
getAllRegistrations: () => {
|
||
return allQuery(`
|
||
SELECT r.*, l.class_name, l.subject, l.teacher, l.date, l.time
|
||
FROM registrations r
|
||
JOIN lessons l ON r.lesson_id = l.id
|
||
ORDER BY r.created_at DESC
|
||
`);
|
||
},
|
||
|
||
getRegistrationsWithFilters: (filters) => {
|
||
let sql = `
|
||
SELECT r.id, r.parent_name, r.parent_phone, r.created_at,
|
||
l.class_name, l.subject, l.teacher, l.topic, l.date, l.time
|
||
FROM registrations r
|
||
JOIN lessons l ON r.lesson_id = l.id
|
||
WHERE 1=1
|
||
`;
|
||
const params = [];
|
||
if (filters.parent_name) {
|
||
sql += ' AND r.parent_name LIKE ?';
|
||
params.push(`%${filters.parent_name}%`);
|
||
}
|
||
if (filters.class_name) {
|
||
sql += ' AND l.class_name LIKE ?';
|
||
params.push(`%${filters.class_name}%`);
|
||
}
|
||
if (filters.subject) {
|
||
sql += ' AND l.subject LIKE ?';
|
||
params.push(`%${filters.subject}%`);
|
||
}
|
||
if (filters.teacher) {
|
||
sql += ' AND l.teacher LIKE ?';
|
||
params.push(`%${filters.teacher}%`);
|
||
}
|
||
sql += ' ORDER BY r.created_at DESC';
|
||
return allQuery(sql, params);
|
||
},
|
||
|
||
// НОВЫЙ МЕТОД – полная очистка базы
|
||
clearAllData: async () => {
|
||
await runQuery('DELETE FROM registrations');
|
||
await runQuery('DELETE FROM lessons');
|
||
await runQuery("DELETE FROM sqlite_sequence WHERE name IN ('lessons', 'registrations')");
|
||
}
|
||
}; |