Resminama mazmuny

月底对账与开票

本文档说明对账单与发票的对账汇总逻辑,通过新增发货单硬关联列和按单聚合,解决多张对账单开票、已收金额雷同及余额被客户级回款摊薄的问题。

  • 对账单由完成发货自动生成,一次发货一张,不再按客户账期合并
  • 新增发货单硬关联列,取代凭备注文字匹配订单与发货单
  • 开票与已收按单聚合写回,余额只减本单回款不再被摊薄
  • 发票状态移出可写清单,新建即已开票且明写不做红冲
  • 对账确认仅回写本单关联订单,六个财务口补齐权限卡控

29.1 三张纸上的开票数一模一样

小谢是恒达的会计。月底那两天,她打印了三张对账单:同一个客户,三次发货,一人一张。

她发现三张纸上的"开票金额"和"已收金额"分毫不差,"订单金额"却各不一样——第一张四万二,第三张一万八。她把三张纸并排放在桌上,问小徐:到底哪张是真数。

三张都不算真数。 那两格金额不是"这一张单子"的钱,是这个客户此刻的总账被抄了三遍;而"订单金额"那一格记的其实只是这一次的发货额。一套总账、三张分账,写在同一行里,就成了三张一模一样的假分账。

这一章说清这四格钱是怎么变成一样的,再顺带说三件露在外面的事:发票的状态、对账的确认、月底那三个数。

29.2 对账单是从发货那一刻冒出来的

系统里能对账单动手的地方有两处。

第一处不用人建。 发货单走到"完成发货"那一步,程序连着做四件事:发货单标成"已送达"、扣成品仓库存、订单改成"已发货"、顺手建一张对账单。这张单的账期填当月,状态"待确认",订单金额和发货金额都是这一次的发货额,开票和已收填 0,余额等于发货额,备注自动写一句话:"发货单某某自动生成"。

这里有个改过的痕迹要交底。代码里留着一句注释:每次发货建独立一张,不再按客户和账期合并。 意思是过去想做"一月一张",现在改成"一发一张"。能力篇第十三章还写着"按客户和账期生成一张对账单"——那句现在不对了,这一章顺手改掉。所以小谢手上那三张纸是三次发货的结果,跟"六月账"没关系。一个客户分八次发货,他就有八张对账单,账期那一格写着同一个"2026年8月"。

第二处是人建。 对账单页有个"新增对账单"。它和自动那路以前有三点不一样,如今补了两点:单号以前要人手填(不填就存不进去),现在接上了统一取号;账期以前是"2026-08"这种写法、跟自动生成的"2026年08月"不是同一个式样,现在两处统一成一个写法。四格金额仍全手填,余额只在你改动某一格时顺手算一次。

还有一处更要紧:以前这个页面只有详情、确认、删除,就是没有"编辑"——手工单四格金额填错一个数,唯一的修法是把整张删掉重建。现在给手工单补上了编辑按钮(自动单仍不给改,因为它的钱货由发货单联动而来)。

发货这一步另外还有一条岔路。系统里有两处能建发货单,只有"完成发货"那一步会生成对账单。另一条在订单页里:它建完发货单就顺手扣了库存、把订单直接标成"已发货",可发货单自己停在"备货中",也不生成对账单。从这里发出去的货,月底不会有单子在小谢桌上等她——除非有人再到车间那一步点一次"完成发货"。而补点那一次,扣库存的两个分支也都落空:这条路建的发货明细没挂库存记录、也没挂物料,只剩一个产品名。

29.3 对账单和发货单之间,从前只有一行字,现在多了一个硬关联

几张单据要能对起来,总得有个能凭着的格子。以前发票上留着"关联订单""关联发货单"两格,收款上也有;唯独对账单上,跟订单和发货单有关的格子一个都没有——只有客户、账期、四格金额、状态,和一行备注。对账单和发货单之间的联系,全靠那行备注里的一句人话。

