网站租赁最容易被低估的不是价格,而是“日期到底能不能下单”。企业版把这件事做成了购物车级规则,而不是某一行商品自己的小判断。
核心链路
controllers/main.py里的product()、_get_search_options()和_get_product_query_params()会把 start/end date 带进产品页、搜索和 URL 参数,因此“租期”从浏览开始就是网站上下文的一部分。- 到模型层,
sale.order._cart_add()若发现商品rent_ok,会先尝试补默认起止日期;一旦购物车里已有租赁日期,再加新商品时若日期不同就直接抛出 “You cannot mix different rental periods in the same order.”。 - 合法性判断集中在
_is_valid_renting_dates():它会把数据库里的 UTC 时间通过convert_to_website_tz()转换成网站时区,再检查是否落在过去、是否命中禁用星期、是否满足最短租期。 - 订单确认前,
_is_cart_ready()和_check_cart_is_ready_to_be_paid()还会二次把关;不是前端日期控件选得出来就能付钱,服务端仍会重新验证。 - 如果客户在购物车里改期,
_cart_update_renting_period()会先写入新日期,再检查可租性;失败时它会恢复旧日期并保留shop_warning。这就是为什么前端看起来像“系统没采纳我的改期”,实际上是后端主动回滚。
关键源码位置
/home/ubuntu/odoo-temp/enterprise/website_sale_renting/models/sale_order.py/home/ubuntu/odoo-temp/enterprise/website_sale_renting/controllers/main.py
容易误解的地方
- 误区一:租赁日期只影响单个商品行。企业版把租期视为整单属性,不能在同一单里混不同周期。
- 误区二:数据库里合法就代表网站上合法。
website.tz参与换算后,边界时间会变化。 - 误区三:前端选不到的日期才是非法日期。最短租期、禁用星期、过去 15 分钟缓冲等都是后端复核。
实战注意事项
- 跨时区卖租赁服务时,业务说明应明确以网站时区还是门店时区为准,不然用户会觉得“同一天被系统判成过去”。
- 如果要支持库存可租校验,应继续顺着
_available_dates_for_renting()这个 hook 扩展,而不是重写整套购物车逻辑。 - 测试时别只测“新增商品”,还要测“改期后购物车回滚”和“已有租赁商品后再加普通商品”的混搭场景。
结语
企业版这些代码共同说明一件事:真正可上线的业务流程,靠的不是“页面上看起来能点通”,而是权限、状态、时机、对账口径和跨模块回写都被收紧。理解这些边界,实施和二开时就不容易走进“功能演示能跑、真实业务一用就散”的坑。
DISCUSSION
评论区