第39章 Django调用验证码

在保持不修改Django框架源代码的基准下,只好通过ajax调用captcha库返回验证码了。可惜vue.js不支持ajax功能,但好在有axios等第3方插件助力。

39.1 安装axios

要想使用axios插件,可以通过npm指令进行安装或直接引入cdn地址。注意:大部分操作系统本身是不支持npm指令,它可通过安装node.js获得。

使用 npm:

npm install axios

使用 cdn:

<script src='https://unpkg.com/axios/dist/axios.min.js'></script>

39.2 应用axios

不懂偷懒的程序猿不是好工程师,我喜欢偷懒,喜欢用cdn的方式。打开templates/ admin/login.html文件,在引入login.js的上一行,加入引入axios的代码。另外在表单(form.errors)错误提示信息的下方,加入验证码错误提示的代码;在输入密码框的下方,加入输入验证码的的代码,还有一个隐藏hashkey的hiddle,自己找找看。

{% load i18n static simpletags %}{% get_current_language as LANGUAGE_CODE %}{% get_current_language_bidi as LANGUAGE_BIDI %}<!DOCTYPE html><html lang='{{ LANGUAGE_CODE|default:'en-us' }}' {% if LANGUAGE_BIDI %}dir='rtl'{% endif %}><head> <meta charset='UTF-8'> <meta name='renderer' content='webkit'> <meta http-equiv='X-UA-Compatible' content='IE=edge,chrome=1'> <meta name='viewport' content='width=device-width, initial-scale=1, maximum-scale=1'> <title>{{ site_title }}-{% trans 'Log in' %}</title> <link rel='icon' href='{% static '/admin/simpleui-x/img/favicon.png' %}'> {% if 'SIMPLEUI_STATIC_OFFLINE'|get_config %} <link rel='stylesheet' href='{% static '/admin/simpleui-x/elementui/theme-chalk/index.css' %}'> <link rel='stylesheet' href='{% static '/admin/simpleui-x/fontawesome-free-5.8.1-web/css/all.min.css' %}'> {% else %} <link rel='stylesheet' href='https://unpkg.com/element-ui/lib/theme-chalk/index.css'> <link rel='stylesheet' href='https://cdn.bootcss.com/font-awesome/5.8.1/css/all.min.css'> {% endif %} <link rel='stylesheet' href='{% static '/admin/simpleui-x/css/login.css' %}?_=2.1'> <style type='text/css'> .bg { background: #f0f2f5; background-image: url('{% static '/admin/simpleui-x/img/bg.svg' %}'); min-height: 100%; background-repeat: no-repeat; background-position: 50%; background-size: 100%; padding: 20px 0; position: relative; } </style> {% block head %} {# You can add code here. #} {% endblock %}</head><body class='bg'><div class='login-main'> {% block logo %} <div class='logo'> {% if 'SIMPLEUI_LOGO'|get_config %} <img src='{{ 'SIMPLEUI_LOGO'|get_config |safe }}'> {% else %} <img src='{% static '/admin/simpleui-x/img/logo.png' %}'> {% endif %} </div> {% endblock %} {% block header %} <div class='header'>{{ site_header }}</div> {% endblock %} {% block errors %} {% if form.non_field_errors %} {% for error in form.non_field_errors %} <el-alert title='{{ error }}' type='error'> </el-alert> {% endfor %} {% endif %} {% if form.errors and not form.non_field_errors %} <p class='errornote'> {% if form.errors.items|length == 1 %} <el-alert title='{% trans 'Please correct the error below.' %}' type='error'></el-alert> {% else %} <el-alert title='{% trans 'Please correct the errors below.' %}' type='error'></el-alert> {% endif %} </p> {% endif %} <el-alert v-if='show_error' title='验证码错误' type='error'></el-alert> {% endblock %} {% block form %} <form class='simpleui-form' action='{{ app_path }}' method='post' id='login-form'> {% csrf_token %} <div class='simpleui-input-inline'> <el-input prefix-icon='fas fa-user' v-model='username' name='username' placeholder='{% trans 'username' %}'></el-input> </div> <div class='simpleui-input-inline'> <el-input prefix-icon='fas fa-lock' type='password' v-model='password' name='password' placeholder='{% trans 'password' %}' show-password></el-input> </div> <div class='simpleui-input-inline'> <el-input prefix-icon='fas el-icon-s-help' v-model='captcha' name='captcha' placeholder='验证码'> <img slot='append' :src='img_url' @click='refresh()'/> </el-input> </div> <div class='simpleui-input-inline login-btn'> <el-button :icon='loading?'el-icon-loading':''' @click='login()' type='primary'>{% trans 'Log in' %}</el-button> </div> <input id='hashkey' type='hidden' v-model='hashkey' name='hashkey'/> <input type='hidden' name='next' value='{{ next }}'/> </form> {% endblock %}</div>{% if 'SIMPLEUI_STATIC_OFFLINE'|get_config %} <script type='text/javascript' src='{% static '/admin/simpleui-x/js/vue.min.js' %}'></script> <script type='text/javascript' src='{% static '/admin/simpleui-x/elementui/index.js' %}'></script>{% else %} <script src='https://cdn.jsdelivr.net/npm/vue'></script> <script src='https://unpkg.com/element-ui/lib/index.js'></script>{% endif %} <script src='https://unpkg.com/axios/dist/axios.min.js'></script> <script type='text/javascript' src='{% static '/admin/simpleui-x/js/login.js' %}?_=2.3'></script>{% if 'SIMPLEUI_LOGIN_PARTICLES'|get_config != False %}<style type='text/css'> #particles-js{ position: fixed; top: 0px; left: 0px; right: 0px; bottom: 0px; z-index: -1; } </style><!-- particles.js container --><div id='particles-js'></div><script type='text/javascript' src='{% static '/admin/simpleui-x/particles/particles.js' %}'></script><script type='text/javascript' src='{% static '/admin/simpleui-x/particles/app.js' %}'></script>{% endif %}</body></html>

39.3 调用验证码

在模板文件上的添油加醋,只是对验证码进行一番造势而已,如果没有真材实料,最终火不过3天,活不到第二集。我说的是什么,你懂得。打开static/simpleui-x/js/login.js,调整内容如下。

if (parent.callback) {    //如果是在子框架内就把首页刷新    parent.callback();}new Vue({    el: '.login-main',    data: {        username: '',        password: '',        captcha:'',        hashkey:'',        img_url:'',        show_error: false,        loading: false    },    created: function () {        this.get_captcha();    },methods: {refresh:function () {       this.get_captcha();    },        login: function () {            hash_key = this.hashkey;            captcha_str = this.captcha;            this.loading = true;            this.show_error = false;            var that = this;            axios.get('/special/check_captcha/', {                    params: {                        hash_key: hash_key,                        captcha_str: captcha_str                    }                }            ).then(function (response) {                    var json = JSON.parse(JSON.stringify(response.data));                    var result =  json['result'];                    if (result) {                        document.getElementById('login-form').submit();                    }                    else {                        that.loading = false;                        that.show_error = true;                    }                })        },       get_captcha: function () {            var that=this;            axios.get('/special/captcha/')            .then(function (response) {                var result = JSON.parse(JSON.stringify(response.data));                that.hashkey = result['hashkey'];                that.img_url = result['image_url'];            })        } ,    }})

辛苦了好久,我也想早点见到效果(图),有效果才有成就,有效果,才有说服力。

(0)

相关推荐