使用Django URL规则配合fetch API出现URL转义404问题如何解决?
问题原因
Django的模板标签(包括{% url %}、{% static %}等)只会对后缀为.html的模板文件进行解析渲染,你写在单独的静态JS文件(/static/js/actions.js)里的模板标签不会被Django处理,会被直接当做普通字符串拼接进请求地址,所以才会出现转义后的无效URL,触发404错误。
解决方案
方案1:HTML模板提前声明全局URL变量(最常用)
在引入外部JS之前,先在模板的script块中定义Django渲染好的URL变量,外部JS可直接调用,同时可以同步声明CSRF Token避免POST请求报403错误。
修改你的模板scripts块代码:
{% block scripts %} <script> // Django渲染的路由地址 const USER_SEARCH_URL = "{% url 'myapp:search_user' %}"; // POST请求必填的CSRF凭证 const CSRF_TOKEN = "{{ csrf_token }}"; </script> <script src={% static "js/actions.js" %}></script> {% endblock %}
修改actions.js中的对应代码:
document.querySelectorAll('.list-group-item-action').forEach( elem => { elem.addEventListener("click", event => { event.preventDefault(); // 直接调用模板中提前渲染好的变量 let url = USER_SEARCH_URL const request = new Request(url, { method: 'POST', body: formData, headers: { 'X-CSRFToken': CSRF_TOKEN } }); fetch(request) .then(response => response.json()) .then(result => { console.log(result) }) }) })
方案2:JS代码内嵌到HTML模板
如果不想定义全局变量,可以直接把这段JS逻辑写在HTML模板的<script>块中,不要放在单独的静态JS文件里,{% url %}标签就可以被Django正常解析。
方案3:URL挂载到DOM元素的data属性
如果需要适配多个动态路由,可将URL挂载到对应触发元素的自定义属性上,JS读取属性值即可:
- 修改模板中对应元素的代码:
<a href="{{ action.dest }}" data-search-url="{% url 'myapp:search_user' %}" class="list-group-item list-group-item-action">{{ action.display }}</a> - 修改JS中读取URL的逻辑:
let url = event.currentTarget.dataset.searchUrl
内容的提问来源于stack exchange,提问作者safepost
相关产品推荐
相关产品推荐

