# `Sp_saveReturn_sSfu` (procedure)

> 商机跟进存前反写数量


- **Type:** PROCEDURE
- **Deterministic:** NO
- **SQL data access:** CONTAINS SQL

## Parameters

| # | Mode | Name | Type |
|---|---|---|---|
| 1 | IN | `sGuid` | `longtext` |
| 2 | IN | `sBrId` | `varchar(100)` |
| 3 | IN | `sSuId` | `varchar(100)` |
| 4 | IN | `iTag` | `int` |
| 5 | OUT | `sCode` | `int` |
| 6 | OUT | `sReturn` | `longtext` |

## Body

_Body is not pre-cached. To inspect: `mysql --defaults-file=~/.my.cnf -e 'SHOW CREATE PROCEDURE `Sp_saveReturn_sSfu`'`._

## Narrative

**Business context:** 销售管理 → 商机/客户跟进 — quantity back-write helper for 商机跟进 (`salsalesFollowUpmaster`/Slave). When a follow-up record is saved or invalidated the proc rolls up the follow-up qty/money columns onto the source 报价 / 订单 (quotation/order) row so summary screens stay accurate.

**What it does:** Parses comma-list `sGuid` into a temp id set, joins `salsalesFollowUpmaster` to find the `sSrcId` (source slave) of every affected follow-up, then assembles per-source aggregates (`dProductQty`, `dProductMoney`, `dLossQty`, `dMaterialsQty`, `dProofingMoney`, `dPlateMoney`, `dKnifeMouldMoney`, `dFreightMoney`, `dRemainderQty`, `sFollowUpPhase`) honouring `iTag` (1 = before-save excludes the rows in this batch, 2 = after-save includes them). The aggregates are then UPDATE'd onto the upstream slave.

**Invocation:** Wrapped by `Sp_beforeSave_sSfu(iTag=1)` and `Sp_afterSave_sSfu(iTag=2)`. Those wrappers fire on the 商机跟进 form save and on invalidate/delete via the `Sp_Invalid_backwriting` / `Sp_delete_backwriting` dispatchers. No direct gdsmodule hook references `Sp_saveReturn_sSfu` — it is only reachable through its before/after siblings.
