【自学开发之旅】Flask-restful-Jinjia页面编写template-回顾(五)

restful是web编程里重要的概念

-- 一种接口规范也是一种接口设计风格

设计接口:

要考虑:数据返回、接收数据的方式、url、方法

统一风格

rest--表现层状态转移

web--每一类数据--资源

资源通过http的动作来实现状态转移 GET、PUT、POST、DELETE

path组成:

/{version}/{resources}/{resource_id}

restful api设计

方法

/v1/product POST 新增

GET 查询所有

/v1/product/id PUT 修改

DELETE 删除

GET 查询某一个

router/product_view/product_api.py

bash 复制代码
from flask import Blueprint, request
from flask_restful import Api, Resource
from libs.response import generate_response
from . import product_bp

# 将restful api对象和蓝图绑定
api = Api(product_bp)

# 每个资源就是类,定义类
class ProductView(Resource):
    def get(self, id = None):
        return generate_response(msg="get product")
    def post(self):
        generate_response(msg="add product")
    def put(self, id):
        generate_response(msg="modify success!")
    def delete(self, id):
        return generate_response(msg="delete success!")


# 路由
api.add_resource(ProductView, "/product")
api.add_resource(ProductView, "/product/<id>", endpoint="productid")

为什么要设置endpoint:由flask路由管理可知endpoint全局唯一,不指定的话都会默认endpoint为函数名(这里为类名)ProductView重复名了。

这行代码是使用Flask框架(一个Python微型web框架)来定义一个路由。'api.add_resource'是Flask-RESTful扩展提供的方法,用于将资源(这里是'ProductView')映射到URL(这里是'/product')。'ProductView'可能是一个你定义的类,它继承自Flask-RESTful的'Resource'类,用于处理与产品相关的HTTP请求。'/product'是URL路径,当用户发送请求到这个路径时,Flask会调用'ProductView'类中对应的方法来处理请求。

接着将增删改查功能都实现restful接口规范

router/product_view/product_api.py

bash 复制代码
"""
@date: 2023/9/12
@file: product_api
@author: Jiangda
@desc: test

"""
from flask import Blueprint, request
from flask_restful import Api, Resource
from libs.response import generate_response
from . import product_bp
from models.product import ProductInfo
from models import db

# 将restful api对象和蓝图绑定
api = Api(product_bp)

# 每个资源就是类,定义类
class ProductView(Resource):
    def get(self, id = None):
        if id:
            result = ProductInfo.query.get(id)
        else:
            result = ProductInfo.query.all()
        if result:
            if isinstance(result, list):
                result2 = [dict(pro) for pro in result]
            else:
                result2 = dict(result)
            return generate_response(msg="get success!", data=result2)
        else:
            return generate_response(code=1010, msg="data empty!")
    def post(self):
        pro_name = request.json.get("proname")
        pro_kind = request.json.get("prokind")
        pro_price = request.json.get("proprice")
        pro_address = request.json.get("proadd")
        if pro_name and pro_kind and pro_price and pro_address:

            proinfo = ProductInfo(product_name = pro_name,
                                  product_kind = pro_kind,
                                  product_price = pro_price,
                                  product_address = pro_address)
            db.session.add(proinfo)
            db.session.commit()
            return generate_response(msg="add success!")
        else:
            return generate_response(msg="add fail!", code=1011)
    def put(self, id):
        p1 = ProductInfo.query.get(id)
        if p1:
            # 接收客户端的传递
            pro_name = request.json.get("proname")
            pro_kind = request.json.get("prokind")
            pro_price = request.json.get("proprice")
            pro_address = request.json.get("proadd")

            p1.product_name = pro_name
            p1.product_kind = pro_kind
            p1.product_price = pro_price
            p1.product_address = pro_address

            db.session.add(p1)
            db.session.commit()
            return generate_response(msg="modify success!")
        else:
            return generate_response(msg="no such product!", code=1012)
    def delete(self, id):
        p2 = ProductInfo.query.get(id)
        if p2:
            db.seesion.delete(p2)
            db.session.commit()
            return generate_response(msg="delete success!")
        else:
            return generate_response(msg="delete failed!", code=1013)

# 路由
api.add_resource(ProductView, "/product")
api.add_resource(ProductView, "/product/<id>", endpoint="productid")

不做前后端分离的项目的话:直接返回网页 web开发模式:MVC(model数据模型+view视图用户界面+control控制路由查找)

flask -- MTV模型(M-model,T-template,V-view),写网站(Jinjia模板引擎)

router/view01.py

bash 复制代码
#render_template()函数:页面渲染
import render_template
@view01_bp.route("index2")
def index2():
    return render_template("index.html", message = "hello k8s")

templates/index.html

bash 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
{{ message }}
<img src="/static/images/k8s.jpg">
</body>
</html>

使用bootstrap4实例:

router/product_view/product.py

添加

bash 复制代码
import render_template


return render_template("product.html", prolist=result2)

访问http://127.0.0.1:9000/v1/product/get

templates/product.html

在body加入

bash 复制代码
  <table class="table">
      <th><td>产品名称</td>
      <td>产品种类</td>
      <td>产品价格</td>
      <td>产品产地</td>
      </th>
      {% for pro in prolist %}
      <tr><td></td>
      <td>{{ pro["product_name"] }}</td>
      <td>{{ pro["product_kind"] }}</td>
      <td>{{ pro["product_price"] }}</td>
      <td>{{ pro["product_address"] }}</td>
  </tr>
      {% endfor %}
  </table>

加按钮,且利用url_for()通过endpoint找url

templates/product.html

html 复制代码
<td>操作</td>
<td><button type="button" class="btn btn-light"><a href="{{ url_for('product_bp.productdelete', id = pro.product_id) }}">删除</a></button></td>

