管理信息系统 课程设计

一、系统概要说明

我这次课程设计的主题是影评,一个可以让用户发表电影评论的平台,其他用户看到这篇影评可以发表他的评论,让用户能参与互动,这样用户交流更加的便捷。用户在首页可以对帖子进行搜索,这样更方便用户搜索到感兴趣的电影影评。因此,系统的设计包括登录、注册、首页、帖子发布、帖子搜索、详情页、个人中心。使用的工具是Pycharm跟Mysql。

二、网站结构设计

 

 

在设计网站的过程中想要给每个页面都加上一个顶部导航,但是如果在每个页面都定义一个导航的话就会显得很麻烦,所以使用了模板跟子叶的方式来做页面。定义一个母板,在子页继承需要的部分,可以达到简化代码的效果,在母板定义了头部的链接块,在母板主体部分定义了主体块,在底部定义了页脚块,这些都在子页进行使用。

页面设计方面包括了首页、登录和注册页面、帖子发布页面、帖子详情页、个人中心、个人中心里面包括了上传头像功能、修改信息功能、查询收藏、查询发布的帖子这些功能。

三、模块详细设计

1.首页

@bp.route('/')
def index():

     board_id = request.args.get('bd',type=int,default=None)
     page = request.args.get(get_page_parameter(),type=int, default=1)
     boards = BoardModel.query.all()
     start =(page-1)*config.PER_PAGE
     end = start + config.PER_PAGE
     total = 0

     query_obj=PostModel.query.order_by(PostModel.create_time.desc())
     if board_id:
         query_obj = query_obj.filter_by(board_id=board_id)
         posts = query_obj.slice(start,end)
         total = query_obj.count()
     else:
         posts = query_obj.slice(start,end)
         total = query_obj.count()
     pagination = Pagination(bs_version=3,page=page,total=total,outer_window=0,inner_window=2)
     context={
         'boards': boards,
         'posts':posts,
         'pagination':pagination,
         'current_board':board_id
     }
     return render_template('front/front_index.html',**context)

首页里面包含的东西很多,有用户发表的帖子,分页功能,这些数据都是通过context传过去相应的html页面再进行显示的,在帖子数量多的时候会进行分页,这样做显得比较人性化,超过十条帖子就会进行分页,这样页面看起来比较的简洁。首页是前端的模块,这些前端功能都定义在前端文件夹的视图文件views.py里面。

2.注册

#注册功能后台视图
class SignupView(views.MethodView):
    def get(self):
        return_to = request.referrer
        if return_to and return_to != request.url and safeutils.is_safe_url(return_to):
            return  render_template('front/front_signup.html',return_to=return_to)
        else:
            return render_template('front/front_signup.html')
    def post(self):
        form = SignupForm(request.form)
        if form.validate():
            email = form.email.data
            username = form.username.data
            password = form.password1.data
            user = FrontUser(email=email,username=username,password=password)
            db.session.add(user)
            db.session.commit()
            return restful.success()
        else:
            print(form.get_error())
            return restful.params_error(message=form.get_error())

注册功能使用到了AJAX技术,与传统的表单提交方式不同,AJAX是先获取页面的值然后去表单判断

class SignupForm(BaseForm):
    email = StringField(validators=[Email(message='请输入正确的邮箱格式'), InputRequired(message='请输入邮箱')])
    username = StringField(validators=[Regexp(r".{2,20}", message='请输入正确格式的用户名!')])
    password1 = StringField(validators=[Regexp(r"[0-9a-zA-Z_\.]{6,20}", message='请输入正确格式的密码!')])
    password2 = StringField(validators=[EqualTo("password1", message='两次输入的密码不一致!')])

在表单进行判断数据是否输入正确,这时候表单是没有进行提交到后台的,只有表单验证通过之后才会进行提交,进行数据库的操作。注册功能其实就是数据库的查询与插入,如果在表单判断到后台有这个用户名的话就用javascript的弹窗提示用户说用户名有误,请重新输入,密码判断也是通过javascript进行提示,验证都通过之后就会将数据提交到后台,执行数据库的插入操作,完成注册。

3.登录

#登录功能后台视图
class SigninView(views.MethodView):
    def get(self):
        return_to = request.referrer
        if return_to and return_to != request.url and return_to != url_for("front.signup") and safeutils.is_safe_url(
                return_to):
            return render_template('front/front_signin.html', return_to=return_to)
        else:
            return render_template('front/front_signin.html')
    def post(self):
        form =SigninForm(request.form)
        if form.validate():
            email = form.email.data
            password = form.password.data
            remember = form.remeber.data
            user = FrontUser.query.filter_by(email=email).first()
            if user and user.check_password(password):
                session[config.FRONT_USER_ID]=user.id
                if remember:
                    session.permanent= True
                return
restful.success()
            else:
                return restful.params_error(message='邮箱或密码错误!')
        else:
            return restful.params_error(message=form.get_error())

