美文网首页
基于Bottle 封装一下自用web前后端分离开发框架(1):项

基于Bottle 封装一下自用web前后端分离开发框架(1):项

作者: 小钟钟同学 | 来源:发表于2019-12-26 11:50 被阅读0次

    因起初开始自己入门web的时候,是由以前我们的大牛主管来引导,非常感谢他一直以来的指导。接下来的系列文章主要是自己再这几天使用了flask之后,尝试继续使用Bottle封装成类似的那种来处理。

    关于代码说明

    每一章节对应当前主题的代码来提供。
    

    框架说明

    • Token令牌:使用JWT令牌机制,可用于单页面应用程序,合适做前后端分离等应用
    • bottle全局异常处理
    • 使用wtforms表单验证相关的表单提交参数
    • 重写HTTPError 统一异常返回格式,方便前端开发
    • 更详细log日志记录,记录整个请求链路相关记录,也可以记录自己定义记录
    • peewee orm数据库的使用和简单封装
    • 类似Flask蓝图应用

    详细日志记录示例如下:

     2019-12-27 16:56:04:121 | process_id:40532 process_name:MainProcess | thread_id:24044 thread_name:MainThread | INFO |
    {
        "headers":"{     "Content-Length": "0",     "Content-Type": "text/plain",     "Aaa": "sadasd",     "Sfdsdui": "sdasd",     "User-Agent": "PostmanRuntime/7.21.0",     "Accept": "*/*",     "Cache-Control": "no-cache",     "Postman-Token": "75287742-d0c9-429a-bdc5-f03072480e8d",     "Host": "127.0.0.1:8889",     "Accept-Encoding": "gzip, deflate",     "Connection": "keep-alive" }",
        "host":"127.0.0.1:8889",
        "ip":"127.0.0.1",
        "url":"[http://127.0.0.1:8889/?sdasd=43543&username=22222222222&AAAAAAAAAAAA=%E8%AF%B4%E7%9A%84%E5%B0%B1%E6%98%AF%E7%9A%84%E5%AF%8C%E5%AE%B6%E5%A4%A7%E5%AE%A4](http://127.0.0.1:8889/?sdasd=43543&username=22222222222&AAAAAAAAAAAA=%E8%AF%B4%E7%9A%84%E5%B0%B1%E6%98%AF%E7%9A%84%E5%AF%8C%E5%AE%B6%E5%A4%A7%E5%AE%A4)",
        "method":"POST",
        "params":{
            "query_string":"sdasd=43543&username=22222222222&AAAAAAAAAAAA=说的就是的富家大室",
            "query":{
                "sdasd":"43543",
                "username":"22222222222",
                "AAAAAAAAAAAA":"说的就是的富家大室"
            },
            "forms":""
        },
        "req_stime":"2019-12-27 16:56:03.773712",
        "req_links_logs":[
            {
                "link_index":1,
                "event_des":"请求开始"
            },
            {
                "link_index":2,
                "event_des":"第三方接口请求日志",
                "msg_dict":{
                    "url":"[https://www.baidu.com](https://www.baidu.com/)",
                    "method":"GET",
                    "params":null,
                    "params_str":"None",
                    "this_time_out":"15s",
                    "req_stime":"2019-12-27 16:56:03",
                    "cost_time":58.509,
                    "state_code":"200",
                    "result":"<!DOCTYPE html> <!--STATUS OK--><html> <head><meta http-equiv=content-type content=text/html;charset=utf-8><meta http-equiv=X-UA-Compatible content=IE=Edge><meta content=always name=referrer><link rel=stylesheet type=text/css href=https://ss1.bdstatic.com/5eN1bjq8AAUYm2zgoY3K/r/www/cache/bdorz/baidu.min.css><title>百度一下,你就知道</title></head> <body link=#0000cc> <div id=wrapper> <div id=head> <div class=head_wrapper> <div class=s_form> <div class=s_form_wrapper> <div id=lg> <img hidefocus=true src=//www.baidu.com/img/bd_logo1.png width=270 height=129> </div> <form id=form name=f action=//www.baidu.com/s class=fm> <input type=hidden name=bdorz_come value=1> <input type=hidden name=ie value=utf-8> <input type=hidden name=f value=8> <input type=hidden name=rsv_bp value=1> <input type=hidden name=rsv_idx value=1> <input type=hidden name=tn value=baidu><span class="bg s_ipt_wr"><input id=kw name=wd class=s_ipt value maxlength=255 autocomplete=off autofocus=autofocus></span><span class="bg s_btn_wr"><input type=submit id=su value=百度一下 class="bg s_btn" autofocus></span> </form> </div> </div> <div id=u1> <a href=http://news.baidu.com name=tj_trnews class=mnav>新闻</a> <a href=https://www.hao123.com name=tj_trhao123 class=mnav>hao123</a> <a href=http://map.baidu.com name=tj_trmap class=mnav>地图</a> <a href=http://v.baidu.com name=tj_trvideo class=mnav>视频</a> <a href=http://tieba.baidu.com name=tj_trtieba class=mnav>贴吧</a> <noscript> <a href=http://www.baidu.com/bdorz/login.gif?login&tpl=mn&u=http%3A%2F%2Fwww.baidu.com%2f%3fbdorz_come%3d1 name=tj_login class=lb>登录</a> </noscript> <script>document.write('<a href="http://www.baidu.com/bdorz/login.gif?login&tpl=mn&u='+ encodeURIComponent(window.location.href+ (window.location.search === "" ? "?" : "&")+ "bdorz_come=1")+ '" name="tj_login" class="lb">登录</a>');                 </script> <a href=//www.baidu.com/more/ name=tj_briicon class=bri style="display: block;">更多产品</a> </div> </div> </div> <div id=ftCon> <div id=ftConw> <p id=lh> <a href=http://home.baidu.com>关于百度</a> <a href=http://ir.baidu.com>About Baidu</a> </p> <p id=cp>©2017 Baidu <a href=http://www.baidu.com/duty/>使用百度前必读</a>  <a href=http://jianyi.baidu.com/ class=cp-feedback>意见反馈</a> 京ICP证030173号  <img src=//www.baidu.com/img/gs.gif> </p> </div> </div> </div> </body> </html> "
                },
                "remarks":"第三方接口请求【OK】"
            },
            {
                "link_index":3,
                "event_des":"第三方接口请求日志",
                "msg_dict":{
                    "url":"[https://juejin.im/post/5dee431c518825122e0a764c](https://juejin.im/post/5dee431c518825122e0a764c)",
                    "method":"POST",
                    "params":{
                        "ssdsd":230
                    },
                    "params_str":"{'ssdsd': 230}",
                    "this_time_out":"15s",
                    "req_stime":"2019-12-27 16:56:04",
                    "cost_time":179.218,
                    "state_code":"404",
                    "result":"<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <title>Error</title> </head> <body> <pre>Cannot POST /post/5dee431c518825122e0a764c</pre> </body> </html> "
                },
                "remarks":"第三方接口请求【FAIL】,status_code:404 错误"
            },
            {
                "link_index":4,
                "event_des":"第三方接口请求日志",
                "msg_dict":{
                    "url":"[https://www.jianshu.com/p/c192f3dc3e0c](https://www.jianshu.com/p/c192f3dc3e0c)",
                    "method":"POST",
                    "params":{
                        "ssdsd":230
                    },
                    "params_str":"{'ssdsd': 230}",
                    "this_time_out":"15s",
                    "req_stime":"2019-12-27 16:56:04",
                    "cost_time":96.011,
                    "state_code":"403",
                    "result":"<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html> <head><title>403 Forbidden</title></head> <body bgcolor="white"> <h1>403 Forbidden</h1> <p>You don't have permission to access the URL on this server. Sorry for the inconvenience.<br/> Please report this message and include the following information to us.<br/> Thank you very much!</p> <table> <tr> <td>URL:</td> <td>https://www.jianshu.com/p/c192f3dc3e0c</td> </tr> <tr> <td>Server:</td> <td>zurich</td> </tr> <tr> <td>Date:</td> <td>2019/12/27 16:56:04</td> </tr> </table> <hr/>Powered by Tengine</body> </html> "
                },
                "remarks":"第三方接口请求【FAIL】,status_code:403 错误"
            },
            {
                "link_index":5,
                "event_des":"请求结束"
            }
        ],
        "rsp_data":{
            "msg":"roleId 必须传入",
            "code":400,
            "error_code":10031
        },
        "cost_time":"353.0"
    }
    
    

    长远目标计划

    基于Bottle做一个简单后台权限管理系统,自用
    系统是基于https://github.com/wuyouzhuguli/FEBS-Vue的前端源码上来做,后端就改成了我自己用bottle

    1.登入界面

    image.png

    2.系统主页

    image.png
    image.png
    image.png
    image.png
    image.png
    image.png

    3.数据分析页

    image.png

    本文目标

    • 框架模块分层

    准备环节

    关于环境安装等问题,在此也不再重复的叙述,其实网上也有大把的教程。

    项目规划

    因为后续我们的很多的项目都依赖一个公共的基础库,而且相关的开发都是基于自由的基础库上进行开发,所以我个人的洗好,则是把相关的一些基础的放在同一个大项目文件夹下,这样也方便后续的其他微服务开发。

    项目总体结构

    1. 基础库划分

    因为我个人的喜欢,还是喜欢把一些独立的东西放在独立的包下去管理。可能划分多也未必是好事,不过目前我基础库也不算是非常多,所有相关的包都是独立的。

    image.png

    相关的包的解析如下:

    - lib 一些其他第三库源码包
    - xcache 关于redis缓存工具包
    - xcors 关于bottle跨域的处理包
    - xexception 关于bottley全局异常捕获插件包
    - xtyform 关于bottle表单验证处理包
    - xwtforms 关于bottle使用WTForms表单验证处理包
    - xhelper 关于常用一些工具类的封装
    - xhttp 关于reuqests简单的封装,加上日志记录
    - xlog 日志记录初始化基础吧包
    - xmodels 关于peewee基础modeljw包
    - xplugins 其他插件包的封装
    - xresponse 关于响应报文统一封装包统一返回格式,方便前端开发
    - xscheduler 任务调度基础
    - xsingnal 信号库的简单封装,封装发送信号和接受信号的装饰器
    

    2. API相关开发

    因为每个项目都是独立的,所以后续各自项目开发人员都负责自己的项目即可。相关基础库原则上,只需要新增相关其他方法,后续同步上不及时的问题,也不会因为某个人修改了基础库,导致某个项目异常等问题。

    项目划分明细

    相关的包的解析如下:

    - api 项目设计接口开发路由
    - apirsp 统一定义返回响应体
    - config 项目设计常量等信息配置(一般线上的话可能 会写入环境变量中)
    - jobs  定义相关定时任务或消息队列任务
    - log app产品的日志记录
    - models 数据库下对于的ORM模型
    - utils 针对此应用下一些特定的工具类
    - validators 封装当前API接口使用到的表单校验器
    - x-tests API单元测试
    -- app 应用示例对象
    -test-results.xml 测试结果
    - test_start 加载x-tests下的测试用例,执行测试脚本
    

    总结

    因为个人喜欢问题,可能相关分包其实是有问题,过多的分包后期也许可能对管理来说可能会有点不好,不过,我个人喜欢的事一个独立的包处理独立的事,所以分包上,可能有点个人形式主义。

    相关文章

      网友评论

          本文标题:基于Bottle 封装一下自用web前后端分离开发框架(1):项

          本文链接:https://www.haomeiwen.com/subject/hsyfoctx.html