Django如何将JavaScript变量传递到HTML模板用于模板标签条件判断
核心逻辑问题
Django的模板标签(比如{% if mark >=4 %})是在服务端渲染阶段执行的,页面返回到浏览器之后模板标签就已经完成渲染失效了。你现在通过AJAX把前端生成的测试分数传给后端的操作,不会触发页面重新渲染,所以原本依靠模板标签判断控制表单的逻辑完全走不通。
问题修复方案
1. 重写逻辑流程
正确的流程应该是:
- 前端JS生成测试分数
userScore后,先在前端做第一层判断:分数>=4才允许提交完成请求,不够则提示重考 - 提交请求时把分数传给后端,后端必须二次校验分数是否达标,再更新课程完成状态,避免恶意请求绕过前端判断篡改状态
- AJAX请求后端返回JSON响应,不要返回重定向或页面渲染结果
2. 修复views.py代码
需要先导入JsonResponse:
from django.http import JsonResponse def practice(request, lesson_id): form = LessonDone() posts = get_object_or_404(Lessons, pk=lesson_id) lessonid = Lessons.objects.get(pk=lesson_id) # 页面首次加载时mark为None mark = None if request.method == 'POST': # 拿到前端传的分数,转换为整数 mark = int(request.POST.get('mark', 0)) p, created = DoneLessonsModel.objects.get_or_create( user=request.user, lessons=lessonid, defaults={'done': False}, ) form = LessonDone(request.POST, instance=p) if form.is_valid(): try: # 后端二次校验分数达标才标记完成 if mark >=4: p.done = True form.save() return JsonResponse({'status': 'success', 'msg': '测试通过,课程已标记完成'}) else: return JsonResponse({'status': 'fail', 'msg': '分数不足,未通过测试'}) except: return JsonResponse({'status': 'error', 'msg': '保存失败,请重试'}) context = {'posts': posts, 'form': form, 'mark': mark} return render(request, 'landing/../static/practice.html', context)
3. 修复practice.html代码
... <div class="buttons "> <button class="restart btn-dark">Перепройти тест</button> <!-- 不要用模板if包裹form,直接写完整表单,或者干脆不用表单,所有提交走AJAX --> <form action="" method="POST" id="lesson-form"> {% csrf_token %} {{ form }} <!-- 按钮type改为button,避免默认提交 --> <button class="quit btn-dark" type="button" id="send-my-url-to-django-button">Выйти</button> </form> </div> ... <script type="text/javascript"> $(document).ready(function() { // 假设userScore是你之前JS生成的测试分数,这里确认已经赋值 var mark = userScore; $("#send-my-url-to-django-button").click(function() { // 前端先判断分数是否达标 if(mark < 4){ alert("分数不足4分,请重新测试"); return; } $.ajax({ // 模板url输出要加引号 url: "{% url 'practice' posts.pk %}", type: "POST", dataType: "json", data: { mark: mark, csrfmiddlewaretoken: '{{ csrf_token }}' }, success : function(res) { alert(res.msg); if(res.status == 'success'){ // 可以自定义后续操作,比如跳转到课程列表 // window.location.href = "{% url 'lesson_list' %}" } }, error : function(xhr,errmsg,err) { alert("请求失败,错误:" + xhr.status + ": " + xhr.responseText); } }); }); }); </script> ...
4. 补充说明
- 你原本的
urls.py配置没有问题,可以正常使用 - 不要依赖前端判断作为唯一校验依据,后端必须二次校验分数,防止用户恶意传值直接修改课程完成状态
内容的提问来源于stack exchange,提问作者Becker Wesley
相关产品推荐
相关产品推荐