登录功能与注册功能类似,也是使用AJAX技术,去后台表单进行判断,如果数据库用户表存在一个用户的用户名跟密码与输入的账户跟密码一致就登录到首页,并且通过session的传值将用户ID传到首页,有了这个值就可以完成后面的个人中心的设计。

4.帖子发布

def login_required(func):
    @wraps(func)
    def inner(*args,**kwargs):
        if config.FRONT_USER_ID in session:
            return func(*args,**kwargs)
        else:
            return redirect(url_for('front.signin'))
    return inner
 

帖子发布功能只有在用户登录之后才可以使用,如此一来就要定义一个装饰器,通过session去判断用户是否登录,如果判断成功则可以发布,如果判断用户没有登录则跳转到登录页面。这也是为什么用户登录成功之后要把session值传到页面的原因。

@bp.route('/apost/',methods=['GET','POST'])
@login_required
def apost():
    if request.method == 'GET':
        boards = BoardModel.query.all()
        return render_template('front/front_apost.html', boards=boards)
    else:
        form = AddPostForm(request.form)
        if form.validate():
            title = form.title.data
            content = form.content.data
            board_id = form.board_id.data
            board = BoardModel.query.get(board_id)
            if not board:
                return restful.params_error(message='没有这个板块!')
            post = PostModel(title=title, content=content)
            post.board = board
            post.author= g.front_user
            db.session.add(post)
            db.session.commit()
            return restful.success()
        else:
            return restful.params_error(message=form.get_error())

帖子发布功能通过获取用户在页面获取到输入的各项数值,然后将其提交到数据库进行插入操作完成帖子发布。

5.搜索

@bp.route('/search/')
def search():
    qu = request.args.get('q')
    ques = PostModel.query.filter(
        and_(
            PostModel.title.contains(qu)
        )
    ).order_by('-create_time')
    board_id = request.args.get('bd', type=int, default=None)
    page = request.args.get(get_page_parameter(), type=int, default=1)
    boards = BoardModel.query.all()
    start = (page - 1) * config.PER_PAGE
    end = start + config.PER_PAGE
    total = 0

    query_obj = PostModel.query.order_by(PostModel.create_time.desc())
    if board_id:
        query_obj = query_obj.filter_by(board_id=board_id)
        posts = query_obj.slice(start, end)
        total = query_obj.count()
    else:
        posts = query_obj.slice(start, end)
        total = query_obj.count()
    pagination = Pagination(bs_version=3, page=page, total=total, outer_window=0, inner_window=2)
    context = {
        'boards': boards,
        'posts': ques,
        'pagination': pagination,
        'current_board': board_id

    }

    return render_template('front/front_index.html',**context)

搜索功能通过获取到用户输入的关键字,查找到这条记录,然后赋值给ques,再将ques放到context里面传到前端,点击搜索按钮之后,这些过程就会执行,然后将查询出来的数据展示在首页。

6.个人中心页面

#个人中心
@bp.route('/usercenter/<user_id>/<tag>')
@login_required
def usercenter(user_id,tag):
    user = FrontUser.query.filter(FrontUser.id==user_id).first()
    posts = PostModel.query.filter(PostModel.author_id == user_id).all()
    collection = CollectionModel.query.filter(CollectionModel.user_id ==user_id).all()
    context = {
        'user':user,
        'posts':posts,
        'collection':collection
    }
    if tag == '1':
        return render_template('front/front_usercenter.html',**context)
    if tag == '2':
        return render_template('front/front_user_apost.html',**context)
    else:
        return render_template('front/front_user_collection.html',**context)
 
#用户修改个人信息
@bp.route('/user_updata/<user_id>',methods=['GET','POST'])
@login_required
def user_updata(user_id):
    if request.method == 'GET':
        user= FrontUser.query.filter(FrontUser.id==user_id).first()
        return render_template('front/front_user_updata.html',user=user)
    else:
        form = UserupdataForm(request.form)
        if form.validate():
            username = form.username.data
            realname = form.realname.data
            signature = request.form.get('signature')
            user = g.front_user
            user.username =username
            user.realname = realname
            user.signature = signature
            db.session.commit()
            return restful.success()
        else:
            return restful.params_error(form.get_error())


#用户修改密码
@bp.route('/resetpwd/',methods=['GET','POST'])
@login_required
def resetpwd():
    if request.method == 'GET':
        return render_template('front/front_resetpwd.html')
    else:
        form = ResetpwdForm(request.form)
        if form.validate():
            oldpwd = form.oldpwd.data
            newpwd = form.newpwd.data
            user = g.front_user
            if user.check_password(oldpwd):
                user.password = newpwd
                db.session.commit()
                # {"code":200,message=""}
                # return jsonify({"code":200,"message":""})
               
return restful.success()
            else:
                return restful.params_error("旧密码错误!")
        else:
            return restful.params_error(form.get_error())
 