这就带出过一处很安静的坏法。三个地方都靠读那行备注:算金额那一路拿真实单号去备注里做包含匹配;锁门那一路只要求句子里出现"发货单""自动生成"两个词;读明细那一路更把单号样式写死成"发货单 FH-……自动生成"。可真实发货单号从来不是 FH- 开头,于是这一路永远落空。

落空的后果当场看得见:对账单详情里那块"订单金额明细"在任何一张单子上都不出现;产品清单退回拿账期猜年月,同一个月发两次货,两张单的产品清单一模一样。更拧的是锁门和救明细读的是同一行字、一个读得中一个读不中:自动单不许编辑恰恰因为备注被锁在门外,改不动。

现在这一处不再靠猜字。 对账单补了一个可空的发货单关联列,发货自动建单时把那张发货单的编号写进去。上面三路一起改读这个硬关联:找单按它命中、判定是不是自动单按它、读明细也顺着它去取真正的发货内容。那行"自动生成"的备注退成一句人看的说明,不再是谁的判据。手工建的单这一列为空,走的是上一节那个编辑口,也不再被一行字锁死。

29.4 那两格钱是怎么算出来的

刚才说三张对账单的开票数一样。这一节说为什么一样。

只要有人新建、修改或删除一张发票、一笔收款,系统就会跑一遍汇总。汇总分三步(这一步现在按单收口了):

  1. 找单:拿这次的发票/收款,顺它关联的发货单,找到那张发货单对应的对账单(就是 29.3 补的那个硬关联列)。命中就按这张单聚合;实在没有硬关联的旧单,才回退按客户。
  2. 算总账:开票合计 = 这一张发货单名下的发票相加;已收合计 = 同一范围内、状态是"已收款"的收款相加。
  3. 写回:把这两个合计写给这一张对账单——不再原样摊给找到的每一条。

这三步收口后,小谢那三张纸就不该一模一样了。订单金额那一格还是这一次的发货额,开票和已收也只收这一张单的票与款。一张分账的余额 = 这一次的发货额 − 这一次的开票/回款,不再是拿这一次的发货额去减这个客户的全部回款。货发得少、款回得多就把余额压成负的那种摊法,去掉了。

负数那一重身份还剩一半。驾驶舱那个应收账款只把大于 0 的余额加起来,负数会从统计里消失这一条还在;但一个客户十张单、回款被扣十次的全摊算法已经废除——每张单只算自己的钱,应收不再被摊薄到看不见。

还有一格。对账单列表上那个"不一致 / 正常"的红绿标,判据合并成了一个函数:开票大于 0、且开票不等于已收(差过一分)才算异常。前面那个"开票必须大于 0"的前提没变——一分票都没开出去的客户仍显示正常——但这个前提现在明写进了界面提示。红标也不再等人点,自动汇总只在新翻转成异常时给财务发一次通知(见 29.5)。

这四格不是躺着的字段。演示数据里那三行手工造出来的数字,任何一次真实的开票或收款,都会把它们重写成上面这个样子。

29.5 "标红会通知财务",这句如今接上了

能力篇第十三章写过一句话,意思是对账单被标成异常时会通知财务主管。这句以前不成立,现在接上了——接线补在自动汇总里。

以前不成立,是三件事凑在一块:界面上那枚"检查不一致"按钮被删了,删它的注释以为另一路会发通知、可另一路只算那一格不发;两套判据正好相反,手工那路要求两格都有值才判,任何一格是 0 就把已亮的红标抹成正常;而收件人也不是财务。

现在这两处并到了一起:判据合成一个函数(开票大于 0、且开票不等于已收才算异常),自动那路与手工那路口径一致,不再互相抹平;通知也接上了——自动汇总只在一张单新翻转成异常时,按部门码找到在岗的财务、发一次对账异常通知。那枚没有入口的按钮不再需要有人去按。

给销售的那几条也不是按编号找人,是拿客户名字去精确匹配业务员。名字多一个空格、少一个简称就撞不上;撞不上只往日志里写一行,界面上不会有任何提示。"已通知销售"这句话,在系统里的实际形状是:应该通知到了。

