Skip to content

Commit 2b714ae

Browse files
authored
Merge pull request #170 from Spaghetti-OJ/feat/finish_all_submission_function
Feat/finish all submission function
2 parents f3ce171 + a0e2011 commit 2b714ae

5 files changed

Lines changed: 340 additions & 34 deletions

File tree

docs/submissions.MD

Lines changed: 30 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -236,15 +236,18 @@ curl -X PUT http://localhost:8000/submission/a1b2c3d4-5678-90ab-cdef-1234567890a
236236
**認證**: 必須(Bearer Token)
237237

238238
**查詢參數**:
239-
- `page` (可選): 頁碼預設 1
240-
- `page_size` (可選): 每頁數量預設 20
239+
- `page` (可選): 頁碼,預設 1
240+
- `page_size` (可選): 每頁數量,預設 20
241241
- `problem_id` (可選): 篩選特定題目的提交
242242
- `username` (可選): 篩選特定使用者的提交
243-
- `status` (可選): 篩選判題狀態如 "0"=AC, "1"=WA, "2"=CE, "3"=TLE, "4"=MLE, "5"=RE
243+
- `status` (可選): 篩選判題狀態(如 "0"=AC, "1"=WA, "2"=CE, "3"=TLE, "4"=MLE, "5"=RE)
244244
- `course_id` (可選): 篩選特定課程的所有提交
245-
- `language_type` (可選): 篩選程式語言(0=C, 1=C++, 2=Python, 3=Java, 4=JavaScript)
246-
- `before` (可選): 篩選某時間之前的提交(Unix 時間戳記,單位:秒)
247-
- `after` (可選): 篩選某時間之後的提交(Unix 時間戳記,單位:秒)
245+
- `language_type` (可選): 篩選程式語言(0=C, 1=C++, 2=Python, 3=Java, 4=JavaScript)
246+
- `before` (可選): 篩選某時間之前的提交(Unix 時間戳記,單位:秒)
247+
- `after` (可選): 篩選某時間之後的提交(Unix 時間戳記,單位:秒)
248+
- `ip_prefix` (可選): 篩選 IP 網段前綴,支援以下格式:
249+
- 簡單前綴: `192.168.` 匹配所有 192.168.x.x
250+
- CIDR 表示法: `192.168.1.0/24` 匹配 192.168.1.0-255 範圍
248251