#用户修改个人信息
@bp.route('/user_updata/<user_id>',methods=['GET','POST'])
@login_required
def user_updata(user_id):
    if request.method == 'GET':
        user= FrontUser.query.filter(FrontUser.id==user_id).first()
        return render_template('front/front_user_updata.html',user=user)
    else:
        form = UserupdataForm(request.form)
        if form.validate():
            username = form.username.data
            realname = form.realname.data
            signature = request.form.get('signature')
            user = g.front_user
            user.username =username
            user.realname = realname
            user.signature = signature
            db.session.commit()
            return restful.success()
        else:
            return restful.params_error(form.get_error())


#用户修改密码
@bp.route('/resetpwd/',methods=['GET','POST'])
@login_required
def resetpwd():
    if request.method == 'GET':
        return render_template('front/front_resetpwd.html')
    else:
        form = ResetpwdForm(request.form)
        if form.validate():
            oldpwd = form.oldpwd.data
            newpwd = form.newpwd.data
            user = g.front_user
            if user.check_password(oldpwd):
                user.password = newpwd
                db.session.commit()
                # {"code":200,message=""}
                # return jsonify({"code":200,"message":""})
               
return restful.success()
            else:
                return restful.params_error("旧密码错误!")
        else:
            return restful.params_error(form.get_error())
 

个人中心根据session的ID进入,里面展示了用户发表的帖子,用户收藏的文章,还有用户的个人信息。在个人中心里面可以进行头像上传,密码修改,个人信息修改,这些功能也是使用了AJAX技术来提交的。

四、数据库设计

这次课程设计使用到了六个表,这六个表包括了系统里面所有的功能。有用户表、帖子表、评论表、收藏表、点赞表、板块表。数据库表的设计定义在models.py文件里面而不是在主py文件里面,这样的目的是为了数据库的可维护性。因为模型分离可以在后期对数据库里面的表进行增加删除操作,这些只需要在命令行就可一完成,提高了代码的可重复利用还有可维护性。这样的数据库设计也比较合理。合理的定义主键跟外键可以使得表之间联系起来,可以通过一个表的主键去获得另外一个表的信息。

 

class BoardModel(db.Model):
    __tablename__='board'
   
id = db.Column(db.Integer,primary_key=True,autoincrement=True)
    name = db.Column(db.String(20),nullable=False)
    create_time = db.Column(db.DateTime,default=datetime.now)

class PostModel(db.Model):
    __tablename__ ='post'
   
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
    title = db.Column(db.String(200),nullable=False)
    content = db.Column(db.Text,nullable=False)
    create_time = db.Column(db.DateTime,default=datetime.now)
    board_id = db.Column(db.Integer,db.ForeignKey("board.id"))
    author_id = db.Column(db.String(100),db.ForeignKey("front_user.id"),nullable=False)
    author = db.relationship("FrontUser",backref="posts")
    board=db.relationship("BoardModel",backref="posts")

class CommentModel(db.Model):
    __tablename__='comment'
   
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
    content = db.Column(db.Text,nullable=False)
    create_time = db.Column(db.DateTime,default=datetime.now)
    post_id = db.Column(db.Integer,db.ForeignKey("post.id"),nullable=False)
    author_id = db.Column(db.String(100),db.ForeignKey("front_user.id"),nullable=False)
    post = db.relationship("PostModel",backref='comments')
    author = db.relationship("FrontUser",backref='comments')

class DianzanModel(db.Model):
    __tablename__ = 'dianzan'
   
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
    post_id = db.Column(db.Integer, db.ForeignKey("post.id"), nullable=False)
    user_id = db.Column(db.String(100), db.ForeignKey("front_user.id"), nullable=False)
    post = db.relationship("PostModel", backref=("dianzan"))
    user = db.relationship("FrontUser", backref=("dianzan"))

class CollectionModel(db.Model):
    __tablename__ = 'collection'
   
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
    user_id = db.Column(db.String(100), db.ForeignKey("front_user.id"), nullable=False)
    post_id = db.Column(db.Integer, db.ForeignKey("post.id"), nullable=False)
    create_time = db.Column(db.DateTime, default=datetime.now)
    post = db.relationship("PostModel", backref=("collection"))
    user = db.relationship("FrontUser", backref=("collection"))

 

五、成果展示

登录界面

 

 

注册页面

 

 

首页

 

 

 

 

 

帖子发布

 

 

个人中心

 

 

头像上传

 

 

密码修改

 

 

个人信息修改

 

 

帖子详情

 

 

六、总结

在进行这次课程设计之后我意识到了一个好的网站不是随随便便就能完成的,一个好的网站需要大量的时间投入,需要不断的修改完善。在这个过程中遇到过许多困难,但是最终都通过网上百度文档和视频的教学解决了。学习是没有止境的,想要做一个专业的人员我还是有相当大的差距,以后会继续学习,不断提升自己的能力。

posted @ 2018-06-16 12:57  yishhaoo  阅读(1161)  评论(0编辑  收藏  举报