【问题标题】:Django Vue.js PasswordResetView posted with Axios gets Error 403 Forbidden CSRF Token使用 Axios 发布的 Django Vue.js PasswordResetView 获取错误 403 禁止 CSRF 令牌
【发布时间】:2021-11-04 13:44:30
【问题描述】:

我正在尝试使用 Vue.js 在前端创建自定义电子邮件恢复页面。在那里,我试图通过 /api/v1/accounts/password_reset/ 使用 Axios 发送带有电子邮件的输入,所以基本上我试图使用原始的 ResetPasswordView 而不是使用它的模板,而是将它用作端点。当我提交值时,控制台返回错误 403 Forbidden CSRF Token,如下所示。有什么办法可以避免呢?

Forbidden (CSRF cookie not set.): /api/v1/accounts/password_reset/
[07/Sep/2021 16:32:55] "POST /api/v1/accounts/password_reset/ HTTP/1.1" 403 2864
/Users/IvanStepanchuk/Desktop/web-project/web-backend/core/settings.py changed, reloading.
Watching for file changes with StatReloader
Performing system checks...

这是我的 ResetPassword.vue:

<template>
    <div id="login">
        <div class="w-100 d-flex justify-content-center" id="home__screen">
            <div class="col-sm col-lg-4 text-center align-self-center decorator__spacing">
                <div class="card bg-white p-4">
                    <h1 class="fs-3 pb-3">Recover your account</h1>
                    <form @submit.prevent="passwordReset">
                        <div class="mb-3">
                            <input type="email" class="form-control" id="username" v-model="email" aria-describedby="emailHelp" placeholder="Email con el cual se ha registrado">
                        </div>
                        <div class="alert alert-primary d-flex flex-column" role="alert" v-if="errors.length">
                            <span v-for="error in errors" v-bind:key="error">{{error}}</span>
                        </div>
                        <button type="submit" class="btn btn-primary mb-3">Enviar</button>
                    </form>
                </div>
            </div>
        </div>
    </div>
</template>

<script>
import axios from 'axios'

export default {
  name: 'ResetPassword',
  data() {
      return {
          email: '',
          errors: []
      }
  },
  components: {
    
  },
  mounted() {
      document.title = 'Company | Recover Account'
  },
  methods: {
        passwordReset() {
            this.errors = []
            if (this.email === '') {
                this.errors.push('Email field is empty')
            }

            const passwordResetForm = {
                email: this.email
            }
            axios
                .post("/api/v1/accounts/password_reset/", passwordResetForm)
                .then(response => {
                    this.$router.push('/login')
                    return response
                })
                .catch(error => {
                    this.errors.push('Something is not working well')
                    console.log(error)
                })
        }

  }
}
</script>

<style scoped>

</style>

或者使用自定义 Vue.js 视图来管理密码重置功能的最佳方式是什么(因此它不使用 Django 模板)?谢谢!

【问题讨论】:

    标签: javascript python django vue.js django-rest-framework


    【解决方案1】:

    问题是你的passwordResetForm 里面没有csrf_token。好吧,它只是一个带有电子邮件的对象。出于安全原因,Django 默认不允许这样做。 (详情见:documentation关于CSRF)

    您可以使用以下代码从页面获取 csrf 令牌:

    function getCookie(name) {
        let cookieValue = null;
        if (document.cookie && document.cookie !== '') {
            const cookies = document.cookie.split(';');
            for (let i = 0; i < cookies.length; i++) {
                const cookie = cookies[i].trim();
                // Does this cookie string begin with the name we want?
                if (cookie.substring(0, name.length + 1) === (name + '=')) {
                    cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
                    break;
                }
            }
        }
        return cookieValue;
    }
    const csrftoken = getCookie('csrftoken');
    
    

    然后在 ajax.post() 的标题中传递 csrftoken

    【讨论】:

    • 太棒了,这会很好用。谢谢!此外,我正在研究一种解决方法,它允许通过自定义 Vue.js 视图更改密码等。稍后将分享代码。
    • @IvanStepanchuk,你有机会分享代码吗?
    • 嗨@finite_diffidence,该问题的解决方案可以在这里找到stackoverflow.com/questions/69049040/…。上面的方法对我不起作用,所以我不得不以不同的方式实现它,比如解决方法。
    【解决方案2】:

    我能够通过创建自定义 Views.py 方法和类来解决这个问题,您可以在此处查看解决方案:Django Rest Framework + Serializers + Vue.js, Reset Password Functionality

    • 这不是重复的。这是一个类似的主题,但采用了不同的方法,效果很好。

    【讨论】:

      猜你喜欢
      • 2015-07-30
      • 2016-05-08
      • 2021-07-08
      • 2013-05-25
      • 2020-06-21
      • 2015-10-15
      • 1970-01-01
      • 2020-08-03
      • 2014-08-21
      相关资源
      最近更新 更多