丽江市网站建设_网站建设公司_营销型网站_seo优化
2026/1/18 6:08:21 网站建设 项目流程

Day 81:【99天精通Python】项目篇 - 微信小程序后端开发 (下) - 业务接口实现

前言

欢迎来到第81天!

在昨天的课程中,我们成功搭建了小程序的用户认证系统,用户可以通过wx.login获取code,后端换取openid并返回一个自定义的 JWT Token。

今天,我们要在登录的基础上,开发真正的业务接口。我们将模拟一个简单的电商场景,实现:

  1. 商品列表的展示。
  2. 用户创建订单
  3. 用户查看自己的历史订单

这三个接口分别对应了 CRUD 中的R (Read)C (Create),并且会用到我们昨天写的@login_required装饰器。

本节内容:

  • 扩展数据库模型 (Product, Order)
  • 实现公开的商品列表 API
  • 实现受保护的下单 API
  • 实现受保护的用户订单查询 API
  • 前后端联调思路

一、数据库模型扩展

我们需要ProductOrder两张表。为了方便,我们继续使用 Flask-SQLAlchemy。

修改app.py(或者新建一个models.py拆分出去):

# app.pyfromflaskimportFlask,request,jsonify,gfromflask_sqlalchemyimportSQLAlchemy# ... (其他 import)app=Flask(__name__)# ... (配置)db=SQLAlchemy(app)classUser(db.Model):id=db.Column(db.Integer,primary_key=True)openid=db.Column(db.String(128),unique=True,nullable=False)classProduct(db.Model):id=db.Column(db.Integer,primary_key=True)name=db.Column(db.String(100),nullable=False)price=db.Column(db.Float,nullable=False)image_url=db.Column(db.String(255))classOrder(db.Model):id=db.Column(db.Integer,primary_key=True)user_id=db.Column(db.Integer,db.ForeignKey('user.id'),nullable=False)total_price=db.Column(db.Float,nullable=False)status=db.Column(db.String(20),default='pending')# pending, paid, shippedcreated_at=db.Column(db.DateTime,server_default=db.func.now())# 初始化数据库并添加示例商品definit_db():withapp.app_context():db.create_all()# 添加一些商品数据,如果它们不存在ifProduct.query.count()==0:products=[Product(name="Python 编程从入门到实践",price=68.5,image_url="/static/python-book.jpg"),Product(name="Flask Web 开发",price=55.0,image_url="/static/flask-book.jpg")]db.session.add_all(products)db.session.commit()print("示例商品已添加。")

二、API 1:获取商品列表 (公开)

这个接口不需要登录就能访问。

@app.route("/api/products",methods=["GET"])defget_products():products=Product.query.all()# 将对象列表转换为字典列表result=[{"id":p.id,"name":p.name,"price":p.price,"image_url":p.image_url}forpinproducts]returnjsonify(result)

三、API 2:创建订单 (受保护)

下单操作必须是登录用户才能进行,所以我们要用@login_required装饰器。

# app.pyfromutils.jwt_authimportlogin_required# 引入昨天的装饰器@app.route("/api/orders",methods=["POST"])@login_requireddefcreate_order():# 1. 获取请求数据data=request.get_json()product_id=data.get("product_id")quantity=data.get("quantity",1)# 2. 校验product=Product.query.get(product_id)ifnotproduct:returnjsonify({"error":"商品不存在"}),404# 3. 计算价格total=product.price*quantity# 4. 创建订单# g.user_id 是在装饰器里注入的new_order=Order(user_id=g.user_id,total_price=total,status="paid")db.session.add(new_order)db.session.commit()returnjsonify({"message":"下单成功","order_id":new_order.id}),201

四、API 3:获取我的订单 (受保护)

同样,用户只能看自己的订单。

@app.route("/api/orders",methods=["GET"])@login_requireddefget_my_orders():# 查询当前用户的所有订单user_orders=Order.query.filter_by(user_id=g.user_id).order_by(Order.created_at.desc()).all()result=[{"id":o.id,"total_price":o.total_price,"status":o.status,"created_at":o.created_at.strftime("%Y-%m-%d %H:%M")}foroinuser_orders]returnjsonify(result)

五、联调测试 (Postman)

  1. 初始化数据库

    • 运行python
    • from app import init_db; init_db()
    • 启动 Flaskpython app.py
  2. 获取商品GET http://127.0.0.1:5000/api/products,应该能看到商品列表。

  3. 登录

    • POST http://127.0.0.1:5000/api/login
    • Body:{"code": "从微信开发者工具拿到的临时code"}
    • 复制返回的token
  4. 下单

    • POST http://127.0.0.1:5000/api/orders
    • Headers:Authorization-> (刚才复制的 token)
    • Body:{"product_id": 1, "quantity": 2}
    • 应该返回 “下单成功”。
  5. 查订单

    • GET http://127.0.0.1:5000/api/orders
    • Headers:Authorization-> (token)
    • 应该能看到刚才下的订单。

六、常见问题

Q1:g对象是什么?

g(global) 是 Flask 提供的一个请求上下文全局变量。它在每次请求开始时创建,请求结束时销毁。非常适合在一次请求的不同函数间(比如装饰器和视图函数)传递数据。

Q2:server_default=db.func.now()有什么用?

这告诉数据库,当插入一条新记录且没有指定created_at时,直接使用数据库服务器的当前时间。这比在 Python 里datetime.now()更准。

Q3:为什么不直接把 openid 存 Token 里?

JWT 的 payload (载荷) 是 Base64 编码的,不是加密的,任何人都能解开。绝对不要在里面放敏感信息。user_id是我们自己系统的内部 ID,对外无意义,相对安全。


七、小结

这个小小的电商后端,已经包含了现代 Web 应用的核心要素:

  • 分层架构:工具类、模型、视图各司其职。
  • 用户认证:JWT 保证了接口安全。
  • 数据交互:ORM 简化了数据库操作。
  • RESTful 设计:清晰的 URL 和 HTTP 方法。

八、课后作业

  1. 订单详情:实现GET /api/orders/<order_id>接口,返回单个订单的详细信息(包含商品名、价格等,需要多表查询 Join)。
  2. 库存系统:给Product模型增加stock(库存) 字段。下单时检查库存,如果不足则返回错误;下单成功则扣减库存。
  3. 分页:当商品或订单数量很多时,需要分页。给GET /api/products接口增加pageper_page参数,并实现分页逻辑。

下节预告

Day 82:机器学习入门 - Scikit-Learn- Web 部分暂告一段落。明天,我们将进入 Python 的另一个王牌领域——机器学习,学习如何用sklearn库进行数据预测!


系列导航

  • 上一篇:Day 80 - 小程序后端开发上
  • 下一篇:Day 82 - 机器学习入门Scikit-Learn(待更新)

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询