From 2e05322909c26ec3340268c255ea3e9d756339ee Mon Sep 17 00:00:00 2001 From: jeremygan2021 Date: Sun, 22 Mar 2026 21:15:34 +0800 Subject: [PATCH] pdf upload --- backend/competition/judge_views.py | 14 +++++++ backend/competition/serializers.py | 29 +++++++++++++- .../templates/judge/dashboard.html | 40 +++++++++++++++++++ backend/competition/views.py | 18 ++++++++- .../competition/ProjectSubmission.jsx | 34 +++++++++++++++- 5 files changed, 130 insertions(+), 5 deletions(-) diff --git a/backend/competition/judge_views.py b/backend/competition/judge_views.py index fc248d0..47fbf90 100644 --- a/backend/competition/judge_views.py +++ b/backend/competition/judge_views.py @@ -435,6 +435,19 @@ def project_detail_api(request, project_id): # 判断是否为选手查看自己的项目 is_own_project = role == 'contestant' and project.contestant.user == user + # 获取项目文件(PPT、PDF等) + project_files = ProjectFile.objects.filter(project=project) + files_data = [] + for f in project_files: + file_url = f.file.url if f.file else f.file_url + if file_url: + files_data.append({ + 'id': f.id, + 'name': f.name, + 'file_type': f.file_type, + 'file_url': file_url + }) + data = { 'id': project.id, 'title': project.title, @@ -445,6 +458,7 @@ def project_detail_api(request, project_id): 'current_comment': current_comment, 'ai_result': ai_data, 'audio_url': audio_url, + 'files': files_data, 'can_grade': role == 'judge' or (role == 'contestant' and project.contestant.user != user), 'is_own_project': is_own_project, # 评分细项(评委、嘉宾可见,选手查看自己的项目时也可见) diff --git a/backend/competition/serializers.py b/backend/competition/serializers.py index 689884a..e220480 100644 --- a/backend/competition/serializers.py +++ b/backend/competition/serializers.py @@ -33,19 +33,44 @@ class CompetitionEnrollmentSerializer(serializers.ModelSerializer): read_only_fields = ['status'] class ProjectFileSerializer(serializers.ModelSerializer): + file_url_display = serializers.SerializerMethodField() + class Meta: model = ProjectFile - fields = ['id', 'project', 'file_type', 'file', 'file_url', 'name', 'created_at'] + fields = ['id', 'project', 'file_type', 'file', 'file_url', 'name', 'created_at', 'file_url_display'] + + def get_file_url_display(self, obj): + if obj.file: + return obj.file.url + return obj.file_url def validate_file(self, value): if not value: return value - # 50MB limit limit_mb = 50 if value.size > limit_mb * 1024 * 1024: raise serializers.ValidationError(f"文件大小不能超过 {limit_mb}MB") return value + def create(self, validated_data): + file_obj = validated_data.get('file') + if file_obj: + ext = file_obj.name.split('.')[-1].lower() if '.' in file_obj.name else '' + if ext in ['ppt', 'pptx']: + validated_data['file_type'] = 'ppt' + elif ext == 'pdf': + validated_data['file_type'] = 'pdf' + elif ext in ['jpg', 'jpeg', 'png', 'gif', 'webp']: + validated_data['file_type'] = 'image' + elif ext in ['mp4', 'mov', 'avi', 'webm']: + validated_data['file_type'] = 'video' + elif ext in ['doc', 'docx']: + validated_data['file_type'] = 'doc' + + if not validated_data.get('name'): + validated_data['name'] = file_obj.name + return super().create(validated_data) + class ProjectSerializer(serializers.ModelSerializer): files = ProjectFileSerializer(many=True, read_only=True) contestant_info = serializers.SerializerMethodField() diff --git a/backend/competition/templates/judge/dashboard.html b/backend/competition/templates/judge/dashboard.html index d2112fb..efc61b5 100644 --- a/backend/competition/templates/judge/dashboard.html +++ b/backend/competition/templates/judge/dashboard.html @@ -116,6 +116,13 @@ + +