Skip to content

Commit aa9c8eb

Browse files
authored
#437 커뮤니티 DB Schema 설계 (#443)
1 parent 8fdf27d commit aa9c8eb

5 files changed

Lines changed: 148 additions & 0 deletions

File tree

backend/community/__init__.py

Whitespace-only changes.
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
# Generated by Django 3.2.25 on 2025-08-11 05:58
2+
3+
from django.conf import settings
4+
from django.db import migrations, models
5+
import django.db.models.deletion
6+
import utils.models
7+
8+
9+
class Migration(migrations.Migration):
10+
11+
initial = True
12+
13+
dependencies = [
14+
('contest', '0001_initial'),
15+
('problem', '0001_initial'),
16+
migrations.swappable_dependency(settings.AUTH_USER_MODEL),
17+
]
18+
19+
operations = [
20+
migrations.CreateModel(
21+
name='Post',
22+
fields=[
23+
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
24+
('title', models.CharField(max_length=200)),
25+
('content', utils.models.RichTextField()),
26+
('community_type', models.CharField(choices=[('GENERAL', '일반'), ('PROBLEM', '문제'), ('CONTEST', '대회')], default='GENERAL', max_length=20)),
27+
('post_type', models.CharField(choices=[('QUESTION', '질문'), ('ARTICLE', '글'), ('ANNOUNCEMENT', '공지')], default='ARTICLE', max_length=20)),
28+
('question_status', models.CharField(choices=[('OPEN', '진행중'), ('CLOSED', '해결됨')], default='OPEN', max_length=20)),
29+
('created_at', models.DateTimeField(auto_now_add=True)),
30+
('updated_at', models.DateTimeField(auto_now=True)),
31+
('author', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
32+
('contest', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, to='contest.contest')),
33+
('problem', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, to='problem.problem')),
34+
],
35+
options={
36+
'ordering': ['-created_at'],
37+
},
38+
),
39+
migrations.CreateModel(
40+
name='Comment',
41+
fields=[
42+
('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
43+
('content', utils.models.RichTextField()),
44+
('created_at', models.DateTimeField(auto_now_add=True)),
45+
('updated_at', models.DateTimeField(auto_now=True)),
46+
('author', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to=settings.AUTH_USER_MODEL)),
47+
('parent_comment', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='replies', to='community.comment')),
48+
('post', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='comments', to='community.post')),
49+
],
50+
options={
51+
'ordering': ['created_at'],
52+
},
53+
),
54+
]

backend/community/migrations/__init__.py

Whitespace-only changes.

backend/community/models.py

Lines changed: 93 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
from django.db import models
2+
3+
from account.models import User
4+
from contest.models import Contest
5+
from problem.models import Problem
6+
from utils.models import RichTextField
7+
8+
9+
class Post(models.Model):
10+
"""커뮤니티 게시글 모델
11+
12+
Attributes:
13+
title (CharField): 게시글 제목 (최대 200자)
14+
content (RichTextField): 게시글 내용
15+
author (ForeignKey): 작성자 (User 모델 외래 키)
16+
problem (ForeignKey): 연관된 문제 (Problem 모델 외래 키, community_type이 'PROBLEM'일 경우)
17+
contest (ForeignKey): 연관된 대회 (Contest 모델 외래 키, community_type이 'CONTEST'일 경우)
18+
community_type (CharField): 커뮤니티 종류 (일반, 문제, 대회)
19+
post_type (CharField): 게시글 종류 (질문, 글, 공지)
20+
question_status (CharField): 질문 상태 (진행중, 해결됨), post_type이 'QUESTION'일 경우
21+
created_at (DateTimeField): 생성 일시 (자동 생성)
22+
updated_at (DateTimeField): 수정 일시 (자동 업데이트)
23+
"""
24+
25+
class CommunityType(models.TextChoices):
26+
"""게시글의 커뮤니티 종류"""
27+
GENERAL = 'GENERAL', '일반'
28+
PROBLEM = 'PROBLEM', '문제'
29+
CONTEST = 'CONTEST', '대회'
30+
31+
class PostType(models.TextChoices):
32+
"""게시글의 종류"""
33+
QUESTION = 'QUESTION', '질문'
34+
ARTICLE = 'ARTICLE', '글'
35+
ANNOUNCEMENT = 'ANNOUNCEMENT', '공지'
36+
37+
class QuestionStatus(models.TextChoices):
38+
"""질문 게시글의 상태"""
39+
OPEN = 'OPEN', '진행중'
40+
CLOSED = 'CLOSED', '해결됨'
41+
42+
title = models.CharField(max_length=200)
43+
content = RichTextField()
44+
author = models.ForeignKey(User, on_delete=models.CASCADE)
45+
46+
problem = models.ForeignKey(Problem, null=True, blank=True, on_delete=models.CASCADE)
47+
contest = models.ForeignKey(Contest, null=True, blank=True, on_delete=models.CASCADE)
48+
49+
community_type = models.CharField(
50+
max_length=20,
51+
choices=CommunityType.choices,
52+
default=CommunityType.GENERAL,
53+
)
54+
55+
post_type = models.CharField(
56+
max_length=20,
57+
choices=PostType.choices,
58+
default=PostType.ARTICLE,
59+
)
60+
61+
question_status = models.CharField(
62+
max_length=20,
63+
choices=QuestionStatus.choices,
64+
default=QuestionStatus.OPEN,
65+
)
66+
67+
created_at = models.DateTimeField(auto_now_add=True)
68+
updated_at = models.DateTimeField(auto_now=True)
69+
70+
class Meta:
71+
ordering = ['-created_at']
72+
73+
74+
class Comment(models.Model):
75+
"""게시글 댓글 모델
76+
77+
Attributes:
78+
post (ForeignKey): 댓글이 달린 게시글 (Post 모델 외래 키)
79+
author (ForeignKey): 댓글 작성자 (User 모델 외래 키)
80+
content (RichTextField): 댓글 내용
81+
parent_comment (ForeignKey): 부모 댓글 (대댓글의 경우)
82+
created_at (DateTimeField): 생성 일시 (자동 생성)
83+
updated_at (DateTimeField): 수정 일시 (자동 업데이트)
84+
"""
85+
post = models.ForeignKey(Post, related_name='comments', on_delete=models.CASCADE)
86+
author = models.ForeignKey(User, on_delete=models.CASCADE)
87+
content = RichTextField()
88+
parent_comment = models.ForeignKey('self', null=True, blank=True, related_name='replies', on_delete=models.CASCADE)
89+
created_at = models.DateTimeField(auto_now_add=True)
90+
updated_at = models.DateTimeField(auto_now=True)
91+
92+
class Meta:
93+
ordering = ['created_at'] # 댓글은 오래된 순서대로 정렬

backend/oj/settings.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@
4545
LOCAL_APPS = [
4646
'account',
4747
'announcement',
48+
'community',
4849
'conf',
4950
'problem',
5051
'contest',

0 commit comments

Comments
 (0)