zoukankan      html  css  js  c++  java
  • flask-日料网站搭建-后台登录

    引言:想使用python的flask框架搭建一个日料网站,主要包含web架构,静态页面,后台系统,交互,今天教大家实现后台登录功能,比较简单。

    本节知识:表单标签,表单验证,数据查询,模板

    python环境:python2.7,flask,以及flask相关的库(没有列完,如果运行manage.py时提示未安装的库安装就ok了。)

    上节已经把admin(后台用户表)表建好了,再看看模型吧。

    -----models.py

    class Admin(db.Model):
        __tablename__ = 'admin'
        id = db.Column(db.Integer, primary_key=True)
        username = db.Column(db.String(64), unique=True, index=True)
        password = db.Column(db.String(128))
        ###权限  admin=1   1>2>3
        power  = db.Column(db.Integer)
        set_time = db.Column(db.DateTime)
        set_user = db.Column(db.Integer)
        email = db.Column(db.String(128))
        phone = db.Column(db.String(128))
        '''
        def __init__(self, username=None, password=None, power=None,phone=phone):
            self.username = username
            self.password = password
            self.power = power
            self.phone = phone
        '''
        def __repr__(self):
            return '<User %r>' % self.username,
        def check_user(self,username,password):
            obj = self.query.filter_by(username=username,password=password).first()
            return obj
        def check_user_aru(self,username):
            obj = self.query.filter_by(username=username).first()
            return obj
    
        def get_auser(self):
            obj = db.session.execute('select b.* ,a.username as set_user_name from  admin as a ,admin as b where a.id =b.set_user ').fetchall()
            return obj

    上面大部分是admin表的字段定义内容,下面的函数是我以后会用到的函数。

    虽然字段有点多,不过我们只需要用到username和password就行了,确定了表单字段,接下来就要生成login页面。

    -----先在视图文件定义  views.py   这不是完整版,因为还需要定义表单类,下面的LoginForm 还未写出来。

    @main.route('/admin/login', methods=['GET', 'POST'])
    def Alogin():
        form  = LoginForm()
        if request.method=='POST':
            if form.validate_on_submit():
                username = form.username.data
                password = form.password.data
                ####查询数据
                try:
                    obj = Admin.check_user(Admin(),username, password)
                    if obj:
                        session['username'] = username
                        session['userid'] = obj.id
                        ###记入adminlog
                        session['login_time'] = int(time.time())
                        login_time=time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
                        ip = get_ip()
                        log_list = AdminLog(username=username,userid=obj.id,login_time=login_time,ip=ip,email=obj.email, phone=obj.phone,power=obj.power,loginout_time='')
                        db.session.add(log_list)
                        db.session.commit()
                        log_id = log_list.id
                        session['log_id'] = log_id
                        return redirect('/admin/')
                    
                    
                except:
                    return render_template('admin/login.html',form=form,errors_info=u'用户名或密码错误!!')
                    
            else:
                return render_template('admin/login.html',form=form,error=form.errors)
        else:
            if session.has_key('username'):
                return redirect('/admin/')
            return render_template('admin/login.html',form=form)

    上述代码已经写出大概逻辑了,接下来是login.html以及_formhelpers1.html的内容

    -----login.html   只看表单部分就好了

    {% from "_formhelpers.html" import render_field %}           
                <form id="loginform" class="form-vertical" action="/admin/login" method="post">
                     {{ form.hidden_tag() }}
                     <div class="control-group normal_text"> <h3><img src="{{url_for('static', filename='images/admin/logo.png')}}" alt="Logo" /></h3></div>
                    <div class="control-group">
                        <div class="controls">
                            <div class="main_input_box">
                                <span class="add-on bg_lg"><i class="icon-user"></i></span>{{ render_field(form.username) }}
                            </div>
                        </div>
                    </div>
                    <div class="control-group">
                        <div class="controls">
                            <div class="main_input_box">
                                <span class="add-on bg_ly"><i class="icon-lock"></i></span>{{ render_field(form.password) }}
                            </div>
                        </div>
                    </div>
                    
                   {% if errors_info %} <span style="margin-left:26px; color:red">{{ errors_info }}</span>{% endif %}
                    
                    <div class="form-actions">
                        <span class="pull-left"><a href="#" class="flip-link btn btn-info" id="to-recover">Lost password?</a></span>
                        <span class="pull-right"><input type="submit"  class="btn btn-success"  value="Login"/> </span>
                    </div>
                </form>

    从_formhelpers1.html引入字段,赋值到form标签里面,这里需要注意_formhelpers1.html放置的路径,对应就ok了。

    ------_formhelpers1.html

    {% macro render_field(field) %}
      {{ field(**kwargs)|safe }}
      {% if field.errors %}
        {% for error in field.errors %}
         <span for="required" generated="true" class="help-inline">{{ error }}</span>
         {% endfor %}
      {% endif %}
    {% endmacro %}

    该文件的内容就是定义的表单标签,以及输出错误的信息(error)。

    接下来上完整版views.py  加上LoginForm

    class LoginForm(FlaskForm):
        username = StringField('Username', validators=[Length(min=3, max=25,message=u'请输入3-25个字符!')],render_kw={"placeholder": "username",})
        password = PasswordField('Password',validators= [
            Length(min=3, max=25,message=u'请输入4-25个字符!')],
            render_kw={"placeholder": "password",}
        )
    
    class AuserForm(FlaskForm):
        username = StringField('username',validators=[Length(min=3, max=25,message=u'请输入3-25个字符!')],)
        password = PasswordField('password',validators= [
            Length(min=3, max=25,message=u'请输入4-25个字符!')],
        )
        repassword = PasswordField('repassword',validators= [
            Length(min=3, max=25,message=u'请输入4-25个字符!')],
        )
        email = StringField('email', validators=[Length(min=3, max=25,message=u'请输入3-25个字符!')],)
        phone = StringField('phone', validators=[Length(min=3, max=25,message=u'请输入3-25个字符!')],)
        power = SelectField('power',choices=[(2,u'管理账户'),(3,u'普通账户')],coerce=int)
    
    @main.route('/', methods=['GET', 'POST'])
    def index():
        return render_template('index.html')
    
    @main.route('/admin/login', methods=['GET', 'POST'])
    def Alogin():
        form  = LoginForm()
        if request.method=='POST':
            if form.validate_on_submit():
                username = form.username.data
                password = form.password.data
                ####查询数据
                try:
                    obj = Admin.check_user(Admin(),username, password)
                    if obj:
                        session['username'] = username
                        session['userid'] = obj.id
                        ###记入adminlog
                        session['login_time'] = int(time.time())
                        login_time=time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
                        ip = get_ip()
                        log_list = AdminLog(username=username,userid=obj.id,login_time=login_time,ip=ip,email=obj.email, phone=obj.phone,power=obj.power,loginout_time='')
                        db.session.add(log_list)
                        db.session.commit()
                        log_id = log_list.id
                        session['log_id'] = log_id
                        return redirect('/admin/')
                    
                    
                except:
                    return render_template('admin/login.html',form=form,errors_info=u'用户名或密码错误!!')
                    
            else:
                return render_template('admin/login.html',form=form,error=form.errors)
        else:
            if session.has_key('username'):
                return redirect('/admin/')
            return render_template('admin/login.html',form=form)

    认真看下class LoinForm 怎么定义字段的照葫芦画瓢就ok了。

    ----------------------这是分割线----------------------------

    没有报错的话现在打开页面是ok的

    ----先测试下,表单字段的验证有没有问题

     当我直接点击登录,没有填写字段名,肯定是通不过验证的

    符合class LoginForm 设置的错误信息,验证还有很多方式,网上查阅下资料即可。

    ----------接下来我们来看看views.py 登录的逻辑,基本大功告成了

    @main.route('/admin/login', methods=['GET', 'POST'])##定义可以请求的方式
    def Alogin():
        form  = LoginForm()##实例登录类,传到页面
        if request.method=='POST':  ##提交方式
            if form.validate_on_submit():  ##可以通过验证
                username = form.username.data   ##获取表单数据
                password = form.password.data
                ####查询数据
                try:
                    obj = Admin.check_user(Admin(),username, password) ##开始查询
                    if obj:
                        session['username'] = username
                        session['userid'] = obj.id
                        ###记入adminlog
                        session['login_time'] = int(time.time())
                        login_time=time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())
                        ip = get_ip()
                        log_list = AdminLog(username=username,userid=obj.id,login_time=login_time,ip=ip,email=obj.email, phone=obj.phone,power=obj.power,loginout_time='')
                        db.session.add(log_list)
                        db.session.commit()
                        log_id = log_list.id
                        session['log_id'] = log_id
                        return redirect('/admin/')
                    
                    
                except:
                    return render_template('admin/login.html',form=form,errors_info=u'用户名或密码错误!!')  ##传入自己设置的error信息
                    
            else:
                return render_template('admin/login.html',form=form,error=form.errors)
        else:
            if session.has_key('username'):    ##登录时需要判断用户是否已经登陆了,当然还有其他,别入不同的ip继续登录,就要把他挤下去等
                return redirect('/admin/')
            return render_template('admin/login.html',form=form)

    里面的check_user函数,正式models.py里面定义的

    当然不定义在这里也可以,后期还需要规整,关于数据库的操作还有有些些麻烦,搞得我每次都想用原生sql来搞了,网上资料也总是对不上我的点,忧伤。

    下次根据后台的功能,再分享下增删改查的操作,大家一起学习。

    暂时没有把项目上传到github上面,以后我再传。

  • 相关阅读:
    性能测试中的二八原则
    OS + Linux Shell Programme / 100 cases
    db postgres openGauss
    OS + Linux sshkeygen / sshcopyid / id_rsa / id_rsa.pub / authorized_keys
    OS + Android performance matrix / memory LeakCanary
    springBoot 使用ConfigurationProperties+PropertySource注解 引入yml配置文件
    SpringBoot2.0集成WebSocket,实现后台向前端推送信息
    springBoot + rabbitMQ +手动确认消息 + 控制(接口、定时任务)消费者上下线
    linux 环境下安装keepalived 并且进行简单的主备配置
    eureka 注册列表低延迟注册、剔除服务配置 实现8s延迟
  • 原文地址:https://www.cnblogs.com/shuangzikun/p/taotao_python_flask_alogin.html
Copyright © 2011-2022 走看看