一、系统概要

本次作业参考了简书网站,为创作者提供创作和交流平台,布局简单明了,色调整体偏冷,为创作者提供干净的创作空间。

网站的设计与实现使用了Python+Flask+Mysql的web建设技术,实现了以下几个功能:

  1. 网站父模板统一布局:头部导航条、底部图片导航、中间主显示区域布局
  2. 注册、登录、注销
  3. 发布、列表显示
  4. 详情页
  5. 评论、列表显示
  6. 个人中心
  7. 搜索,条件组合搜索
  8. 文章分类、显示
  9. 点赞、收藏
  10. 修改密码、头像、上传头像
  11. 我的发布、点赞、收藏、评论
  12. 高级搜索
  13. 热门文章、推荐文章

 

二、网站结构设计

(1)业务流程图

根据该项目的功能要求,得到的业务流程图所示:

 

(2)数据库表

考虑各个字段数据类型和数据之间的关系,可以得到用户表、发布表、评论表、收藏表、点赞表:

 

三、模块实现

以下1-5点是实现登录、注册、修改密码和头像等等各个功能的必要算法:

1、建立实现各模块的视图函数,之后在html文件中通过{{ url_for('') }}调用各函数,以此实现登录、查询、发布、修改密码和头像等功能。

2、通过request请求获取表单内容并传值。

3、通过filter函数过滤掉不符合条件的元素,返回由符合条件元素组成的新列表。

4、用if函数进行条件判断。

5、通过session进行会话连接,匹配成功,return下一步操作。

举个例子,登录操作中的视图函数如图所示:


# 登录
@app.route('/denglu/', methods=['GET', 'POST']) # methods定义两种请求方式
def denglu():
if request.method == 'GET':
return render_template('denglu.html')
else:
username = request.form.get('user') # post请求模式,安排对象接收数据
password = request.form.get('pass')
user = User.query.filter(User.username == username).first() # 作查询,并判断
if user: # 判断用户名
if user.check_password(password): # 判断密码
session['user'] = username
session['user_id'] = user.id
session.permanent = True # 设置永久有效
return redirect(url_for('daohang')) #重定向到首页
else:
return u'用户密码错误'
else:
return u'用户不存在,请先注册'
 

6、作为游客,想要实现发布帖子、评论、收藏、点赞等功能,需要先登录,定义一个登录装饰器,在游客点击发布评论等操作时跳转到登录页面:

def loginFirst(fabu):
    @wraps(fabu)  
    def wrapper(*args, **kwargs):  # 定义wrapper函数将其返回,用*args, **kwargs把原函数的参数进行传递
        if session.get('user'):  # 只有经过登陆,session才能记住并get到值
            return fabu(*args, **kwargs)
        else:
            return redirect(url_for('denglu'))

    return wrapper
7、定义上下文处理器,定义变量然后在所有模板中都可以调用:

#上下文处理器
@app.context_processor def mycontext(): user
= session.get('user') user_id = session.get('user_id') if user: return {'username': user, 'sessionuserid': user_id} else: return {}

 

8、在评论、收藏、点赞等操作时,需要定义一个参数,例如comment、dianzan、shoucang,这个参数包含了详情、发布者id和评论者id,将对象从表单中接受到的数据commit存到数据库中:

 

# 跳转评论。
@app.route('/comment/', methods=['POST'])
@loginFirst  
def comment():
    detail = request.form.get('pinglun') 
    author_id = User.query.filter(User.username == session.get('user')).first().id
    fabu_id = request.form.get('fa_id')
    comment = Comment(detail=detail, author_id=author_id, fabu_id=fabu_id)  
    db.session.add(comment)  # 执行操作
    db.session.commit()  # 提交到数据库
    return redirect(url_for('fabuview', fabu_id=fabu_id))  # 重定向到fabuview请求时要带fabu_id

 

9、在做用户个人中心时,定义了几个tag,将各个页面区分开,在执行不同的请求时跳到不同的页面:

# 跳转用户详情
@app.route('/yonghu/<username_id>/<tag>')  
def yonghu(username_id, tag):
    user = User.query.filter(User.id == username_id).first()
    shoucang = Shoucang.query.filter(Shoucang.author_id == username_id).all()
    context = {
        'userid': user.id,
        'username': user.username,
        'nickname': user.nickname,
        'fabus': user.fabu,
        'comments': user.comments,
        'shoucang': shoucang,
        'user': username_id

    } 
    if tag == '1':
        return render_template('usercenter1.html', **context)
    elif tag == '2':
        return render_template('usercenter2.html', **context)
    elif tag == '3':
        return render_template('usercenter3.html', **context)
    elif tag=='4':
        return render_template('usercenter4.html', **context)
    else:
        return render_template('password_update.html', **context)

 

10、在做模糊查找时可参考:

# 模糊查找
@app.route('/search')
def search():
    qu = request.args.get('q')
    c = '' if request.args.get('c') == '' else request.args.get('c')
    y = '' if request.args.get('y') == '' else request.args.get('y')
    query = Fabu.query.filter(
        or_(
            Fabu.title.contains(qu),
            Fabu.detail.contains(qu),
        ),
        Fabu.cf.like('%' + c + '%'),
        Fabu.creat_time.like('%' + y + '%'),
    ).order_by('-creat_time').all()
    context = {
        'questions': query,
        'cf': Cf.query.all(),
    }
    return render_template('daohang.html', **context)

 

11、在html文件中定义{% X in Y}可进行迭代排序:

 {% for foo in fabus %}
                  <tr>
                    <td><a href="{{ url_for('fabuview',fabu_id=foo.id) }}">{{ foo.title }}</a></td>
                     <td><span class="    "></span><em>
                     <small>作者:{{ foo.author.username }}</small>
                      </em></td>
                  </tr>
 {% endfor %}

12、
子模板继承父模板 {% extends 'base.html’ %}
  1. 父模板提前定义好子模板可以实现一些自己需求的位置及名称。
    1. <title>{% block title %}{% endblock %}-首页</title>
    2. {% block head %}{% endblock %}
    3. {% block main %}{% endblock %}
  2. 子模板中写代码实现自己的需求。
    1.   {% block title %}登录{% endblock %}
{% extends 'daohang.html' %}
{% block daohangtitle %}发布详情{% endblock %}
{% block daohanghead %}{% endblock %}
{% block daohangbody %}


四、成品展示

 

 

 

 

 

 

五、总结

python的学习已有一年,比刚开始的一无所知好多了,但依然任重道远,一步步来吧。flask框架是一个非常灵活的框架,希望继续深入学习。

 

 posted on 2018-06-16 20:13  048刘思华  阅读(237)  评论(0编辑  收藏  举报