'task3TAPD过期单推送'

This commit is contained in:
zelong 2026-03-13 14:21:45 +08:00
parent 704318077d
commit af7243cf4e
9 changed files with 210 additions and 63 deletions

1
.gitignore vendored
View File

@ -133,6 +133,7 @@ cython_debug/
# Custom
logs/
logs2/
logs3/
.claude/
# Project documentation

View File

@ -1,4 +1,4 @@
{
"access_token": "aAYJlq4Ueq_gF7-Rx8vfQixphAVb716T9Y6Baixp5zM-3tdA0dDXpEtacGI4DRSuDqzNC5x6Dq0NomwJvo5Glq6lwMvi9gCxV9Eu3FxGpk6AELfduZ8wRPTMJrOy4Y4-q0Xk_MLbUTtVlps5TXuMiDFNYVnCu6-DKONMgKarVPJQrlLa84QO1muTJIk_mg-BLCpf5XLEWKNgwbtyLTrO39RBoAtCRNYcqxFywJUrxIs",
"fetch_time": 1773296159.0088081
"access_token": "28gECNTAJqbnb4w4V8SfXKq6EIBaamsIFwrqNy0KkABSCPzZz5BWERID2zg9JXGKnr48Ug3GDqAy46EdY047BQocXTUNdMgFCmzHZHgPJxfKtbqr_4pAq_tGvX5TfWVWbQxu-ZjnNsNLoGef7nLW4E-ykYzRQ-I7qqIZwePYevo6-Q_ezF0ImXDyD9I_LOXmQZ9vuGFWsjYGFddKBQ8bSfePtudJvio5ILiuRgwUsXc",
"fetch_time": 1773373351.2013075
}

View File

@ -6,7 +6,11 @@ push_time = 15:35
skip_weekend = true
[WeWork]
# 测试
webhook_url = https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key=026670e0-9e8d-4f61-9b3f-1f81365954ff
# 实际
# webhook_url = https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key=20dd49fb-7663-4e16-98fe-f0e71d8126fb
[Smartsheet]
# 技术组成员配置表

View File

