CoolFace
Modelpublic

HungLuong10/microservice

sourceHugging Faceupdated 8mo agoView on Hugging Face
0likes
db.sql377 linesDownload Raw Back to root
1-- Merged & ordered schema (ensure dependencies created before dependent tables)
2-- Date: 2025-12-20
3-- Notes:
4--  - This script assumes pgvector is available on the server.
5--  - Enums and extension are created first.
6--  - Tables are ordered so referenced tables/types exist before being used in foreign keys.
7--  - Indexes created at the end.
8
9-- 1) Extension
10CREATE EXTENSION IF NOT EXISTS vector;
11
12-- 2) ENUM types (create only if not exists)
13DO $$
14BEGIN
15  IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'flashcard_status') THEN
16    CREATE TYPE flashcard_status AS ENUM ('pending','done','miss');
17  END IF;
18  IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'roadmap_status') THEN
19    CREATE TYPE roadmap_status AS ENUM ('pending','done','skip','in_process');
20  END IF;
21  IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'study_status') THEN
22    CREATE TYPE study_status AS ENUM ('pending','done','miss');
23  END IF;
24END$$;
25
26-- 3) Roles
27CREATE TABLE IF NOT EXISTS role (
28  role_id SERIAL PRIMARY KEY,
29  role_name VARCHAR(50) NOT NULL UNIQUE
30);
31
32INSERT INTO role (role_id, role_name)
33VALUES (1, 'USER'), (2, 'ADMIN')
34ON CONFLICT (role_id) DO NOTHING;
35
36-- 4) Users (depends on role)
37CREATE TABLE IF NOT EXISTS "user" (
38  user_id SERIAL PRIMARY KEY,
39  user_name VARCHAR(100) NOT NULL,
40  email VARCHAR(200) UNIQUE,
41  password_hash VARCHAR(200),
42  birthday DATE,
43  created_at TIMESTAMPTZ DEFAULT now(),
44  updated_at TIMESTAMPTZ,
45  role_id INT DEFAULT 1 REFERENCES role(role_id) ON DELETE SET NULL,
46  available BOOLEAN DEFAULT true
47);
48
49-- 5) User update / history (depends on "user")
50CREATE TABLE IF NOT EXISTS user_update (
51  user_update_id SERIAL PRIMARY KEY,
52  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
53  user_name VARCHAR(100),
54  email VARCHAR(200),
55  password_hash VARCHAR(200),
56  birthday DATE,
57  created_at TIMESTAMPTZ DEFAULT now(),
58  updated_by INT REFERENCES "user"(user_id) ON DELETE SET NULL
59);
60
61-- 6) Subjects
62CREATE TABLE IF NOT EXISTS subject (
63  subject_id SERIAL PRIMARY KEY,
64  subject_name VARCHAR(100) NOT NULL,
65  subject_type INT DEFAULT 1,
66  available BOOLEAN DEFAULT true
67);
68
69-- 7) Topics (depends on subject)
70CREATE TABLE IF NOT EXISTS topic (
71  topic_id SERIAL PRIMARY KEY,
72  title TEXT,
73  description TEXT,
74  subject_id INT REFERENCES subject(subject_id) ON DELETE SET NULL
75);
76
77-- 8) Roadmap steps (depends on topic)
78CREATE TABLE IF NOT EXISTS roadmap_step (
79  roadmap_step_id SERIAL PRIMARY KEY,
80  title VARCHAR(200) NOT NULL,
81  description TEXT,
82  topic_id INT REFERENCES topic(topic_id) ON DELETE SET NULL
83);
84
85-- 9) Documents (depends on topic)
86CREATE TABLE IF NOT EXISTS document (
87  document_id SERIAL PRIMARY KEY,
88  title TEXT NOT NULL,
89  description TEXT,
90  link VARCHAR(500),
91  embedding vector(1536),
92  created_at TIMESTAMPTZ DEFAULT now(),
93  topic_id INT REFERENCES topic(topic_id) ON DELETE SET NULL,
94  available BOOLEAN DEFAULT true
95);
96
97-- 10) Document history (depends on document and user)
98CREATE TABLE IF NOT EXISTS document_history (
99  document_history_id SERIAL PRIMARY KEY,
100  start_time TIMESTAMPTZ,
101  end_time TIMESTAMPTZ,
102  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
103  document_id INT REFERENCES document(document_id) ON DELETE CASCADE,
104  created_at TIMESTAMPTZ DEFAULT now()
105);
106
107-- 11) Chunk (depends on document)
108CREATE TABLE IF NOT EXISTS chunk (
109  chunk_id SERIAL PRIMARY KEY,
110  title TEXT NOT NULL,
111  text TEXT,
112  link VARCHAR(250),
113  embedding vector(384),
114  document_id INT REFERENCES document(document_id) ON DELETE CASCADE
115);
116
117-- 12) Roadmap step <-> document mapping (depends on roadmap_step and document)
118CREATE TABLE IF NOT EXISTS roadmap_step_document (
119  roadmap_step_id INT NOT NULL,
120  document_id INT NOT NULL,
121  PRIMARY KEY (roadmap_step_id, document_id),
122  FOREIGN KEY (roadmap_step_id) REFERENCES roadmap_step(roadmap_step_id) ON DELETE CASCADE,
123  FOREIGN KEY (document_id) REFERENCES document(document_id) ON DELETE CASCADE
124);
125
126-- 13) User roadmap step (depends on roadmap_step and user)
127CREATE TABLE IF NOT EXISTS user_roadmap_step (
128  user_roadmap_step_id SERIAL PRIMARY KEY,
129  status roadmap_status DEFAULT 'pending',
130  roadmap_step_id INT REFERENCES roadmap_step(roadmap_step_id) ON DELETE CASCADE,
131  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE
132);
133
134-- 14) Flashcard deck (depends on user)
135CREATE TABLE IF NOT EXISTS flashcard_deck (
136  flashcard_deck_id SERIAL PRIMARY KEY,
137  title VARCHAR(500) NOT NULL,
138  description TEXT,
139  created_at TIMESTAMPTZ DEFAULT now(),
140  last_reviewed TIMESTAMPTZ,
141  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE
142);
143
144-- 15) Flashcard (depends on flashcard_deck)
145CREATE TABLE IF NOT EXISTS flashcard (
146  flashcard_id SERIAL PRIMARY KEY,
147  front TEXT NOT NULL,
148  back TEXT,
149  example TEXT DEFAULT '',
150  created_at TIMESTAMPTZ DEFAULT now(),
151  status flashcard_status DEFAULT 'pending',
152  flashcard_deck_id INT REFERENCES flashcard_deck(flashcard_deck_id) ON DELETE CASCADE
153);
154
155-- 16) Study schedule (depends on user and subject)
156CREATE TABLE IF NOT EXISTS study_schedule (
157  study_schedule_id SERIAL PRIMARY KEY,
158  title VARCHAR(500) NOT NULL,
159  description TEXT,
160  start_time TIMESTAMPTZ,
161  end_time TIMESTAMPTZ,
162  status study_status DEFAULT 'pending',
163  target_question INT,
164  created_at TIMESTAMPTZ DEFAULT now(),
165  update_at TIMESTAMPTZ DEFAULT now(),
166  user_id INT REFERENCES "user"(user_id),
167  subject_id INT REFERENCES subject(subject_id) ON DELETE SET NULL
168);
169
170-- 17) User goal (depends on user and subject)
171CREATE TABLE IF NOT EXISTS user_goal (
172  user_goal_id SERIAL PRIMARY KEY,
173  target_score DECIMAL(5,2),
174  deadline TIMESTAMPTZ,
175  created_at TIMESTAMPTZ DEFAULT now(),
176  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
177  subject_id INT REFERENCES subject(subject_id) ON DELETE SET NULL
178);
179
180-- 18) Current progress (depends on user and optionally user_goal)
181CREATE TABLE IF NOT EXISTS current_progress (
182  current_progress_id SERIAL PRIMARY KEY,
183  current_progress DECIMAL(5,2),
184  created_at TIMESTAMPTZ DEFAULT now(),
185  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
186  user_goal_id INT REFERENCES user_goal(user_goal_id)
187);
188
189-- 19) Bank (depends on topic)
190CREATE TABLE IF NOT EXISTS bank (
191  bank_id SERIAL PRIMARY KEY,
192  description VARCHAR(500),
193  topic_id INT REFERENCES topic(topic_id) ON DELETE SET NULL,
194  time_limit INT,
195  available BOOLEAN DEFAULT true
196);
197
198
199
200
201
202
203-- 20) Question (standalone)
204CREATE TABLE IF NOT EXISTS question (
205  question_id SERIAL PRIMARY KEY,
206  question_name VARCHAR(1000),
207  question_content VARCHAR(10000),
208  embedding vector(1536),
209  image JSON,
210  type_question INT DEFAULT 1,
211  source VARCHAR(50),
212  available BOOLEAN DEFAULT true
213);
214
215-- 21) Answer (depends on question)
216CREATE TABLE IF NOT EXISTS answer (
217  answer_id SERIAL PRIMARY KEY,
218  question_id INT NOT NULL REFERENCES question(question_id) ON DELETE CASCADE,
219  answer_content VARCHAR(10000) NOT NULL,
220  is_correct BOOLEAN DEFAULT FALSE,
221  image JSON
222);
223
224
225
226
227
228-- 22) question_bank (depends on question and bank)
229CREATE TABLE IF NOT EXISTS question_bank (
230  question_id INT NOT NULL REFERENCES question(question_id) ON DELETE CASCADE,
231  bank_id INT NOT NULL REFERENCES bank(bank_id) ON DELETE CASCADE,
232  PRIMARY KEY (question_id, bank_id)
233);
234
235
236
237
238-- 23) Exam schedule
239CREATE TABLE IF NOT EXISTS exam_schedule (
240  exam_schedule_id SERIAL PRIMARY KEY,
241  start_time TIMESTAMPTZ,
242  end_time TIMESTAMPTZ,
243  created_at TIMESTAMPTZ DEFAULT now(),
244  updated_at TIMESTAMPTZ DEFAULT now()
245);
246
247-- 24) Exam (depends on topic and exam_schedule)
248CREATE TABLE IF NOT EXISTS exam (
249  exam_id SERIAL PRIMARY KEY,
250  exam_name VARCHAR(200) NOT NULL,
251  created_at TIMESTAMPTZ DEFAULT now(),
252  time_limit INT, -- minutes
253  topic_id INT REFERENCES topic(topic_id) ON DELETE SET NULL,
254  exam_schedule_id INT REFERENCES exam_schedule(exam_schedule_id) ON DELETE SET NULL,
255  description VARCHAR(200),
256  available BOOLEAN DEFAULT true
257);
258
259-- 25) Contestants (depends on exam and user)
260CREATE TABLE IF NOT EXISTS contestants (
261  contestants_id SERIAL PRIMARY KEY,
262  exam_id INT REFERENCES exam(exam_id) ON DELETE CASCADE,
263  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE
264);
265
266-- user từng làm exam nào, điểm số ra sao
267-- 26) history_exam (depends on exam and user)
268CREATE TABLE IF NOT EXISTS history_exam (
269  history_exam_id SERIAL PRIMARY KEY,
270  exam_id INT NOT NULL REFERENCES exam(exam_id) ON DELETE CASCADE,
271  user_id INT NOT NULL REFERENCES "user"(user_id) ON DELETE CASCADE,
272  score DECIMAL(4,2),
273  time_test  BIGINT,
274  created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
275);
276
277-- 27) history_bank (depends on bank and user)
278CREATE TABLE IF NOT EXISTS history_bank (
279  history_bank_id SERIAL PRIMARY KEY,
280  bank_id INT NOT NULL REFERENCES bank(bank_id) ON DELETE CASCADE,
281  user_id INT NOT NULL REFERENCES "user"(user_id) ON DELETE CASCADE,
282  score DECIMAL(4,2),
283  time_test  BIGINT,
284  created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
285);
286
287-- 28) user_exam_answer (depends on user, exam, history_exam)
288CREATE TABLE IF NOT EXISTS user_exam_answer (
289  user_exam_answer_id SERIAL PRIMARY KEY,
290  created_at TIMESTAMPTZ DEFAULT now(),
291  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
292  exam_id INT REFERENCES exam(exam_id) ON DELETE CASCADE,
293  answer_id INT, -- optional pointer to chosen answer
294  user_answer_text TEXT DEFAULT '',
295  history_exam_id INT,
296  question_id INT,
297  CONSTRAINT fk_user_exam_answer_history FOREIGN KEY (history_exam_id) REFERENCES history_exam(history_exam_id) ON DELETE CASCADE
298);
299-- ALTER TABLE user_exam_answer
300-- ADD COLUMN IF NOT EXISTS question_id INT;
301
302-- 29) user_bank_answer (depends on bank, user, answer, history_bank)
303CREATE TABLE IF NOT EXISTS user_bank_answer (
304  user_bank_answer_id SERIAL PRIMARY KEY,
305  created_at TIMESTAMPTZ DEFAULT now(),
306  bank_id INT REFERENCES bank(bank_id) ON DELETE SET NULL,
307  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
308  answer_id INT REFERENCES answer(answer_id) ON DELETE SET NULL,
309  user_answer_text TEXT DEFAULT '',
310  question_id INT,
311  history_bank_id INT,
312  CONSTRAINT fk_user_bank_answer_history FOREIGN KEY (history_bank_id) REFERENCES history_bank(history_bank_id) ON DELETE CASCADE
313);
314
315-- 30) question_exam mapping (depends on question and exam)
316CREATE TABLE IF NOT EXISTS question_exam (
317  question_id INT NOT NULL REFERENCES question(question_id) ON DELETE CASCADE,
318  exam_id INT NOT NULL REFERENCES exam(exam_id) ON DELETE CASCADE,
319  PRIMARY KEY (question_id, exam_id)
320);
321
322
323
324
325
326
327-- 31) Chat history (depends on user)
328CREATE TABLE IF NOT EXISTS chat_history (
329  chat_history_id SERIAL PRIMARY KEY,
330  user_id INT REFERENCES "user"(user_id) ON DELETE CASCADE,
331  is_user BOOLEAN,
332  role VARCHAR(20), -- 'user','assistant','system'
333  message TEXT,
334  embedding vector(1536),
335  created_at TIMESTAMPTZ DEFAULT now()
336);
337
338
339
340
341
342
343-- 32) Image tables (depend on question/answer)
344CREATE TABLE IF NOT EXISTS image_question (
345  image_question_id SERIAL PRIMARY KEY,
346  image_link TEXT,
347  question_id INT REFERENCES question(question_id) ON DELETE CASCADE
348);
349
350CREATE TABLE IF NOT EXISTS image_answer (
351  image_answer_id SERIAL PRIMARY KEY,
352  image_link TEXT,
353  answer_id INT REFERENCES answer(answer_id) ON DELETE CASCADE
354);
355
356-- 33) Indexes (created after tables)
357CREATE INDEX IF NOT EXISTS idx_topic_subject ON topic(subject_id);
358CREATE INDEX IF NOT EXISTS idx_document_topic ON document(topic_id);
359CREATE INDEX IF NOT EXISTS idx_document_history_user ON document_history(user_id);
360CREATE INDEX IF NOT EXISTS idx_document_history_document ON document_history(document_id);
361CREATE INDEX IF NOT EXISTS idx_chat_history_user ON chat_history(user_id);
362CREATE INDEX IF NOT EXISTS idx_answer_question ON answer(question_id);
363CREATE INDEX IF NOT EXISTS idx_question_exam_exam ON question_exam(exam_id);
364CREATE INDEX IF NOT EXISTS idx_bank_topic ON bank(topic_id);
365CREATE INDEX IF NOT EXISTS idx_user_goal_user ON user_goal(user_id);
366CREATE INDEX IF NOT EXISTS idx_user_email ON "user"(email);
367
368-- Optional pgvector ANN index suggestions (create these AFTER you have vectors and tested tuning lists):
369-- CREATE INDEX IF NOT EXISTS idx_document_embedding ON document USING ivfflat (embedding vector_cosine_ops) WITH (lists = 100);
370-- CREATE INDEX IF NOT EXISTS idx_question_embedding ON question USING ivfflat (embedding vector_cosine_ops) WITH (lists = 100);
371-- CREATE INDEX IF NOT EXISTS idx_chat_history_embedding ON chat_history USING ivfflat (embedding vector_cosine_ops) WITH (lists = 100);
372-- CREATE INDEX IF NOT EXISTS idx_chunk_embedding ON chunk USING ivfflat (embedding vector_cosine_ops) WITH (lists = 100);
373
374-- End of ordered merged schema
375
376CREATE EXTENSION IF NOT EXISTS unaccent;
377