文睿 张
|
e1401532f1
|
docs: show BOM history in a dedicated dialog
|
2026-09-23 13:41:23 +08:00 |
|
文睿 张
|
0336181832
|
docs: plan BOM usage-position details
|
2026-09-23 12:05:39 +08:00 |
|
文睿 张
|
6933cd82cc
|
docs: defer automatic BOM position remarks
|
2026-09-23 12:00:12 +08:00 |
|
文睿 张
|
0c7da9d394
|
docs: refine BOM version and audit design
|
2026-09-23 10:31:40 +08:00 |
|
文睿 张
|
b75696f44a
|
docs: add initial BOM management design
|
2026-09-22 18:25:38 +08:00 |
|
文睿 张
|
5d508cd2bb
|
fix: 给不存在的仓库建库位时误报创建成功
CreateLocation 的 INSERT...SELECT 匹配不到仓库时影响 0 行,MySQL 不报错:
err 为 nil、LastInsertId() 返回 0。此前只看 err,接口回 201
"Location created successfully" 且 data.id 为 0,而库里一行都没写进去——
刷新后库位消失,重试还是"成功"。
改为以 RowsAffected 为准(INSERT 的 RowsAffected 就是实际插入行数,不受
clientFoundRows 影响),影响 0 行返回 ErrWarehouseNotFound,接口回 400
"仓库不存在,可能已被删除或不属于当前组织"。与既有的 execExpectingRow、
role_permissions 插入保持同一套路。
实测(docker,重建后端镜像后):
不存在的仓库 999 -> HTTP 400,warehouse_locations 1 行 -> 1 行
真实仓库 1 -> HTTP 201 id=3,1 行 -> 2 行,库中确有此行
新增 warehouse_test.go 覆盖两个分支,变异验证:去掉 affected==0 判断后
"影响 0 行"用例失败(返回 <nil>,正是线上症状)。
|
2026-09-22 18:21:31 +08:00 |
|
文睿 张
|
aa017a32b4
|
fix: 已停用角色导致用户无法保存编辑
|
2026-09-22 16:41:19 +08:00 |
|
文睿 张
|
688dffebaa
|
fix: 物料页两个作废入口的按钮宽度对齐
「作废」和「撤销作废」轮流出现在同一列,2 字对 4 字,宽度不一样,最右边按钮的
位置会参差。把「作废」改成「作废物料」,两边都是 4 个中文字,同字体同字号下自然
等宽,不依赖写死的 px 值——本项目的测试环境是 jsdom,不做布局计算,量不了像素,
写死的值只能靠猜。
顺带修了测试里的一个自欺:那行物料原本叫「作废物料」,和按钮文案撞名,而按钮
自身就在那一行里,用 toContain 断言行归属会恒为真。改成「旧螺丝」才真的在测。
测试补 1 条(锁住两个按钮的文案字数相同)。变异验证:把「作废物料」改回「作废」,
文案断言和字数断言都变红。
|
2026-09-22 15:15:54 +08:00 |
|
文睿 张
|
b9c0681c47
|
fix: 物料页的「撤销」按钮文案改成「撤销作废」
「撤销」在中文 UI 里默认指撤销上一步(Ctrl+Z),看不出在撤销什么;这一页又
没有状态列(文案即状态),用户看到一行数据和绿色「撤销」按钮,无从判断这条
物料被作废了。改成「撤销作废」后,按钮自身就说明了这条物料怎么了。
只改这一处按钮文案。全站其他实体(仓库与库位、主数据、组织、角色、往来单位)
仍用「停用/启用」,那是另一套配对,跟这里的「作废/撤销作废」不冲突。
测试补 1 条,同时锁住两个入口的互斥关系(作废的那行不该再有「作废」,有效的
那行不该有「撤销作废」)。变异验证两处:文案改回「撤销」、以及把作废按钮的
状态条件去掉让两个入口同时出现,断言都变红。
|
2026-09-22 15:06:08 +08:00 |
|
文睿 张
|
43f680219e
|
fix: 物料主数据页检索不到已作废的物料
检索框是 el-select,必须从下拉候选项里选一项才能设上关键字,而候选项取自
materialOptions(status='active'),作废物料压根不在里面,搜不到也选不中。
可这一页的列表查询走 status='all',本身就显示着作废物料——同一份数据两条
路径不一致,而且这一页正是恢复作废物料的入口。
改法照 Logs.vue / Stock.vue 流水检索框的既有做法:这一页改用含作废的
historicalMaterialOptions / fetchHistoricalMaterialOptions()。业务单据页
(入库/出库/申请)保持只用有效物料不动。
后端无需改动,已实测:status=all&search=A010201 返回 1 条 obsolete,
status=active 对同一关键字返回 0 条。
测试补 1 条。变异验证:候选项来源和 onMounted 那处分别改回原样,断言都变红。
|
2026-09-22 14:53:18 +08:00 |
|
文睿 张
|
bcee877278
|
fix: 物料/用户增删改后列表的搜索关键字被丢弃
写操作后原地重新拉取列表时,search 参数被写死成缺省的空串:搜索框里还显示着
用户输入的关键字,列表却退回全量。用户会把全量列表当成筛选结果,接下来的作废/
删除操作就打在被误认的那一条上。store 层一直有这个缺陷却没被拦住,因为页面
那层没有测试。
修法照 stock.js / approval.js 已有的约定(store 存一份 filters,写操作原地刷新
时取出来用):
- materials.js:编辑/作废/恢复沿用 search 和 status
- users.js:编辑/删除沿用 search
- 新增走反方向,清空筛选并回第 1 页:新建的项不一定匹配当前关键字,沿用搜索
就看不见它,用户会以为没建成功。物料按 id 倒序,回第 1 页正好能看见
- Materials.vue / Users.vue:新增成功后把搜索框一起清空,否则 store 清了筛选而
搜索框没清,同样是表里不一
测试补 14 条(两个 store + 两个页面)。全部做过变异验证:把实现改回原样后,
6 条 store 断言和 2 条页面断言确实变红,且只有它们变红。
|
2026-09-22 14:40:21 +08:00 |
|
文睿 张
|
fbd0bc1341
|
fix: 审批/取消后列表的筛选条件被丢弃
写操作后原地重新拉取列表时,status 参数被写死成 '':列表悄悄退回全量(已通过、
已拒绝的单子全冒出来),而页面下拉框仍显示着用户选中的筛选值。用户以为看到的
是筛选结果,实际不是。store 层一直有这个缺陷却没被拦住,因为页面那层没有测试。
修法照 stock.js 已有的约定(stockFilters 配合 stock.test.js 的断言):store 存一份
filters,写操作原地刷新时取出来用。
- approval.js:approve / reject 沿用筛选
- application.js:cancel 沿用筛选
- application.js:create 保持清空筛选并回第 1 页——刚提交的是待审批单,若沿用
「已通过」之类的筛选就看不见它,用户会以为没提交成功
- Application.vue:提交成功后同步把下拉框重置为「全部」,否则 store 清了筛选而
下拉没清,同样是表里不一
测试补 9 条(approval/application 两个 store + Application 页面层)。全部做过变异
验证:把实现改回原样后对应断言确实变红,且只有该变红的那几条变红。
|
2026-09-22 14:10:52 +08:00 |
|
文睿 张
|
bf7f7129dc
|
feat: 审批页状态筛选补上「已取消」
下拉此前只有全部/待处理/已通过/已拒绝。既然已通过、已拒绝都列了,说明这页是想
看历史单子的,已取消的缺席就不一致。
后端无需改动:material_applications.status 是 ENUM('pending','approved',
'rejected','cancelled'),ListAll 直接 AND a.status = ?,没有白名单拦截。
StatusBadge 也已备好 cancelled 的灰色标签,筛选结果不会显示成裸英文。
|
2026-09-22 14:10:51 +08:00 |
|
文睿 张
|
4905e60f8c
|
feat: 仓库与库位补上编辑与停用/启用入口
后端 PUT /warehouses/:id 与 PUT /warehouses/:warehouseId/locations/:locationId
本就接受 name + status(service/repository 都只改这两列),api 层的 update/updateLocation
也早已封装好,缺的只是前端入口——页面此前只有「新增」,无法改状态。
- 仓库标题栏与库位行各加「编辑」按钮,弹窗内改名称 + 启用/停用
- 标题栏按钮必须 @click.stop:el-collapse-item 整条 header 都挂着展开/收起监听
- 库位状态列从直接显示英文 inactive 改为中文 el-tag,与仓库及主数据页统一
- 编辑态编码只读且不参与必填校验(code 不可变,后端 Update 也不接收)
- 表单重置走已有的 replaceAllKeys,编辑只灌白名单字段,避免残留 id 让新增变成覆盖更新
- 库位所属仓库只存 id 不存对象,load() 整体替换列表后不会读到旧数据
- save() 显式吞掉错误:提示由 axios 响应拦截器统一负责,同时避免 @click 经
el-button 透传到原生 button、绕过 Vue 异步错误包装而产生的 unhandled rejection
- 测试补 8 条:update/updateLocation 的参数与顺序、编辑态不误报编码、
改完再新增仍走 create、状态列中文、编辑按钮不收起面板、失败不关窗
|
2026-09-21 17:49:49 +08:00 |
|
文睿 张
|
696e90893b
|
fix: 主数据编辑的两类静默失败
UPDATE 漏列:
- code_rules 的 SET 补上 category_id。此前改分类提示"保存成功"但不落库,
是唯一用户可达的活缺陷(同页的分类下拉没有 disabled,且规则只能改不能删,
没有"删了重建"这条退路)
- code_rules 有 uk_code_rules_org_category,补列后改到已占用的分类会撞唯一键,
新建与更新统一翻成中文的 ErrDuplicateCodeRule
- 分类/单位/仓库/库位/伙伴的编码定为不可变:分类编码是编码规则前缀的来源
(init.sql 的种子数据直接取 material_categories.code),伙伴编码是对外业务
编号,改掉会让历史数据脱节且查不回来。service 的 Update* 不再要求编码非空
——原先是"必须传、传了却被丢弃";新建侧的必填校验保留
- 顺带补齐两处同款漏网:organization.go 的 code 与 partner.go 的 partner_code
(前者 service 本就不校验编码,自洽,无需改)
记录不存在时的静默成功:
- DSN 开启 clientFoundRows,让 RowsAffected 返回"匹配"行数而非"实际改变"行数。
否则"编辑时一个字段都没改"和"记录不存在"都返回 0,无法区分,直接加检查会把
正常保存误判成记录不存在(真 MySQL 8.0 实测)
- 新增 repository.execExpectingRow,7 个 Update* 影响 0 行时返回 ErrRecordNotFound;
伙伴走事务内的 SELECT ... FOR UPDATE,只需翻译 sql.ErrNoRows
- 既有 4 处 RowsAffected 用法逐处核对过,均不受该 flag 影响
测试:补 6 个 Update* 的存在性检查、编码必填约束的两端、唯一键翻译、DSN 拼接;
全部做过变异验证(抽掉实现后对应测试确实变红)。
|
2026-09-21 17:26:53 +08:00 |
|
文睿 张
|
837cc5787b
|
前端问题优化
|
2026-09-21 16:53:44 +08:00 |
|
文睿 张
|
85d9683754
|
前端提示优化
|
2026-09-21 16:40:43 +08:00 |
|
文睿 张
|
f0722eed00
|
fix: 审批页申请人列去掉永远取不到的 row.applicant
后端返回里没有 applicant 键。model.ApplyOrder 确实有 Applicant 字段,但那是
另一张旧表的模型;审批页走的 MaterialApplication 只 SELECT u.username 并扫进
&app.Username(json tag 为 username)。列显示一直正常,全靠 || 后半段兜住,
左分支是死代码,去掉以免误导成还有第二个数据来源。
改为 row.username || '-'。
|
2026-09-21 16:19:22 +08:00 |
|
文睿 张
|
71d1829c29
|
fix: 库存列表分类筛选失效,后端补上 category 参数
前端 stores/stock.js 一直在发 category,但 handler 只读 search,service 与
repository 的方法签名里也没有这个参数,整条链路把它静默丢弃,于是选完分类
点「查询」没有任何反应。前端本来就传对了,无需改动。
repository 侧按大类 code 过滤(material_categories 里 parent_id 为空的那层,
即 SQL 里的 pc.code),与列表「大类类型」列同口径,前端下拉的 value 正是大类
code。注意 GetAllStock 的 COUNT 查询原本没有 JOIN 分类表,加 pc.code 前必须
补上与主查询一致的 LEFT JOIN,否则分页总数会和实际行数对不上、末尾多出空白
页;两张表都按主键关联,实测计数不变。小类码不会误命中(category=A01 返回 0)。
顺带修掉同一功能里的耦合缺陷:updateWarningStock 刷新列表时不传筛选参数,
筛选一旦生效,保存预警就会把列表刷回全量、而下拉框仍显示选中的分类。store
新增 stockFilters 记住当前条件,刷新时沿用。
stock_test.go 里 COUNT 的正则随 SQL 变形同步放宽,新增
TestStockRepoGetAllStockAppliesCategoryToBothQueries 覆盖两条 SQL 的成对条件
与参数顺序;前端补 4 条用例(store 沿用/清空筛选、组件查询与翻页传递分类)。
|
2026-09-21 16:19:18 +08:00 |
|
文睿 张
|
121d0c9e1f
|
fix: 申请与审批页翻页失效,页码换算成后端认识的 limit/offset
后端 GetMyApplications / GetAllApplications 只读 limit/offset,前端原先发
page/pageSize,无法识别的参数被静默忽略并退回默认的 limit=20 offset=0,
于是翻页不报错但始终返回第一页。
转换点固定在 api/application.js,对外签名 (status, page, pageSize) 不变,
stores/application.js 与 stores/approval.js 两个调用点无需改动;同时对非法
页码兜底,避免算出负 offset。
application.test.js 覆盖换算结果与边界,其中「第 2 页不再是 offset=0」
是本次的回归点。
|
2026-09-21 16:00:35 +08:00 |
|
文睿 张
|
102c75079d
|
refactor: 去掉 replaceAllKeys 无人使用的返回值
两处调用点都是裸语句、忽略返回值,函数保持原地修改语义,调用方行为不变。
连带删掉专门断言返回值的那个用例,其余测试不变。
|
2026-09-21 15:34:45 +08:00 |
|
文睿 张
|
72bc6c9af2
|
test: 补齐 Update 的 happy-path 用例,锁定「编辑走 UPDATE」而非 INSERT
六个 Update* 此前只有 UpdateRequiresID 覆盖到拒绝分支,方法体里的
s.repo.Update*(item) 从未被执行。这 12 个方法互为复制粘贴的模板,
尾行一旦误写成 Create* 全部测试仍然绿灯,生产行为会退化成「编辑即新增」。
新增两条用例:PartnerService.Update(事务:SELECT ... FOR UPDATE + 两条
UPDATE)与 MasterDataService.UpdateCategory(单条 UPDATE),均登记
UPDATE 期望并以 ExpectationsWereMet 兜底。把尾行改成 Create* 实测两条
用例都会失败并指名收到了 INSERT。
同时 gofmt internal/service/admin_master.go:新增中文注释紧贴前一个函数的
},补上缺失的空行,纯空白改动。
|
2026-09-21 15:34:41 +08:00 |
|
文睿 张
|
f3124e96cc
|
refactor: 抽出 replaceAllKeys 共享工具,消除两处重复的表单重置
|
2026-09-21 15:22:23 +08:00 |
|
文睿 张
|
7f19a37591
|
fix: 新增表单重置为干净状态,不再把上一次编辑的 id 带进请求体
|
2026-09-21 15:16:22 +08:00 |
|
文睿 张
|
6ed205dcb8
|
refactor: 拆分 WarehouseService 的 Create/Update,去掉 ID==0 猜分支
|
2026-09-21 15:09:37 +08:00 |
|
文睿 张
|
16ca9c02ba
|
refactor: 拆分 MasterDataService 的 Create/Update,分类与单位创建不再受脏 id 影响
|
2026-09-21 15:03:57 +08:00 |
|
文睿 张
|
1b0cdde780
|
refactor: 拆分 PartnerService 的 Create/Update,创建接口不再被脏 id 带偏
|
2026-09-21 14:59:01 +08:00 |
|
文睿 张
|
cbcd54b70c
|
fix: 伙伴列表的合作状态列显示中文,不再直接暴露英文枚举值
|
2026-09-21 14:56:32 +08:00 |
|
文睿 张
|
ea63cd9931
|
修改一致性问题
|
2026-09-21 14:13:30 +08:00 |
|
文睿 张
|
8a60e2cb00
|
前端报错提示优化
|
2026-09-20 17:17:28 +08:00 |
|
文睿 张
|
d463fbf71a
|
修改前端报错文案
|
2026-09-20 16:59:38 +08:00 |
|
文睿 张
|
a7c7936e0b
|
feat: 实现物料编码按分类规则自动生成、手工修改及并发安全的流水号管理
|
2026-09-20 16:48:06 +08:00 |
|
文睿 张
|
84d775bc90
|
补充文档
|
2026-09-20 14:30:15 +08:00 |
|
文睿 张
|
936a8d3b61
|
完善库存流水
|
2026-09-20 14:29:41 +08:00 |
|
文睿 张
|
332ac1ff7a
|
完善出库和入库逻辑
|
2026-09-20 11:18:00 +08:00 |
|
文睿 张
|
d9da2ed672
|
库存,入库,出库相关问题修改
|
2026-09-20 10:31:28 +08:00 |
|
文睿 张
|
6fe9d0da40
|
物料分类重构、物料恢复、入库预警阈值与库存明细接口
|
2026-09-18 17:20:45 +08:00 |
|
文睿 张
|
6a443577b0
|
更新init.sql
|
2026-09-17 17:55:03 +08:00 |
|
文睿 张
|
855642ea75
|
已完成迁移体系清理和 Docker 初始化改造:
- 新版 [init.sql](C:\\1111\\12.project\\VSCode\\warehouse-mms\\scripts\\init.sql) 直接创建最新空库结构、默认组织/权限/仓库/分类。
- [docker-compose.yml](C:\\1111\\12.project\\VSCode\\warehouse-mms\\docker-compose.yml) 改为由 MySQL 在空数据卷首次启动时自动执行 init.sql。
- [entrypoint.sh](C:\\1111\\12.project\\VSCode\\warehouse-mms\\scripts\\entrypoint.sh) 不再重复执行迁移。
- 已删除 scripts/migrations/、pkg/migration/、cmd/migrate/ 和旧迁移说明。
- 已执行 docker compose down -v --remove-orphans;输出确认删除了 warehouse-mms_uploads_data 卷。
- go test ./... 全部通过;git diff --check 与 Compose 配置检查通过。
|
2026-09-17 16:22:52 +08:00 |
|
文睿 张
|
8cafca4b44
|
已完成迁移体系清理和 Docker 初始化改造:
- 新版 [init.sql](C:\\1111\\12.project\\VSCode\\warehouse-mms\\scripts\\init.sql) 直接创建最新空库结构、默认组织/权限/仓库/分类。
- [docker-compose.yml](C:\\1111\\12.project\\VSCode\\warehouse-mms\\docker-compose.yml) 改为由 MySQL 在空数据卷首次启动时自动执行 init.sql。
- [entrypoint.sh](C:\\1111\\12.project\\VSCode\\warehouse-mms\\scripts\\entrypoint.sh) 不再重复执行迁移。
- 已删除 scripts/migrations/、pkg/migration/、cmd/migrate/ 和旧迁移说明。
- 已执行 docker compose down -v --remove-orphans;输出确认删除了 warehouse-mms_uploads_data 卷。
|
2026-09-17 16:21:53 +08:00 |
|
文睿 张
|
bf48c5a60f
|
chore: remove generated caches and temporary files
|
2026-09-17 15:17:23 +08:00 |
|
文睿 张
|
368c0bfb99
|
fix: improve material search selectors
|
2026-09-17 09:48:04 +08:00 |
|
文睿 张
|
bb195610fd
|
fix role permission API requests
|
2026-09-17 00:06:27 +08:00 |
|
文睿 张
|
1cc3584f1a
|
restore lost frontend and backend changes
|
2026-09-16 23:30:25 +08:00 |
|
文睿 张
|
5a0376f318
|
拆分主数据和仓库数据
|
2026-09-16 16:32:02 +08:00 |
|
文睿 张
|
a103549854
|
拆分主数据和仓库数据
|
2026-09-16 16:29:04 +08:00 |
|
文睿 张
|
31aae223c2
|
Initial commit
|
2026-09-15 16:08:18 +08:00 |
|
文睿 张
|
39387b6edc
|
add .gitignore
|
2026-09-15 16:04:06 +08:00 |
|