首页/新闻资讯/正文详情

基于微信小程序与Django的工厂生产库存一体化系统

发布时间:2026/9/25 4:02:11 来源:云帆数科 栏目:资讯中心
基于微信小程序与Django的工厂生产库存一体化系统
做中小工厂的信息化项目最怕的不是代码难写而是需求本身是散的。车间主任要的是“今天排了几个单、做到哪一步”库管要的是“哪个料剩多少、够不够明天用”老板要的是“这批货到底什么时候能发”。三方看的东西不一样数据又不互通长期下来就成了各说各话。我做的这套“python基于微信小程序的工厂生产流程与库存管理一体化系统”就是典型的一体化解决思路后端用 Django 把生产工单、工序报工、原料领用、成品入库、库存台账放在一套数据体系里前端用微信小程序让一线人员扫码、点按就能操作。这篇文章我会把这套系统的架构、数据库设计、接口实现、小程序联调和上线后的踩坑记录都摊开讲适合正在做工厂数字化、MES 或进销存类项目的朋友参考。1. 项目为什么要做工厂数据孤岛与一体化思路1.1 车间、仓库与计划之间的三个账本我接手这个需求的时候先去现场转了三天发现工厂内部存在很典型的数据断层。计划科用的是 Excel 排产表每天早上把生产任务打印出来下发到车间车间领料靠手写领料单仓库凭单发料但实际用了多少、有没有超领没人回头核对产成品下线后车间填一张入库单送到仓库可仓库干活的师傅经常忙起来就忘记更新进销存软件。等到月底一对账库存对不上、工单耗料对不上最后只能安排人加班盘点把差异强行调整掉。这是很多中小制造企业都有的通病生产执行和库存管理在流程上强相关但在数据上是隔离的。生产不知道库存够不够仓库不知道工单进行到哪一步计划部门只能靠微信群来回确认。所以项目立项时客户提的第一句话不是“做好看一点”而是“能不能让我随时知道每一个工单现在到了哪道工序、该领的料有没有领完、库里还剩多少”。一体化系统的核心价值就体现在这里把“生产执行流”和“库存流水账”绑定在同一模型里。工单一下达系统自动算出物料的定额用量工人领料时扫码扣减库存系统同时把领料流水挂到工单上产品完工后报工入库库存增加。整条链路都在一套事务里哪个环节出问题都能追到源头。1.2 技术选型为什么是 Python Django 微信小程序选型阶段其实对比过几套方案。当时客户考虑过直接用市面上的 SaaS MES但工厂的工序划分和物料编码规则比较特殊定制费用高而且老板希望数据放在自己服务器上。自研的话前端有两种常见路线原生 App 和微信小程序。小程序胜在落地门槛低工人不需要额外安装软件微信里打开就能用特别是扫码这个动作小程序可以直接调起摄像头或者读取剪贴板体验不比原生差。而后台管理、报表统计、权限控制这些Django 自带 Admin 和成熟的 ORM非常适合做这类业务系统。Python 生态里既有 Django REST Framework 做接口又有 JWT 做登录态员工账号体系完全自己掌握不用依赖第三方认证。开发周期上Django 的单体架构足够支撑一个小工厂几百号人的日常操作不需要一开始就上微服务。等订单量、用户量上来以后再把任务队列、统计报表拆出去也不迟。技术选型不是越新越好而是匹配当前阶段的人力、预算和业务复杂度。2. 系统架构与核心模型设计2.1 模块边界与整体数据流整个系统我按业务边界拆成四个模块模块主要功能对应 Django App基础数据产品、物料、BOM、仓库、用户角色base生产管理工单、工序、报工、完工production库存管理库存结存、出入库流水、领料退料stock报表统计工单进度、库存预警、耗料汇总report数据流上核心是“工单驱动库存”。计划员创建工单时选择产品系统读取 BOM 计算标准用料实际操作时工人提交领料请求经过仓管员确认后扣减库存每一笔扣减都会生成一条流水并写回工单关联字段。这样工单和库存之间不是两张独立的表而是通过流水表形成闭环。2.2 Django 模型层的关键设计模型设计决定了一个业务系统能走多远。先看生产工单这块我建议用状态机驱动而不是用一个字段随意填。工单状态从“待下发”“生产中”“已完工”到“已入库”每一步只能走固定的流转方向这样避免操作人员误改状态导致数据错乱。class ProductionOrder(models.Model): order_no models.CharField(工单号, max_length50, uniqueTrue) product models.ForeignKey(Product, on_deletemodels.PROTECT, verbose_name产品) plan_qty models.DecimalField(计划数量, max_digits12, decimal_places2) done_qty models.DecimalField(完工数量, max_digits12, decimal_places2, default0) STATUS_CHOICES ( (pending, 待下发), (running, 生产中), (finished, 已完工), (stocked, 已入库), ) status models.CharField(状态, max_length20, choicesSTATUS_CHOICES, defaultpending) manager models.ForeignKey(User, on_deletemodels.SET_NULL, nullTrue, verbose_name负责人) created_at models.DateTimeField(auto_now_addTrue)物料和产品分开建模这是一个很多新手容易踩的坑。建议不要在产品和物料之间用“父子表”硬套因为实际工厂场景里同一种原料可能被多个产品用到同一个产品也可能有不同的物料替代关系。简单一点物料表独立产品表里存一个 BOM 列表用 JSON 字段存需要按行展开统计时再解析。虽然 JSON 查询性能一般但中小工厂的数据量完全够用。库存核心表只有两张一张存“当前结存”一张存“流水记录”。流水记录每一次增减变动结存表只显示当前值。这种设计的好处是即使有人误操作也能通过流水逆向还原历史。class Stock(models.Model): material models.ForeignKey(Material, on_deletemodels.PROTECT, verbose_name物料) warehouse models.CharField(仓库, max_length50) quantity models.DecimalField(当前结存, max_digits14, decimal_places3, default0) updated_at models.DateTimeField(auto_nowTrue) class Meta: unique_together (material, warehouse) class StockFlow(models.Model): FLOW_CHOICES ( (purchase, 采购入库), (issue, 领料出库), (return, 退料入库), (finish, 成品入库), (adjust, 盘盈盘亏), ) order models.ForeignKey(ProductionOrder, on_deletemodels.SET_NULL, nullTrue) material models.ForeignKey(Material, on_deletemodels.PROTECT, verbose_name物料) flow_type models.CharField(流水类型, max_length20, choicesFLOW_CHOICES) quantity models.DecimalField(变动数量, max_digits14, decimal_places3) before_qty models.DecimalField(变动前结存, max_digits14, decimal_places3) after_qty models.DecimalField(变动后结存, max_digits14, decimal_places3) operator models.ForeignKey(User, on_deletemodels.SET_NULL, nullTrue, verbose_name操作人) created_at models.DateTimeField(auto_now_addTrue)2.3 库存账务模型怎么用流水表避免“月底对不上”很多项目里开发图省事领料的时候直接去Stock表的quantity字段做减法。表面看没什么问题但一旦出现并发操作两个工人同时领料库存就可能被扣成负数。更重要的是库存为什么少、什么时候少的没有记录月底只能干瞪眼。我的做法是业务操作永远先写流水再更新结存。更新结存的时候不能用“先查后算再存”的裸逻辑而是用 Django 的F()表达式或者select_for_update()做原子更新。实际代码里我是这样处理的from django.db import transaction from django.db.models import F transaction.atomic def issue_material(order, material, qty, operator): stock Stock.objects.select_for_update().get(materialmaterial, warehouse原料仓) if stock.quantity qty: raise ValueError(库存不足) before stock.quantity stock.quantity F(quantity) - qty stock.save(update_fields[quantity]) stock.refresh_from_db() StockFlow.objects.create( orderorder, materialmaterial, flow_typeissue, quantityqty, before_qtybefore, after_qtystock.quantity, operatoroperator, )select_for_update()会把这一行锁住直到事务提交第二个请求只能排队等待这样就不会出现两个车间同时领同一批料、把库存扣穿的情况。流水表记录了每笔操作的前值后值月底对不上账的时候直接按时间轴拉流水谁在什么时间领了什么料、扣了多少一目了然。3. 后端 Django 实现与 API 开发3.1 搭建项目骨架与基础配置环境准备是第一个卡点。我在开发机上用的是 Python 3.10 Django 4.2 Django REST Framework建议用虚拟环境隔离不要直接装在系统 Python 里。如果用 VSCode记得把解释器指向.venv目录否则经常出现“代码里能 import终端跑不了”的鬼问题。依赖安装其实就那几样django、djangorestframework、djangorestframework-simplejwt、django-cors-headers如果需要调微信接口再加一个requests。pip install django djangorestframework djangorestframework-simplejwt django-cors-headers requests新建项目后强烈建议把TIME_ZONE改成Asia/ShanghaiUSE_TZ保持True。很多人前后端联调时发现时间差了 8 个小时就是时区没配好。数据库我用的是 MySQL注意charset要设置为utf8mb4否则小程序端输入中文表情符号会报数据插入错误。3.2 小程序登录与鉴权实现小程序端不能像 Web 端那样用账号密码登录它的标准姿势是wx.login()拿到临时code后端拿这个code去微信接口换取openid。我在这套系统里做得更轻量微信登录成功后自动创建本地用户然后发一个 JWT 给前端后续所有请求都带这个 token。class WxLoginView(APIView): def post(self, request): code request.data.get(code) resp requests.get( https://api.weixin.qq.com/sns/jscode2session, params{ appid: settings.WX_APPID, secret: settings.WX_SECRET, js_code: code, grant_type: authorization_code, }, timeout5, ) data resp.json() openid data.get(openid) if not openid: return Response({detail: 登录失败}, status400) user, _ User.objects.get_or_create(usernameopenid, defaults{nickname: 微信用户}) refresh RefreshToken.for_user(user) return Response({ access: str(refresh.access_token), refresh: str(refresh), user: {id: user.id, name: user.nickname, role: user.role}, })注意小程序的appsecret一定不能写在小程序代码里否则任何人反编译都能拿到。正确的做法是像上面这样小程序只传code密钥只存在于 Django 环境变量中。3.3 生产工单与报工接口工单接口是最频繁被调用的一组接口我按资源方式组织成标准 RESTful 风格。列表接口直接返回工单号、产品名称、计划数量、完工数量、状态和当前工序车间主任打开小程序首页就能看到整体进度。报工的难点在于工序流转。传统离散型工厂一个工单可能要经历下料、焊接、打磨、装配四道工序。我建模时加了一张WorkReport表记录每个工单每道工序的报工人、报工时间和数量工单的status只有在最后一道工序报完时才切到finished。class WorkReport(models.Model): order models.ForeignKey(ProductionOrder, on_deletemodels.CASCADE, related_namereports) process_name models.CharField(工序名称, max_length50) report_qty models.DecimalField(报工数量, max_digits12, decimal_places2) operator models.ForeignKey(User, on_deletemodels.SET_NULL, nullTrue) created_at models.DateTimeField(auto_now_addTrue)工序数量如果固定不变可以直接写在工单模型里如果不同产品的工序数量不一样就建议把工序也建成一张子表和工单关联。我在这套系统里为了快速落地用的是按产品表存processes字段报工时校验当前工序保证不会跳工序报工。3.4 物料领用、退料与成品入库这三个接口的底层逻辑其实是一套写流水、动结存、回写工单。领料是库存减少退料是库存增加成品入库是成品数量增加同时工单变为已入库。每个操作都必须在事务里完成并且校验操作人权限。权限方面我没有用 Django 默认的三级权限模型而是给用户加了role字段区分计划员、仓管员、车间工人和管理员。接口层面用自定义的IsRole权限类class IsRole(BasePermission): def __init__(self, allowed_roles): self.allowed_roles allowed_roles def has_permission(self, request, view): return request.user.is_authenticated and request.user.role in self.allowed_roles这样仓管员不能随便报工车间工人不能直接入库每个角色做自己职责内的事系统才不会乱。4. 微信小程序端实现与前后端联调4.1 小程序端整体结构小程序端我没有用第三方框架直接用原生小程序语法因为业务页面不多没必要为了引入 uniapp 而增加一层编译复杂度。页面大概四五个登录页、工作台首页、工单列表页、工单详情页、库存查询页。首页是小程序的核心入口。顶部展示今天的排产数量、进行中工单数、低库存预警数底部是两个大按钮“扫码领料”和“报工入库”。工人进车间不需要去想“我要点哪个菜单”扫码和报工就是最高频的动作这比传统的 PC 端 MES 体验强很多。请求封装我写在utils/request.js里统一带上Authorization头响应码为 401 时自动跳转登录页。const request (url, method GET, data {}) { return new Promise((resolve, reject) { wx.request({ url: baseUrl url, method, data, header: { Content-Type: application/json, Authorization: Bearer wx.getStorageSync(token) }, success: (res) { if (res.statusCode 401) { wx.navigateTo({ url: /pages/login/index }); reject(res); } else { resolve(res.data); } }, fail: reject }); }); };4.2 扫码与手动录入的交互细节扫码领料页用微信的wx.scanCode可以直接调起摄像头。扫描到的数据一般有两种格式如果物料包装上印的是二维码内容可能直接是物料编码如果印的是条码可能是包装号后端需要根据编码规则解析出物料 ID。因此扫码组件不能写死扫码后先调一个解析接口解析失败再让用户手动选择物料。手动录入的兜底很重要。车间环境光线差二维码容易扫不出来所以我做了一个“手动输入物料编码”的入口输入后前端自动匹配物料名称和规格。操作成功之后页面会用wx.showToast显示剩余库存工人能立刻看到本次领料后的结存这个细节很受现场人员欢迎。4.3 前后端联调阶段必须处理的细节联调是最容易出问题的地方。第一小程序发起请求的域名必须在微信公众平台配置并且要备案开发阶段可以在开发者工具里勾选“不校验合法域名”。第二生产环境必须用 HTTPS否则真机预览时请求会被拦。第三后端 CORS 要放开虽然小程序请求不强制要求 CORS但如果你同时还要调试 Web 管理后台后端就必须配django-cors-headers。我在联调时遇到过几次“后端明明没错前端就是报错”的情况最后定位都是 token 过期或请求头没带对。建议前端把所有请求都封装到一个模块里统一处理 token 注入和错误提示避免每个页面重复写逻辑。5. 常见问题与排查技巧实录5.1 开发期最常踩的坑做一个速查表都是我实际调试时见过的问题现象原因解决办法小程序请求发出去但后端收不到域名没配或不是 HTTPS开发工具勾选不校验域名生产配 HTTPS时间显示相差 8 小时Django 时区设置不对TIME_ZONEAsia/Shanghai中文乱码数据库字符集不对MySQL 建库时指定utf8mb4Decimal 字段传给小程序变成字符串DRF 默认序列化行为页面里Number()转一下真机上扫码没反应权限没配置在app.json里声明permissionscope5.2 并发扣库存、重复提交这类“现场事故”工厂的并发高峰往往集中在早上领料和下午入库两个时段。十几个工人同时扫码领料如果库存扣减逻辑不加锁很容易把库存扣成负数。用select_for_update锁行是第一个保障但还不够。第二个隐患是工人连续快速点击“提交”按钮前端防抖是一层后端还要通过工单号加唯一约束或者检查“是否已领过该物料”避免同一张领料单被提交两遍。5.3 权限与数据安全小程序端拿到的openid不能直接暴露给前端。我实际项目中后端把openid作为用户名但接口返回用户信息时只给id、name、role不给username。权限控制上简单场景用role判断足够但如果后续工厂人数变多、角色变细建议升级成 Django 自带的Group和Permission不要自己在模型里加一堆布尔字段。5.4 库存准确率与盘点系统上线第一周库存准确率从原来的 80% 提到了 95% 左右但离 99% 还有距离。问题出在“线下变更”没有及时录入系统比如车间临时借料、仓库报废一批物料这些在 ERP 里都算库存异动。后来我在系统里加了一个“盘点调整”功能仓管员盘点时发现差异直接录入adjust类型的流水系统自动把差异记到账上月底就能给财务一个合理的解释。6. 一点个人经验这类工厂管理系统真正难的不是怎么写 Django 模型也不是怎么调微信接口而是让现场的人愿意用。我的体会是小程序页面上的按钮一定要少、字号一定要大、操作步骤一定要短。车间工人戴着手套不可能在屏幕上精细操作扫码、确认、完成三步之内搞定一次动作系统才有生命力。如果后续要扩展我建议优先做两件事一是把 Excel 导入导出做完善很多工厂的物料主数据仍然在 Excel 里没有导入功能系统就很难真正跑起来二是加一个简单的消息通知比如库存低于安全库存时向仓管员的小程序推送一条提醒。这两块投入不大但对用户粘性的提升非常明显。

相关推荐

UltraEdit自动换行与制表符设置:TaoToken统一Key下编辑配置骨架
UltraEdit自动换行与制表符设置:TaoToken统一Key下编辑配置骨架

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 4:02:11

使用 TypeScript + LangChain.js + Bindu 构建 10 题 MCQ 测验 Agent:从 bindufy 配置到 JSON-RPC 调用完整实战
使用 TypeScript + LangChain.js + Bindu 构建 10 题 MCQ 测验 Agent:从 bindufy 配置到 JSON-RPC 调用完整实战

【免费下载链接】Bindu Bindu: The identity, communication, and payments layer for AI agents. 项目地址: https://gitcode.com/gh_mirrors/bin/Bindu 点击查看 免费下载 本文以 Bindu 仓库中的 typescript-langchain-quiz-agent 示例 为线索,完整讲… · 2026/9/25 4:02:11

HEIC图片怎么转PNG?在线转换工具与格式兼容性全指南
HEIC图片怎么转PNG?在线转换工具与格式兼容性全指南

iPhone 的 HEIC 图片怎么转 PNG?90% 的人第一步就选错了工具上周帮朋友导一批照片,他手机里存了大半年的图,传到 Windows 电脑上全打不开。文件夹里一堆 .heic 后缀文件,Windows 自带看图不认识,双击提示"不支持此… · 2026/9/25 4:02:11

Apereo CAS OAuth 2.0 授权码流程(Authorization Code)与 PKCE 扩展实战指南
Apereo CAS OAuth 2.0 授权码流程(Authorization Code)与 PKCE 扩展实战指南

后端认证鉴权单点登录 【免费下载链接】cas Apereo CAS - Identity & Single Sign On for all earthlings and beyond. 项目地址: https://gitcode.com/gh_mirrors/ca/cas 点击查看 免费下载 导读 授权码(Authorization Code)是 OAuth … · 2026/9/25 4:26:38

从SQL注入到应急响应:安全工程师面试的闭环答题思路
从SQL注入到应急响应:安全工程师面试的闭环答题思路

每次整理网络安全面试题,我都会提醒候选人:别把希望压在背payload上,真正值钱的答题思路是把“SQL注入怎么发现、怎么防御、出了事怎么应急响应”串成一条闭环。你看标题里“从SQL注入到应急响应”这八个字,其实正是一个安全工程师… · 2026/9/25 4:26:38

ESPnet2 目标说话人提取(TSE)实战:基于 LibriMix 与 TD-SpeakerBeam 的训练、评估与结果解读
ESPnet2 目标说话人提取(TSE)实战:基于 LibriMix 与 TD-SpeakerBeam 的训练、评估与结果解读

人工智能语音音频深度学习NLP 【免费下载链接】espnet End-to-End Speech Processing Toolkit 项目地址: https://gitcode.com/gh_mirrors/es/espnet 点击查看 免费下载 本指南以 ESPnet 仓库中 egs2/librimix/tse1 目标说话人提取(Target Speaker Extr… · 2026/9/25 4:26:32

PS图片出血扩展神器Image Extend:原理、安装与避坑完全指南
PS图片出血扩展神器Image Extend:原理、安装与避坑完全指南

简介:这是一份专为Photoshop设计的图片出血扩展插件Image Extend 1.0.0中文汉化版,面向需要处理印刷品出血位设计的UI设计师、平面设计师及印前工作人员。插件可智能分析图像背景并自动扩展至所需尺寸,支持自定义出血宽度和高度、多图层分别处… · 2026/9/25 4:26:32

AWS HealthImaging 像素数据校验实战:使用 AWS SDK for JavaScript v3 验证 DICOM 解码帧的 CRC32 一致性
AWS HealthImaging 像素数据校验实战:使用 AWS SDK for JavaScript v3 验证 DICOM 解码帧的 CRC32 一致性

示例工程教程后端 【免费下载链接】aws-doc-sdk-examples Welcome to the AWS Code Examples Repository. This repo contains code examples used in the AWS documentation, AWS SDK Developer Guides, and more. For more information, see the Readme.md file below. 项目地… · 2026/9/25 4:26:32

Moto 中的 Bedrock AgentCore 模拟:事件 API 实现与实战指南
Moto 中的 Bedrock AgentCore 模拟:事件 API 实现与实战指南

Mock测试 【免费下载链接】moto A library that allows you to easily mock out tests based on AWS infrastructure. 项目地址: https://gitcode.com/gh_mirrors/mo/moto 点击查看 免费下载 导读 Amazon Bedrock AgentCore 是 AWS 面向智能体(Agent&a… · 2026/9/25 4:26:26

数值优化(Numerical Optimization)学习系列-03-共轭梯度方法(Conjugate Gradient)
数值优化(Numerical Optimization)学习系列-03-共轭梯度方法(Conjugate Gradient)

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 1:00:31

创维E900V22D刷机全攻略:S905L3SB芯片兼容性解析与救砖实战
创维E900V22D刷机全攻略:S905L3SB芯片兼容性解析与救砖实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 1:00:31

MQTT协议原理与Broker服务器搭建实战:从Mosquitto到EMQX
MQTT协议原理与Broker服务器搭建实战:从Mosquitto到EMQX

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/25 1:00:37

了解更多?预约专属演示

我们的顾问将为您一对一讲解产品与方案

企业微信二维码