@ -95,3 +95,27 @@
{"event_type": "api_call", "timestamp": "2026-03-12 15:35:03", "task": "task3", "sync_id": "task3_20260312_153500_8f56d85c", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "星渊", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296797", "title": "优化性能分辨率提升为1080P静态帧率基本稳定60fps", "deadline": "2025-12-22", "status": "closed"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 15:35:03", "task": "task3", "sync_id": "task3_20260312_153500_8f56d85c", "module": "wework", "operation": "webhook/send", "success": true, "request": {"msgtype": "markdown", "markdown": {"content": "⏰ TAPD 过期单提醒2026-03-12\n\n\n<@xingyuan>13 条过期)\n1.【需求】AS脚本Bind扩展 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839302)\n2.【需求】尝试AS写Validator | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839301)\n3.【需求】Data Validator框架 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839234)\n4.【需求】材质Mask模式不受motion blur影响 | 过期 35 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839323)\n5.【需求】KawaiiMagicAnimVelet调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839272)\n6.【需求】Chaos布料算法调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839270)\n7.【需求】编译Android版 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839267)\n8.【需求】对GPU解算进行改近 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839266)\n9.【需求】理解GPU算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839259)\n10.【需求】调试和理解NvCloth算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839246)\n11.【需求】NvCloth调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839241)\n12.【需求】布料解算基建 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839239)\n13.【需求】3C-基础移动-Bug-Dodge卡帧 | 过期 2 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004866823)\n\n\n========================\n共 13 条过期单,请今日内更新状态 🙏"}, "mentioned_list": ["xingyuan"]}, "response": {"errcode": 0, "errmsg": "ok"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 15:35:03", "task": "task3", "sync_id": "task3_20260312_153500_8f56d85c", "success": true, "stats": {"overdue_count": 13}, "error_message": null, "extra": {}}
{"event_type": "start_sync", "timestamp": "2026-03-12 16:07:51", "task": "task3", "sync_id": "task3_20260312_160751_c8a45221", "trigger": "manual", "metadata": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:07:53", "task": "task3", "sync_id": "task3_20260312_160751_c8a45221", "module": "tapd", "operation": "stories", "success": true, "request": {"workspace_id": "58335167", "owner": "星渊", "fields": "id,name,due,status"}, "response": {"status": 1, "data": [{"Story": {"id": "1158335167004866823", "name": "3C-基础移动-Bug-Dodge卡帧", "due": "2026-03-10", "status": "status_9"}}, {"Story": {"id": "1158335167004839323", "name": "材质Mask模式不受motion blur影响", "due": "2026-02-05", "status": "status_9"}}, {"Story": {"id": "1158335167004839302", "name": "AS脚本Bind扩展", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839301", "name": "尝试AS写Validator", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839299", "name": "简单Sample跑下流程", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839298", "name": "文档阅读", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839272", "name": "KawaiiMagicAnimVelet调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839270", "name": "Chaos布料算法调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839267", "name": "编译Android版", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839266", "name": "对GPU解算进行改近", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839263", "name": "育碧GPU布料结算的GDC Paper", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839259", "name": "理解GPU算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839251", "name": "增加Profiler", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839246", "name": "调试和理解NvCloth算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839242", "name": "编译NvCloth", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839241", "name": "NvCloth调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839239", "name": "布料解算基建", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839234", "name": "Data Validator框架", "due": "2026-02-03", "status": "status_5"}}, {"Story": {"id": "1158335167004834466", "name": "Horde相关-持续开发项", "due": "2026-05-30", "status": "status_5"}}, {"Story": {"id": "1158335167004834018", "name": "【引擎/TA】2026年1月 - 凡人各组月度产出梳理", "due": "2026-01-28", "status": "status_8"}}, {"Story": {"id": "1158335167004828309", "name": "技术基建-基础可过滤编辑器控件开发", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004802628", "name": "技术基建-XianDebugger-法术场Debugger", "due": null, "status": "status_9"}}, {"Story": {"id": "1158335167004802626", "name": "技术基建-XianDebugger", "due": null, "status": "status_5"}}, {"Story": {"id": "1158335167004800837", "name": "VAT贴图Foramt以及各种选项的意义", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800834", "name": "VAT贴图尺寸和种类优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800832", "name": "VAT内存优化", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800829", "name": "内存Profiling", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800828", "name": "内存优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800819", "name": "Async优化Lumen反射", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800816", "name": "优化Lumen反射包括水的反射性能", "due": null, "status": "status_8"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:07:54", "task": "task3", "sync_id": "task3_20260312_160751_c8a45221", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "星渊", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296797", "title": "优化性能分辨率提升为1080P静态帧率基本稳定60fps", "deadline": "2025-12-22", "status": "closed"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:07:54", "task": "task3", "sync_id": "task3_20260312_160751_c8a45221", "module": "wework", "operation": "webhook/send", "success": true, "request": {"msgtype": "markdown", "markdown": {"content": "⏰ TAPD 过期单提醒2026-03-12\n\n\n<@xingyuan>13 条过期)\n1.【需求】AS脚本Bind扩展 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839302)\n2.【需求】尝试AS写Validator | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839301)\n3.【需求】Data Validator框架 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839234)\n4.【需求】材质Mask模式不受motion blur影响 | 过期 35 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839323)\n5.【需求】KawaiiMagicAnimVelet调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839272)\n6.【需求】Chaos布料算法调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839270)\n7.【需求】编译Android版 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839267)\n8.【需求】对GPU解算进行改近 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839266)\n9.【需求】理解GPU算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839259)\n10.【需求】调试和理解NvCloth算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839246)\n11.【需求】NvCloth调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839241)\n12.【需求】布料解算基建 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839239)\n13.【需求】3C-基础移动-Bug-Dodge卡帧 | 过期 2 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004866823)\n\n\n========================\n共 13 条过期单,请今日内更新状态 🙏"}, "mentioned_list": ["xingyuan"]}, "response": {"errcode": 0, "errmsg": "ok"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 16:07:54", "task": "task3", "sync_id": "task3_20260312_160751_c8a45221", "success": true, "stats": {"overdue_count": 13}, "error_message": null, "extra": {}}
{"event_type": "start_sync", "timestamp": "2026-03-12 16:22:57", "task": "task3", "sync_id": "task3_20260312_162257_935477a8", "trigger": "manual", "metadata": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:00", "task": "task3", "sync_id": "task3_20260312_162257_935477a8", "module": "tapd", "operation": "stories", "success": true, "request": {"workspace_id": "58335167", "owner": "星渊", "fields": "id,name,due,status"}, "response": {"status": 1, "data": [{"Story": {"id": "1158335167004866823", "name": "3C-基础移动-Bug-Dodge卡帧", "due": "2026-03-10", "status": "status_9"}}, {"Story": {"id": "1158335167004839323", "name": "材质Mask模式不受motion blur影响", "due": "2026-02-05", "status": "status_9"}}, {"Story": {"id": "1158335167004839302", "name": "AS脚本Bind扩展", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839301", "name": "尝试AS写Validator", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839299", "name": "简单Sample跑下流程", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839298", "name": "文档阅读", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839272", "name": "KawaiiMagicAnimVelet调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839270", "name": "Chaos布料算法调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839267", "name": "编译Android版", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839266", "name": "对GPU解算进行改近", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839263", "name": "育碧GPU布料结算的GDC Paper", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839259", "name": "理解GPU算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839251", "name": "增加Profiler", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839246", "name": "调试和理解NvCloth算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839242", "name": "编译NvCloth", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839241", "name": "NvCloth调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839239", "name": "布料解算基建", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839234", "name": "Data Validator框架", "due": "2026-02-03", "status": "status_5"}}, {"Story": {"id": "1158335167004834466", "name": "Horde相关-持续开发项", "due": "2026-05-30", "status": "status_5"}}, {"Story": {"id": "1158335167004834018", "name": "【引擎/TA】2026年1月 - 凡人各组月度产出梳理", "due": "2026-01-28", "status": "status_8"}}, {"Story": {"id": "1158335167004828309", "name": "技术基建-基础可过滤编辑器控件开发", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004802628", "name": "技术基建-XianDebugger-法术场Debugger", "due": null, "status": "status_9"}}, {"Story": {"id": "1158335167004802626", "name": "技术基建-XianDebugger", "due": null, "status": "status_5"}}, {"Story": {"id": "1158335167004800837", "name": "VAT贴图Foramt以及各种选项的意义", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800834", "name": "VAT贴图尺寸和种类优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800832", "name": "VAT内存优化", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800829", "name": "内存Profiling", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800828", "name": "内存优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800819", "name": "Async优化Lumen反射", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800816", "name": "优化Lumen反射包括水的反射性能", "due": null, "status": "status_8"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:00", "task": "task3", "sync_id": "task3_20260312_162257_935477a8", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "星渊", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296797", "title": "优化性能分辨率提升为1080P静态帧率基本稳定60fps", "deadline": "2025-12-22", "status": "closed"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:01", "task": "task3", "sync_id": "task3_20260312_162257_935477a8", "module": "wework", "operation": "webhook/send", "success": true, "request": {"msgtype": "markdown", "markdown": {"content": "⏰ TAPD 过期单提醒2026-03-12\n\n\n<@xingyuan>13 条过期)\n1.【需求】AS脚本Bind扩展 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839302)\n2.【需求】尝试AS写Validator | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839301)\n3.【需求】Data Validator框架 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839234)\n4.【需求】材质Mask模式不受motion blur影响 | 过期 35 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839323)\n5.【需求】KawaiiMagicAnimVelet调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839272)\n6.【需求】Chaos布料算法调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839270)\n7.【需求】编译Android版 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839267)\n8.【需求】对GPU解算进行改近 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839266)\n9.【需求】理解GPU算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839259)\n10.【需求】调试和理解NvCloth算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839246)\n11.【需求】NvCloth调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839241)\n12.【需求】布料解算基建 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839239)\n13.【需求】3C-基础移动-Bug-Dodge卡帧 | 过期 2 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004866823)\n\n\n========================\n共 13 条过期单,请今日内更新状态 🙏"}, "mentioned_list": ["xingyuan"]}, "response": {"errcode": 0, "errmsg": "ok"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 16:23:01", "task": "task3", "sync_id": "task3_20260312_162257_935477a8", "success": true, "stats": {"overdue_count": 13}, "error_message": null, "extra": {}}
{"event_type": "start_sync", "timestamp": "2026-03-12 16:23:23", "task": "task3", "sync_id": "task3_20260312_162323_eea7a0d6", "trigger": "manual", "metadata": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:25", "task": "task3", "sync_id": "task3_20260312_162323_eea7a0d6", "module": "tapd", "operation": "stories", "success": true, "request": {"workspace_id": "58335167", "owner": "星渊", "fields": "id,name,due,status"}, "response": {"status": 1, "data": [{"Story": {"id": "1158335167004866823", "name": "3C-基础移动-Bug-Dodge卡帧", "due": "2026-03-10", "status": "status_9"}}, {"Story": {"id": "1158335167004839323", "name": "材质Mask模式不受motion blur影响", "due": "2026-02-05", "status": "status_9"}}, {"Story": {"id": "1158335167004839302", "name": "AS脚本Bind扩展", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839301", "name": "尝试AS写Validator", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839299", "name": "简单Sample跑下流程", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839298", "name": "文档阅读", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839272", "name": "KawaiiMagicAnimVelet调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839270", "name": "Chaos布料算法调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839267", "name": "编译Android版", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839266", "name": "对GPU解算进行改近", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839263", "name": "育碧GPU布料结算的GDC Paper", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839259", "name": "理解GPU算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839251", "name": "增加Profiler", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839246", "name": "调试和理解NvCloth算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839242", "name": "编译NvCloth", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839241", "name": "NvCloth调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839239", "name": "布料解算基建", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839234", "name": "Data Validator框架", "due": "2026-02-03", "status": "status_5"}}, {"Story": {"id": "1158335167004834466", "name": "Horde相关-持续开发项", "due": "2026-05-30", "status": "status_5"}}, {"Story": {"id": "1158335167004834018", "name": "【引擎/TA】2026年1月 - 凡人各组月度产出梳理", "due": "2026-01-28", "status": "status_8"}}, {"Story": {"id": "1158335167004828309", "name": "技术基建-基础可过滤编辑器控件开发", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004802628", "name": "技术基建-XianDebugger-法术场Debugger", "due": null, "status": "status_9"}}, {"Story": {"id": "1158335167004802626", "name": "技术基建-XianDebugger", "due": null, "status": "status_5"}}, {"Story": {"id": "1158335167004800837", "name": "VAT贴图Foramt以及各种选项的意义", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800834", "name": "VAT贴图尺寸和种类优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800832", "name": "VAT内存优化", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800829", "name": "内存Profiling", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800828", "name": "内存优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800819", "name": "Async优化Lumen反射", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800816", "name": "优化Lumen反射包括水的反射性能", "due": null, "status": "status_8"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:25", "task": "task3", "sync_id": "task3_20260312_162323_eea7a0d6", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "星渊", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296797", "title": "优化性能分辨率提升为1080P静态帧率基本稳定60fps", "deadline": "2025-12-22", "status": "closed"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:23:26", "task": "task3", "sync_id": "task3_20260312_162323_eea7a0d6", "module": "wework", "operation": "webhook/send", "success": true, "request": {"msgtype": "markdown", "markdown": {"content": "⏰ TAPD 过期单提醒2026-03-12\n\n\n<@xingyuan>13 条过期)\n1.【需求】AS脚本Bind扩展 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839302)\n2.【需求】尝试AS写Validator | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839301)\n3.【需求】Data Validator框架 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839234)\n4.【需求】材质Mask模式不受motion blur影响 | 过期 35 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839323)\n5.【需求】KawaiiMagicAnimVelet调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839272)\n6.【需求】Chaos布料算法调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839270)\n7.【需求】编译Android版 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839267)\n8.【需求】对GPU解算进行改近 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839266)\n9.【需求】理解GPU算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839259)\n10.【需求】调试和理解NvCloth算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839246)\n11.【需求】NvCloth调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839241)\n12.【需求】布料解算基建 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839239)\n13.【需求】3C-基础移动-Bug-Dodge卡帧 | 过期 2 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004866823)\n\n\n========================\n共 13 条过期单,请今日内更新状态 🙏"}, "mentioned_list": ["xingyuan"]}, "response": {"errcode": 0, "errmsg": "ok"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 16:23:26", "task": "task3", "sync_id": "task3_20260312_162323_eea7a0d6", "success": true, "stats": {"overdue_count": 13}, "error_message": null, "extra": {}}
{"event_type": "start_sync", "timestamp": "2026-03-12 16:27:11", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "trigger": "manual", "metadata": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:27:14", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "module": "tapd", "operation": "stories", "success": true, "request": {"workspace_id": "58335167", "owner": "星渊", "fields": "id,name,due,status"}, "response": {"status": 1, "data": [{"Story": {"id": "1158335167004866823", "name": "3C-基础移动-Bug-Dodge卡帧", "due": "2026-03-10", "status": "status_9"}}, {"Story": {"id": "1158335167004839323", "name": "材质Mask模式不受motion blur影响", "due": "2026-02-05", "status": "status_9"}}, {"Story": {"id": "1158335167004839302", "name": "AS脚本Bind扩展", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839301", "name": "尝试AS写Validator", "due": "2026-02-03", "status": "status_10"}}, {"Story": {"id": "1158335167004839299", "name": "简单Sample跑下流程", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839298", "name": "文档阅读", "due": "2026-02-03", "status": "status_8"}}, {"Story": {"id": "1158335167004839272", "name": "KawaiiMagicAnimVelet调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839270", "name": "Chaos布料算法调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839267", "name": "编译Android版", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839266", "name": "对GPU解算进行改近", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839263", "name": "育碧GPU布料结算的GDC Paper", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839259", "name": "理解GPU算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839251", "name": "增加Profiler", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839246", "name": "调试和理解NvCloth算法", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839242", "name": "编译NvCloth", "due": "2026-02-13", "status": "status_8"}}, {"Story": {"id": "1158335167004839241", "name": "NvCloth调研", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839239", "name": "布料解算基建", "due": "2026-02-13", "status": "status_5"}}, {"Story": {"id": "1158335167004839234", "name": "Data Validator框架", "due": "2026-02-03", "status": "status_5"}}, {"Story": {"id": "1158335167004834466", "name": "Horde相关-持续开发项", "due": "2026-05-30", "status": "status_5"}}, {"Story": {"id": "1158335167004834018", "name": "【引擎/TA】2026年1月 - 凡人各组月度产出梳理", "due": "2026-01-28", "status": "status_8"}}, {"Story": {"id": "1158335167004828309", "name": "技术基建-基础可过滤编辑器控件开发", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004802628", "name": "技术基建-XianDebugger-法术场Debugger", "due": null, "status": "status_9"}}, {"Story": {"id": "1158335167004802626", "name": "技术基建-XianDebugger", "due": null, "status": "status_5"}}, {"Story": {"id": "1158335167004800837", "name": "VAT贴图Foramt以及各种选项的意义", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800834", "name": "VAT贴图尺寸和种类优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800832", "name": "VAT内存优化", "due": null, "status": "status_7"}}, {"Story": {"id": "1158335167004800829", "name": "内存Profiling", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800828", "name": "内存优化", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800819", "name": "Async优化Lumen反射", "due": null, "status": "status_8"}}, {"Story": {"id": "1158335167004800816", "name": "优化Lumen反射包括水的反射性能", "due": null, "status": "status_8"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:27:14", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "module": "tapd", "operation": "stories", "success": true, "request": {"workspace_id": "58335167", "owner": "v_linzelong", "fields": "id,name,due,status"}, "response": {"status": 1, "data": [{"Story": {"id": "1158335167004820451", "name": "自动化测试单", "due": null, "status": "status_12"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:27:14", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "星渊", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296797", "title": "优化性能分辨率提升为1080P静态帧率基本稳定60fps", "deadline": "2025-12-22", "status": "closed"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:27:14", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "module": "tapd", "operation": "bugs", "success": true, "request": {"workspace_id": "58335167", "current_owner": "v_linzelong", "fields": "id,title,deadline,status"}, "response": {"status": 1, "data": [{"Bug": {"id": "1158335167002296876", "title": "测试状态回写", "deadline": null, "status": "closed"}}, {"Bug": {"id": "1158335167002299210", "title": "测试状态回写", "deadline": null, "status": "rejected"}}, {"Bug": {"id": "1158335167002299743", "title": "多子表测试", "deadline": "2025-12-29", "status": "closed"}}, {"Bug": {"id": "1158335167002300470", "title": "测试描述", "deadline": "2025-12-30", "status": "rejected"}}], "info": "success"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "api_call", "timestamp": "2026-03-12 16:27:15", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "module": "wework", "operation": "webhook/send", "success": true, "request": {"msgtype": "markdown", "markdown": {"content": "⏰ TAPD 过期单提醒2026-03-12\n\n\n<@xingyuan>13 条过期)\n1.【需求】AS脚本Bind扩展 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839302)\n2.【需求】尝试AS写Validator | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839301)\n3.【需求】Data Validator框架 | 过期 37 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839234)\n4.【需求】材质Mask模式不受motion blur影响 | 过期 35 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839323)\n5.【需求】KawaiiMagicAnimVelet调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839272)\n6.【需求】Chaos布料算法调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839270)\n7.【需求】编译Android版 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839267)\n8.【需求】对GPU解算进行改近 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839266)\n9.【需求】理解GPU算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839259)\n10.【需求】调试和理解NvCloth算法 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839246)\n11.【需求】NvCloth调研 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839241)\n12.【需求】布料解算基建 | 过期 27 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004839239)\n13.【需求】3C-基础移动-Bug-Dodge卡帧 | 过期 2 天 | [查看](https://www.tapd.cn/58335167/prong/stories/view/1158335167004866823)\n\n\n========================\n共 13 条过期单,请今日内更新状态 🙏"}, "mentioned_list": ["xingyuan"]}, "response": {"errcode": 0, "errmsg": "ok"}, "error_message": null, "duration_ms": null, "extra": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 16:27:15", "task": "task3", "sync_id": "task3_20260312_162711_4f28fc16", "success": true, "stats": {"overdue_count": 13}, "error_message": null, "extra": {}}
{"event_type": "start_sync", "timestamp": "2026-03-12 16:41:15", "task": "task3", "sync_id": "task3_20260312_164115_81d6cac5", "trigger": "manual", "metadata": {}}
{"event_type": "end_sync", "timestamp": "2026-03-12 16:41:16", "task": "task3", "sync_id": "task3_20260312_164115_81d6cac5", "success": false, "stats": {}, "error_message": "白名单错误: 智能表格中没有启用的技术组成员", "extra": {}}

View File

@ -14,6 +14,36 @@ from src3.message_formatter import MessageFormatter
from src3.webhook_sender import WebhookSender
def _send_error_notification(webhook_url: str, logger):
"""发送错误通知"""
import requests
payload = {
"msgtype": "markdown",
"markdown": {
"content": "⚠️ 今日过期单提醒获取失败,请人工检查"
}
}
try:
requests.post(webhook_url, json=payload, timeout=10)
except:
pass
def _send_no_overdue_message(webhook_url: str, logger):
"""发送无过期单消息"""
import requests
payload = {
"msgtype": "markdown",
"markdown": {
"content": "✅ 今日程序组无过期单,大家保持!"
}
}
try:
requests.post(webhook_url, json=payload, timeout=10)
except:
pass
def run_once():
"""执行一次过期单推送"""
logger = get_task3_logger()
@ -23,31 +53,58 @@ def run_once():
print("任务三TAPD过期单推送")
# 1. 加载配置
config = Task3ConfigManager()
workspace_id = config.get_workspace_id()
webhook_url = config.get_webhook_url()
tech_team = config.get_tech_team_config()
member_list = tech_team['member_list']
user_mapping = tech_team['user_mapping']
try:
config = Task3ConfigManager()
workspace_id = config.get_workspace_id()
webhook_url = config.get_webhook_url()
except ValueError as e:
print(f"✗ 配置错误: {e}")
logger.end_sync_with_stats({}, False, f"配置错误: {e}", sync_id=sync_id)
return
# 2. 加载技术组配置
try:
tech_team = config.get_tech_team_config()
member_list = tech_team['member_list']
user_mapping = tech_team['user_mapping']
except ValueError as e:
print(f"✗ 白名单为空: {e}")
logger.end_sync_with_stats({}, False, f"白名单错误: {e}", sync_id=sync_id)
return
except Exception as e:
print(f"✗ 获取技术组配置失败: {e}")
logger.end_sync_with_stats({}, False, f"配置加载失败: {e}", sync_id=sync_id)
return
print(f"技术组成员: {member_list}")
# 2. 获取过期单
fetcher = OverdueFetcher(workspace_id, logger)
items = fetcher.fetch_all_overdue(member_list)
# 3. 获取过期单
try:
fetcher = OverdueFetcher(workspace_id, logger)
items = fetcher.fetch_all_overdue(member_list)
except Exception as e:
print(f"✗ TAPD API调用失败: {e}")
_send_error_notification(webhook_url, logger)
logger.end_sync_with_stats({}, False, f"TAPD API失败: {e}", sync_id=sync_id)
return
if not items:
print("没有过期单")
print("✅ 今日程序组无过期单")
_send_no_overdue_message(webhook_url, logger)
logger.end_sync_with_stats({"overdue_count": 0}, True, sync_id=sync_id)
return
print(f"获取到 {len(items)} 条过期单")
# 3. 格式化消息
formatter = MessageFormatter()
# 4. 格式化消息
formatter = MessageFormatter(logger)
today = datetime.now().strftime('%Y-%m-%d')
content, mentioned_list = formatter.format_message(items, user_mapping, today)
# 4. 发送消息
if formatter.unmapped_users:
print(f"⚠️ 未映射用户: {', '.join(formatter.unmapped_users)}")
# 5. 发送消息
sender = WebhookSender(webhook_url, logger)
success = sender.send_markdown(content, mentioned_list)
@ -59,9 +116,8 @@ def run_once():
logger.end_sync_with_stats({"overdue_count": len(items)}, False, "推送失败", sync_id=sync_id)
except Exception as e:
print(f"执行失败: {e}")
logger.end_sync_with_stats({}, False, str(e), sync_id=sync_id)
raise
print(f"✗ 未知错误: {e}")
logger.end_sync_with_stats({}, False, f"未知错误: {e}", sync_id=sync_id)
if __name__ == "__main__":

View File

@ -6,6 +6,10 @@ from datetime import datetime
class MessageFormatter:
"""消息格式化器"""
def __init__(self, logger=None):
self.logger = logger
self.unmapped_users = set()
def format_message(self, items: List[dict], user_mapping: Dict[str, str], date: str = None) -> tuple:
"""格式化消息
返回: (markdown_content, mentioned_list)
@ -29,10 +33,17 @@ class MessageFormatter:
item_index = 1
for owner, owner_items in sorted_groups:
wework_id = user_mapping.get(owner, owner)
mentioned_list.append(wework_id)
wework_id = user_mapping.get(owner)
lines.append(f"<@{wework_id}>{len(owner_items)} 条过期)")
if wework_id:
mentioned_list.append(wework_id)
lines.append(f"<@{wework_id}>{len(owner_items)} 条过期)")
else:
# 处理人不在映射表中
self.unmapped_users.add(owner)
lines.append(f"@{owner}{len(owner_items)} 条过期)")
if self.logger:
self.logger.log_api_call("formatter", "unmapped_user", {"owner": owner}, {}, False, "用户未在映射表中")
for item in owner_items:
type_label = "需求" if item['type'] == 'story' else "缺陷"

View File

@ -51,16 +51,23 @@ class Task3Scheduler:
try:
run_once()
self.success_count += 1
print(f"[{datetime.now().strftime('%Y-%m-%d %H:%M:%S')}] ✓ 执行成功")
except Exception as e:
self.fail_count += 1
print(f"执行失败: {e}")
print(f"[{datetime.now().strftime('%Y-%m-%d %H:%M:%S')}] ✗ 执行失败: {e}")
import traceback
traceback.print_exc()
def start(self):
"""启动调度器"""
from src3.config import Task3ConfigManager
config = Task3ConfigManager()
push_time = config.get_push_time()
try:
config = Task3ConfigManager()
push_time = config.get_push_time()
except Exception as e:
print(f"✗ 配置加载失败: {e}")
return
print("="*50)
print("任务三TAPD过期单推送调度器")

View File

@ -47,6 +47,18 @@ class TAPDUnifiedApi:
self.logger.log_api_call("tapd", endpoint, params, {}, False, str(e))
raise
def _make_request_with_retry(self, endpoint: str, params: Dict, retries=2, delay=30) -> Dict:
"""带重试的TAPD API请求"""
import time
for attempt in range(retries + 1):
try:
return self._make_request(endpoint, params)
except Exception as e:
if attempt < retries:
time.sleep(delay)
else:
return None
def get_overdue_stories(self, owner_list: List[str]) -> List[dict]:
"""获取过期需求"""
today = datetime.now().strftime('%Y-%m-%d')
@ -59,27 +71,25 @@ class TAPDUnifiedApi:
'fields': 'id,name,due,status'
}
try:
result = self._make_request("stories", params)
data = result.get('data', [])
result = self._make_request_with_retry("stories", params)
if not result:
continue
for item in data:
story = item.get('Story', {})
due_date = story.get('due', '')
status = story.get('status', '')
data = result.get('data', [])
for item in data:
story = item.get('Story', {})
due_date = story.get('due', '')
status = story.get('status', '')
# 过滤:有截止日期、已过期、非终态
if due_date and due_date < today and status not in self.STORY_TERMINAL_STATUSES:
all_stories.append({
'id': story.get('id'),
'name': story.get('name'),
'owner': owner,
'due': due_date,
'status': status,
'type': 'story'
})
except Exception as e:
pass
if due_date and due_date < today and status not in self.STORY_TERMINAL_STATUSES:
all_stories.append({
'id': story.get('id'),
'name': story.get('name'),
'owner': owner,
'due': due_date,
'status': status,
'type': 'story'
})
return all_stories
@ -95,27 +105,25 @@ class TAPDUnifiedApi:
'fields': 'id,title,deadline,status'
}
try:
result = self._make_request("bugs", params)
data = result.get('data', [])
result = self._make_request_with_retry("bugs", params)
if not result:
continue
for item in data:
bug = item.get('Bug', {})
deadline = bug.get('deadline', '')
status = bug.get('status', '')
data = result.get('data', [])
for item in data:
bug = item.get('Bug', {})
deadline = bug.get('deadline', '')
status = bug.get('status', '')
# 过滤:有截止日期、已过期、非终态
if deadline and deadline < today and status not in self.BUG_TERMINAL_STATUSES:
all_bugs.append({
'id': bug.get('id'),
'title': bug.get('title'),
'owner': owner,
'due': deadline,
'status': status,
'type': 'bug'
})
except Exception as e:
pass
if deadline and deadline < today and status not in self.BUG_TERMINAL_STATUSES:
all_bugs.append({
'id': bug.get('id'),
'title': bug.get('title'),
'owner': owner,
'due': deadline,
'status': status,
'type': 'bug'
})
return all_bugs

View File

@ -7,12 +7,48 @@ from typing import List
class WebhookSender:
"""企微Webhook推送器"""
MAX_BYTES = 4096 # 企微消息最大字节数
def __init__(self, webhook_url: str, logger):
self.webhook_url = webhook_url
self.logger = logger
def send_markdown(self, content: str, mentioned_list: List[str]) -> bool:
"""发送Markdown消息"""
"""发送Markdown消息自动分段"""
messages = self._split_by_bytes(content)
for msg in messages:
if not self._send_single(msg, mentioned_list):
return False
time.sleep(1) # 避免频率限制
return True
def _split_by_bytes(self, content: str) -> List[str]:
"""按字节长度分段,不切断单个用户的过期单"""
lines = content.split('\n')
messages = []
current = []
current_bytes = 0
for line in lines:
line_bytes = len(line.encode('utf-8')) + 1 # +1 for \n
if current_bytes + line_bytes > self.MAX_BYTES and current:
messages.append('\n'.join(current))
current = [line]
current_bytes = line_bytes
else:
current.append(line)
current_bytes += line_bytes
if current:
messages.append('\n'.join(current))
return messages
def _send_single(self, content: str, mentioned_list: List[str]) -> bool:
"""发送单条消息"""
payload = {
"msgtype": "markdown",
"markdown": {