249252
**權限說明**:
250253
- 學生:只能查看自己的提交
@@ -316,6 +319,18 @@ curl -X GET "http://localhost:8000/submission/?after=1735286400&before=173537279
316319
# 組合多個篩選條件
317320
curl -X GET "http://localhost:8000/submission/?problem_id=123&status=0&language_type=2" \
318321
-H "Authorization: Bearer YOUR_TOKEN"
322+
323+
# 查詢特定 IP 網段的提交(簡單前綴)
324+
curl -X GET "http://localhost:8000/submission/?ip_prefix=192.168." \
325+
-H "Authorization: Bearer YOUR_TOKEN"
326+
327+
# 查詢特定 IP 網段的提交(CIDR 表示法)
328+
curl -X GET "http://localhost:8000/submission/?ip_prefix=192.168.1.0/24" \
329+
-H "Authorization: Bearer YOUR_TOKEN"
330+
331+
# 組合 IP 網段與其他條件
332+
curl -X GET "http://localhost:8000/submission/?ip_prefix=10.0.0.0/8&status=0" \
333+
-H "Authorization: Bearer YOUR_TOKEN"
319334
```
320335

321336
---
@@ -662,9 +677,9 @@ submissionId: "a1b2c3d4-5678-90ab-cdef-1234567890ab"
662677
### 1. 提交限制檢查
663678
- [ ] `"problem permission denied"` - 題目權限檢查
664679
- [ ] `"homework hasn't start"` - 作業時間檢查
665-
- [ ] `"Invalid IP address"` - IP 白名單檢查
680+
- [x] IP 網段前綴篩選 - 支援簡單前綴和 CIDR 表示法
666681
- [ ] `"you have used all your quotas"` - 配額限制
667-
- [ ] `"Submit too fast!"` - 提交頻率限制`waitFor` 欄位
682+
- [ ] `"Submit too fast!"` - 提交頻率限制(`waitFor` 欄位)
668683

669684
### 2. 判題系統整合
670685
- [ ] 實際連接 SandBox 判題系統
@@ -834,9 +849,15 @@ curl -X GET http://localhost:8000/submission/student-submission-id/ \
834849

835850
## 版本歷史
836851

852+
**v1.1 (2025-12-28)**
853+
- 新增 IP 網段前綴篩選功能
854+
- 支援簡單前綴匹配(如 `192.168.`)
855+
- 支援 CIDR 表示法(如 `192.168.1.0/24`)
856+
- 實作統計資料自動更新(全域與作業層級)
857+
837858
**v1.0 (2025-11-09)**
838859
- 初始版本
839-
- 實作基本提交功能創建、上傳、查詢
860+
- 實作基本提交功能(創建、上傳、查詢)
840861
- 兼容 NOJ 格式標準
841862
- 實作角色權限系統
842863
- 支援重新判題功能

submissions/serializers.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -352,7 +352,7 @@ class SubmissionBaseCreateSerializer(serializers.ModelSerializer):
352352
min_value=0,
353353
max_value=4,
354354
error_messages={
355-
'invalid': 'invalid data!',
355+
'invalid': 'languageType 格式錯誤:必須是 0-4 的整數 (收到的類型不正確)',
356356
'required': 'post data missing!',
357357
'min_value': 'not allowed language',
358358
'max_value': 'not allowed language'

submissions/test_file/get_test_token.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,9 +39,25 @@ def create_test_user():
3939
if created:
4040
user.set_password(password)
4141
user.save()
42-
print(f"創建新用戶: {username}")
42+
print(f"創建新用戶: {username}")
4343
else:
44-
print(f"使用現有用戶: {username}")
44+
print(f"✓ 使用現有用戶: {username}")
45+
46+
# 確保 email 已驗證(測試用)
47+
try:
48+
from user.models import UserProfile
49+
profile, profile_created = UserProfile.objects.get_or_create(
50+
user=user,
51+
defaults={'email_verified': True}
52+
)
53+
if not profile.email_verified:
54+
profile.email_verified = True
55+
profile.save()
56+
print(f"✓ Email 已設為驗證狀態")
57+
else:
58+
print(f"✓ Email 已是驗證狀態")
59+
except Exception as e:
60+
print(f"⚠ 無法設置 email 驗證狀態: {e}")
4561

4662
return user, password
4763

submissions/test_file/test_submission_views_api.py

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,31 +39,50 @@ class SubmissionAPITestSetup:
3939
@classmethod
4040
def create_test_users(cls):
4141
"""創建測試用戶"""
42+
from user.models import UserProfile
43+
4244
# 普通學生
4345
cls.student1 = User.objects.create_user(
4446
username='api_student1',
4547
email='api_student1@test.com',
4648
password='testpass123'
4749
)
50+
# 設置郵箱驗證
51+
profile1, _ = UserProfile.objects.get_or_create(user=cls.student1)
52+
profile1.email_verified = True
53+
profile1.save()
54+
4855
cls.student2 = User.objects.create_user(
4956
username='api_student2',
5057
email='api_student2@test.com',
5158
password='testpass123'
5259
)
60+
# 設置郵箱驗證
61+
profile2, _ = UserProfile.objects.get_or_create(user=cls.student2)
62+
profile2.email_verified = True
63+
profile2.save()
5364

5465
# 老師
5566
cls.teacher = User.objects.create_user(
5667
username='api_teacher',
5768
email='api_teacher@test.com',
5869
password='testpass123'
5970
)
71+
# 設置郵箱驗證
72+
profile_teacher, _ = UserProfile.objects.get_or_create(user=cls.teacher)
73+
profile_teacher.email_verified = True
74+
profile_teacher.save()
6075

6176
# TA
6277
cls.ta = User.objects.create_user(
6378
username='api_ta',
6479
email='api_ta@test.com',
6580
password='testpass123'
6681
)
82+
# 設置郵箱驗證
83+
profile_ta, _ = UserProfile.objects.get_or_create(user=cls.ta)
84+
profile_ta.email_verified = True
85+
profile_ta.save()
6786

6887
# 管理員
6988
cls.admin = User.objects.create_user(
@@ -73,6 +92,11 @@ def create_test_users(cls):
7392
is_staff=True,
7493
is_superuser=True
7594
)
95+
# 設置郵箱驗證
96+
profile_admin, _ = UserProfile.objects.get_or_create(user=cls.admin)
97+
profile_admin.email_verified = True
98+
profile_admin.save()
99+
76100

77101
@classmethod
78102
def create_test_courses(cls):
@@ -117,6 +141,7 @@ def create_test_problems(cls):
117141
description='API測試:給定一個整數數組,返回兩個數字的索引',
118142
course_id=cls.course1,
119143
creator_id=cls.teacher, # 添加必需的 creator_id
144+
is_public='course', # 設置為課程可見
120145
difficulty=Problems.Difficulty.EASY
121146
)
122147

@@ -126,6 +151,7 @@ def create_test_problems(cls):
126151
description='API測試:反轉一個單鏈表',
127152
course_id=cls.course2,
128153
creator_id=cls.teacher, # 添加必需的 creator_id
154+
is_public='course', # 設置為課程可見
129155
difficulty=Problems.Difficulty.MEDIUM
130156
)
131157

@@ -136,6 +162,7 @@ def create_test_problems(cls):
136162
description='API測試:用於測試權限的題目(關聯到 course2)',
137163
course_id=cls.course2, # 修改:不能為 None,使用 course2
138164
creator_id=cls.teacher, # 添加必需的 creator_id
165+
is_public='course', # 設置為課程可見
139166
difficulty=Problems.Difficulty.HARD
140167
)
141168

@@ -290,6 +317,11 @@ def test_create_submission_success(self):
290317

291318
response = self.client.post(self.get_submission_create_url(), data)
292319

320+
# 調試:打印響應內容
321+
if response.status_code != status.HTTP_201_CREATED:
322+
print(f"\n錯誤狀態碼: {response.status_code}")
323+
print(f"響應內容: {response.data}")
324+
293325
# 驗證 NOJ 格式響應 (通過 api_response 包裝)
294326
self.assertEqual(response.status_code, status.HTTP_201_CREATED)
295327
message = self.get_api_message(response)

0 commit comments

Comments
 (0)