router/product_view/product2.py

html 复制代码
@product_bp.route("/product2/delete", methods=['GET'])
def productdelete():
    id = request.args.get("id")
    p2 = ProductInfo.query.get(id)
    if p2:
        db.session.delete(p2)
        db.session.commit()
        return render_template("product.html",msg="delete success!")
    else:
        return generate_response(msg="no such product", code=6)

添加增加功能

router/product_view/product2.py

html 复制代码
@product_bp.route("/product2/add" ,methods=['GET','POST'])
def productadd():
    # 接收客户端的传递
    pro_name = request.form.get("proname")
    pro_kind = request.form.get("prokind")
    pro_price = request.form.get("proprice")
    pro_address = request.form.get("proadd")

    proinfo = ProductInfo(product_name = pro_name,
                          product_kind = pro_kind,
                          product_price = pro_price,
                          product_address = pro_address)

    # 生效到数据库
    db.session.add(proinfo)
    db.session.commit()

    return render_template("product_add.html")

templates/product_add.html

html 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <link rel="stylesheet" type="text/css" href="/static/css/bootstrap.css">
</head>
<body>
<form method="post">

  <div class="form-group row">
    <label for="inputPassword" class="col-sm-2 col-form-label">产品名称</label>
    <div class="col-sm-10">
      <input class="form-control" name="proname">
    </div>
  </div>

      <div class="form-group row">
    <label for="inputPassword" class="col-sm-2 col-form-label">产品类型</label>
    <div class="col-sm-10">
      <input class="form-control" name="prokind">
    </div>
  </div>

      <div class="form-group row">
    <label for="inputPassword" class="col-sm-2 col-form-label">产品价格</label>
    <div class="col-sm-10">
      <input class="form-control" name="proprice">
    </div>
  </div>

      <div class="form-group row">
    <label for="inputPassword" class="col-sm-2 col-form-label">产品产地</label>
    <div class="col-sm-10">
      <input class="form-control" name="proadd">
    </div>
  </div>
    <input type="submit" value="新增">
    <input type="reset" value="取消">
</form>
</body>
</html>

为什么用orm?什么是orm?

对象关系映射,它不需要和复杂的sql语句打交道,直接操控对象就是操控数据库,把表映射为类,把字段映射为属性,每一行记录映射为对象,提高我们开发的速度,方便开发。

可以不用,我们用过pymysql去创建sql语句去做的。

对象关系映射(Object Relational Mapping,简称ORM)是一种程序技术,用于实现面向对象编程语言里不同类型系统的数据之间的转换。它通过使用描述对象和数据库之间映射的元数据,将程序中的对象自动持久化到关系数据库中。

ORM的由来:面向对象是从软件工程基本原则(如耦合、聚合、封装)的基础上发展起来的,而关系数据库则是从数学理论发展而来的,两套理论存在显著的区别。为了解决这个不匹配的现象,对象关系映射技术应运而生。

简单的说,ORM是通过使用描述对象和数据库之间映射的元数据,将程序中的对象自动持久化到关系数据库中。 ORM提供了实现持久化层的另一种模式,它采用映射元数据来描述对象关系的映射,使得ORM中间件能在任何一个应用的业务逻辑层和数据库层之间充当桥梁。

什么是restful?

一种接口规范也是一种接口设计风格,一般来说api的设计都会遵循,他是表现层状态转移,它将每一类数据看做成资源,每一类资源又为其设计一种url,这种资源的增删改查通过http的动作(get post put delete)等方法来实现

RESTful是一种网络应用程序的设计风格和开发方式,基于HTTP,可以使用XML格式定义或JSON格式定义。它适用于移动互联网厂商作为业务使能接口的场景,实现第三方OTT调用移动网络资源的功能。

在RESTful中,每个资源都有一个唯一的URL,可以通过HTTP请求来获取或修改该资源的状态。RESTful采用了一种无状态协议,即服务器不维护与客户端的连接状态,每个请求都是独立的。这种无状态协议使得RESTful更加灵活和可扩展,可以轻松地支持并发请求和负载均衡。

RESTful的核心思想是将网络资源视为一种状态,并通过HTTP协议来传输和操作这些状态。在RESTful中,每个资源都有一个唯一的URL,可以通过HTTP请求来获取或修改该资源的状态。客户端使用GET、POST、PUT、DELETE4个表示操作方式的动词对服务端资源进行操作:GET用来获取资源,POST用来新建资源(也可以用于更新资源),PUT用来更新资源,DELETE用来删除资源。

统一接口返回

也是restful接口返回的一种规范,返回json数据,返回data,code,message。

相关推荐
Dyan_csdn2 小时前
【Python项目】基于深度学习的身份证识别考勤系统
python·深度学习
抠头专注python环境配置3 小时前
如何在Jupyter中快速切换Anaconda里不同的虚拟环境
人工智能·python·jupyter
安冬的码畜日常5 小时前
利用 Python 脚本批量创建空白 Markdown 笔记
开发语言·python·批量生成
一水鉴天7 小时前
为AI聊天工具添加一个知识系统 开发环境准备
python
sysu639 小时前
73.矩阵置零 python
开发语言·数据结构·python·线性代数·leetcode·面试·矩阵
代码的乐趣9 小时前
支持selenium的chrome driver更新到131.0.6778.264
chrome·python·selenium
爱喝热水的呀哈喽9 小时前
pytorch模型的保存失敗しましたが、
人工智能·pytorch·python
pzx_00110 小时前
【深度学习】通俗理解偏差(Bias)与方差(Variance)
人工智能·python·深度学习·算法·机器学习·集成学习
莲动渔舟11 小时前
Python自学 - 类进阶(可调用对象)
开发语言·python
Reese_Cool11 小时前
【Python】Python与C的区别
java·c语言·python