四条给财务写好的消息模板——开票、收款、对账确认、对账异常各一条——以前躺在初始化数据里全系统一次也没被引用过。现在对账异常这一条接上了(就是上面那个自动通知);开票、收款、对账确认那三条仍走通用类型,模板立着没接线。

同一个形状的还有一处:对账单也有一张打印模板,格位、汇总列都排好了。而"生成文档"那一步只认工单,别的对象一律不接。这张模板能看,不能出。

29.6 开票这件事:三档状态只有一档能用

发票状态当初设计了三档:待开票、已开票、已红冲,字段注释、管理端下拉、内置帮助页都按这三档写。现在这一格收口了:后端把状态移出可写清单,新建发票一律落成"已开票",想手工改成别的值直接拒;本系统明写不做红冲,帮助页那句也跟着改成了实话。

以前那句"新建时无条件改写成已开票"、管理端表单里根本没有状态栏——这个行为没变,只是从"偷偷覆盖"变成"明写不支持改写"。"待开票"这个值如今基本走不到,除非有人直接改库。

"已红冲"这一档以前更孤。 管理端发票页只有新增、编辑、删除三个动作、没有"红冲"这个动作,想红冲只能进编辑把状态改成那三个字,而那一格以前还允许写成任何东西——作废、开错了、一个空格都行。现在这行改不动了:状态不可手工写、红冲不做,那一格不再是个随便填的口子。

而开票合计以前不过滤状态,一张被"红冲"掉的发票照样参与合计——作废那张还躺在合计里,作废重开等于把开票数翻倍,帮助页那句"红冲 = 作废重开"后半句成立前半句不成立。现在既然明写不做红冲,这个翻倍口径也就没了入口去造它;那句帮助话改成了和实现一致的说法。要不要真做红冲、做了怎么冲减合计,仍是一个没定的业务决定。

三件小事一并说了。

  • 订单上那个"开票日期",只在这一格为空的时候写一次。开第二张票不改它,把第一张票删掉也不回退。订单上永远留着第一次开票那天的日期。
  • 新增发票要先选客户,那个下拉来自"未开票客户"这个口子。它的口径是:先看这个客户建过对账单没有,再拿本次发货额和他的开票合计比大小。一个从没建过对账单的新客户不会出现在这里——想给他开发票,得先有一张对账单。而且这个列表在你点"新增"时不刷新(点"编辑"时会刷一次)。
  • 状态选项、状态颜色、状态筛选,读的都是管理端自己写死的一份中文,没走全系统的状态字典。

手机端另说一处,这个也修了。以前手机上那个"新增发票"表单保存时不发任何请求,只弹一句"保存成功"退回列表,状态值还是第四套写法(四个英文词,一个也不在系统真用的那三个里);手机收款页两个页签按"已核销 / 待核销"筛、库里存的却是"已收款",两个页签常年是空的。现在手机端新增发票接上了真实接口、删了那个假状态选择器,收款页页签也改成"已收款"——不再是一个按下去什么都不发生的假表单。

开票这件事,以前手机上看着能办其实办不了、在电脑上根本不需要办(一存就成),两边的状态字还不是一套。现在手机端接了真接口、状态这一格收成"新建即已开票、不做红冲"。"三档状态"从一套能点的下拉,收成了一个说明。

29.7 确认对账那一下,改的不止这一张单

对账单列表上那个"确认"按钮只在状态是"待确认"时出现。以前它的门槛是四格金额任一为 0 就按不下,把刚自动生成、开票和已收还都是 0 的单全挡在外面;现在门槛松成"开票或收款其一大于 0"就能确认,不再要求四格齐。顺序那层意思还在——要先开过票或回过款才对得了账——只是不再苛刻到一格都不能空。

按下去以后发生三件事:状态写"已确认";给销售发一条消息;以及回写订单的对账日期——但回写范围收了:现在只写这张对账单关联的那张发货单对应的那个订单(顺着 29.3 那个硬关联列回溯),不再把这个客户名下所有对账日期为空的订单一律写成今天。一张单的确认不再变成一批单的日期。

