2026-04-24 19:00:07 +08:00
|
|
|
|
# Inventory Analytics 重构记录与后续计划
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
## 1. 当前目标
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
本次整理后的工程目标是将项目收束为两条清晰链路:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
- 委外批次库存上传:本地页面上传文件,归档原始文件,并写入 Raw PostgreSQL。
|
|
|
|
|
|
- 飞书库存同步:从 Analytics PostgreSQL 查询库存数据,并同步到飞书多维表格。
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
重构重点:
|
|
|
|
|
|
|
|
|
|
|
|
- 删除与当前工程目标无关的旧脚本。
|
|
|
|
|
|
- 将上传页入库逻辑整理为清晰的函数边界。
|
|
|
|
|
|
- 添加工程化日志,保证关键执行信息可追踪。
|
|
|
|
|
|
- 保留飞书同步原入口,并补齐入口、CLI、业务同步阶段日志。
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
## 2. 当前目录结构
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
inventory_analytics/
|
|
|
|
|
|
├── .env
|
2026-04-24 19:00:07 +08:00
|
|
|
|
├── PROJECT_GUIDE.md
|
2026-04-20 15:02:17 +08:00
|
|
|
|
├── REFACTOR_PLAN.md
|
2026-04-24 19:00:07 +08:00
|
|
|
|
├── upload_inventory_page.py
|
|
|
|
|
|
├── list_feishu_base_tables.py
|
2026-04-20 15:02:17 +08:00
|
|
|
|
└── inventory_sync/
|
|
|
|
|
|
├── __init__.py
|
|
|
|
|
|
├── cli.py
|
|
|
|
|
|
├── feishu.py
|
|
|
|
|
|
├── postgres.py
|
|
|
|
|
|
├── service.py
|
|
|
|
|
|
├── settings.py
|
|
|
|
|
|
├── specs.py
|
|
|
|
|
|
└── sql.py
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
已删除旧脚本:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
```text
|
|
|
|
|
|
crud.py
|
|
|
|
|
|
base_xlsx_to_db.py
|
|
|
|
|
|
save_orders.py
|
|
|
|
|
|
session.py
|
|
|
|
|
|
tmall_orders_flow.py
|
|
|
|
|
|
```
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
## 3. 上传页重构结果
|
|
|
|
|
|
|
|
|
|
|
|
文件:`upload_inventory_page.py`
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
职责:
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
- 启动本地上传页面。
|
|
|
|
|
|
- 接收拖拽上传的 Excel/CSV 文件。
|
|
|
|
|
|
- 保存原始文件到 `batch_inventory_data/`。
|
|
|
|
|
|
- 读取 `.env` 中的 Raw 数据库配置。
|
|
|
|
|
|
- 创建 `raw_data.wangdian_batch_inventory`。
|
|
|
|
|
|
- 按文件行粒度写入 JSONB payload。
|
|
|
|
|
|
- 输出结构化日志。
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
关键常量:
|
|
|
|
|
|
|
|
|
|
|
|
```python
|
|
|
|
|
|
HOST = "127.0.0.1"
|
|
|
|
|
|
PORT = 8080
|
|
|
|
|
|
UPLOAD_DIR = PROJECT_ROOT / "batch_inventory_data"
|
|
|
|
|
|
MAX_UPLOAD_BYTES = 200 * 1024 * 1024
|
|
|
|
|
|
DB_SCHEMA = "raw_data"
|
|
|
|
|
|
DB_TABLE = "wangdian_batch_inventory"
|
|
|
|
|
|
DATA_FIELD = "inventory_data"
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
payload 结构:
|
|
|
|
|
|
|
|
|
|
|
|
```json
|
|
|
|
|
|
{
|
|
|
|
|
|
"source_file": "原始文件名.xlsx",
|
|
|
|
|
|
"stored_file": "带时间戳的归档文件名.xlsx",
|
|
|
|
|
|
"uploaded_at": "上传时间",
|
|
|
|
|
|
"total_count": 100,
|
|
|
|
|
|
"inventory_data": {
|
|
|
|
|
|
"每一行的字段": "每一行的值"
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
说明:
|
|
|
|
|
|
|
|
|
|
|
|
- `total_count` 表示本批上传文件解析出的总行数。
|
|
|
|
|
|
- `inventory_data` 保存当前行的完整数据。
|
|
|
|
|
|
- Excel 多 sheet 文件会在行数据中补充 `_sheet_name`。
|
|
|
|
|
|
- 空值会写入 JSON `null`。
|
|
|
|
|
|
- 日期类单元格会转成 ISO 字符串。
|
|
|
|
|
|
|
|
|
|
|
|
## 4. 飞书同步重构结果
|
|
|
|
|
|
|
|
|
|
|
|
入口文件:`list_feishu_base_tables.py`
|
|
|
|
|
|
|
|
|
|
|
|
模块职责:
|
|
|
|
|
|
|
|
|
|
|
|
| 文件 | 职责 |
|
|
|
|
|
|
| --- | --- |
|
|
|
|
|
|
| `list_feishu_base_tables.py` | 兼容入口、配置日志、记录启动和退出 |
|
|
|
|
|
|
| `inventory_sync/cli.py` | 解析 action、编排顶层执行、输出 JSON 结果 |
|
|
|
|
|
|
| `inventory_sync/settings.py` | 加载 `.env`,构建配置对象 |
|
|
|
|
|
|
| `inventory_sync/postgres.py` | 执行 Analytics PostgreSQL 查询 |
|
|
|
|
|
|
| `inventory_sync/sql.py` | 维护库存同步 SQL |
|
|
|
|
|
|
| `inventory_sync/feishu.py` | 封装飞书 API |
|
|
|
|
|
|
| `inventory_sync/service.py` | 编排品牌同步业务流程 |
|
|
|
|
|
|
| `inventory_sync/specs.py` | 维护品牌目标和字段映射 |
|
|
|
|
|
|
|
|
|
|
|
|
当前 action:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
feishu 查看飞书 Base 表信息
|
|
|
|
|
|
postgres 查询 Analytics PostgreSQL
|
|
|
|
|
|
sync-brand 按配置同步品牌数据到飞书
|
|
|
|
|
|
all 执行完整流程
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
## 5. 日志方案
|
|
|
|
|
|
|
|
|
|
|
|
日志统一采用事件式结构:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
YYYY-MM-DD HH:MM:SS LEVEL logger_name 事件=中文事件描述 中文字段=字段值 ...
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
上传页 logger:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
inventory_upload
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
飞书同步 logger:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
inventory_sync_entrypoint
|
|
|
|
|
|
inventory_sync.cli
|
|
|
|
|
|
inventory_sync.service
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
上传页关键事件:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
上传服务启动中
|
|
|
|
|
|
上传服务已启动
|
|
|
|
|
|
收到GET请求
|
|
|
|
|
|
开始处理POST请求
|
|
|
|
|
|
收到上传请求
|
|
|
|
|
|
已解析上传文件
|
|
|
|
|
|
已分配上传归档路径
|
|
|
|
|
|
上传文件已保存
|
|
|
|
|
|
开始解析库存文件
|
|
|
|
|
|
已解析Excel工作表
|
|
|
|
|
|
已解析CSV文件
|
|
|
|
|
|
已加载Raw数据库配置
|
|
|
|
|
|
开始连接Raw数据库
|
|
|
|
|
|
开始确认Raw数据表
|
|
|
|
|
|
Raw数据表确认完成
|
|
|
|
|
|
开始写入Raw数据
|
|
|
|
|
|
Raw数据写入完成
|
|
|
|
|
|
上传请求处理完成
|
|
|
|
|
|
上传文件写入Raw数据库失败
|
|
|
|
|
|
上传服务已停止
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
飞书同步关键事件:
|
|
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
飞书同步入口启动
|
|
|
|
|
|
飞书同步动作开始
|
|
|
|
|
|
已加载环境变量文件
|
|
|
|
|
|
开始读取飞书Base信息
|
|
|
|
|
|
飞书Base信息读取完成
|
|
|
|
|
|
开始查询PostgreSQL
|
|
|
|
|
|
PostgreSQL查询完成
|
|
|
|
|
|
开始准备品牌同步
|
|
|
|
|
|
开始同步目标飞书表
|
|
|
|
|
|
目标飞书表已有记录读取完成
|
|
|
|
|
|
目标飞书表同步完成
|
|
|
|
|
|
飞书同步动作完成
|
|
|
|
|
|
飞书同步入口完成
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
## 6. 执行方式
|
|
|
|
|
|
|
|
|
|
|
|
启动上传页:
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
python3 upload_inventory_page.py
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
查看飞书表:
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
python3 list_feishu_base_tables.py --action feishu
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
查询 PostgreSQL:
|
|
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
python3 list_feishu_base_tables.py --action postgres
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
同步品牌数据:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```bash
|
|
|
|
|
|
python3 list_feishu_base_tables.py --action sync-brand
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
执行完整飞书同步:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
```bash
|
|
|
|
|
|
python3 list_feishu_base_tables.py --action all
|
|
|
|
|
|
```
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
## 7. 配置维护
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
### 7.1 上传页 Raw 数据库配置
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
```text
|
|
|
|
|
|
RAW_DB_HOST
|
|
|
|
|
|
RAW_DB_PORT
|
|
|
|
|
|
RAW_DB_USER
|
|
|
|
|
|
RAW_DB_PASSWORD
|
|
|
|
|
|
RAW_DB_NAME
|
|
|
|
|
|
```
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
### 7.2 飞书同步配置
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```text
|
|
|
|
|
|
FEISHU_APP_ID
|
2026-04-24 19:00:07 +08:00
|
|
|
|
FEISHU_APP_SECRET
|
2026-04-20 15:02:17 +08:00
|
|
|
|
FEISHU_BASE_URL
|
2026-04-24 19:00:07 +08:00
|
|
|
|
FEISHU_APP_TOKEN
|
2026-04-20 15:02:17 +08:00
|
|
|
|
ANALYTICS_DB_HOST
|
|
|
|
|
|
ANALYTICS_DB_PORT
|
|
|
|
|
|
ANALYTICS_DB_USER
|
|
|
|
|
|
ANALYTICS_DB_PASSWORD
|
|
|
|
|
|
ANALYTICS_DB_NAME
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
### 7.3 品牌和字段配置
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
品牌同步目标维护在 `inventory_sync/specs.py`:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```python
|
|
|
|
|
|
BRAND_SYNC_TARGETS = [
|
2026-05-11 16:56:27 +08:00
|
|
|
|
BrandSyncTarget(brand_name="羽心堂", table_name="羽心堂渠道库存-9:00和19:00", warehouse_keys=(2, 3, 7, 13)),
|
2026-04-20 15:02:17 +08:00
|
|
|
|
]
|
|
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
字段映射维护在 `FIELD_SPECS`:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```python
|
2026-04-24 19:00:07 +08:00
|
|
|
|
FieldSpec("飞书字段名", "SQL 输出字段名", field_type, formatter, scale)
|
2026-04-20 15:02:17 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
## 8. 验证命令
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
语法检查:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```bash
|
2026-04-24 19:00:07 +08:00
|
|
|
|
python3 -m py_compile upload_inventory_page.py list_feishu_base_tables.py inventory_sync/*.py
|
2026-04-20 15:02:17 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
帮助信息:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
|
|
|
|
|
```bash
|
2026-04-24 19:00:07 +08:00
|
|
|
|
python3 list_feishu_base_tables.py --help
|
2026-04-20 15:02:17 +08:00
|
|
|
|
```
|
|
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
端口检查:
|
2026-04-20 15:02:17 +08:00
|
|
|
|
|
2026-04-24 19:00:07 +08:00
|
|
|
|
```bash
|
|
|
|
|
|
lsof -nP -iTCP:8080 -sTCP:LISTEN
|
2026-04-20 15:02:17 +08:00
|
|
|
|
```
|
2026-04-24 19:00:07 +08:00
|
|
|
|
|
|
|
|
|
|
## 9. 后续计划
|
|
|
|
|
|
|
|
|
|
|
|
- 为上传页增加 dry-run 或预览模式,只解析文件不写库。
|
|
|
|
|
|
- 为上传页增加重复文件或重复批次检测。
|
|
|
|
|
|
- 为 Raw 表增加按 `stored_file` 或 `uploaded_at` 的查询辅助索引。
|
|
|
|
|
|
- 为飞书同步增加 dry-run,预览删除和新增数量。
|
|
|
|
|
|
- 为飞书同步增加 upsert 模式,降低全量删除带来的风险。
|
|
|
|
|
|
- 增加单元测试,覆盖文件解析、payload 构造、字段映射、数字转换。
|
|
|
|
|
|
- 将日志接入文件轮转或统一日志采集系统。
|
|
|
|
|
|
- 将运行命令接入 Makefile 或任务脚本,减少人工输入成本。
|