以前那个连带代价也消了。回款效率那一页进门条件是"订单上有对账日期",过去确认一张就把全部订单写成今天,那一页的"未对账"档永远不出现。现在回写只碰本单关联的订单,没对过账的订单留在"未对账"档里,那一档不再是死的。

月底看数的时候,以前同一件事在好几个地方各有一个数。四个最常被问的——超期、回款周转天数、对账完成率、财务时间线——如今抽成了共用口径,标题、注释和实现对上了;剩下几处仍各算各的。

  • 对得上的四口:超期判据从"超过 91 天"改回和标题一致的"90 天以上";回款周转天数的注释与实现对上了;对账完成率加了 100% 封顶,不再十张单把回款摊成十倍、算出个远超百分之百的数;财务时间线改按 29.3 那个硬关联列回溯,没有关联就显式返空,不再拿这个客户最新一张"待确认"的单当本单的对账单。
  • 还散着的:订单金额那一格,回款效率页按订单明细现算(含工装费、工艺开发费),驾驶舱和时间线读的是订单表上那两个格子,仍是两个答案;账龄分段配置里五档、回款效率页读它,驾驶舱看板另起四档把末两档并成"90 天以上"没读配置;同一页账龄起点也不统一,已发货的按最近一次发货日算、其他的按下单日算。

这几处散,是因为它们分属不同页各自的算法。回款这一个口径已经钉死成"已收款",对账汇总与回款效率认的一致了;但金额、账龄这些还没并成一处。

顺带记一笔权限。三个列表口本来就查权限码、限数据范围。以前三个导出按钮和回款效率、财务时间线、未开票客户三个只读口子,进门只看出没登录、不看你是哪个角色——一个仓管登录后能直接把全公司应收明细导走。这一处补上了:六个口都挂上了权限卡控,未登录拉不开、跨角色也导不走。仍留的尾巴是:三张财务表本身没有创建人格,同角色内部还是无行级隔离;回款效率与财务时间线两个只读口因为查到订单头上(订单有属主格),数据范围才真正生效。

"月底对不上"最直接的原因也在这里:账这件事,四个最常被问的口径如今共用了,但金额、账龄还散在各自页里——全并成一处,是下一步的活。

29.8 这一章不做的事

  • 对账单的发货关联已补、汇总也改成按单收。 这一条不再是"补格子才有意义"——硬关联列补上了、一张对账单只收自己那张发货单的票与款(见 29.3、29.4)。
  • 不做红冲。 状态移出可写、新建即已开票,红冲这个动作明写不做。要真做红冲,得先把"作废一张票"做成一个动作(状态、合计、订单开票日期三处一起变)再谈。
  • 发票状态值域没并进全系统字典。 后端已不许乱写这一格,但管理端下拉、颜色、筛选仍读一份写死的中文,没走状态字典——这是这本书写过几次的同一类病,留待一次性收口。
  • 手工建单那一路要补的都补上了。 一期没有自动对账的厂子靠它活着。单号自动取、账期统一式样、编辑口开在界面上,这三件都做了。
  • 不写回款率、超期率、坏账比例任何数字。 上面这些口径没统一之前,任何一个百分比都是三个数的平均。

29.9 今晚能定的两件事

  1. 定一次发货一张还是一月一张。 汇总已经改成一张单只收自己那张发货的票款,"单按发货分、钱按客户摊"那个各做一半的拧巴收住了。剩下的问题是粒度:现在每次发货建一张,一个客户一月发八次就有八张,账期那一格只是同一个标签。要不要保留这个粒度、还是真要"一月一张",是个没定的决定——但不再是口径自相矛盾。
  2. 发票状态已定成一个口径。 新建即已开票、不支持手工改写、不做红冲,三档里能用的一档写进了实现、另两档从界面上撤了。剩下的悬念只有一个:要不要哪天真做红冲;不做,这一格就算定了,开票金额那个数也敢往发票上签了。

下一章不谈数字。李工提离职那天,她脑子里的东西留下了多少。