From 4a5afb7ed75bd2fe43bbddb83c57621f22092e4c Mon Sep 17 00:00:00 2001 From: yuyr Date: Tue, 13 Jan 2026 10:46:43 +0800 Subject: [PATCH] cleaning code --- .gitignore | 3 +- doc/arch.excalidraw | 2133 ----------------- {specs => doc}/assets/arch.png | Bin {specs => doc}/assets/layout.png | Bin {specs => doc}/assets/networking.png | Bin {specs => doc}/assets/node_bootstrap.png | Bin {specs => doc}/assets/node_onboarding.png | Bin {specs => doc}/assets/scheduling.png | Bin {specs => doc}/assets/task_submit.png | Bin doc/hl_design.md | 279 --- {specs => doc}/hl_design_v2.md | 0 doc/requirements.md | 18 - doc/storage_deployment.md | 315 --- {specs/mvp => doc}/sw_arch.excalidraw | 0 .../image/Snipaste_2025-12-30_16-06-37.png | Bin 77632 -> 0 bytes .../image/Snipaste_2025-12-30_17-02-20.png | Bin 53286 -> 0 bytes specs/mvp/image/roadmap_v2.5.png | Bin 82052 -> 0 bytes specs/mvp/image/roadmap_v3.0.png | Bin 66842 -> 0 bytes specs/mvp/milestones.md | 34 - specs/mvp/mvp_roadmap.md | 348 --- specs/mvp/mvp_roadmap_v2.md | 133 - specs/mvp/refactor/code_refactor.md | 301 --- specs/mvp/remain_problems.md | 27 - specs/mvp/v1.1/mvp_plan.md | 169 -- specs/mvp/v1.1/sdk_submit_refactor.md | 148 -- specs/mvp/v1.1/v1.1_action.md | 333 --- specs/mvp/v1/mvp_plan.md | 120 - specs/mvp/v1/v1_action.md | 111 - specs/mvp/v2.0/v2_api.md | 194 -- specs/mvp/v2.0/v2_plan.md | 306 --- specs/mvp/v2.5/README.md | 15 - specs/mvp/v2.5/notices.md | 3 - specs/mvp/v2.5/v2.5_acceptance.md | 67 - specs/mvp/v2.5/v2.5_api.md | 109 - specs/mvp/v2.5/v2.5_container_design.md | 202 -- specs/mvp/v2.5/v2.5_design.md | 255 -- specs/mvp/v2.5/v2.5_dev_plan.md | 229 -- specs/mvp/v2.5/v2.5_e2e_test_cases.md | 132 - specs/mvp/v2.5/v2.5_summary.md | 92 - specs/mvp/v3.0/README.md | 15 - specs/mvp/v3.0/v3.0_acceptance.md | 55 - specs/mvp/v3.0/v3.0_api.md | 109 - specs/mvp/v3.0/v3.0_design.md | 358 --- specs/mvp/v3.0/v3.0_dev_plan.md | 232 -- specs/mvp/v3.0/v3.0_progress.md | 154 -- specs/mvp/v3.0/v3.0_summary.md | 166 -- specs/mvp/v3.5/README.md | 7 - specs/mvp/v3.5/note.md | 3 - specs/mvp/v3.5/requirement.md | 40 - specs/mvp/v3.5/roadmap_v3.5.png | Bin 100850 -> 0 bytes specs/mvp/v3.5/v3.5_changes.md | 67 - specs/mvp/v3.5/v3.5_design.md | 366 --- specs/mvp/v3.5/v3.5_dev_plan.md | 200 -- specs/mvp/v3.6/README.md | 9 - .../mvp/v3.6/Snipaste_2026-01-05_10-56-34.png | Bin 72243 -> 0 bytes specs/mvp/v3.6/requirements.md | 3 - specs/mvp/v3.6/v3.6_design.md | 280 --- specs/mvp/v3.6/v3.6_dev_plan.md | 194 -- specs/mvp/v3.6/v3.6_progress.md | 42 - specs/mvp/v3.6/v3.6_summary.md | 126 - specs/mvp/v3.6/wandb.md | 70 - specs/mvp/v3.7/v3.7_design.md | 215 -- specs/mvp/v3.7/v3.7_dev_plan.md | 122 - specs/mvp/v3.7/v3.7_summary.md | 121 - .../mvp/v3.8/Snipaste_2026-01-08_17-17-57.png | Bin 413025 -> 0 bytes specs/mvp/v3.8/ray_serve.md | 314 --- specs/mvp/v3.8/ray_serve_llm.md | 87 - specs/mvp/v3.8/requirements.md | 8 - specs/mvp/v3.8/v3.8_api.md | 224 -- specs/mvp/v3.8/v3.8_design.md | 371 --- specs/mvp/v3.8/v3.8_dev_plan.md | 266 -- specs/mvp/v3.8/v3.8_per_model_app.md | 189 -- specs/mvp/v3.8/v3.8_per_model_app_dev_plan.md | 174 -- specs/mvp/v3.8/v3.8_progress.md | 48 - specs/mvp/v3.9/ui_refactor_plan.md | 108 - src/mvp/configs/dev_v30.yaml | 64 - src/mvp/v1/README.md | 118 - src/mvp/v1/arch.excalidraw | 1877 --------------- src/mvp/v1/docker-compose.yaml | 86 - src/mvp/v1/scripts/00_prereq_check.sh | 17 - src/mvp/v1/scripts/01_up.sh | 20 - src/mvp/v1/scripts/02_down.sh | 9 - src/mvp/v1/scripts/05_ensure_verl_repo.sh | 19 - .../v1/scripts/10_install_verl_editable.sh | 22 - src/mvp/v1/scripts/20_start_head.sh | 17 - src/mvp/v1/scripts/21_start_workers.sh | 33 - .../v1/scripts/30_prepare_data_and_model.sh | 37 - src/mvp/v1/scripts/40_submit_ppo_epoch1.sh | 70 - src/mvp/v1/scripts/50_status.sh | 26 - src/mvp/v1/scripts/lib.sh | 48 - src/mvp/v1/scripts/run_all.sh | 13 - 91 files changed, 1 insertion(+), 13294 deletions(-) delete mode 100644 doc/arch.excalidraw rename {specs => doc}/assets/arch.png (100%) rename {specs => doc}/assets/layout.png (100%) rename {specs => doc}/assets/networking.png (100%) rename {specs => doc}/assets/node_bootstrap.png (100%) rename {specs => doc}/assets/node_onboarding.png (100%) rename {specs => doc}/assets/scheduling.png (100%) rename {specs => doc}/assets/task_submit.png (100%) delete mode 100644 doc/hl_design.md rename {specs => doc}/hl_design_v2.md (100%) delete mode 100644 doc/requirements.md delete mode 100644 doc/storage_deployment.md rename {specs/mvp => doc}/sw_arch.excalidraw (100%) delete mode 100644 specs/mvp/image/Snipaste_2025-12-30_16-06-37.png delete mode 100644 specs/mvp/image/Snipaste_2025-12-30_17-02-20.png delete mode 100644 specs/mvp/image/roadmap_v2.5.png delete mode 100644 specs/mvp/image/roadmap_v3.0.png delete mode 100644 specs/mvp/milestones.md delete mode 100644 specs/mvp/mvp_roadmap.md delete mode 100644 specs/mvp/mvp_roadmap_v2.md delete mode 100644 specs/mvp/refactor/code_refactor.md delete mode 100644 specs/mvp/remain_problems.md delete mode 100644 specs/mvp/v1.1/mvp_plan.md delete mode 100644 specs/mvp/v1.1/sdk_submit_refactor.md delete mode 100644 specs/mvp/v1.1/v1.1_action.md delete mode 100644 specs/mvp/v1/mvp_plan.md delete mode 100644 specs/mvp/v1/v1_action.md delete mode 100644 specs/mvp/v2.0/v2_api.md delete mode 100644 specs/mvp/v2.0/v2_plan.md delete mode 100644 specs/mvp/v2.5/README.md delete mode 100644 specs/mvp/v2.5/notices.md delete mode 100644 specs/mvp/v2.5/v2.5_acceptance.md delete mode 100644 specs/mvp/v2.5/v2.5_api.md delete mode 100644 specs/mvp/v2.5/v2.5_container_design.md delete mode 100644 specs/mvp/v2.5/v2.5_design.md delete mode 100644 specs/mvp/v2.5/v2.5_dev_plan.md delete mode 100644 specs/mvp/v2.5/v2.5_e2e_test_cases.md delete mode 100644 specs/mvp/v2.5/v2.5_summary.md delete mode 100644 specs/mvp/v3.0/README.md delete mode 100644 specs/mvp/v3.0/v3.0_acceptance.md delete mode 100644 specs/mvp/v3.0/v3.0_api.md delete mode 100644 specs/mvp/v3.0/v3.0_design.md delete mode 100644 specs/mvp/v3.0/v3.0_dev_plan.md delete mode 100644 specs/mvp/v3.0/v3.0_progress.md delete mode 100644 specs/mvp/v3.0/v3.0_summary.md delete mode 100644 specs/mvp/v3.5/README.md delete mode 100644 specs/mvp/v3.5/note.md delete mode 100644 specs/mvp/v3.5/requirement.md delete mode 100644 specs/mvp/v3.5/roadmap_v3.5.png delete mode 100644 specs/mvp/v3.5/v3.5_changes.md delete mode 100644 specs/mvp/v3.5/v3.5_design.md delete mode 100644 specs/mvp/v3.5/v3.5_dev_plan.md delete mode 100644 specs/mvp/v3.6/README.md delete mode 100644 specs/mvp/v3.6/Snipaste_2026-01-05_10-56-34.png delete mode 100644 specs/mvp/v3.6/requirements.md delete mode 100644 specs/mvp/v3.6/v3.6_design.md delete mode 100644 specs/mvp/v3.6/v3.6_dev_plan.md delete mode 100644 specs/mvp/v3.6/v3.6_progress.md delete mode 100644 specs/mvp/v3.6/v3.6_summary.md delete mode 100644 specs/mvp/v3.6/wandb.md delete mode 100644 specs/mvp/v3.7/v3.7_design.md delete mode 100644 specs/mvp/v3.7/v3.7_dev_plan.md delete mode 100644 specs/mvp/v3.7/v3.7_summary.md delete mode 100644 specs/mvp/v3.8/Snipaste_2026-01-08_17-17-57.png delete mode 100644 specs/mvp/v3.8/ray_serve.md delete mode 100644 specs/mvp/v3.8/ray_serve_llm.md delete mode 100644 specs/mvp/v3.8/requirements.md delete mode 100644 specs/mvp/v3.8/v3.8_api.md delete mode 100644 specs/mvp/v3.8/v3.8_design.md delete mode 100644 specs/mvp/v3.8/v3.8_dev_plan.md delete mode 100644 specs/mvp/v3.8/v3.8_per_model_app.md delete mode 100644 specs/mvp/v3.8/v3.8_per_model_app_dev_plan.md delete mode 100644 specs/mvp/v3.8/v3.8_progress.md delete mode 100644 specs/mvp/v3.9/ui_refactor_plan.md delete mode 100644 src/mvp/configs/dev_v30.yaml delete mode 100644 src/mvp/v1/README.md delete mode 100644 src/mvp/v1/arch.excalidraw delete mode 100644 src/mvp/v1/docker-compose.yaml delete mode 100755 src/mvp/v1/scripts/00_prereq_check.sh delete mode 100755 src/mvp/v1/scripts/01_up.sh delete mode 100755 src/mvp/v1/scripts/02_down.sh delete mode 100755 src/mvp/v1/scripts/05_ensure_verl_repo.sh delete mode 100755 src/mvp/v1/scripts/10_install_verl_editable.sh delete mode 100755 src/mvp/v1/scripts/20_start_head.sh delete mode 100755 src/mvp/v1/scripts/21_start_workers.sh delete mode 100755 src/mvp/v1/scripts/30_prepare_data_and_model.sh delete mode 100755 src/mvp/v1/scripts/40_submit_ppo_epoch1.sh delete mode 100755 src/mvp/v1/scripts/50_status.sh delete mode 100755 src/mvp/v1/scripts/lib.sh delete mode 100755 src/mvp/v1/scripts/run_all.sh diff --git a/.gitignore b/.gitignore index f9a0a18..5dd8c6d 100644 --- a/.gitignore +++ b/.gitignore @@ -5,5 +5,4 @@ __pycache__/ .venv/ .pytest_cache/ .coverage -htmlcov/ -AGENTS.md \ No newline at end of file +htmlcov/ \ No newline at end of file diff --git a/doc/arch.excalidraw b/doc/arch.excalidraw deleted file mode 100644 index eabf1ab..0000000 --- a/doc/arch.excalidraw +++ /dev/null @@ -1,2133 +0,0 @@ -{ - "type": "excalidraw", - "version": 2, - "source": "https://marketplace.visualstudio.com/items?itemName=pomdtr.excalidraw-editor", - "elements": [ - { - "id": "9Ql3xet2wP4Oy9RJ4s-8H", - "type": "rectangle", - "x": 36.00023651123047, - "y": 132.66671752929688, - "width": 201.66666412353516, - "height": 144.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a0", - "roundness": { - "type": 3 - }, - "seed": 1490759950, - "version": 343, - "versionNonce": 480492174, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "Yx_fL1nYHbxINMBHYImpi" - }, - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow" - } - ], - "updated": 1765768777801, - "link": null, - "locked": false - }, - { - "id": "Yx_fL1nYHbxINMBHYImpi", - "type": "text", - "x": 97.75359725952148, - "y": 192.5000457763672, - "width": 78.15994262695312, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a1", - "roundness": null, - "seed": 122704078, - "version": 196, - "versionNonce": 229193934, - "isDeleted": false, - "boundElements": [], - "updated": 1765768777801, - "link": null, - "locked": false, - "text": "desktop", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "9Ql3xet2wP4Oy9RJ4s-8H", - "originalText": "desktop", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "1BW7RJyVw0yjg93vAIlWT", - "type": "rectangle", - "x": 688.5001335144043, - "y": 25.000045776367188, - "width": 159.9999771118164, - "height": 88.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a2", - "roundness": { - "type": 3 - }, - "seed": 929976718, - "version": 607, - "versionNonce": 1421967566, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "E6pCjIGdOvsBKIu6w2tUA" - }, - { - "id": "ye7b-vsIkRFaAtO9UNCf1", - "type": "arrow" - } - ], - "updated": 1765768506683, - "link": null, - "locked": false - }, - { - "id": "E6pCjIGdOvsBKIu6w2tUA", - "type": "text", - "x": 723.7201614379883, - "y": 44.3333740234375, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a3", - "roundness": null, - "seed": 1091104718, - "version": 489, - "versionNonce": 1003055054, - "isDeleted": false, - "boundElements": [], - "updated": 1765768542188, - "link": null, - "locked": false, - "text": "container\n8 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "1BW7RJyVw0yjg93vAIlWT", - "originalText": "container\n8 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "nIO4qa9Aj4LF_WlHt2BNO", - "type": "rectangle", - "x": 326.5000419616699, - "y": 133.6666717529297, - "width": 201.66666412353516, - "height": 144.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a4", - "roundness": { - "type": 3 - }, - "seed": 2137052434, - "version": 248, - "versionNonce": 1543678354, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "xKyNarDpAWsNVlcCC8N-N" - }, - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow" - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow" - }, - { - "id": "5tNZW8jUhEBPa946TLQfX", - "type": "arrow" - } - ], - "updated": 1765768808905, - "link": null, - "locked": false - }, - { - "id": "xKyNarDpAWsNVlcCC8N-N", - "type": "text", - "x": 367.89341735839844, - "y": 143.5, - "width": 118.87991333007812, - "height": 125, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a5", - "roundness": null, - "seed": 711484114, - "version": 158, - "versionNonce": 772410466, - "isDeleted": false, - "boundElements": [], - "updated": 1765770671319, - "link": null, - "locked": false, - "text": "container\nWeb server \n+\nSkyPilot like\nmanager", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "nIO4qa9Aj4LF_WlHt2BNO", - "originalText": "container\nWeb server \n+\nSkyPilot like manager", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow", - "x": 242.66690063476562, - "y": 204.9000457763672, - "width": 78.8331413269043, - "height": 0.9999542236328125, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a6", - "roundness": null, - "seed": 1158070290, - "version": 228, - "versionNonce": 2034953426, - "isDeleted": false, - "boundElements": [], - "updated": 1765768780570, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 78.8331413269043, - 0.9999542236328125 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "9Ql3xet2wP4Oy9RJ4s-8H", - "fixedPoint": [ - 1.0247933887424108, - 0.4993087557117625 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "nIO4qa9Aj4LF_WlHt2BNO", - "focus": -0.008594144923853504, - "gap": 14.333358764648438, - "fixedPoint": [ - 0.48677675845282387, - 1.0990785237732301 - ] - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "aBQ9npStDj077n0B7_JZ3", - "type": "rectangle", - "x": 690.000072479248, - "y": 147.6666717529297, - "width": 159.9999771118164, - "height": 88.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a7", - "roundness": { - "type": 3 - }, - "seed": 1963206674, - "version": 685, - "versionNonce": 329674770, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "dGa3VHynwpnzguZ5kDJTr" - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow" - }, - { - "id": "-w3fkuAvGpZM4OdIK7N85", - "type": "arrow" - } - ], - "updated": 1765768511284, - "link": null, - "locked": false - }, - { - "id": "dGa3VHynwpnzguZ5kDJTr", - "type": "text", - "x": 725.220100402832, - "y": 167, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a8", - "roundness": null, - "seed": 1445549522, - "version": 568, - "versionNonce": 406828686, - "isDeleted": false, - "boundElements": [], - "updated": 1765768553134, - "link": null, - "locked": false, - "text": "container\n8 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "aBQ9npStDj077n0B7_JZ3", - "originalText": "container\n8 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "Yba-9HedLPKxDUD1wthap", - "type": "rectangle", - "x": 695.3333854675293, - "y": 274.33338928222656, - "width": 159.9999771118164, - "height": 88.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a9", - "roundness": { - "type": 3 - }, - "seed": 259691346, - "version": 730, - "versionNonce": 1394721042, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "NfiPIJkEoh7Nlnz6VVp0Y" - }, - { - "id": "lQj9EyeS508UiTeYSg02r", - "type": "arrow" - } - ], - "updated": 1765768515918, - "link": null, - "locked": false - }, - { - "id": "NfiPIJkEoh7Nlnz6VVp0Y", - "type": "text", - "x": 730.5534133911133, - "y": 293.6667175292969, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aA", - "roundness": null, - "seed": 87054610, - "version": 614, - "versionNonce": 2098855246, - "isDeleted": false, - "boundElements": [], - "updated": 1765768564520, - "link": null, - "locked": false, - "text": "container\n8 X H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "Yba-9HedLPKxDUD1wthap", - "originalText": "container\n8 X H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow", - "x": 533.1667060852051, - "y": 205.9, - "width": 136.83329391479492, - "height": 0.7666870117187443, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aC", - "roundness": null, - "seed": 990553042, - "version": 41, - "versionNonce": 821443154, - "isDeleted": false, - "boundElements": [], - "updated": 1765768401701, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 136.83329391479492, - 0.7666870117187443 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "nIO4qa9Aj4LF_WlHt2BNO", - "fixedPoint": [ - 1.0247933887424108, - 0.4993087557117625 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "aBQ9npStDj077n0B7_JZ3", - "fixedPoint": [ - -0.12500047087676108, - 0.66541378226761 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "z4vmx2a_K8omTNuLcVRld", - "type": "diamond", - "x": 910.3333740234375, - "y": 154.66668701171875, - "width": 96.33331298828125, - "height": 120, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aF", - "roundness": { - "type": 2 - }, - "seed": 2059710478, - "version": 40, - "versionNonce": 573449362, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "_CVsRhVz21ru5fuqV5vp7" - }, - { - "id": "ye7b-vsIkRFaAtO9UNCf1", - "type": "arrow" - }, - { - "id": "-w3fkuAvGpZM4OdIK7N85", - "type": "arrow" - }, - { - "id": "lQj9EyeS508UiTeYSg02r", - "type": "arrow" - } - ], - "updated": 1765768515919, - "link": null, - "locked": false - }, - { - "id": "_CVsRhVz21ru5fuqV5vp7", - "type": "text", - "x": 945.3567123413086, - "y": 189.66668701171875, - "width": 26.119979858398438, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aG", - "roundness": null, - "seed": 104641810, - "version": 10, - "versionNonce": 121397710, - "isDeleted": false, - "boundElements": [], - "updated": 1765768473262, - "link": null, - "locked": false, - "text": "IB\nsw", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "z4vmx2a_K8omTNuLcVRld", - "originalText": "IB sw", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "ye7b-vsIkRFaAtO9UNCf1", - "type": "arrow", - "x": 853.5001106262207, - "y": 69.2333740234375, - "width": 104.8999198913574, - "height": 80.43331298828124, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aH", - "roundness": null, - "seed": 1146593042, - "version": 30, - "versionNonce": 45365006, - "isDeleted": false, - "boundElements": [], - "updated": 1765768506683, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 104.8999198913574, - 0 - ], - [ - 104.8999198913574, - 80.43331298828124 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "1BW7RJyVw0yjg93vAIlWT", - "fixedPoint": [ - 1.031250004470349, - 0.4988721803217357 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "z4vmx2a_K8omTNuLcVRld", - "fixedPoint": [ - 0.49896193749702983, - -0.041666666666666664 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "-w3fkuAvGpZM4OdIK7N85", - "type": "arrow", - "x": 855.0000495910645, - "y": 191.9, - "width": 50.33332443237305, - "height": 22.66668701171875, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aI", - "roundness": null, - "seed": 1001105870, - "version": 16, - "versionNonce": 2034408914, - "isDeleted": false, - "boundElements": [], - "updated": 1765768511284, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 25.166662216186523, - 0 - ], - [ - 25.166662216186523, - 22.66668701171875 - ], - [ - 50.33332443237305, - 22.66668701171875 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "aBQ9npStDj077n0B7_JZ3", - "fixedPoint": [ - 1.031250004470349, - 0.4988721803217357 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "z4vmx2a_K8omTNuLcVRld", - "fixedPoint": [ - -0.05190312514849603, - 0.4991666666666667 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "lQj9EyeS508UiTeYSg02r", - "type": "arrow", - "x": 860.3333625793457, - "y": 318.56671752929685, - "width": 98.0666679382324, - "height": 38.9000305175781, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aJ", - "roundness": null, - "seed": 1380767506, - "version": 47, - "versionNonce": 791400146, - "isDeleted": false, - "boundElements": [], - "updated": 1765768515919, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 98.0666679382324, - 0 - ], - [ - 98.0666679382324, - -38.9000305175781 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "Yba-9HedLPKxDUD1wthap", - "fixedPoint": [ - 1.031250004470349, - 0.49887218032173536 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "z4vmx2a_K8omTNuLcVRld", - "fixedPoint": [ - 0.49896193749702983, - 1.0416666666666667 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "Rsu2l5FbjC-YeEsUJuZ8e", - "type": "rectangle", - "x": 699.4999694824219, - "y": 411.3334045410156, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aO", - "roundness": { - "type": 3 - }, - "seed": 1067651918, - "version": 127, - "versionNonce": 1654930766, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "PP3Q89REJw99Q6rQVaV55" - } - ], - "updated": 1765768653875, - "link": null, - "locked": false - }, - { - "id": "PP3Q89REJw99Q6rQVaV55", - "type": "text", - "x": 733.2200088500977, - "y": 431.6667175292969, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aP", - "roundness": null, - "seed": 1891596686, - "version": 78, - "versionNonce": 772498318, - "isDeleted": false, - "boundElements": [], - "updated": 1765768653875, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "Rsu2l5FbjC-YeEsUJuZ8e", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "AZXoJzGVX5uoKshaeKQek", - "type": "rectangle", - "x": 713.5000305175781, - "y": 419.3333435058594, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aQ", - "roundness": { - "type": 3 - }, - "seed": 2030401490, - "version": 163, - "versionNonce": 2142662354, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "ydc8eycBIHMLutlmYkUH8" - } - ], - "updated": 1765768657308, - "link": null, - "locked": false - }, - { - "id": "ydc8eycBIHMLutlmYkUH8", - "type": "text", - "x": 747.2200698852539, - "y": 439.6666564941406, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aR", - "roundness": null, - "seed": 887795090, - "version": 114, - "versionNonce": 1214563474, - "isDeleted": false, - "boundElements": [], - "updated": 1765768657308, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "AZXoJzGVX5uoKshaeKQek", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "cd8duVnreXCTzqLOws63b", - "type": "rectangle", - "x": 730.8333435058594, - "y": 428.0000305175781, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aS", - "roundness": { - "type": 3 - }, - "seed": 743406094, - "version": 193, - "versionNonce": 1116698638, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "N1-LLyWwsryNzbp5IxXA5" - } - ], - "updated": 1765768660341, - "link": null, - "locked": false - }, - { - "id": "N1-LLyWwsryNzbp5IxXA5", - "type": "text", - "x": 764.5533828735352, - "y": 448.3333435058594, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aT", - "roundness": null, - "seed": 1085343822, - "version": 144, - "versionNonce": 1245791822, - "isDeleted": false, - "boundElements": [], - "updated": 1765768660341, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "cd8duVnreXCTzqLOws63b", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "N98V2SE6XUuoHWnKGx7Nf", - "type": "rectangle", - "x": 700.1666564941406, - "y": 531.0000915527344, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aU", - "roundness": { - "type": 3 - }, - "seed": 528387662, - "version": 211, - "versionNonce": 1184314770, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "ARZv73nqYLBG1llkZAoCX" - }, - { - "id": "5tNZW8jUhEBPa946TLQfX", - "type": "arrow" - } - ], - "updated": 1765768742972, - "link": null, - "locked": false - }, - { - "id": "ARZv73nqYLBG1llkZAoCX", - "type": "text", - "x": 733.8866958618164, - "y": 551.3334045410156, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aV", - "roundness": null, - "seed": 1567855758, - "version": 161, - "versionNonce": 1767508046, - "isDeleted": false, - "boundElements": [], - "updated": 1765768703417, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "N98V2SE6XUuoHWnKGx7Nf", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "i2ZxkoxnCoyAnZe4KBHsQ", - "type": "rectangle", - "x": 714.1667175292969, - "y": 539.0000305175781, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aW", - "roundness": { - "type": 3 - }, - "seed": 460182222, - "version": 246, - "versionNonce": 298831502, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "L4x3Y2L00Gw6130G6lU9W" - } - ], - "updated": 1765768703417, - "link": null, - "locked": false - }, - { - "id": "L4x3Y2L00Gw6130G6lU9W", - "type": "text", - "x": 747.8867568969727, - "y": 559.3333435058594, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aX", - "roundness": null, - "seed": 335956238, - "version": 197, - "versionNonce": 741526734, - "isDeleted": false, - "boundElements": [], - "updated": 1765768703417, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "i2ZxkoxnCoyAnZe4KBHsQ", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "RsHyOceETLPpOF-hqhu84", - "type": "rectangle", - "x": 731.5000305175781, - "y": 547.6667175292969, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aY", - "roundness": { - "type": 3 - }, - "seed": 1186330446, - "version": 276, - "versionNonce": 1981547278, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "fIcwnXZ9pveKZfR6TRcaa" - } - ], - "updated": 1765768703417, - "link": null, - "locked": false - }, - { - "id": "fIcwnXZ9pveKZfR6TRcaa", - "type": "text", - "x": 765.2200698852539, - "y": 568.0000305175781, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aZ", - "roundness": null, - "seed": 1540742542, - "version": 229, - "versionNonce": 302281038, - "isDeleted": false, - "boundElements": [], - "updated": 1765768703417, - "link": null, - "locked": false, - "text": "container\n2 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "RsHyOceETLPpOF-hqhu84", - "originalText": "container\n2 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "cti4IlX8pCaQ3LQzTJVGl", - "type": "rectangle", - "x": 902.8333435058594, - "y": 416.3334655761719, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aa", - "roundness": { - "type": 3 - }, - "seed": 1357303054, - "version": 271, - "versionNonce": 216485262, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "2kUMneeoOFXj5_Ooa3RKS" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "2kUMneeoOFXj5_Ooa3RKS", - "type": "text", - "x": 936.5533828735352, - "y": 436.6667785644531, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ab", - "roundness": null, - "seed": 484834126, - "version": 222, - "versionNonce": 1979870158, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "cti4IlX8pCaQ3LQzTJVGl", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "GKmziFZzlbsnmMSSs5SBZ", - "type": "rectangle", - "x": 916.8334045410156, - "y": 424.3334045410156, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ac", - "roundness": { - "type": 3 - }, - "seed": 1969578382, - "version": 307, - "versionNonce": 1117766158, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "xlfGTET36AVVDlpQgBRCD" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "xlfGTET36AVVDlpQgBRCD", - "type": "text", - "x": 950.5534439086914, - "y": 444.6667175292969, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ad", - "roundness": null, - "seed": 1302200270, - "version": 258, - "versionNonce": 901271630, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "GKmziFZzlbsnmMSSs5SBZ", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "C2Rakvrst2HdxFq6yB2oR", - "type": "rectangle", - "x": 934.1667175292969, - "y": 433.0000915527344, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ae", - "roundness": { - "type": 3 - }, - "seed": 1235801614, - "version": 337, - "versionNonce": 1260721806, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "WjewWchfoQAb_fO4XwVO4" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "WjewWchfoQAb_fO4XwVO4", - "type": "text", - "x": 967.8867568969727, - "y": 453.3334045410156, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "af", - "roundness": null, - "seed": 578741326, - "version": 290, - "versionNonce": 463410382, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n4 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "C2Rakvrst2HdxFq6yB2oR", - "originalText": "container\n4 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "GQAuJzEnRE7cwh01SCj2r", - "type": "rectangle", - "x": 905.4999694824219, - "y": 531.6669006347656, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ag", - "roundness": { - "type": 3 - }, - "seed": 1259957198, - "version": 294, - "versionNonce": 1086278414, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "05b5QF2wFlFPzlyknjo-l" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "05b5QF2wFlFPzlyknjo-l", - "type": "text", - "x": 939.2200088500977, - "y": 552.0002136230469, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ah", - "roundness": null, - "seed": 1557578254, - "version": 245, - "versionNonce": 956217678, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "GQAuJzEnRE7cwh01SCj2r", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "trV5f691bxKhXCvtAsFJp", - "type": "rectangle", - "x": 919.5000305175781, - "y": 539.6668395996094, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ai", - "roundness": { - "type": 3 - }, - "seed": 1896829006, - "version": 330, - "versionNonce": 1270243214, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "zDLI66UPB74U0-pceROrx" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "zDLI66UPB74U0-pceROrx", - "type": "text", - "x": 953.2200698852539, - "y": 560.0001525878906, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aj", - "roundness": null, - "seed": 60561038, - "version": 281, - "versionNonce": 1830763982, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n1 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "trV5f691bxKhXCvtAsFJp", - "originalText": "container\n1 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "zjH8FeFL_DKnnms6pEZGl", - "type": "rectangle", - "x": 936.8333435058594, - "y": 548.3335266113281, - "width": 157, - "height": 90.6666259765625, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ak", - "roundness": { - "type": 3 - }, - "seed": 758518990, - "version": 360, - "versionNonce": 575820814, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "pEXkPy2D2mjJ4et_R9S-G" - } - ], - "updated": 1765768729712, - "link": null, - "locked": false - }, - { - "id": "pEXkPy2D2mjJ4et_R9S-G", - "type": "text", - "x": 970.5533828735352, - "y": 568.6668395996094, - "width": 89.55992126464844, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "al", - "roundness": null, - "seed": 125192974, - "version": 315, - "versionNonce": 1699258958, - "isDeleted": false, - "boundElements": [], - "updated": 1765768729712, - "link": null, - "locked": false, - "text": "container\n8 x H100", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "zjH8FeFL_DKnnms6pEZGl", - "originalText": "container\n8 x H100", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "5tNZW8jUhEBPa946TLQfX", - "type": "arrow", - "x": 531.6771272112763, - "y": 258.6784160210832, - "width": 152.98952928286428, - "height": 303.98824047305743, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "am", - "roundness": null, - "seed": 1864421970, - "version": 209, - "versionNonce": 911403858, - "isDeleted": false, - "boundElements": [], - "updated": 1765768746717, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 46.32296434145803, - 0 - ], - [ - 46.32296434145803, - 303.98824047305743 - ], - [ - 152.98952928286428, - 303.98824047305743 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "nIO4qa9Aj4LF_WlHt2BNO", - "fixedPoint": [ - 1.0174070471256513, - 0.864136541879758 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "N98V2SE6XUuoHWnKGx7Nf", - "fixedPoint": [ - -0.09872611464968153, - 0.3492637406579144 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": [ - { - "index": 2, - "start": [ - 46.32296434145803, - 0 - ], - "end": [ - 46.32296434145803, - 303.98824047305743 - ] - } - ], - "startIsSpecial": false, - "endIsSpecial": false - }, - { - "id": "L5L-dHWhO7QDfKsx-auzO", - "type": "line", - "x": 679.6486400773596, - "y": 68.05050870475259, - "width": 6.218773981147137, - "height": 125.20467479135232, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aq", - "roundness": { - "type": 2 - }, - "seed": 1924412686, - "version": 48, - "versionNonce": 2072832782, - "isDeleted": false, - "boundElements": [], - "updated": 1765768839277, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - -6.218773981147137, - 125.20467479135232 - ] - ], - "lastCommittedPoint": null, - "startBinding": null, - "endBinding": null, - "startArrowhead": null, - "endArrowhead": null - }, - { - "id": "L7fPHZgtyOHIM1-qa1gD7", - "type": "line", - "x": 673.0152305556237, - "y": 218.13027942069357, - "width": 15.339693095341886, - "height": 102.8170125464543, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ar", - "roundness": { - "type": 2 - }, - "seed": 1982802578, - "version": 50, - "versionNonce": 247804498, - "isDeleted": false, - "boundElements": [], - "updated": 1765768879487, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 15.339693095341886, - 102.8170125464543 - ] - ], - "lastCommittedPoint": null, - "startBinding": null, - "endBinding": null, - "startArrowhead": null, - "endArrowhead": null - }, - { - "id": "f7LL01k78v1et3Xn56EDr", - "type": "text", - "x": 763.394771052552, - "y": -27.304050977093425, - "width": 161.1998748779297, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "as", - "roundness": null, - "seed": 1515956750, - "version": 39, - "versionNonce": 727326030, - "isDeleted": false, - "boundElements": [], - "updated": 1765768936418, - "link": null, - "locked": false, - "text": "multi-nodes task", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "multi-nodes task", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "tuQoRzheGl5PV5c38jxd1", - "type": "text", - "x": 812.567405914188, - "y": 658.3570252482072, - "width": 158.2798614501953, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "at", - "roundness": null, - "seed": 609937742, - "version": 89, - "versionNonce": 2106648658, - "isDeleted": false, - "boundElements": [], - "updated": 1765768928899, - "link": null, - "locked": false, - "text": "single-node task", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "single-node task", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "atIqduRWNX97Sp6yKe4hj", - "type": "rectangle", - "x": 301.8035086475226, - "y": -105.80058630360065, - "width": 819.6344107151963, - "height": 1019.8789708645193, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "dotted", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aw", - "roundness": { - "type": 3 - }, - "seed": 311282494, - "version": 157, - "versionNonce": 601142206, - "isDeleted": false, - "boundElements": null, - "updated": 1765770973019, - "link": null, - "locked": false - }, - { - "id": "k6SXmpRXbeQSbRrXG_o6a", - "type": "text", - "x": 691.5133194951555, - "y": -158.86744495726174, - "width": 111.85990905761719, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "dotted", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ax", - "roundness": null, - "seed": 570087970, - "version": 13, - "versionNonce": 2027488254, - "isDeleted": false, - "boundElements": null, - "updated": 1765770695453, - "link": null, - "locked": false, - "text": "K8S cluster", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "K8S cluster", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "bhihBvlxof1k0U05Mpyjq", - "type": "ellipse", - "x": 397.77986981471486, - "y": 830.7468511699307, - "width": 659.6046775421883, - "height": 43.94597749585046, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "az", - "roundness": { - "type": 2 - }, - "seed": 718418402, - "version": 98, - "versionNonce": 948231742, - "isDeleted": false, - "boundElements": [], - "updated": 1765771067870, - "link": null, - "locked": false - }, - { - "id": "V2T98L5fdxwL266Zl6nbF", - "type": "rectangle", - "x": 398.8163827534184, - "y": 773.1195329591723, - "width": 662.0921112218787, - "height": 80.4294262143244, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b00", - "roundness": null, - "seed": 1034220734, - "version": 126, - "versionNonce": 721447970, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "iqdjGP3so6IznFUVxyJ5u" - } - ], - "updated": 1765771080130, - "link": null, - "locked": false - }, - { - "id": "iqdjGP3so6IznFUVxyJ5u", - "type": "text", - "x": 568.7425653174828, - "y": 800.8342460663345, - "width": 322.23974609375, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b00V", - "roundness": null, - "seed": 204793534, - "version": 39, - "versionNonce": 2093989474, - "isDeleted": false, - "boundElements": null, - "updated": 1765771090688, - "link": null, - "locked": false, - "text": "shared storage for all containers", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "V2T98L5fdxwL266Zl6nbF", - "originalText": "shared storage for all containers", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "vJ4ppQKXnitvRup82_d2B", - "type": "ellipse", - "x": 397.9871875850093, - "y": 749.9027514586334, - "width": 659.6046775421883, - "height": 43.94597749585046, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffffff", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b01", - "roundness": { - "type": 2 - }, - "seed": 1318325922, - "version": 68, - "versionNonce": 818986238, - "isDeleted": false, - "boundElements": null, - "updated": 1765771024715, - "link": null, - "locked": false - } - ], - "appState": { - "gridSize": 20, - "gridStep": 5, - "gridModeEnabled": false, - "viewBackgroundColor": "#ffffff" - }, - "files": {} -} \ No newline at end of file diff --git a/specs/assets/arch.png b/doc/assets/arch.png similarity index 100% rename from specs/assets/arch.png rename to doc/assets/arch.png diff --git a/specs/assets/layout.png b/doc/assets/layout.png similarity index 100% rename from specs/assets/layout.png rename to doc/assets/layout.png diff --git a/specs/assets/networking.png b/doc/assets/networking.png similarity index 100% rename from specs/assets/networking.png rename to doc/assets/networking.png diff --git a/specs/assets/node_bootstrap.png b/doc/assets/node_bootstrap.png similarity index 100% rename from specs/assets/node_bootstrap.png rename to doc/assets/node_bootstrap.png diff --git a/specs/assets/node_onboarding.png b/doc/assets/node_onboarding.png similarity index 100% rename from specs/assets/node_onboarding.png rename to doc/assets/node_onboarding.png diff --git a/specs/assets/scheduling.png b/doc/assets/scheduling.png similarity index 100% rename from specs/assets/scheduling.png rename to doc/assets/scheduling.png diff --git a/specs/assets/task_submit.png b/doc/assets/task_submit.png similarity index 100% rename from specs/assets/task_submit.png rename to doc/assets/task_submit.png diff --git a/doc/hl_design.md b/doc/hl_design.md deleted file mode 100644 index fd19aa7..0000000 --- a/doc/hl_design.md +++ /dev/null @@ -1,279 +0,0 @@ -# AI Infra 训练平台建设方案 - -## 1. 愿景与目标 - -### 1.1 愿景 - -构建一套**端到端的智能化AI训练平台**,将分散的训练框架、资源调度、监控运维、数据管理能力整合为统一的标准化流水线,让大模型训练算法团队**专注于模型创新而非基础设施运维**,同时与现有运维智能体深度协同,实现训练任务的智能化运维闭环。 - -### 1.2 核心目标 - -| 目标维度 | 描述 | -|---------|------| -| **效率提升** | 训练任务从准备到启动时间缩短 70%,故障恢复时间缩短 50% | -| **标准化** | 建立统一的训练流程规范,消除"人人一套环境"的混乱局面 | -| **可观测性** | 全链路监控覆盖,训练状态、资源利用、异常事件一目了然 | -| **智能运维** | 与运维智能体对接,实现断训自动分析、故障智能诊断 | - - ---- - -## 2. 整体架构概览 - -``` -┌─────────────────────────────────────────────────────────────────────┐ -│ 用户交互层 │ -│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │ -│ │ Web 前端 │ │ CLI 工具 │ │ API 接口 │ │ -│ │ (任务提交) │ │ (高级用户) │ │ (自动化集成) │ │ -│ └─────────────┘ └─────────────┘ └─────────────┘ │ -└─────────────────────────────────────────────────────────────────────┘ - │ -┌─────────────────────────────────────────────────────────────────────┐ -│ 平台服务层 │ -│ ┌───────────────┐ ┌───────────────┐ ┌───────────────┐ │ -│ │ 任务调度 │ │ 数据管理 │ │ 模型管理 │ │ -│ │ (SkyPilot) │ │(schema/dataset)│ │ (版本/产物) │ │ -│ └───────────────┘ └───────────────┘ └───────────────┘ │ -│ ┌───────────────┐ ┌───────────────┐ ┌───────────────┐ │ -│ │ 镜像管理 │ │ 指标追踪 │ │ 日志中心 │ │ -│ │(Local Registry)│ │ (W&B) │ │ (集中采集) │ │ -│ └───────────────┘ └───────────────┘ └───────────────┘ │ -└─────────────────────────────────────────────────────────────────────┘ - │ -┌─────────────────────────────────────────────────────────────────────┐ -│ 智能运维层 │ -│ ┌─────────────────────────────────────────────────────────────┐ │ -│ │ 运维智能体对接 │ │ -│ │ • 断训自动分析 • 故障根因定位 • 资源利用率优化建议 │ │ -│ └─────────────────────────────────────────────────────────────┘ │ -└─────────────────────────────────────────────────────────────────────┘ - │ -┌─────────────────────────────────────────────────────────────────────┐ -│ 基础设施层 │ -│ ┌───────────────┐ ┌───────────────┐ ┌───────────────┐ │ -│ │ Kubernetes │ │ GPU 集群 │ │ 分布式存储 │ │ -│ │ (容器编排) │ │ H20/A6000/H100│ │ (JuiceFS) │ │ -│ └───────────────┘ └───────────────┘ └───────────────┘ │ -└─────────────────────────────────────────────────────────────────────┘ -``` - ---- - -## 3. 用户故事 - -### 3.1 算法工程师视角 - -> **作为**一名算法工程师, -> **我希望**通过简单的界面配置就能提交一个多节点 RLHF 训练任务, -> **以便于**我可以专注于模型和数据本身,而不是花大量时间在环境配置和资源协调上。 - -**验收标准:** -- [ ] 在 Web 界面上选择数据集、模型、训练配置 -- [ ] 一键提交后,系统自动完成资源分配、镜像拉取、任务启动 -- [ ] 实时查看训练进度曲线和关键指标 - ---- - -> **作为**一名算法工程师, -> **我希望**训练中断时能快速定位问题原因, -> **以便于**减少排查时间,尽快恢复训练。 - -**验收标准:** -- [ ] 系统自动检测训练中断事件 -- [ ] 智能体自动分析中断原因(OOM、网络故障、硬件异常等) -- [ ] 提供可操作的恢复建议 - ---- - -> **作为**一名算法工程师, -> **我希望**启动一个 Notebook 环境调试代码. -> **以便于**小规模试跑训练,测试训练数据集、调整模型参数 - -**验收标准:** -- [ ] Notebook容器启动速度 -- [ ] 开发容器内置依赖包完善度,按照新包 - ---- - -### 3.2 团队负责人视角 - -> **作为**团队负责人, -> **我希望**能够看到所有训练任务的整体资源利用情况, -> **以便于**合理规划算力资源,识别资源浪费。 - -**验收标准:** -- [ ] 仪表盘展示各集群 GPU 利用率趋势 -- [ ] 任务队列可视化,等待/运行/完成状态一目了然 -- [ ] 资源使用报表按项目/用户统计 - ---- - -### 3.3 运维工程师视角 - -> **作为**运维工程师, -> **我希望**训练任务的监控数据能自动接入现有运维系统, -> **以便于**统一管理,减少割裂的监控工具。 - -**验收标准:** -- [ ] 训练任务指标自动推送到运维智能体 -- [ ] 异常告警自动触发智能体分析流程 -- [ ] 与现有运维系统数据互通 - ---- - -## 4. 里程碑规划 - -### 里程碑总览 - -``` - M1 M2 M3 M4 - │ │ │ │ -────●──────────────────●──────────────────●──────────────────●────────▶ - │ │ │ │ - 基础设施就绪 训练流水线上线 监控运维闭环 智能化运维 -``` - ---- - -### M1: 基础设施就绪 - -**目标:** 完成底层平台搭建,具备运行训练任务的基础能力 - -| 交付物 | 说明 | -|-------|------| -| K8S 集群 | H20 集群上部署 Kubernetes,支持 GPU 调度 | -| 本地 Registry | 内网镜像仓库,解决镜像拉取问题 | -| JuiceFS/MinIO | 分布式存储,数据集和模型 checkpoint 持久化 | -| 基础镜像 | veRL 训练镜像,预置常用依赖 | - -**关键验证点:** -- 能够手动在 K8S 上启动单节点训练任务 -- 数据从 JuiceFS 正常读写 -- 镜像从本地 Registry 正常拉取 -- 引入 Volcano 或 Kueue,并配置 Gang Scheduling 策略,实现All-or-Nothing 的资源分配 -- 确认JuiceFS 的本地 SSD 缓存策略,在其中一台机器部署MiniIO单节点,另外两台机器上部署JuiceFS client -- 网络通信支持 RoCE/InfiniBand -- Notebook 交互式开发环境 - ---- - -### M2: 训练流水线上线 - -**目标:** 用户可通过前端提交和管理训练任务 - -| 交付物 | 说明 | -|-------|------| -| SkyPilot 集成 | 任务调度与资源编排 | -| W&B 本地服务 | 训练指标追踪与可视化 | -| 任务管理前端 | 数据上传、任务提交、进度查看、日志查看 | -| 数据管理模块 | 支持从 HuggingFace 链接或 FTP 导入数据集 | - -**关键验证点:** -- 端到端完成一次多节点 SFT 训练 -- 通过前端提交任务,查看 W&B 训练曲线 -- 训练日志完整保存并可查询 -- 多租户、项目制配额管理功能 - ---- - -### M3: 监控运维闭环 - -**目标:** 实现任务全生命周期监控,与运维智能体初步对接 - -| 交付物 | 说明 | -|-------|------| -| 资源监控 | GPU 利用率、显存、网络带宽实时采集 | -| 日志采集 | 训练日志集中存储,支持检索 | -| 智能体对接 | 断训事件自动推送,触发智能体分析 | -| 告警机制 | 异常状态(OOM、任务卡死等)自动告警 | - -**关键验证点:** -- 训练任务异常时,5 分钟内收到告警 -- 断训事件自动生成分析报告 -- Grafana 仪表盘展示集群整体健康状态 -- sidecar方式部署 DCGM Exporter 来获取细粒度指标,自动采集到Prometheus -- 断训时“保留现场”机制,供人工/智能体排查介入 - ---- - -### M4: 智能化运维 - -**目标:** 深度整合运维智能体,实现智能调度与自愈 - -| 交付物 | 说明 | -|-------|------| -| 故障自愈 | 常见故障自动处理(如重新调度到健康节点) | -| 智能调度 | 基于历史数据优化任务资源分配 | -| 根因分析 | 复杂故障场景的深度分析能力 | -| 容量预测 | 基于任务趋势预测算力需求 | - ---- - -## 5. 约束与风险 - -### 5.1 已知约束 - -| 约束项 | 影响 | 应对策略 | -|-------|------|---------| -| **内网环境** | 无法直接访问HF/Dockerhub/Github资源(模型、数据集) | 本地 Registry + 数据导入工具 | -| **算力平台限制** | 现有平台调度能力有限 | 引入 SkyPilot 作为上层调度 | -| **数据持久化** | 需要可靠的分布式存储 | JuiceFS + MinIO 方案 | - -### 5.2 潜在风险 - -| 风险 | 可能性 | 影响 | 缓解措施 | -|-----|-------|------|---------| -| K8S 与现有系统集成复杂 | 中 | 高 | 先在 H20 集群小范围验证 | -| 智能体接口适配工作量大 | 中 | 中 | 早期明确接口规范,持续对齐 | -| 用户习惯迁移阻力 | 低 | 中 | 渐进式推广,保留手动模式 | - ---- - -## 6. 资源与依赖 - -### 6.1 硬件资源 - -| 集群 | 配置 | 用途 | -|-----|------|------| -| H20 集群 | 2 节点 × 8 卡 = 16 卡 | 主力训练集群,首期部署目标 | -| A6000 集群 | 2 节点 × 4 卡 = 8 卡 | 开发测试、小规模实验 | -| H100 集群 | 多节点 | 目前仅提供容器方式,不确定能否提供KubeConfig接入,大规模训练 | - -### 6.2 外部依赖 - -| 依赖项 | 状态 | 负责方 | -|-------|------|-------| -| yd运维智能体接口 | 已有基础 | | -| argus运维系统 | 已有 | 运维团队 | - ---- - -## 7. 成功标准 - -### 阶段一完成标准(M1 + M2) - -- [ ] 算法工程师可通过 Web 界面完成 SFT/RLHF 训练全流程 -- [ ] 任务提交到开始训练时间 < 10 分钟 -- [ ] 训练指标实时可视化,延迟 < 1 分钟 -- [ ] 至少完成 3 个实际项目的验证使用 - -### 阶段二完成标准(M3 + M4) - -- [ ] 断训事件 100% 自动检测并推送智能体 -- [ ] 常见故障(OOM、节点失联)自动生成分析报告 -- [ ] GPU 整体利用率提升 20%(通过更好的调度) -- [ ] 平均故障恢复时间(MTTR)缩短 50% - ---- - -## 附录:关键技术选型 - -| 领域 | 选型 | 选型理由 | -|-----|------|---------| -| 容器编排 | Kubernetes | 业界标准,生态成熟 | -| 任务调度 | SkyPilot | 专为 ML 场景设计,支持多集群 | -| 分布式存储 | JuiceFS + MinIO | 兼容 POSIX,适合训练场景 | -| 实验追踪 | W&B (自部署) | 功能完善,团队已有使用经验 | -| 镜像仓库 | Harbor / Registry | 内网环境必需 | -| 训练框架 | veRL / Megatron | 支持 RLHF,与现有工作对齐 | diff --git a/specs/hl_design_v2.md b/doc/hl_design_v2.md similarity index 100% rename from specs/hl_design_v2.md rename to doc/hl_design_v2.md diff --git a/doc/requirements.md b/doc/requirements.md deleted file mode 100644 index c2734fb..0000000 --- a/doc/requirements.md +++ /dev/null @@ -1,18 +0,0 @@ - -目标:设计一套AI任务调度和管理系统 -环境:在K8S集群(商业化封装的算力平台)上运行若干个GPU容器和CPU容器 -约束:CPU容器可以暴露端口供desktop访问,CPU容器可以通过ssh访问GPU容器,容器的生命周期在单独的算力平台控制台上管理;所有容器 - 有共享的NFS文件系统 -目标:在CPU容器上部署一个web server 向desktop提供服务,后端运行一个类似skypilot的程序,能够注册和管理GPU容器实例进来。 - - 用户在desktop上通过网站提交执行模型训练的任务,任务管理程序会将任务加入调度队列,等资源池有空闲资源的时候,就会调度任务到对应的GPU节点上执行任务。任务有单节点任务,和多节点任务两类,预先的节点也提前配置好了,多节点任务的容器之间是专门 - 走的IB网络。 -任务:完成技术选型,主要是普通的skypilot不支持现成的ssh节点管理。你调研是否有节点满足需求的任务调度管理方案。 -补充:运行的任务一般是 verl / skyRL 强化学习训练框架,以及llamafactory 框架等。GPU节点容器假设是已经预先安装好了对应的环境依赖,任务管理器只需要调度和查看任务执行情况,还有监控任务是否健康,有没有任务中断。 -未来规划: - - 统一数据集管理,包括模型库、数据集库 - - 统一日志采集&规范 - - 统一容器GPU/CPU指标采集 - - 统一的 weight & bias 指标服务器 -结构图:见附件 - - diff --git a/doc/storage_deployment.md b/doc/storage_deployment.md deleted file mode 100644 index 4bf2589..0000000 --- a/doc/storage_deployment.md +++ /dev/null @@ -1,315 +0,0 @@ -# 关于MinIO + JuiceFS 在H20部署 - -这是一个架构设计的关键决策点。在 **H20 节点运行 K3s** 的前提下,我建议采取 **“存储组件独立部署(Outside),客户端插件化接入(Inside)”** 的混合策略。 - -简单来说:**MinIO 和 Redis 跑在 K3s 外面(用 Docker),JuiceFS Client 通过 CSI 跑在 K3s 里面。** - -以下是详细的架构拆解和理由: - -### 1\. 架构图解 - -```mermaid -graph TD - subgraph "物理层 / Host OS (H20 Node)" - NVMe[NVMe SSD (物理盘)] - end - - subgraph "K3s 集群 (容器层)" - Pod[训练任务 Pod] - CSI[JuiceFS CSI Driver (DaemonSet)] - - Pod -- "PVC 挂载" --> CSI - end - - subgraph "独立 Docker 容器 (非 K3s)" - Redis[Redis 容器] - MinIO[MinIO 容器] - end - - %% 关键数据流 - CSI -- "1. 读写缓存" --> NVMe - CSI -- "2. 网络 IO" --> MinIO - CSI -- "3. 元数据 IO" --> Redis - - %% 避免环路 - MinIO -. "数据持久化" .- NVMe -``` - ------ - -### 2\. 组件部署位置详解 - -#### A. MinIO & Redis:建议 **独立于 K3s 部署 (Outside)** - -**方式**:直接在宿主机(Host OS)上使用 `docker run` 或 `docker-compose` 启动,或者使用 `systemd` 管理。 - -**理由**: - -1. **爆炸半径隔离(最重要)**:AI 实验初期,K3s 集群可能会因为 CNI 网络插件配置错误、Device Plugin 崩溃、或者各种误操作导致集群不可用(Crash)。如果存储后端(MinIO)跑在 K3s 里,K3s 一挂,你的数据就“锁”在里面了,连日志都拷不出来。 -2. **资源竞争保护**:K8s 的调度器虽然有 QoS,但在只有 2 个节点的情况下,H20 的高负载很容易导致控制面不稳。把 MinIO 独立出来,保证存储服务的 CPU/内存资源不受 K3s 内部 Pod 挤压。 -3. **网络直通**:宿主机直接部署 MinIO,使用的是 `host` 网络,少了一层 K8s Service/Ingress 转发,对于大带宽吞吐稍微有一点点性能优势。 - -#### B. JuiceFS Client:建议 **集成在 K3s 内部 (Inside)** - -**方式**:使用 **JuiceFS CSI Driver**。 - -**理由**: - -1. **符合“平台化”愿景**:你的目标是做一个 "AI Infra 平台"。对于上层用户(算法工程师),他们不应该关心宿主机挂载了什么目录。他们提交的 YAML 只需要写: - ```yaml - volumes: - - name: data - persistentVolumeClaim: - claimName: pvc-juicefs - ``` - 这是标准的云原生体验。 -2. **权限与隔离**:CSI Driver 可以更好地处理容器内的挂载点权限问题。如果手动在宿主机 `mount` 然后用 `hostPath` 映射进容器,经常会遇到 `Permission Denied` 或者 `root` 用户归属问题,非常头疼。 -3. **自动缓存管理**:CSI Driver 可以通过配置 `StorageClass`,自动帮你处理缓存路径的挂载和清理。 - ------ - -### 3\. 实操配置指南 (关键点) - -既然你只有两台 H20 并且要上 K3s,以下是落地的关键配置: - -#### 第一步:在宿主机启动 MinIO 和 Redis (后端) - -不要用 Helm,直接写一个 `docker-compose.yml` 放在 `/opt/ai-infra/` 下运行: - -```yaml -version: '3' -services: - minio: - image: minio/minio - network_mode: "host" # 直接用宿主机网络,性能最好 - volumes: - - /mnt/data1/minio_data:/data # 挂载到大容量HDD或SATA SSD - command: server /data --console-address ":9001" - - redis: - image: redis:7 - network_mode: "host" - volumes: - - /mnt/data1/redis_data:/data - command: redis-server --appendonly yes -``` - -#### 第二步:在 K3s 中安装 JuiceFS CSI Driver (前端) - -1. **安装 CSI Driver**: - - ```bash - helm repo add juicefs https://juicedata.github.io/charts/ - helm install juicefs-csi-driver juicefs/juicefs-csi-driver -n kube-system - ``` - -2. **创建 Secret (连接信息)**: - - ```yaml - apiVersion: v1 - kind: Secret - metadata: - name: juicefs-sc-secret - namespace: default - type: Opaque - stringData: - name: "myjfs" - metaurl: "redis://<宿主机IP>:6379/1" # 注意这里填宿主机内网IP - storage: "minio" - bucket: "http://<宿主机IP>:9000/mybucket" - access-key: "minioadmin" - secret-key: "minioadmin" - ``` - -3. **创建 StorageClass (核心中的核心)**: - 这里要配置**本地缓存**,让 JuiceFS 能够利用 H20 的 NVMe。 - - ```yaml - apiVersion: storage.k8s.io/v1 - kind: StorageClass - metadata: - name: juicefs-sc - provisioner: csi.juicedata.com - parameters: - csi.storage.k8s.io/node-publish-secret-name: juicefs-sc-secret - csi.storage.k8s.io/node-publish-secret-namespace: default - csi.storage.k8s.io/provisioner-secret-name: juicefs-sc-secret - csi.storage.k8s.io/provisioner-secret-namespace: default - - # === 关键性能参数 === - cache-dir: /mnt/nvme0/juicefs-cache # H20 宿主机上的 NVMe 路径 - cache-size: "2048000" # 2TB 缓存上限 - buffer-size: "512" # 写缓冲 - prefetch: "2" # 预读并发度 - ``` - -### 4\. 备选方案:如果 CSI 搞不定怎么办? - -如果 M1 阶段你发现 CSI Driver 调试太麻烦(有时候 K3s 的路径和标准 K8s 不一样,导致 CSI 挂载失败),可以退回到 **“Host Mount + HostPath”** 模式: - -1. **Outside**: 在宿主机直接运行 `juicefs mount ... /mnt/ai-data`。 -2. **Inside**: 在 Pod YAML 里直接映射: - ```yaml - volumes: - - name: data - hostPath: - path: /mnt/ai-data - type: Directory - ``` - -**结论:** -优先尝试 **CSI Driver** 方案,这才是正规军的做法,能为你的“平台化”愿景打下基础。MinIO/Redis 请务必保持独立,不要让 K3s 的波动影响到底层数据安全。 - - ----------------- - -# 关于Minio扩容 -这是一个非常关键的运维问题。 - -首先要泼一盆冷水(也是为了避坑):**MinIO 不支持从“单机模式(Standalone)”无缝平滑扩容到“分布式模式(Distributed)”**。 - - * **单机模式**下,MinIO 是直接把文件存成普通文件。 - * **分布式模式**下,MinIO 会启用**纠删码(Erasure Coding)**,把文件切片打散存储。 - -底层数据结构完全不同,因此你**不能**简单地把新节点加入旧集群。你必须通过\*\*“建立新集群 -\> 数据迁移 -\> 切换流量”\*\*的方式来完成。 - -鉴于你使用了 JuiceFS,这个迁移过程其实比纯 MinIO 迁移要灵活得多。以下是针对你 H20/K3s 环境的最佳实战方案: - ------ - -### 方案概览:蓝绿部署迁移法 - -我们不修改旧的 MinIO,而是搭建一个新的 3 节点集群,同步数据,然后改一下 K8s Secret 指向新集群。 - -#### 前置条件 - -假设你现有的环境是: - - * **Old MinIO**: 跑在 Node A (192.168.1.10) - * **New Target**: 准备在 Node A, Node B, Node C 上跑 3 节点分布式 MinIO。 - ------ - -### 第一步:搭建全新的 3 节点 MinIO 集群 - -由于旧的 MinIO 还在通过 `host` 网络运行(占用 9000 端口),新集群如果不关掉旧的,需要用**不同端口**(比如 9100)或者部署在不同机器上。 - -假设你新增了机器,或者错开端口。以下是 3 节点分布式 MinIO 的 `docker-compose.yml` 示例(需要在三台机器上都运行): - -```yaml -version: '3' -services: - minio-distributed: - image: minio/minio - network_mode: "host" - hostname: "node1" # 另外两台改为 node2, node3 - # 关键:分布式启动命令,必须列出所有节点 - command: server http://192.168.1.10:9100/data http://192.168.1.11:9100/data http://192.168.1.12:9100/data --console-address ":9101" - volumes: - - /mnt/data_new:/data # 挂载新的数据盘(或者旧盘的新目录) - environment: - MINIO_ROOT_USER: "admin" - MINIO_ROOT_PASSWORD: "strongpassword" -``` - -*注意:3 节点 MinIO 允许挂掉 1 台机器而不丢失数据。* - ------ - -### 第二步:数据迁移 (两种路径) - -鉴于你用的是 JuiceFS,这里有**两条路**可选: - -#### 路径 A:底座迁移(推荐,速度快,原汁原味) - -直接搬运 MinIO 里的对象块(Block)。因为 JuiceFS 把数据切成了固定的 Block 存在 MinIO 里,我们只需要把这些 Block 从旧 MinIO 搬到新 MinIO,**不需要经过 JuiceFS 客户端**。 - -1. **安装 `mc` (MinIO Client)** 命令行工具。 -2. **配置别名**: - ```bash - mc alias set oldm http://192.168.1.10:9000 minioadmin minioadmin - mc alias set newm http://192.168.1.10:9100 admin strongpassword - ``` -3. **全量镜像 (Mirror)**: - ```bash - # 创建新桶 - mc mb newm/mybucket - - # 开始同步数据 (将旧桶数据镜像到新桶) - # --watch 参数可以持续监听增量数据,适合不停机迁移 - mc mirror --watch oldm/mybucket newm/mybucket - ``` - -#### 路径 B:JuiceFS 层面迁移(适合要换云厂商/存储类型) - -如果你想顺便整理数据碎片,或者从 MinIO 迁移到 阿里云 OSS,可以用这个。但在你的场景下,路径 A 更快。 - - * 命令:`juicefs sync minio://... minio://...` (不推荐,因为需要解密再加密,消耗 CPU)。 - ------ - -### 第三步:停机切换 (Cutover) - -为了保证 100% 数据一致性,建议申请一个短时间的维护窗口(10-20分钟)。 - -1. **停止训练任务**:Scale down 所有的 Training Job。 -2. **停止旧 MinIO 写入**: - * 确保 `mc mirror` 已经追平了数据(没有 pending)。 - * 你可以把旧 MinIO 设为只读,或者直接停止旧容器。 -3. **最后一次 Sync**: - * 运行 `mc mirror --overwrite` 确保最后一点差异也同步了。 -4. **修改 K8s Secret**: - * 这是 JuiceFS 的魔力所在。你**不需要**重新格式化 JuiceFS,也**不需要**修改元数据引擎(Redis)。你只需要告诉 JuiceFS:“底下的对象存储换地方了”。 - * 编辑 K8s 里的 Secret: - - ```bash - kubectl edit secret juicefs-sc-secret - ``` - * 修改 `bucket` 和 `access-key/secret-key`: - - ```yaml - stringData: - # Redis 配置保持不变!元数据还在那里 - metaurl: "redis://192.168.1.10:6379/1" - - # 修改 bucket 地址为新集群地址 - # 注意:MinIO 分布式集群通常前面会加一个 Nginx 做负载均衡 - # 或者你可以填任意一个节点的 IP (MinIO 会自动转发) - bucket: "http://192.168.1.10:9100/mybucket" - access-key: "admin" - secret-key: "strongpassword" - ``` -5. **重启 CSI Driver**: - * 删除 JuiceFS CSI 的 Pod,让它们重建并加载新的 Secret。 - * 删除使用该 PVC 的 Pod。 - ------ - -### 第四步:验证与回收 - -1. **验证**: - * 启动一个测试 Pod,挂载 PVC。 - * `ls` 一下目录,确认文件都在。 - * `cat` 一个文件,确认能读(JuiceFS 会去新 MinIO 拿数据块)。 -2. **回收**: - * 确认一切正常运行几天后。 - * 下线旧的单节点 MinIO 容器。 - * 释放旧的磁盘空间。 - -### 专家建议 (Pro Tips) - -1. **负载均衡 (Load Balancer)**: - - * 到了 3 节点分布式阶段,建议在 3 台 MinIO 前面架设一个 **Nginx** 或者 **HAProxy**。 - * 这样 JuiceFS Client 连接的是 `http://nginx:9000`,Nginx 轮询转发给后端 3 台 MinIO。 - * **好处**:如果某台 MinIO 挂了,Nginx 自动剔除,训练任务完全无感。如果直连某台 IP,那台挂了训练就断了。 - -2. **元数据备份**: - - * 在做这一切之前,**务必备份 Redis 的 dump.rdb**。 - * 只要 Redis 在,JuiceFS 的文件结构就在。对象存储里的数据块丢了还能通过文件名找回来(虽然内容坏了),但 Redis 丢了,对象存储里那一堆 `chunk-xxx` 的文件就是一堆毫无意义的二进制垃圾,神仙难救。 - -3. **拓扑限制**: - - * MinIO 扩容通常是“倍增”或者“对等扩容”。比如 4 节点扩容,通常是再加 4 节点(变成 2 个 Server Pool)。 - * 所以,规划 3 节点时,最好磁盘大小一致,网络环境一致。 \ No newline at end of file diff --git a/specs/mvp/sw_arch.excalidraw b/doc/sw_arch.excalidraw similarity index 100% rename from specs/mvp/sw_arch.excalidraw rename to doc/sw_arch.excalidraw diff --git a/specs/mvp/image/Snipaste_2025-12-30_16-06-37.png b/specs/mvp/image/Snipaste_2025-12-30_16-06-37.png deleted file mode 100644 index fb62750ceb093cf70887e1608fd6d099a4bcd09f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 77632 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 diff --git a/specs/mvp/image/Snipaste_2025-12-30_17-02-20.png b/specs/mvp/image/Snipaste_2025-12-30_17-02-20.png deleted file mode 100644 index 4005c93cb419c4eeee22cddb8032ad0cfe021e87..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 53286 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 Wt09b;OilVALp)vmT-G@yGywnx-WCo3 diff --git a/specs/mvp/image/roadmap_v3.0.png b/specs/mvp/image/roadmap_v3.0.png deleted file mode 100644 index 84243452c189b329f346f53efa6b1c4c567049af..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 66842 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 z zWTLq0*}>Nj*Y7&Lr}noPLqby0q6dz@z1)}ERID=l+o;^B#AUNHB|*xqsFfG*NKdryROxj z|Gy3lvekFbFp-+*aRz)B%w&-Yrbf_VygFjq1_l$(rj=LzuCd#{XHQIUaBz6|_I2yt zfsPg7=l`EFZR^UFFHcR?HZ?Kf;RS(>PiM`V6?<>Dio9LTiv!Ky_y7N!|NY(F52gSA z{k^_6`uW3$3zrnR>bZs~cuiS(Lsz4l{rt(3FaQ1hz2TyapLtXDhk_+8f~@mmR>^g% zXxVAAwu*`x_RG)y_O`m}b(nH&ECYj*kn8{7>pgVVW#`mPoo;^N1P8;1CtqK8w6H8s zJj}N)YN_LLW`SXz{a26)Uu0?OFc}u%aojP^oh>OQ`z zd3kwjYikoP-+t$G>C5|dxsT-boHMHX^FuRu*^y(%o;`WuAtrhL#EFVOKQ{LF_m`G$ zd88uLsUr09Xt%h!|2!6k4H0WzUS94$*Q)f&ia-&rr}y?&+yD7+cuys0_rrJ7YDWPT zZSC&E4@E>pL3iy0E7$-1WeTdSWo)ai96s#4QdYJob239oiZc z^fJG>QBhG<4-PcGc=6)>{{Q=eg*dkDcdBrQ{w)&{m|9-oD`ZdQf_ z1JJ#T=g#Hb+LC#=jra4{uc<~e?^cMEmX`kh{(gVWPopxXJyl;{eR+9#e)k#Bg|NTh z@Asc)W0`cMBl&orp+ryS{)^&6~A) zV!IYCdi3e(X~>%Jy1Kfww6wR!Kb*J!|K!P&01c7&`1_8{Y^5(RJnh%2{*ch2mbasR zl6n5U1sYkInJcecR+VjT&v@j~>BPNfp39P)uvr_Hx)z;TnSVdevQCC!L;caN;*TFs zu8%A1?q;7ogMs0PQ=(_+)X@L`nx;(?HqVpk>L}Q_Rduq*_u$~mMa71V%U7>lc{1UO znHg7f^hp(=c#S7do-r{9OyszynJp!?>ecJ7TenEfo?ZU$ef>m!`KmtYgwv~$jC%)X=&-;prD@KUR_;XYl;7#o}LEx zP2zrwY+bcVi?5xTLBc4dW8c0y>BbfXj$XIdIYza1%&OJWX zyLscr#pl6J_a0gzq~)#`7OiJ+0v6_FV(MhZs$wg zd^2F9gL)#2;ggjwY6Y6{BB=i5{o%|Czr;>Cpl8a!-|`|bZ_*f;3!aui_MS@QByE4O&U zp?U4?$Nla9wpex>85xP`Muh|iJF5uE%E-9&%jITfW~QZm^DJ#&l;Pxb=+@S3X=&+` zDMk19)v_`%HXke~F7EE^`tj6U7jS-frAwi{eGW<1>g{QP{-omrr>R6c%R zFk{6gc7M~^&K}Oe!NCp=4taTbDJf45G%`Q6m5F2&wR?B)@J}T!-46x)aqKTLvMy;( z`QP2~;K{SDBad39>vy_5T6eVj`L11J;bH&ko_fW2ok|d%{L;@aTu6BOo7>Ber-gs6 zNZNQ~QT+bBr>8#`6I0t$Q)z1W@pj4Z!8O`AR)G~RsWN(e*4x^?f?#qQqs^O^LU$L9I>Y>J=p%sx9!q+FVW3_2A3uJ)AtWn1cfo=MnU|L(-tr7u;>q8Aw5YUn?TQrz zrKPo>o_IPtA8ur3x4XHw;r#RW_xJxlGt>Bnkk-^)g^!Q9c8ht=Dvy`ZYEqc-@_s90 zz0lI#r6>4a_IB>8{T&q*wXfo1)9I&K+1bh*ML$11y>{(d z`TN&A|6WW`(594=lU9eXud1xf%+3zh5RsLg+tt-&Tm8+%%nUS(ar34mgM*5Ywzl@_ zRjYh_e5@oGzF5}xwY9bBMsGWE^r&E`OKokf+3ecK$9NeIY|FjC=KN%{Jo z?dae*$-UOLx3~BAx3}FrJuD15QCl)jPt%>0x684a4OBAf>+6FW=v%WVf`OczoT8#) zgjiB;?%QL%(mP|;EnBA6d~n6;)!n_lXHT8lRq&8$n)d031=rR_vol!K{`&IcC>>;L{L^?6WeF{hPV{8PoAPGR+PGYplDjXz&m3A!2P@v+|Dr>YhfxnH%Z5LlYc zc!~K##hycl4(-~tYtf=baXKF!Jee|Oon_2}l}1G$rq&AX9( zEsx*hQSoz<=i<5dHXY5sq{7tr;O)D-yp%70&Pwldcwmrn!cAXaX<|fVxVl((x`k!z z&Aqoh!pqn6_HN%@9hLX)_a>tqj=5slPaYf;-MUpT`&z`A`Sl+@rLO+>ckkW14|mUd zeC%v-v2gd%simbZN`*(y%v7)Y<=O1_UB>)e=8X+YdU|HHvHh%-*(>v=nR-3FP~ z>C?p-6ciN`UtL*gXlUr`>&w8v)VQJUZ&k!|S=>X@$6NITSwI^X;`UTD>U#S4fHuna z_p47ndB6UDZA8S3{(k@3+P|O+71qbyRrt7gvBs=fv!p~sOtP=(u(P)>^`0KLzi#gN z=j9u$jb_RS2uzqbvGBm z-PyTx>C#L5p&BA#p`oQezLrbbxClG{IuOp*Y*_TfgT*oL&W^@K8D(YPdZo?JoIR`B zoj%XL-p#{csf>yqI^-5`Chuh+V&_U@vdu;gHg@uG3y?W)PG|@xl(sg@N zDJiLG`tfq&;?Li|pFel*-!CsOXJ218bHH;sr>xx>GS98Y;1>4fuaI3 zM8u5MtF^yfTN}MSY;Dxl<^J&w| zip9~%*?DKoy9P$)4K>TpU%YaqFw>Ezb1bE zoH;Q80SA&c_Q}~=<=wGhYBWeb*261pCSzUp=EK9opf&v)laH?mS!Lop^_}o+jxFv0Usd+)(;H?x^*ijC+DqOw~W)zwM5tb{Z;Db*0y)=-$Sk34=cTw2G#%n z`+fbNMNcF)HFDeBX}&)1&!0d3VyEAxmT0*I2R$fFerDMhw4g)IX6F{q04shuh6WcE zK4atAS^4%ijAKlF*SAXkq8V53W|&4n||QX4DGNr6MCGJjb>Vx zzcVp6-(UVdZmUat@5jf-@9!?x*Vcah^78V`%uGH$K1)kWP}GLk%E}*q@bcx$M~|BB z3aHG44}&k!@{z_}IZg;(?)S06hQXnx#^%}9YnLxum%X_$S>6B7 z-@n>gTG!S@8drVEI5XRQVZfHHTRB+{H83(4fj5x{g@mZ=Tr931*V5j8_*?m;4L9E` zSfIen-2CQE&W_7__Si5mOh0|p&r(-+ZT|khVvZAj{i+gieSdfN@uZD>G8PGWd2*7H zGbc<)NKY^S_ouSEzw+XS6Kf|g#!>4>apIt?s z@L^zRb-H-tbSJzP`RQ4rps@Gc$Mu+qSwb zF1`B59kvz#bOq0a;~_p~v){gd&(Bct?@#6N##s_;*RH+s=k@OL_jBgVSrE^}_pICZ z+Y&Fluh z{fd~FRu#s^-nFg%R$`R9)*8G2A08fVY-}ukey;Z08%dt+Yz!Q&hyMKe6JP&#>z+M# zjvQ(6TmJcHO+}KtMS+5f3QL^A26N^=pxcVBG;Z6rEqq;!rUnRfbahD?rErv4+`4ru zD=X{b#f!)LWG8=03Q-EV+}tkx`fcO%&7fZY9HCf^O-=KSSG9rrW0JNN7F}-TnS1zj zuJ74nGtr}EQASYECD4vElUt{zYBMsFzrW`y&~h}1SI%a~nl*23ZOuM<6tw@S{rn!w z;%6C|nVy?pgO<;7w7hwf^Fx2lmje$ARMKC2dwXxsy?yLyk+@F8g2juSmtWS^(U~=S zwy?0UVYyh7!uNM~nHgrxo}IigOEw`bjm=i*!~OF2_e4cS54Ld4FrP7VrsmAZi#Klk zIIX|mrshY%u^!0_(#mH8mi}b3@?LHO8rL~D*SfK>v8=3&TTI8I{GH62EQ`cLEt!{> zolL5*^-SmGFgG_}ar^6+FVD`*RQ@@wx0koq?Ki0CE-JcJOcPZ!v_h=q9+p+ot2c8V`F2>-`}%MKR4&vwQH}huV1V& zYx?x(4<3N}I2Bz+GtZR1zIM=O=j-e1j~_X5<@)vgwZEr%sAOelx3{(Z`u*G7%xqos z_H(yx-MV^p>yjlY|Ni`RQ8Lul&VF}i=e29s{{H^{{{H^`t*x!ASHC_x+gw*i=i8f` z&P#&=MMOJYtgJw%5vlvnld-G$(Qp3`)V{rOBO*9BSX*10tJNs&jD%djxR}_rxIKy- zNpS~QLvRN>|Mv%5+2c+}MMc@# zpS}LsV`hx{&RMITK0fK{r6JN)(LbS^eSLZQ(??%;QjB&=`!6w@_Ig9&VbDlq%#MQ3 z&(2=E7G^i!Uv2XLACLPdD!bp?S*&hoIPvsTJ~^8kr%!8ZX}vno$jr_s13K*Q^XKla zu1Wi5$IQ2@H8C|cG;eKhcdw|Zh=_>r@;cSRDg2}6-{$o5^XzK1#JZ>J#lCv~o?llt zKmYxT6)T$A`9TL4Jvh*)tE>C}-|zg&%AJs-JeL%5IQyP{Sa7Uge*X07piO~xwZ9zn zTP9DQ+}i4zlarH|_il=2@QaeFtgI|2C#EKa;N^aQe?FhTaINy$09D`r@3_JzyFK{$ z^Uv;b(8UuPii(V@gZXFL)$UrpeEICz(c5|4_LW?Fapn5;?VC1fX=`uZxbfoueCKlu zo!i&N@2`7*Z*TB2pU90#tTw`zz&l^#;^OSm&&_de=R0`k+_zPe&ZgbIb?exXBTt?@ z*>W>y_Clxl^4W>iRaI#zDK0K9Az@)cokvnnPs_crq0wt;RaMool_6OU4xkImw&mXD z;^KM`x6Eheq&ahH9v|ynv0_D26Vr;bFG{NZ|NHy={QUP%pQ^rWT@avA{r%nEvbVPm zHnT5We*N%aWdj3&Z@wSDe)aY8>gwz~dE!LG#w6C+XY(>Mcb31uw>Ema0L#z&|NogM z9%{L}yL|WV-Tyxxm)DQqw`RqPhS^ImzucUDe%i$&?LG&KKUB4wyJ?7+nV4+2`R3bp zKF!&WwxoY}a4^@&#QwT>@XCoran3*M#!o!c>c_U!hywnHg<&dxSpAGP(>$;s-??EG@3Ss@u2836$k zcJ8b!DEQDPYrSUe+TPyYrFTH{pY!I$6&4y!aS#&|15GbHogP2WzW(2zpT!Ie6Fo`_ z3mYdcx*=+na$>@Z7cY9H&Arw=d-`;1>gj3v*QPb}NE*BO`s(U{0FU0yoyF<<>;67y zoNrN>^!?pketA2anjZ!=*Uz2HdwXl^r2eeTHm%;5_am+BreC^r>CvM{Ny*9G-QB9w zC!b8o&wpR}`Pt1IH%d+$h%}y?_g{o7_3o}xF)`5T26@TLggIK4dQZQUv1P)935(tP zz1|(Vcdzd2tE&tQ{QUgN%E~jUZ>C8cJa}+}*OTXEwpCwV#O^NhooBOi?_8JVm-%HZ z1Vlts1UPQwn3XkUW@H>F31evJ>+=fOgbvQUn4d)R&Damw6n8PPft_ixRjRX zV8v#zynJJ2&>#T5pR94*tCR{l4Z_PfwLevu8)YpW)81gWW%~_iI;Im#lS} zPSlnYH*Z>MYrk%nuhY=f{P^`NFCX8rcXB~ypkV>fRjh@NTxx6gc6WErpD!O{mwip= zWbmTqxLKR*B4#Q*-P87@a#2=XJXb3dYn=Xt&#}&e_4#+2+m*9Zz7&^V=lxPVZS~^C zk0-19zk2m*MaZfp6U|dkiRjGkz?cHQRK0pd$f|w&>OjX56dV7!a$=(L;zf&GlmcU8 z=gyjS>-nu0GiT0pb#?t%Vbkc~pdw^%sd<~x%*@Qr&hFvEhXGS_@9qlSq`rIR%$qZf z(*s0W1q*Y`eoyXyuFn@Lb$S2hnoG@)&EewW;_T8P9!|?IKR-MB`P;X59WPh5F5S6v z=el+4_U)7V*P7tH!N|%U7z#uljn<)UyqJh6sjKfb=cURqijaklE^_tQxmt@4)qvpkXV>D}Gk=6QEKmS492 z{z6HB(;$%;S_#i+cnQ2m33Z#MvMNGE6wc+ z9T7TtnVFU~KMbayj@^9rViFm6`kElcJsO zeKMV0U0M74)~#FD-+z8j<>!P8FT*cgx^(Hz9UTFV2k}3gen>_|McvYGNfU4pv;V?x z|L4NqSoTmcw&ui?lrMjN7N1$XZpN2_Y2ByVGLo45S1R-5-`mr~-s7WnP<`+jpQCZ0^;VrhEw zCg-60t!|S>mibc(KEz9=P6*Nvk?M6@d~rpHR!e@a z-kzVDnwpupa*2Da;DkLaPcp1mO=0)HDP1{z`gC)1b7qD)bLJ$}>M%1iJ3AlVw8_YB zzW?&eOEbHIb(^N0nQ^e0J^A$1jTKe>g&!Ze-bj*T5RjFv z{r2XjS?rZgmqoK?Np&rf;ZxVu&HexHudSI`X=$miudmr`-v3GZ8}@(Lcs*`O>FHpB zds~hsZ9FBW_qr@6H+S~z+3)Y}zP|O3?M=m-{Y%9|ea_igM+lg-@ z*_sn`a?U(0T6kb`PFJ(7zqGXU_qVsde|YFDFF)V0nQd?V|F}<_|Ni~`{q^iVv-iZm8Qb>wOUU_;8K3x|EdEjF!cxpG|rx zqBN01yy9-_(xs{M?P}M>?%r1L(8;y-~G&!?{1^n|SZ7O)^B-Q)u*)z4D+~;PQzP`0J+aS$l)-nq#E33M?I?y>@ zpi!a*AGPPV;X`+IwT z|9-zeF|wYYpI=>FU9vy0bEbWLU1g=EiN0O?&YeFmEOdVR=8cc9@51f8udH0nF7M`+ ztUOUI+1uNjnwt9T*)v)DmmDlj%RwN$pLY%SiNFUdK{>hjL&E>_X57EOy{-QKF80lR zeY2yA0v!MT{d@QBUH-j2h9)L5CK&=@^&JNj=76tbIiMQzx?tN%e`$AQ;xCv>>Ds7#v3xXQvfrLV7Vd;a}tb+t^51{oI?Oqehs?`E~DtE;zn z_m{g@r_O5S7T>mI%bgvC%xasG3wFlnO_!FH&CSk!{pwX#e!hLi1%*o9P3;G7cX>HG zIUNEWG5qtne1t;WN>FQ=P4oAZFHBZ?t9%p$&YU@8cQe1uMJciBefM6IP{uPlfm;Q9 z-&BN}#XAVH%9Xu;7ue{oz;LH|d4-LSzxrek{o*36SFbd(vWjD3a;zf1?B`7p^1N|t z)gHM$ckbLd+|ECH)~t2W+x-%sFV&0LQSkHAQ_w*lO+mXvW#)m>PR` zX7u)Z)2H68{>a22Q1`oRM~iybs&)USGV$AqPu=Lt)V1jPy4c&BQn{NHzJ2@Vv@jqs zKRQH9blb6M(+~W9KEGZ`Ss8TT^20-{%F4CAU-;>{?{!>! z@yXU~%S9YprxZ+KnyS00>G=cAMU5RGhksbW?jNX|#<6~-r;6C-nLd&~%~(M_wRqxrY`&CP8|$3 zUCz>$bt-C(UW2VtsPBV^ayG6uZ{mVemU=2EO!hEXzkc1uj|Wdr*W0%3md>;%R#Qt$ z-IbJuFJBUv*s*HezMIF>SGnjo2Du%(8NJ`o`=-<> z3pje8zIl7Qzl-~Ib5q?}Hb2$#^MBPVM|-VaJ^k;u=wrucz2831?(VzSyK9d1eA|CW zynl7$`TIqGD()PQ*xD}BcfN&l|Bv6!g`t7byB|L}=^DJu;`WV{z4iYO|NE;N8oKX( zo%Eg*&Y3Pn8@Kj)d2KQ@&llsGzrS*G$*nC@H>Z_;oBf_aLvX6!gQd%tgQlu=#D4$! z#m3IA{eyQkyUum^inZ3()~(kol8^U+dRnVOS5KNW>D~SP_Q}V1ZuUNzyt(<+t5?S9 z=jK=zKfAp>|M8VAJ){H27!At`Fs z*F&wBx8<#U_EGA`pU`%`wfx+_U*0fmbeU9g?e}-%ZTbBBYj>~OC&zGL$wel=`F<5Y zg`yw&Iv%_$u5YyCPW8%_yZ`-*))DJI`pAA=Z1#iCOYd_qEZDNE>fO1yiqFr5ey-^7 z__F`TjpOU%=5}>PiU={8Up??V|JUPw9=+@Jx3+8-*R!#xxv?ex{_4)ot-QQ*ZS`DK zeto^ObH|h^CzFpY`TzI(>HmMvC!UxPt*QC`^r;72S8eV+4qv~{zA7XtcJHt6_q|uG zVqg&Dw8o}4 z)$w>ETQfWVy$y+nZ*ES%eEG6|+@2qo{q22c7&y8=T9cQRWmW%g&+_HZH>I9VF+U;4 z_WgmUbN;VsPfCM>OlONSi&t0#HTgEJn6+Dax8(!ZFcFTW-yRg++uQByDVdZdB`43% zps{9!#=12=r%rgBJHx`TWKZ4P_^7O_`|TMTCePme;d*?u;FB-c)(Y?Y+2)|IWPkN@ zQIV1-udW78o3`PgxsnhggI!2S%l&=6fx+Cr{{8M~X?fGsv}e+!hs^9=I|Y6AWNwad zzqYnm!f45wWo{}$viqt`x373n8+p^fc=PA-cPi;=>t@;hR?p8Dnz&-!GBu%Y(-$Q^ zIo|a#-{bb|sQLeIieYkH{O)P1*4;bsy!%L!sgWdiy{n6oVb?Z=6AxF1?>u_6Tg`vj zij{MFIxGLYy4vx-OqrEoN?3UPQ~gVA>-j&usZ2O2ke>ehzyXJ&;pG}#NqmVhYuBz*8SX)LHXSaDCQlZ=R->e^ z|Ni6SeR5mzqzBL`dr-1%*^F)?-1(U-`nNu^>?nE-7mjbyx|pV!seRq#D8&eL;y%}-h9ux%yLERIUb z$}2-&U0WM1YWbe88N3-PJ1gtet5;bW89Y)ZD|YOt`2X+kvuDph(}?$KL&L(<)YO7j zUb%85WMM!?M#hWRuUD^K%X{C{%gmvllj_>b8l^VCpWj|0PDOd0vs*(40r3S*P6BJ*}=msYgfry@UhMHdq3qs@XehJ zZ!WIcB;KvWW%D!SA`3%FFkjrM*Vp|wZ)%%0iz_<1n2X#0*pV6E-d3j_?<;q8Esx)m zk(0;9@MQY5Wqa!0zI|p^`6c7W%0;J6T{h2WVwlx>s9HbHA$MAI2n&NlV9D(!)&k$v z|Ne5aIMrpYoFbj+I-%a!h=IYrqT+_vmWNfdriMnv+TOhw7#{rjUblFvscH89-|N;b zeE4W@b%#gFf~BGloS=tCF+X?a!iN+epHr`|>#!v^Pru$Z(|DtM zQKhf%<^T?c0x7dM&s(`qs!VE}Hf`a$yhvZ(c!i9~k~e;A+&*K$($u>XmH&SE%KYcg zzGv41cU5`4zrVl!%ZrN_7CPJC{Oq2nDAc(@{$hOn->)AY9=>wrilTE{$?0kFdnyD) zMW@c59UTEU+-I$C1(R_#4A2HAt}`x79D+i<=0em z30Jn+rH5GOF)5xGIGgwBLEzP^+jS!Z%HB#bG#pL%voGyzgI(<_Y3Y@(UIlD+3xj)SZ~nI$7;t{^I_=KDB1W zziuWkN?tQEzq6_TxBteC#I&@-XU;^qE?V8$>Ao(`HL&E^jg2WnD`y>NW_Xd6l{d>g zzkmP#>oVcY^YwFbQ!iz#wza)}X6EOUy$)yH76)wm{p*lI5L<8Bn&roJH6L=f&Ny&6 zdGpFwuOd3qa-Esg&8II~*0$)y^*It=&kt&AX{}nl+StS-$DThtF!1Bu^829EK@PX^ zZm^Hb%38I1_wQ?KqfJdr_U(B3ytmZl#+e#|z{pX8yUudgpIKK=a7 z4jVat6`_qcbC?4xjvW`?vc9h`_5Z({ ztgK&seJ|x4xq9wg{jDv}^Y5vor|I3??q4*aD(BmSy1xtzX3w6Pa6LW$BBNc=S?AyF z9X={zi#57B7wOAQpSduxp1E1Ovs2i;SIWF*$CG6NBCak@41%cUQ`;#v&{wNJAv==BB3yo7v^$?SBVYGp;gTgSe#=1{ z3MNYm2skVa+Njy{;ll?;X0{$_b3H@D!i$Ss#l*y>>&J(MhsSTt3N0$yw0rk&$l8_w zjW<_J_9$KcyvjM%*+g~u&m&2OU5k=7MyLoSu2@9T#rmF= zr8h1vbLYfi+j(W-D-L7Fl;TrES@$K>5B_4`{&>M^nGpg$(b{ME?w&E>sxAKy56S3;L4RN z4$;yK23M|>{JpcY`uzO)n<_td%`|SGF^h@e(*3==|GfyT%zY~(KHYhBxOZht+pb-= zYih$~t+sra9>3@A-PoL5MutjN)rtJ_&!$ef!7usg`nFtdb>BsS8U=H16rL?A+xP87 zV5KkbwiJi?cGJ|bkPBck!`aaW8EuE<}e$Mcw+RE7tA0{PO2dpPHJQ zzI^%OH^(9|HC0up^F)eKlfv(BZ>>vTi7+_C$Im~Rl9rOf!onhBQNVC(rPIOQ2t=q)7#4k+FlU<^7mhv z9S5@ei$Yhn9=H?eIbEtrVd27sF?yhroIgK5uP(qL!Q0v;YYnS`apJ$NB)aU>@ zp8eA&tD+|-Rs=47F!kuef~4f+b{~r-R+&AvFN~ICzEPB_V=&X{^yO0lisuELH6o@f7kx2 z7LT*4{dKAT@?qxQo;-P*i0d~zl!PLMj2CQcW=oxC$sGUv>cx*)(`OnNKJi$yq{~E_ zk>SG1EAr{*{}q1A`SE_gq~!GX_vJG)IazfZ9U`o1t$Lj}Ez94%*qVJ~`3aRtd$)eg z@;~nH~swa@$~oi@%!rK^;Cp9oqc@G&&=hHop|rvyIj6i>-)~#b#7Og zo^j#jYFpds@-`hEE@^FT(tGwSyLG$%FaMGfIh%~UX;Y^jY|uNoT?1tU`lPK}O&J(g zS!*0n^Pjh;{(qg>?A}E$c9p(fw0QAypP5X5LBqaBj~)eG(EcPWIQa5B+v*CNd3*Q% z-G0CB_Q45BNlALKyHc{UsvaIAg#3;{X2Ot3*~-*0*opH07($JX)c4xSjw1lgr;GugIAw3L0%<^6v{Zsg_`BT%hW@ zE@XSY%Y{o#i(UkDvh7w;D!lmQ_=;EmwNl^5-vJRQ&$-malKoh7AH%7r3~&&(E=B zX7~YGs)D-8@b-^KW$*9#DhTw+TAQVwnsV&eu`OG+oI2&Dx!=T-hleM{s7-mgM)(h?A@#GKaa;gC?urh*OyENhvMST zd#k@2G)|v1>C=~&mlry>bG06tGiT0Zb^lqjX3euKes*_vdHMT$xj8vgE-Rkunzvmc zbf>SAi%W}#N*3r^?_AIpf?W1(0iR+|wsJI;?2&3xkUbt(XQUBw>Vdy%(fj0$6IFyb zxo5Ym-@R>uQsb^&ztrQsH#;rwy0&T!JAb!R(81j-E(=-Z@+?nw{J9jwHZ|+R##uIO zuD)mQ-P#ph=BPF?=gisMGiUb~S@*o#XEgO(Gw4PTvF^~w$e*8{o;G9Z_ggM4AtAug z;whi~!67LrDZ?ZxAwdDOqR`F7rC?_agF{eIP+(x-{<^;=rlvD})WUe04?lc!f4@9~ zLFy?HcJ_9@W6cU4#l^-`z5XVNigAFq--9mUTD$h@wQHailaY}(Z*2t)?SjtDSLkSL zbaZfNxbFVn;D^N2u0=1l<=$Rkn46mFsvz*`^XJ<+d$w*B&0hHL-QC@;-C}?5|NlEb zMb!6$VX&*Wx3}BniXXYF$`62#0GKmzV&U6cTO&88t&QI=H!r{V*_n%%E*%Qf*3oHM z_u$Q&H}ds=Hm+Ea@%GkM&{beRJ}lh7-#+Y4hu6})+uL+?ba?W9e!pKYZ;;?nTWdSj zYpRam73&GfPx-ITnXL}m;ozBiHf)aH!beQ~9xAJ%+RJ%dP0F6mXuhuP82DvAJO8vd zx7oFW7HQ0yIeq!blvf({U$^O9h%GIt;wdgJzOm%@p;m5QUfxOhf*dX9Q%`;TS#!gc z;n-AJi-H43j~=~yckh}tI=Z^NH9Gn;XU&=gzRzoK+F2>Nes=|dJ$v?8z2ov)81Uum z*V(gY*Z=$Z{LP!3%w@@*DxkP1EHq?TuxpnT!-CbTcc-71)0-Y05b)v6O=Ed^`IA3< z?B??`Y}md%en-K>|N3&bm-jDQmL`4r#+frbjsiL^pYQH2-|#47_TKQYFfJA*v2NAH zdCT|OU2t%1P~Sgm)~!Znb{Sb&ZEfwpfBr=1h?&JFWMyUL=g*%q#iZzohqUzUlatkp zcixe;E?X0`^U}qO6AwQ;@F%om|Nj3cCMqw?+*P5o)>+9q9*ZsY8>C%rHyE)g_ zuU*?}I$?^`o#yuD#T!<e$CN1)ux!@YU7TOpOf(6Dq2!yN^D)x;or{p3Th*7cLw=eE7_noEH}s z#>gAQ}d$<2KWTJZJ2An8a4BQqQ5$|)D6i9TxeKRzs6xstQy%Y#Ju z?He~PyqEzx>(bB9Z?=j6@3)`pcYjCW;+`d-!((E2K4-f3N?pBkr|0UV(71v|a3t(t_cxvUN5Iv@_en&`((pxx zlXPcT2!gj#=KuK{du`3nfVg)rAAS0&>O57@RCSK2gjLCk{rl}19y~bMe15+D^qST2 z`|BK(uE{)l@L)sXV>i%#jYv(g?({P=3ZI@5RaRcSG5L5^b@lS4OZV3Qmt!!f{q?1x zfq|{rF!@+dLqo%rD^~=S-4bd=tPUJIre&=2hbw&sUjF{x#l`NkXU@#MxvAA}`TN`3 z^;J|-j&um#kdx$T+rPg)IeBr)ze_U=ldoL4a_G>ZGiT1I`OKIwfBycQo15zXzx}Kz zz%kFZ+HLX0oSYo1?@PUT?f9=|D+q90UhZH2^AqUWDlIK73z>6QRtBp+=4a=VsrdaZ zm#=;D%$YwwJ@qaxFJEDjlbdU7Z0zjh#K0hJmgC{!(Xdx_?V2?2d=rz?c96v8XXkY%&@$icw&NS zJHPmpsf-MBa&z|WyWcQrk=kqv+nG)Z0%H1cGV=2CCr{p-dU~31`Z*p61BQKDA%`k# zD~z6a@`-8oHJ#{fYZfkSJe!vMO?9TvJT7@=!y8mo5-%~p> zYHMrP#5z_tH8-c9ot666aDMT@Cf0fL=6x`9RuGt`7wfh7qLY(TpPa3hWm0!hiqj~_o4mXq^S5sHn8*_L-VD>L)vvta%BeKmi6e7vyG zd1L;X+Xq?W-ZMK+H~~J4!R+T82C=P^JWl?WdQoC^&DMYALE8!o3$E@{RUZ;w&DA>3 zsJUokH@8isLCu2$JDAxIDJkEt`LQAY=chdVxJ5bvSFWaRFTDA+{MyBfpfj(<^kQbr zpTEE4<)zcp^_|0|r+UenW?fOYXF8qhx%p#TTifgF>%E2NYpUM5b?cqbTmuf4rX`#n zN)yF&qgZM?kyaAz*zDEmqxSyZ-s;E4dP}VK{++l;LrPc}6x7$QU34x!v3@Y)1p9!?2HeWxzg+s`O2zj>OD=Bv{p(bTUa?y{#(o-A3q)OUu#!rj~E%$jxTVL{!WkM0td*Ng)+rhI!h z@!TiN@~)KmieEHh7dpin~&1ab!NcH-t?cV;{ZvCDQ6?={xabY;nC8}+f ze@`daSk~OIS~4^=)X>n-&CPAGd;hfW5mT5gxokqW-76?q!ua{Y$&y9EiGfeqP4qq# zgmBLcyEtVfJ3oVig1|E0+0ULmyVffv+T-^7+3b8aez`lbx2IU&x^?T~#fuBvn~oO< zZ=U|~$H!#7>93zZPftitc)wADy@=;xNa|}|c6TWcl}mSa7T@1n9UdJW9Ugvt-{c8R z&T5nGZ+?qC^{!0z``5R3A29hhIs{J97rCT4#b0b!#)HrDOP8xJTe`R6ci4qXObi7Q zMk*C2g?jaF{?h2WSNH9WVEg7Hhm$WHw|cOuVb`Uq4+<PY$aE&Y(<*e}Z` zx9H~Sir?RK84esd!jgYPOSNcE=>sNy_UGL)HWdM%;x#^JWoN&B{d(hdgDpa3T22B> z{&rux7WV16;zZE&V(z~~PcQvx-Nf70;I%I-Jp6d^)?GbL+%}>=V_lOB)y=0kzJAGyl?yeZ0>i&QIy<{%y8h%#mrrMB->xzE^ziV?Z{LL7`raJ!`|0#> zX7u);xc&Po-p`x4aN+F^!N+gkxJ5>mt}16z60)uP`l>D~E3|emU-#CV$CqbkZC0O{ z*|BVmZN*)_CWQ-g-rnE8f6wtnYaYn$iEEoY`SRc2-;ejnYQJyP;I)lE%Ba7osrhp1 zjU2PtXQ#!cX3DTS3bM|7_2r=U%2mI#_4Je!8?RqsVOS8nl7YcRg^3|$Z~gvX-|z1{ zdbGe-X<~+T#)UbBkB>z}f4_P$(NIEZaqH$p>yYcB zTeqqwC!ITboLfcZtcUk$Nk6~4U!Q6y+deq>I_^ZurrEQjeSLlNyUxE!1SO@1FJAok ze{1*e6)R5F@;}&rv-)0&fW!xeMHv&CBHFl^K4r<7ewZ;ODr(ls$d{2*pMJd)_3-7b zl~Zr+T^d%V8y}>dUFf}g))TFMc41ckeJm?9CV5S4c;M8OcyGqd@BQlEW}ZIaaqP@J z;~M+Zrmtt(RzIt}(s=X!&$oYV*!g58REgYUIjzFLaH3a+dEWW(4=j#5VxoV4`u28B zio46l!)<#F%JV**m{{Y!%r+|S+@-rGZs+~pesl9&Ve#{YkFCS(H{X0~dVQVf)amc_ z_3VmY25mn0VA1!|pFhjpTz$QKY7+15IW=q6q|NE->S}4nj{o;hOuWf&FEVwi=+vn{ zzrWu8?4TDDPBuTT-&7`dWHrENg#i+Hb$Uwyq8j4+$3*JYM)cJ;lZ}*{#IIW%=DS-x(X8 zpP2ai?AhCK6^RKR9_8!H7H=(m{O+#x|9Vwl5z~SPmwvx{{rQ`CoyA8JG&v3}3|>C(=7xn= zGkWCBa^6l-Rc_-6)DX#4n;f;YDE8xP`o5pK?`{0s}cH}O^2 zRX(|L<4(=eb$uO^9zEJ-^S>s+eERa$p{xGY)%oh`?m7KA#D9+c|9|^xT|^dKzB_xC zm8oiLtb6%~Bb~>ut($9G_~=ci@b2n$Hy?#tKx zn8_<`_WpKxbj6Q7n!z0>(zfT{+n)c`UA|D}yF9nJ-K@E~d}sLOH_8fp_$4JGz@TE| zDs11tzz{pB^uXtnT=#MxJ}mE-3=RnTbiS+0J+AiaQ`c@ce(AE)fn{etJiHtf?C$D* zezwuk|K@Qo2!Y%a&ye8$0}Bc6_+7#B+|*!Ar3X ze&6q(p1%BkX*mDxjLdB7+K-Da=Ja*;^ziV0{i!uyM(jI_|Dm5V8RpGTac$v}V{n)b zirfA3@9$bZ-%rl+lfC`VC0ka#+9w__BPF*l=h_-=Zcldfa ztI}7uFI_slb*sylCtqH27Zo`%F`L_cpHr-#vrO#zs@Jc0)Gq&f^yvM$`TSR2o(X&1 z|MhF1zl^l-=Rb$}Kg)bS+bNt~{+8>)OS?0trEP001ZS?j7GC~N$ELRG;gyw_kM*l7 zHJ|*_zCgh+W!p@j?DDs_{#^}!v^w+ZtEZdO?Ptw>`{z2#hae3FhJ;C?3=BIbCLj3x zGty*h*4L&vb1dusJpT9S(f?mxF2CBf>*@PFpD$foo39&fR`@33cvjruUTH~x+p8~M zHd@7&xU{@J`Z|K6WbLcx^E+4EP1}9zM#a{R6FdHFxuuwxnB2zi-_d(k%C_o410z@K zqNQtdAHTa>w)<~>x7fxKcbBtk*RuQ1*>UT}k5BCKd;T0`&q?-4d9r+USSt(5oZUsK zC#Ca4u3r_r*mLI0?&E#7)jvPE$JhV8)h=IG`R2y&`k&q1tGQ|$F3r_8Y*_Q)htMyJ zZO^8L?0qaP#?YX5@}oz{B(8bS4=)K@J8$OH(s;LH-^KOUojz|L6t*qn?5uS8iU%)e z8qf7l{c<^L^P|V_eZ5cj^uM3F^%;xfia#&am1fPGW>$G;N5I~?Ganwt>NSN&g?_CK zy&AjyzMY|>;~fbZfe*_+KK?E)zWsL2bt|zKzhB={H)E@flbss0X$6UYcBi60J(agqk!LnwGR%PAOKR>mfpHDCEK0j~n z_fy)9R(Bf?I4E^VSxo3iOG!)XmD9CzT^;uS=fB_k*RRsDto~M%n>*+Ix;4GYefyYM zSzbI=`S~Jce%p^KR)z)EMKS{fF5=B?Yh zckbE+2Ubiu^=0?FuD*^RYhRxG$~ng+#Xzcl&HCpS=f3L9by*U+T9oVP$x~itZ@tvb zcJKZ0<)!`ppJ}_#ikX*W6gV&lUNtur46G>lkT13QyaVg{_YMbMPg*}Omj9f}$_E?y zUH&X%Wq8piqg}zs$haoaY_@F}&&M;%;tie!L@fbK2Q?7KS0~pIiC~v`DXA z>zbMx{r&xOi#(5ri2Ty$kGyPV-_6^8yShlmOifL#_KHRs+sj$%^L;vcpIY|KomshL zP0s1*@tcBeJ2O7*D14*hUnZ3KbE)@Rv)L89GFM;R@$7LwfBpZz&Xd*dn$%aBhJ5(N zcST@Vi+tlg=Sfqp-n-`q4y@`To(h*G*I&<`HS5)@S4_;zwwD*D_jw2_?d$Ko0%!-cA-?=-UhwXUB(-j+c?!1|hvHfP2l$6ugDslZq zm$RJ1`Cq4bX zUC#24+fnf1%F43YxmjLb_mum8e5>NL*!9-BpyQ_MpUq!nC$a3AHcjl)#i>P%3{|Z@ z%yAhR8NtE9xw*MHIcw6ZzMOHathe7kx3cp1xj85QAGhzDZ>{dD1ix$7I%o=&l_)jyG8krfn~uxvc5W-p8e~yYta`}hBjlSyG+o>9iRbNl-VPo!+bKBRn|$;6{QY!Vzomhl;ezeWrBcT}Gxld1&$PLt?7_syU&X3b5$p8st+l`h z28I-mWsLeJCR1#rKa^O>3T~C?m3u9y($c`bmucxLy@&IczCU1E!N6do@;cb$_3PKR z*OaX_@-wqPNAxQwZfD!Gv-tV0_ebxxKep(5Trp2vnyaNyyy43+n|(J=oTbrJW_!2vQMTJRUIso-FU_(xyRmxbyXgU| zULD(0`T0iuIt5*`_T6{yecmrs zt!}aD_S?5_-zGKhH9x|3_+8ibq{AOeW!`sL-+A@l;eCLHh!)r_S6}(@PW3u^@6V)| z=5{VQhK6h--iqz_>#PN1ca@w>wpDuYRWr{@ufM-vUsqRGQ?u}RcQa3Aj;wh8!8(>c zIa{r-4hzINni4if=!kV6On8we|5w+S`I~j@&Z1VUeH?5I4CzL^6@h_)QoYO8u3fui ziHfS~QD)ms4e19=D{7l(Gu`|3^>uc3wys$B&75r!I$^7)%F2CxvMz$RAg|*q<8#>? z=70CEWO=B&W8DU(z6j%zJMXF%ckBO-EbN@BHpOdc@kXb$VXLoZtqoiKZo$Qj2<3li zmmhvJeSLlX|DVt2-@bLL$8GV!gaqEnCsWL3Ti=bc5{r2ma`DxbvUPbIZ>_u@s3G#` z_NAQ+?;`$|$ zZSI&dG;E)cc_3J8s-~u9JHNc1j?NdK1CJ}`b@-%hX8*;+xv})mos!;w5)jy89VdA} z`++;dowrw32EWnPWwBvscz2>?lBklGx3}`5Lx-HsmmFuBxAC!e>W9!Z9^G3{Ff#19 z*eR?Y!OY0du)z8gZ^g@(FI_?c0}KEDD&;RZF1Fl__5AaVQw__RCxLdHee6YG~ZpS^WIX&CPf3%C3Geb2n#2lfn!gv5);1bIhXG{=b!E zCT%VCh)=EC_0I8}t+(Em?N<0>_1$Xr{JSsLDRAufJEF(Y^w`ej?%VUX-u*iss39`P z>Emk^M%nE=yH_U!CzYI0a%eix8UC^S&E=Pxedm+buX$A28?`n}>#Ek&sFhc;Op>A( z2U+G_S#ecrTkP6vD?;7`UQ37$xm*8XbA$THEB6=}K2(QBNbEv!>xXy68w3{&RK ziwg)Scy?yy;dcJ?)YP3@^~;XrZ;5z!{&aC)ft{sy;(5-d1Ys5>rS~)U`W_+?g|FN{Z1;At9l%_xIkud$%k-eR^2Pj@{xD zn)mG4qdu>~=~W;DgM+^$Pg~*RW0E{sjxqbzTy9F!liQWK zc=z%XmfO3h*qqm%sx|Lb94tZ78_fq_NG)5S5wA9OiipoU0% z{ohg_pB}JXraQwwbYy&Za4>kepX#Dnvu3e!i|yF=kC%agq2}c6{Qa@P!Okwh%X}Pn zF*EGY)L-#HFtE1v?-b48ygNG_T`VmvXPf0ts&ZjqV0cjG>gxLW*;!#0MGK1^3l=0i zIM5i>&%xmEZqI@ycbCM(M9`5~#|vG)Tn&$38@=5R6p0KC)uG|x`jMMl1X#94?M*(; zx5S#EVcvuAwNa{HC8|I(oKb71o!uN16m;lwO;ORNE6q#{3=G>1q+50~plkT_u7UAvPy~P=%t2|;`&dsCU;++{s zyF@K5Era;k84hGu95<~{YCbq&_UzMjkA*=i+|2Xu$w*6Uzg+>kz-W6&c)0z)ACJZL zViXqLxpQaxy(({z%PWNQS3MA%=(qg#?sCu?^xe_1v9`6pzBDy4WxBI6Ffijy;Y~D>AEbr{L(DvhC$`0l$GqP3=eAem_85;3=O^d=xDco{63w$&hGB$T_rEK zWL~bAH@zT%fq~&dF=OE3Lk| zEB*Yuv$M^^!@|0xzgE?{xw)mKJv-7V?Cj*EA|uDZz_24AI(m2R?QQ;cKV9aS>YAH> z|9UM62#bn|?fZVO`gou0>n*lsW@g65#@gE2mX?ug!@P~m7#J7? z?(QgDyaWWE{P_6z`T607v3skwE?l^9@Bn=I62lJ;7RZ%b4Dz7z n5+wUT8Prw+v1(XoZP4>gTe~DWM4fl|!K! diff --git a/specs/mvp/milestones.md b/specs/mvp/milestones.md deleted file mode 100644 index c983f1d..0000000 --- a/specs/mvp/milestones.md +++ /dev/null @@ -1,34 +0,0 @@ - -# milestones - -通过以下几个里程碑来梳理和分析确认可行性,最终目标是产出一套基于Native Ray集群(无k8s底座)的verl 训练平台,支持多用户,运行各类verl任务,提高整体集群的资源利用效率,并且能够通过监测系统进行观察和资源统计,监控报警。未来形成运维SOP后,接入运维智能体,执行自动化运维。 -- Workload - - ppo on ray - - grpo on ray - - sft on ray 可行性 - - model serving on ray - - customize code 自定义代码,任意verl example 提交代码 - - 自定义reward function - - 同时多verl版本支持,同时跑不同的ray任务,但是使用不同版本的verl,甚至是用户魔改版本 -- Ray Job管理 - - 通过python api提交,而不是通过ray cli提交 - - 任务排队机制。无优先级,多个pending job谁先满足资源就谁先执行。 - - 【确认支持】gang scheduling (all or nothing), 指定好trainer.nnodes和trainer.n_gpus_per_node参数,不满足就pending。 - - 无配额管理、公平调度等特性。 - - Ray本身不支持任务超时参数,需要单独job监控,发现超时才停止。 - - Pipeline管理【高级, 暂不实现】 - - 提供对Ray Job进一步封装,串联多个Ray Job,自动完成训练,模型合并等job串联 -- 可观测性 Observability - - 测试本地部署 weight and bias server 可行性,如何集成现有job流程 - - 测试部署 prometheus & grafana,对ray节点进行监测 - - job监控,哪些job使用了多少资源,跑了多长时间,资源利用率是否充分,是否空占着GPU -- 数据、模型存储管理 - - shared dataset管理:所有用户共享的hf数据集 - - hf 模型管理:所有用户共享的hf 基座模型库 - - user dataset 管理: 用户独自的数据集管理 - - user 模型管理:用户独自的模型管理,保存训练好的模型 - - job 作业数据管理,作业产出物,临时目录数据 - - user management:用户可以通过统一界面来管理自己是user dataset/model space和自己运行的job的临时目录,从而灵活组织任务流水线,提供灵活的文件查看方式 -- 网络 - - 确认是否支持IB(H100环境),以及RoCEv2(H20环境),需要怎样配置 - diff --git a/specs/mvp/mvp_roadmap.md b/specs/mvp/mvp_roadmap.md deleted file mode 100644 index 716d002..0000000 --- a/specs/mvp/mvp_roadmap.md +++ /dev/null @@ -1,348 +0,0 @@ -# MVP Roadmap(V1 → V2 → … → 训练平台) - -本文档在 `specs/mvp/milestones.md` 的草稿基础上做**扩展与细化**:把目标拆成可迭代的版本(MVP v1/v2/…),保证每个版本都能**独立运行、可验证验收**,并且在上一版本基础上演进。 - -> 总目标(North Star):产出一套**基于 Native Ray 集群(无 K8s 底座)**的训练平台,面向多用户,支持 `verl` 各类训练/评测/Serving 工作负载,提升集群利用率,并通过可观测系统实现资源统计、监控告警,最终形成运维 SOP 并可接入运维智能体做自动化运维。 - ---- - -## 0. 关键原则(贯穿所有版本) - -1) **版本可独立运行**:每个版本都能从“空环境”按文档跑起来(不依赖未来能力)。 -2) **验收可客观验证**:每个里程碑必须有明确的 DoD(Definition of Done)与可复现步骤。 -3) **强制产物落盘**:模型/数据/日志/ckpt 必须可追踪、可复用、可审计(基于共享存储/NFS)。 -4) **Head 不参与计算**:Head 只承担控制面(GCS/Dashboard/Job server),避免训练抢占控制面资源。 -5) **按 submission id 组织作业**:作业输出目录与 Ray submission id 绑定,方便检索、回收、归档。 -6) **“先把 RL 跑稳”,再扩 workload**:先 PPO(已验证),再 GRPO/SFT/Serving。 - ---- - -## 0.1 里程碑总览(建议交付顺序) - -| 版本 | 定位 | 关键交付 | 核心验收点 | -|---|---|---|---| -| v1 | 可复现实验闭环 | Ray 集群 + PPO 跑通 + 持久化 | driver 不在 head;产物落盘 | -| v1.1 | 实验工程化 | JobSpec 模板 + 新增 1 个 workload | 可回归、可定位、可扩展 | -| v2.0 | 服务化入口 | API + Ray Jobs SDK | API 提交/查询/停止可用 | -| v2.1 | 节点纳管 | SSH 注入 + 资源池/标签 | 节点上线/下线、gang 约束 | -| v3.0 | 平台雏形 | 队列 + 超时 + 最小多用户 | pending→running 自动调度 | -| v3.1 | 可扩展平台 | 自定义代码/reward + 多版本 | 多版本并存、插件可用 | -| v4.0 | 可运营平台 | Prom/Grafana + W&B | 资源核算/告警/归档 | -| v4.1 | 可交接平台 | SOP + 自动化运维接口 | 非开发可按 SOP 运维 | -| v5.0 | 长期形态 | Serving + Pipeline | 训练→发布推理闭环 | - -## 1. 当前基线:MVP v1(已完成/已验证) - -### 1.1 目标 - -在单机(或同一宿主机)用 3 个容器跑通: - -- Ray head(无 GPU,CPU=0/GPU=0) -- 2 个 Ray worker(每个 4 GPU) -- 通过 **head 上的 `ray job submit`** 提交 `verl` PPO(`total_epochs=1`) -- 通过 **entrypoint 自定义资源**强制 driver 在 worker 上 -- 数据/模型/日志/ckpt 全部持久化 - -### 1.2 交付物(repo 中已存在) - -- 脚本与 compose:`src/mvp/v1/` -- 行动与验收文档:`specs/mvp/v1/v1_action.md` -- 共享目录约定:`shared/datasets`、`shared/hf`、`shared/jobs` 等(与 NFS 对齐) - -### 1.3 验收口径(摘要) - -- `ray job list` 的 `driver_info.node_ip_address` ∈ worker IP,且 ≠ head IP -- 训练输出落在 `/mnt/shared/jobs//...` -- checkpoint 按 `save_freq` 产生(避免爆磁盘) - ---- - -## 2. MVP v1.1(Hardening + 多 workload 可行性验证) - -> 目标:把 v1 从“实验脚本”升级成“可长期回归的最小系统”,并验证更多 workload 的可行性边界。 - -### 2.1 主要能力 - -- Workload 扩展(可选顺序): - - PPO(回归金标) - - GRPO on Ray(可运行验证) - - SFT on Ray(可运行验证:`llamafactory` 或 `verl` 相关 SFT 路径) -- 作业模板化(最小实现): - - 统一 JobSpec(YAML/JSON)描述:workload 类型、资源(nnodes/n_gpus_per_node)、数据、模型、输出目录、超时 - - 仍然用 `ray job submit`,但把 entrypoint 组装逻辑标准化 -- checkpoint 策略与磁盘保护: - - 默认 `save_freq` ≥ 10(或按训练总 steps 的比例) - - 明确保留策略(至少提供“保留最后 N 个 ckpt”的配置建议/脚本) -- “失败可定位”: - - 统一收敛日志入口(Ray job logs + hydra 日志目录 + 关键参数快照) - - 失败时能定位:是资源不足 / NCCL / 数据 / 模型 / 配置错误 - -### 2.2 验收(DoD) - -- 同一套脚本在同一台机器能连续跑 3 次 PPO 回归,产物目录不互相覆盖 -- 至少新增 1 个 workload(GRPO 或 SFT)可以跑通 “启动→训练→落盘” 闭环 -- 作业目录内包含: - - `config/submit_cmd.txt`(或 job spec 快照) - - `logs/`(可追踪) - - `checkpoints/`(按策略生成) - ---- - -## 3. MVP v2.0(Control Plane 服务化:API + Ray Jobs SDK) - -> 目标:从“人跑脚本”升级为“服务提交任务”。依然是 Native Ray 集群,但引入一个最小控制平面服务。 - -### 3.1 系统形态 - -- Control Plane(建议部署在 head/CPU 机器): - - FastAPI 服务(REST) - - Job 管理:用 Ray Jobs **Python SDK** 提交/查询/停止(不再依赖 CLI 文本解析) - - 节点视图:读取 Ray state(nodes, actors, placement groups) -- Data Plane: - - 仍然是预先启动的 worker 节点加入集群(先不做 SSH 动态纳管也可) - -### 3.2 API(MVP 级别) - -- `POST /v1/jobs`:提交 JobSpec(ppo/grpo/sft) -- `GET /v1/jobs`:列表(含状态、资源、开始/结束时间) -- `GET /v1/jobs/{id}`:详情(含输出目录、driver node) -- `POST /v1/jobs/{id}:stop`:停止作业 - -### 3.3 验收(DoD) - -- API 提交 PPO,返回 submission id;输出目录为 `/mnt/shared/jobs//...` -- API 查询 job 状态与 driver node(必须是 worker) -- 停止 job 后,资源释放、状态可见 - ---- - -## 4. MVP v2.1(SSH 纳管 + 资源池 + Gang 约束) - -> 目标:对齐你草稿里“SSH 纳管”的约束与需求:控制面能纳管 GPU 节点,形成可运营的资源池。 - -### 4.1 节点纳管(SSH Provisioner) - -- 控制面保存 NodeSpec(ip/user/port/labels/gpu_count) -- 通过 SSH 执行: - - `ray start --address=:6379 --resources=...` - - `ray stop`(drain/下线) -- 维护节点状态机:`pending → online → draining → offline` - -### 4.2 资源池与 gang(All-or-nothing) - -- 资源池最小模型: - - pool 标签(如 `pool_a`、`h20`、`ib_domain_1`) - - 提交 job 时指定 pool 约束 -- Gang 约束(MVP 实现方式): - - job spec 明确 `trainer.nnodes` + `trainer.n_gpus_per_node` - - 提交前检查 Ray 可用资源是否满足,不满足则进入 pending 队列(见 v3.0) - -### 4.3 验收(DoD) - -- 通过 API 注册 2 个 worker(SSH 注入 ray start)后,`ray status` 可见节点上线 -- 通过 API 下线节点,节点被标记不可调度且不再分配新 job -- gang 不满足时 job 不提交(或提交后一直 pending),满足后可运行 - ---- - -## 5. MVP v3.0(调度与多用户:队列 + 超时 + 最小权限) - -> 目标:平台开始“像个平台”:多用户、队列、超时、审计。仍然不做复杂配额/公平调度。 - -### 5.1 作业队列(简单但可用) - -- FIFO 队列:无优先级 -- “资源满足就调度”:谁先满足谁先跑(可接受非严格 FIFO) -- job 超时:Ray 原生不支持统一 timeout(草稿已指出),因此控制面需: - - 记录 start_time - - 定期扫描超时 job → `stop` - -### 5.2 多用户最小闭环 - -- 认证(MVP):token 或 basic auth(先不做复杂 RBAC) -- 归属与隔离(文件层): - - `/mnt/shared/users//datasets/` - - `/mnt/shared/users//models/` - - `/mnt/shared/jobs//` 记录 user/metadata - -### 5.3 验收(DoD) - -- 2 个用户可各自提交 job,能看到自己的 job 列表与输出目录 -- 超时策略可触发(模拟短 timeout),job 被停止且状态标记为 timeout -- 队列在资源不足时保持 pending,资源释放后自动运行 - ---- - -## 6. MVP v3.1(可扩展性:自定义代码/Reward、多版本 VERL) - -> 目标:把“平台内置 workload”升级成“用户可提交自定义代码与 reward”,并支持多版本并存。 - -### 6.1 自定义代码提交(最小实现) - -两种方式二选一(建议先做 A): - -- A:`working_dir` 指向 NFS 上的代码快照目录(用户自己准备/上传) -- B:上传 zip(控制面落到 NFS 并解压为 code snapshot) - -### 6.2 多版本 VERL 并存 - -约束前提:**基础镜像保持同一个**(生产环境容器由算力平台创建时已固定镜像标签)。 - -目标:在同一 Ray 集群内,不同 job 可以使用不同版本的 `verl`(例如不同分支/commit 或用户魔改版)。 - -已确认优先方案(A):**必须通过 Ray Job 的 `runtime_env.env_vars` 透传 `PYTHONPATH`**,让 job 粒度优先 import 指定代码快照。 - -建议方案(以 NFS 为中心,最小可行实现): - -- 在共享存储上以“不可变快照”的方式存放代码版本(推荐 commit hash 命名): - - `${SHARED_ROOT}/common/code/verl//...` - - `${SHARED_ROOT}/users//code/verl//...`(用户魔改版) -- JobSpec 增加 `code_path`(指向上述目录),控制面在提交 job 时注入(必须走 runtime_env): - - `runtime_env.env_vars.PYTHONPATH = ":$PYTHONPATH"`(把 code_path 放最前面,确保 import 优先级) - -示例(概念性,实际以 `${SHARED_ROOT}` 为准): - -```bash -CODE_PATH="${SHARED_ROOT}/common/code/verl/" - -ray job submit \ - --address="http://127.0.0.1:8265" \ - --submission-id="" \ - --runtime-env-json='{"env_vars": {"PYTHONPATH": "'"${CODE_PATH}"':$PYTHONPATH"}}' \ - -- \ - python3 -m verl.trainer.main_ppo ... -``` - -需要验证的关键点(作为 v3.1 的 DoD 之一): - -- 同时运行两个 job: - - jobA 使用 ``,jobB 使用 `` - - 互不影响,且各自训练/日志/ckpt 正常 -- job 粒度是否能做到“依赖隔离”(至少做到 `verl` 版本隔离;第三方依赖冲突可先假设镜像内一致) - -> 备注:当前 v1 的做法是容器内全局 `pip install -e /workspace/verl`,这会让所有 job 默认使用同一份 `verl`。要实现多版本并存,必须让 job 的 import 优先使用 `code_path`(或为每个 job 单独创建 venv/安装 wheel;后者更重,建议后置)。 - -### 6.3 自定义 reward function - -- JobSpec 支持 `reward_fn_path`(Python 模块路径) -- `reward_fn_path` 可指向共享存储中用户自定义代码目录(例如 `${SHARED_ROOT}/users//code/...`) - - 约束:代码必须在 job runtime 中可 import(由 `working_dir`/`PYTHONPATH` 或 runtime_env 保障) -- 控制面校验模块可导入(basic lint/安全白名单可后置) - -### 6.4 验收(DoD) - -- 同时运行两个 job:使用不同的 `verl` 代码版本(或用户魔改版本),互不影响 -- 用户可在 JobSpec 中替换 reward function 并跑通一个最小训练闭环 - ---- - -## 7. MVP v4.0(可观测性:Prometheus/Grafana + W&B 集成) - -> 目标:平台可运营:能回答“谁在用多少资源、跑了多久、利用率如何、是否空占 GPU”。 - -### 7.1 指标与监控 - -- Ray 指标接入 Prometheus(节点/任务/actor) -- GPU 指标:nvidia exporter 或 DCGM exporter -- Dashboard:Grafana(至少 3 张核心面板) - - 集群总 GPU/CPU 使用率、空闲率 - - 每 job 的 GPU 时间、峰值显存、运行时长 - - 节点健康(心跳/掉线)与告警 - -### 7.2 W&B(或等价)集成验证 - -- 最小可行:单机 self-host W&B server 可用性验证 -- JobSpec 支持启用/关闭 W&B,并传入 project/run name - -### 7.3 验收(DoD) - -- Grafana 上能看到集群与 job 资源视图 -- 某个 job GPU 利用率异常(模拟)能触发告警规则(邮件/IM/日志即可) -- W&B 指标能按 job 维度归档(至少 PPO 能上报) - ---- - -## 8. MVP v4.1(运维化:SOP + 自动化运维接口) - -> 目标:把平台变成“可交接”的系统:运维动作标准化,并为智能体留出接口。 - -### 8.1 SOP 与自动化入口 - -- SOP 文档: - - 节点上线/下线 - - 故障定位(Ray session、Ray job、NCCL、OOM) - - 资源回收(停止 job、清理 ckpt) -- 自动化接口(最小): - - `/v1/ops/drain_node` - - `/v1/ops/restart_ray_head`(谨慎:需要保护与权限) - - `/v1/ops/cleanup_job_artifacts` - -### 8.2 验收(DoD) - -- 按 SOP,非开发人员可完成一次“节点上线→跑任务→下线→清理” -- 自动化接口至少能完成 1 个高频动作(如清理/停止/下线) - ---- - -## 9. MVP v5.0(Serving 与 Pipeline,偏长期) - -> 目标:训练-部署一体化:支持 model serving,并在平台内串联训练→评测→发布。 - -### 9.1 Serving - -- Ray Serve(或等价)部署模型推理服务 -- Serving 与训练共用模型库与权限(按 user/project) - -### 9.2 Pipeline(草稿里标为高级) - -- Pipeline 是对多个 job 的封装(训练→merge→eval→publish) -- 可先实现最小 DAG(两步串联)作为验证 - -### 9.3 验收(DoD) - -- 训练产物一键发布为一个可访问的推理 endpoint -- Pipeline 能自动串联并产出最终 artifact(可回滚/可追踪) - ---- - -## 10. 并行技术验证(建议尽早做) - -这些属于“跨版本”风险项,建议在 v1.1 ~ v2.0 期间尽早做: - -### 10.1 网络(IB / RoCEv2) - -- 确认环境是否支持 IB(H100)或 RoCEv2(H20) -- 跑最小 NCCL 通信验证(all-reduce / bandwidth) -- 将必要的 NCCL 环境变量注入到 job runtime_env - -### 10.2 Ray + 多节点容器约束 - -- 多容器同宿主机时的 Ray node_ip/临时目录冲突规律(已踩坑,需固化规范) -- 端口范围与防火墙策略(Ray worker 端口、dashboard、metrics) - ---- - -## 11. 已确认的约束与假设(来自讨论结论) - -这些会直接影响 v2.1(SSH 纳管)与后续多用户/存储设计: - -1) **最终形态仍以“每节点容器”运行**(不是裸机 systemd)。 - - H20 开发环境:我们可在宿主机用 `docker compose` 自建容器,并通过 SSH 进入容器调试/纳管。 - - H100 生产环境:容器由算力平台创建/回收;平台侧控制面只能 **SSH 进入这些容器** 做纳管(执行 `ray start/stop`、注入 env 等)。 -2) **认证**:内部 token 即可(MVP 阶段不对接 SSO)。 -3) **存储**:只考虑 NFS。 - - 开发环境:NFS/共享目录可通过宿主机 bind mount 提供给容器。 - - 生产环境:所有容器挂载相同 NFS,容器内共享根路径为 `/private/`(需要在实现时把“共享根路径”做成可配置项,而不是写死 `/mnt/shared`)。 -4) **网络拓扑约束**:暂不做按 IB 域/机架/拓扑的强约束调度(第 10.1 仍需验证 IB/RoCE 是否可用与配置方式,但调度不引入拓扑维度)。 -5) **共享目录分层**:在 `users//...` 之外增加一个可读写的 `common/` 目录用于共享数据/模型/代码: - - `${SHARED_ROOT}/common/datasets/` - - `${SHARED_ROOT}/common/models/` - - `${SHARED_ROOT}/common/code/` - - 权限(MVP):先默认“所有内部 token 用户可读写”,后续再细化只读/受控写。 - ---- - -## 12. 仍需你确认/讨论的问题(剩余不确定项) - -1) `runtime_env.env_vars` 注入对“子进程/训练框架内部启动进程”的覆盖范围是否足够? - - 需要确认 `verl`/`sglang` 等子进程是否继承 driver 的环境变量(通常会继承,但建议在 v3.1 验收时明确验证)。 diff --git a/specs/mvp/mvp_roadmap_v2.md b/specs/mvp/mvp_roadmap_v2.md deleted file mode 100644 index d6704d4..0000000 --- a/specs/mvp/mvp_roadmap_v2.md +++ /dev/null @@ -1,133 +0,0 @@ -这一版的设计采用了 **Overlay 架构 + GPFS 核心存储 + 无状态(Stateless)节点池** 的模式,逻辑非常自洽且具备极高的云原生弹性。 - ---- - -### **项目代号:AI Infra Overlay Platform (Stateless Ray + GPFS)** - -#### **阶段一:内核构建与验证 (Kernel & Verification)** - -*目标:验证核心计算逻辑,跑通“提交-执行”的最小闭环。* - -* **v1.1: 原型验证 (Verl Task Spec & Ray Job)** -* **核心功能**:实现基础的任务定义与提交。 -* **组件**: -* `Ray Job Tool (Ray Client)`:客户端工具。 -* `VerlTaskSpec YAML`:定义多代码路径 (Multi-Verl Code Path) 和任务参数。 - - -* **基础设施**:Handmade Ray Cluster(手工搭建的集群),用于验证核心代码。 - - -* **v2.0: 任务管理层 (Task Management)** -* **核心功能**:引入服务端,管理任务生命周期。 -* **新增组件**: -* `API Server`:统一接口层。 -* `Task Management`:实现任务的队列 (Queue)、映射 (Map) 和重试 (Resubmit) 机制。 - - -* **基础设施**:仍运行在手工集群上,但控制面开始服务化。 - - - ---- - -### **阶段二:架构质变 - 无状态节点池 (The Stateless Shift)** - -*目标:通过 GPFS 实现控制反转 (IoC),彻底解耦平台层与计算节点层。这是本架构最关键的转折点。* - -* **v2.5: 用户管理 & 无状态 Ray 节点池 (User Mgmt & Stateless Ray Node Pool)** * **核心机制:基于 GPFS 的服务发现 (Service Discovery)** -* **Ray Head (有状态)**:由 `Node Management` 启动(通常通过 SSH 或 K8s StatefulSet)。启动后,将自身的 IP 地址写入 GPFS 中的 `Head IP File`。 -* **Ray Worker (无状态)**: -* **Stateless**:Worker 容器启动时不依赖平台指令。 -* **Auto Connect**:启动脚本读取 GPFS 中的 `Head IP File`,获得 Head 地址并自动加入集群。 -* **Watchdog**:Worker 内部运行看门狗进程,监控 Head IP 变化。如果 Head 变动,Worker 自动重启或重连,实现自愈。 -* **新增组件**: -* `User Management`:多用户隔离。 -* `GPFS`:取代了之前的 JuiceFS,作为唯一的共享存储和元数据交换媒介。 - - - - - ---- - -### **阶段三:产品化与高级能力 (Productization & Advanced Features)** - -*目标:发布首个正式版本,并支持大模型训练所需的复杂网络与推理能力。* - -* **v3.0: 正式发布版 (Release v1.0)** * **里程碑**:**1st Version to Release!!** -* **核心功能**:闭环用户数据流。 -* **新增组件**: -* `WebUI`:可视化操作界面。 -* `Data Management (SFTPGo)`:用户上传数据/代码 -> SFTPGo -> 写入 GPFS -> Ray Worker 可见。 - - -* **基础设施**:全量切换到 `Ray Worker Node` (Stateless) + `GPFS` 的架构。 - - -* **v3.5: 高级定制与训推一体 (Advanced Task & Serving)** * **核心功能**:支持复杂的科研需求。 -* **新增组件**: -* `Model Serving`:支持模型推理服务。 -* `Advanced VerlTaskSpec`:支持自定义 Reward Function、自定义代码、Checkpoint 断点续训 (Resubmit from last checkpoint)。 - - -* **网络增强**: -* **IB Network Supporting**:支持 InfiniBand 网络,确保多机训练的高性能互联。 - - - - - ---- - -### **阶段四:全链路可观测性 (Full-Stack Observability)** - -*目标:打开黑盒,监控基础设施与业务指标。* - -* **v4.0: 系统级可观测性 (System Observability)** * **核心功能**:监控集群“活着”且“健康”。 -* **新增组件**: -* `Prometheus` + `Grafana` + `ELK`:指标与日志平台。 -* `Exporter`:部署在 Ray Worker Node 中的监控探针(采集 GPU/CPU/GPFS IO 指标)。 - - - - -* **v4.5: 算法级可观测性 (ML Observability)** * **核心功能**:监控模型“练得好不好”。 -* **新增组件**: -* `Weights & Bias (WanB)`:集成实验追踪工具,记录 Loss 曲线和训练参数。 - - - - - ---- - -### **阶段五:智能化运维 (AIOps)** - -*目标:迈向自动化与自治。* - -* **v5.0: 智能运维闭环 (Operability)** * **核心功能**:降低运维成本,提升稳定性。 -* **新增组件**: -* `Statistics`:集群资源利用率统计报表。 -* `SOP Tools`:标准运维工具(如自动清理 GPFS 垃圾文件、僵尸节点检测)。 -* `Agent`:智能运维助手(基于 LLM 的日志分析与故障诊断)。 - - - - - ---- - -### **新架构核心亮点总结** - -1. **极简的节点管理**: -* 利用 v2.5 的 **Head IP File + Watchdog** 机制,平台层不再需要维护复杂的 Worker IP 列表和 SSH 连接池。 -* **扩缩容极其简单**:只需在底层(K8s/Docker)增加 Worker 副本数,它们就会自动通过 GPFS 找到 Head 并加入战斗。 - - -2. **统一的数据平面 (GPFS)**: -* 从 v2.5 开始,GPFS 承担了 **数据存储** (Code/Data)、**状态同步** (Head IP) 和 **检查点存储** (Checkpoints) 三大职责,架构非常收敛。 - - -3. **高弹性 (Resilience)**: -* Worker 的 **Watchdog** 机制确保了当 Head 重启或网络抖动时,集群具备自我修复能力,无需人工干预。 \ No newline at end of file diff --git a/specs/mvp/refactor/code_refactor.md b/specs/mvp/refactor/code_refactor.md deleted file mode 100644 index 58ea4f6..0000000 --- a/specs/mvp/refactor/code_refactor.md +++ /dev/null @@ -1,301 +0,0 @@ -# MVP 代码结构重构方案(按功能模块划分) - -背景:当前 `src/mvp/` 下以 `v1.1/`、`v2.0/` 版本目录来组织代码。实际上 **v2.0 是在 v1.1 的 Ray Jobs SDK 提交链路基础上扩展了服务层**,并且为了让 v2.0 工作又对 v1.1 的 `docker-compose.yaml`、`dev.yaml` 做了修改(挂载 v2、开放 8080、增加 `v2:` 配置段)。因此“按版本分目录”会让依赖关系变得不清晰(谁是库、谁是应用、哪些配置是共享的)。 - -本方案目标:把 `src/mvp/` 重构为“按功能模块”划分(ray 提交核心库 / service 服务层 / cli 工具 / TaskSpecs / configs / scripts),并给出迁移后的验证与执行方案。 - -> 本文仅给出设计与迁移/验证方案,不直接改代码(待确认后再实施)。 - ---- - -## 1. 现状梳理(问题点) - -### 1.1 代码重复与耦合 - -- `src/mvp/v2.0/py/mvp_v11/` 是从 `src/mvp/v1.1/py/mvp_v11/` 复制而来用于复用,但这导致: - - **库代码重复**(修 bug 要改两份) - - 谁是“权威实现”不明确 -- v2 API(`mvp_v2`)通过引用复制的 `mvp_v11.RayJobTool` 来提交 Ray Job,本质上依赖 v1.1 提交链路作为“库”。 - -### 1.2 配置与部署目录不稳定 - -- v2.0 复用了 v1.1 config 文件并新增 `v2:` section,这是合理的“向后兼容扩展”,但它把: - - “Ray submit 基础配置” - - “API 服务配置” - - “部署路径约定(/workspace/mvp/v1.1 vs /workspace/mvp/v2)” - 混在一个文件里,不利于长期维护。 - -### 1.3 命名歧义:jobspec 与 Ray job - -- v1.1/v2.0 都使用 `jobspec.yaml` 指代“训练语义参数”(PPO/GRPO/SFT 的训练字段)。 -- 但 Ray 也有 “Ray Job” 概念(submission_id、entrypoint、runtime_env 等),易造成沟通误解。 -- 需要把训练侧 specs 改名为 **TaskSpecs**(代表平台级任务规范),与 Ray Job 区分。 - ---- - -## 2. 重构目标(What good looks like) - -### 2.1 目录与职责清晰 - -- “提交 Ray Job 的 SDK 封装”是一个可复用模块(库)。 -- “服务层(API + scheduler + SQLite)”是一个独立模块(应用/服务)。 -- “训练语义参数(TaskSpecs)”与 “Ray Job 提交参数(RayConfig)”分层清楚。 - -### 2.2 单一真源(Single Source of Truth) - -- 只能有一份“Ray submitter core”实现(不能复制一份到另一个版本目录)。 -- API 与 CLI/脚本都复用同一份 core。 - -### 2.3 兼容现有运行方式(渐进迁移) - -- 保留现有的脚本式启动/准备流程(Ray 起集群、准备模型/数据仍用 scripts)。 -- 允许在迁移期提供薄 wrapper 兼容旧路径(减少一次性 break)。 - ---- - -## 3. 目标结构(按功能模块划分) - -建议把 `src/mvp/` 重构为下面的“功能分层”: - -``` -src/mvp/ - py/ - argus/ # 顶层包(避免与 Ray 的 `ray` 包冲突) - __init__.py - - core/ # 通用:yaml/模型定义/工具函数(纯库) - __init__.py - yaml_io.py - ids.py # task_id / attempt_id 生成规则 - - ray/ # Ray Job 提交“核心库”(由现成 mvp_v11 迁移而来) - __init__.py - models.py # RayConfig, TaskSpec(解析), Attempt, enums - builders.py # build_training_argv (ppo/grpo/sft) - driver_entrypoint.py # 仍然作为 Ray job entrypoint(worker 上执行) - ray_job_tool.py # Ray Jobs SDK 封装(submit/status/stop/logs) - runtime_env.py # 统一 PYTHONPATH/runtime_env 组装逻辑 - - service/ # 服务层:FastAPI + scheduler + sqlite(应用) - __init__.py - app.py - scheduler.py - db.py - config.py # service 相关配置读取(从 configs 读取) - ray_resources.py - - cli/ # 命令行/SDK 提交入口(由现成 v1.1 run.py 迁移而来) - __init__.py - run.py # submit/status/logs/stop 等 action - - server.py # uvicorn 入口(导入 argus.service.*) - - configs/ - dev.yaml # RayConfig + ServiceConfig(按层次组织、可扩展) - prod.yaml # (可选)生产配置模板 - - taskspecs/ # 原 jobspecs/,改名 TaskSpecs(训练语义规范) - ppo.yaml - grpo.yaml - sft.yaml - README.md # TaskSpec 字段解释、示例 - - scripts/ # 宿主机脚本(docker exec/compose 编排) - lib.sh - 00_prereq_check.sh - 01_up.sh / 02_down.sh - 20_start_head.sh / 21_start_workers.sh - 30_prepare_data_and_model.sh - 40_submit_cli.sh # 通过 cli/run.py 提交 TaskSpec - 60_start_api.sh # 启动 API(service) - 61_stop_api.sh - 62_status_api.sh - - docker-compose.yaml # dev 环境 compose(从 v1.1 迁移到这里,路径稳定) - README.md # 总入口文档(运行方式、目录约定) -``` - -### 3.1 关键点:库 vs 应用边界 - -- `argus.ray` 是唯一的 Ray submitter 库(替代当前 v1.1/v2.0 的 `mvp_v11` 双份拷贝)。 -- `argus.service` 依赖 `argus.ray`,不反向依赖。 -- `argus.cli` 依赖 `argus.ray`,用于脚本化提交/调试。 - -### 3.2 TaskSpecs vs RayConfig - -- `taskspecs/*.yaml`:描述训练任务语义参数(workload、nnodes、n_gpus_per_node、数据/模型路径、训练步数等)。 -- `configs/*.yaml`:描述 Ray 提交环境(address、entrypoint_resources、runtime_env 以及 service 配置)。 - ---- - -## 4. 配置策略(重构后如何组织 configs) - -### 4.1 建议的 config 分层 - -把当前 `dev.yaml` 的内容明确分为两段(按模块名分段): - -1) `ray:`(RayConfig) -- job server address -- shared_root(`/private`) -- entrypoint resources(强制 driver 落 worker) -- runtime_env env_vars(HF cache、PYTHONPATH 注入策略) - -2) `service:`(ServiceConfig) -- api host/port -- auth token_env -- sqlite db_path -- scheduler tick/max_running/retry_interval - -示例(结构示意): - -```yaml -ray: - address: "http://127.0.0.1:8265" - shared_root: "/private" - entrypoint_num_cpus: 1 - entrypoint_resources: - worker_node: 1 - runtime_env: - env_vars: - HF_ENDPOINT: "https://hf-mirror.com" - PYTHONUNBUFFERED: "1" - user_code_path: "/private/user/code" - -service: - api: - host: "0.0.0.0" - port: 8080 - auth: - token_env: "MVP_INTERNAL_TOKEN" - sqlite: - db_path: "/private/common/db/mvp.sqlite3" - scheduler: - tick_s: 5 - retry_interval_s: 60 - max_running_tasks: 1 -``` - -> 迁移期可以支持“旧格式”(v1.1 顶层字段 + v2: 段)与“新格式”(ray:/service: 两段)并存:解析时兼容读取,降低一次性改动风险;但最终以新格式为准。 - ---- - -## 5. 迁移路径(推荐分两阶段实施) - -### 阶段 A:先拷贝/迁移现成文件,再做最小调整(保持行为不变) - -目标:不改功能、不改 API 行为。优先通过“拷贝/迁移现成文件 + 修正包引用/路径”完成重构,避免重头重写逻辑(降低出错概率)。 - -建议步骤: - -1) 抽出 `src/mvp/py/argus/ray/`(由现成代码迁移) - - 将 `src/mvp/v1.1/py/mvp_v11/` 迁移到 `src/mvp/py/argus/ray/`,并把它作为 submitter core 的唯一真源(不再保留一份复制品在其它目录)。 - - 只做机械化调整:修正 import、修正默认路径常量(例如 tool code path / working dir)、修正 scripts 的调用路径。 - -2) 抽出 `src/mvp/py/argus/service/`(由现成代码迁移) - - 将 `src/mvp/v2.0/py/mvp_v2/` 迁移到 `src/mvp/py/argus/service/`。 - - service 侧对 submitter 的依赖统一改为 `src/mvp/py/argus/ray/`(不再引用 `src/mvp/v2.0/py/mvp_v11/` 的复制品)。 - -3) CLI 统一入口:`src/mvp/py/argus/cli/run.py`(由现成代码迁移) - - 将 `src/mvp/v1.1/py/run.py` 迁移到 `src/mvp/py/argus/cli/run.py`,保留 action 语义(submit/status/logs/stop)。 - - 仅调整 import 与默认路径,使其指向新目录(configs/taskspecs/py)。 - -4) scripts 合并(以 v1.1 为基、合入 v2 API) - - 将 `src/mvp/v1.1/scripts/` 迁移到 `src/mvp/scripts/`(Ray 集群编排最成熟)。 - - 将 `src/mvp/v2.0/scripts/` 的 API 启停脚本合入 `src/mvp/scripts/`,并统一命名与默认路径。 - -5) docker-compose / mounts 稳定化(你已确认要迁移) - - 将 `src/mvp/v1.1/docker-compose.yaml` 迁移为 `src/mvp/docker-compose.yaml`。 - - 容器内挂载统一:宿主机 `.../src/mvp/` → 容器 `/workspace/mvp/`(包含 `py/ configs/ taskspecs/ scripts/`)。 - - runtime_env 的 `PYTHONPATH` 注入统一指向 `/workspace/mvp/py`(不再出现 `/workspace/mvp/v1.1/py`、`/workspace/mvp/v2/...`)。 - -阶段 A 完成标准: -- 原来 v1.1 的 CLI 提交方式仍可用(提交 PPO/GRPO/SFT)。 -- v2 API 仍可用(队列、取消、日志)。 -- 不再存在 `mvp_v11` 的重复目录。 - -### 阶段 B:配置格式升级(按模块两段)+ TaskSpecs 更名落地 - -目标:把 jobspec 真正改名为 TaskSpec,并把 config 升级为按模块两段(`ray:`/`service:`)清晰分层。 - -建议步骤: -- `jobspecs/` → `taskspecs/`,并更新 README/脚本引用。 -- `dev.yaml` 从“顶层字段 + v2:”迁移为“ray:/service:”两段。 -- 保留一段时间的兼容解析逻辑(读取旧格式时发出 warning)。 -- 完成验证后删除旧版本目录:`src/mvp/v1.1/`、`src/mvp/v2.0/`(以及远端对应目录),确保新结构成为唯一入口。 - -阶段 B 完成标准: -- docs 里不再出现 “jobspec” 词汇,统一称 “TaskSpec”。 -- `configs/dev.yaml` 分层清晰(`ray:`/`service:` 两段按模块名),服务与 Ray 的配置互不干扰。 - ---- - -## 6. 重构后的验证与执行方案(验收/回归) - -### 6.1 本地(仓库内)静态验证 - -1) import / 入口检查(在容器环境) -- `python3 -c "from argus.ray.ray_job_tool import RayJobTool"` -- `python3 -c "from argus.service.app import create_app"` - -2) 目录结构检查 -- 确保 `src/mvp/py` 是唯一 python 代码根 -- 确保 `taskspecs/`、`configs/`、`scripts/` 都在 `src/mvp/` 下 - -### 6.2 dev 环境(argus@h1)端到端验证 - -前置: -- 远端目录:`argus@h1:/home2/argus/infra/mvp/`(维持不变) -- 共享目录:`/home2/argus/infra/mvp/shared` 挂载到容器 `/private` - -验证步骤(推荐顺序): - -1) 重新拉起容器 + 启动 Ray -- `scripts/01_up.sh` -- `scripts/20_start_head.sh`(head `--num-cpus=0 --num-gpus=0`) -- `scripts/21_start_workers.sh`(workers 带 `worker_node` 资源) -- `ray status` / `ray list nodes` 确认 head 无 GPU、workers 各 4 GPU - -2) CLI 提交回归(等价 v1.1) -- 提交 `taskspecs/sft.yaml`,确认成功 -- 提交 `taskspecs/grpo.yaml`,确认成功 -- 提交 `taskspecs/ppo.yaml`,确认成功 - -3) API 服务回归(等价 v2.0) -- `scripts/60_start_api.sh` -- `POST /api/v2/tasks`(raw YAML TaskSpec) -- `GET /api/v2/tasks/{task_id}`:确认返回 `created_at/updated_at` -- `POST /api/v2/tasks/{task_id}:cancel`:确认任务 `state=CANCELED` 且 attempt `ray_status=STOPPED`(服务侧语义一致) - -4) 队列行为回归 -- 在 `service.scheduler.max_running_tasks=1` 下: - - 连续提交两个 8-GPU 任务:第二个应保持 `QUEUED/PENDING_RESOURCES`,直到第一个结束后自动提交。 - -验收标准: -- 三种 workload(PPO/GRPO/SFT)都能通过 CLI 跑通(或至少能正确提交到 Ray 并进入 RUNNING)。 -- API 提交/查询/取消/日志正常。 -- “cancel 后 state=CANCELED 但 attempt 仍 RUNNING”的不一致问题不再出现。 - ---- - -## 7. 风险与注意事项 - -1) PYTHONPATH 注入路径变化 -- 当前 runtime_env 里有 `MVP_TOOL_CODE_PATH=/workspace/mvp/v1.1/py` 的历史路径假设; -- 重构后需统一为 `/workspace/mvp/py`,并确保所有容器都挂载到相同路径。 - -2) SQLite WAL 在 NFS 上的稳定性 -- 目前 db 使用 WAL(生成 `-wal/-shm`),NFS 下可能有一致性风险; -- 可作为后续优化:检测 NFS 时退回 `journal_mode=DELETE` 或换成单机本地盘。 - -3) 渐进迁移的兼容期 -- 迁移期可以短暂保留旧路径(例如 `src/mvp/v1.1`、`src/mvp/v2.0` 仅保留 README 指向新路径)以减少一次性断裂;但你已确认最终会删除这两个目录,因此需要在 scripts/文档同步更新后尽快清理。 - ---- - -## 8. 已确认约束(将按此实施) - -你已明确: - -1) `docker-compose.yaml` 必须迁移到 `src/mvp/` 根;重构完成后 `src/mvp/v1.1`、`src/mvp/v2.0` 都会删除。 -2) `configs/dev.yaml` 升级为两段,按模块名分段:`ray:` 与 `service:`;并保持纯 YAML 风格(不混用 JSON inline map)。 -3) TaskSpec 字段先保持与现有 v1.1 YAML 完全一致(仅目录与命名变化),避免引入不必要的不兼容。 diff --git a/specs/mvp/remain_problems.md b/specs/mvp/remain_problems.md deleted file mode 100644 index 44510aa..0000000 --- a/specs/mvp/remain_problems.md +++ /dev/null @@ -1,27 +0,0 @@ - -# v3.6 -wandb 映射目录是/vol 固定问题: -查过官方文档/公开资料后结论是:wandb/local(W&B local server 容器)没有提供“把服务端持 - 久化根目录从 /vol 改成别的路径”的官方环境变量/启动参数。官方用法一直是假设你把持久化卷 - 挂到容器内的固定路径 /vol(例如 -v :/vol)。(github.com (https://github.com/ - wandb/server)) - - 需要注意区分两类“目录”: - - - 服务端(wandb/local 容器):持久化目录是容器内固定 /vol,用于保存实例元数据、账号/初 - 始化信息等(license 也可以用 env 配,但数据目录仍是 /vol)。(github.com (https:// - github.com/wandb/server)) - - 训练侧(wandb Python SDK / VERL 任务):WANDB_DIR、WANDB_DATA_DIR 等环境变量只影响“客 - 户端本地生成文件/缓存”,不改变服务端容器的数据落盘路径。(docs.wandb.ai (https:// - docs.wandb.ai/platform/hosting/env-vars)) - - 所以如果你现在的约束是“只能挂 ../../shared:/private,不能再额外挂 ../../shared/common/ - wandb:/vol”,要把 W&B 服务端数据落到 shared 下面,现实可行的路子是: - - - 自定义 W&B 容器 entrypoint(或 wrapper)在启动前做一次 ln -s /private/common/wandb / - vol(或 bind-mount 到 /vol),让服务仍然写 /vol,但实际落到 /private/common/wandb。 - 这属于“容器层改造”,不是 W&B 官方参数。 - - 如果你允许 compose 再加一条 volume,那最简单仍是:保留 ../../shared:/private,再额外 - 加 ../../shared/common/wandb:/vol(服务端就无需任何改造)。 - diff --git a/specs/mvp/v1.1/mvp_plan.md b/specs/mvp/v1.1/mvp_plan.md deleted file mode 100644 index 99dbbc9..0000000 --- a/specs/mvp/v1.1/mvp_plan.md +++ /dev/null @@ -1,169 +0,0 @@ -# MVP v1.1 计划(Hardening + 多 Workload 可行性验证) - -本目录是 `specs/mvp/v1/` 的下一步迭代:在 v1 已经跑通(Ray head + 2 worker,PPO on Ray,持久化落盘)的基础上,把它升级为**可长期回归**的最小系统,并扩展至少一个新 workload 的可行性闭环。 - -> v1.1 的目标不是做平台服务化(API/队列/多用户)——那是 v2/v3 的工作;v1.1 聚焦“工程化 + 可行性边界验证 + 可观测/可排障基础”。 - ---- - -## 1. v1 基线回顾(已完成) - -- 拓扑:1 head(无 GPU,CPU/GPU=0)+ 2 worker(各 4 GPU) -- 提交方式:必须用 head 上的 `ray job submit` -- driver 调度:通过 `worker_node` 自定义资源 + `--entrypoint-resources` 强制 driver 在 worker -- 输出:按 `submission_id` 组织到共享目录(NFS) - -相关实现参考: - -- 脚本:`src/mvp/v1/` -- 验收动作:`specs/mvp/v1/v1_action.md` -- Roadmap:`specs/mvp/mvp_roadmap.md` - ---- - -## 2. v1.1 目标(必须达成) - -### 2.1 工程化(Hardening) - -1) **JobSpec 标准化(最小)** - - 把“提交 job 需要的参数”收敛成结构化文件: - - Ray 基础配置(YAML):cluster 地址、entrypoint 资源约束、runtime_env 等 - - 训练 JobSpec(YAML):workload 语义与训练参数 - - 至少覆盖:`submission_id`、workload 类型、资源需求、共享根路径、模型/数据路径、输出目录、超时、环境变量注入。 - - v1.1 实现落点(已在 repo 里提供,SDK 方式): - - RayConfig 示例:`src/mvp/v1.1/py/configs/dev.yaml` - - JobSpec 示例:`src/mvp/v1.1/py/jobspecs/{ppo,grpo,sft}.yaml` - - 提交入口:`src/mvp/v1.1/py/run.py`(在 head 容器内执行,使用 Ray Python SDK 提交) - - 设计文档:`specs/mvp/v1.1/sdk_submit_refactor.md` - -2) **共享根路径抽象(dev/prod 一致)** - - 引入 `SHARED_ROOT` 作为唯一共享根路径: - - dev:建议也用 `/private`(docker compose 把宿主机 shared 挂到容器内 `/private`,模拟生产) - - prod:固定 `/private`(算力平台容器内 NFS) - - 任何代码/脚本不得写死 `/mnt/shared`(允许兼容旧路径但不得作为主路径)。 - -3) **共享目录分层(新增 `common/` 与 `user/`)** - - 在 `datasets/hf/jobs/outputs` 之外,新增一个所有用户可读写的共享区: - - `${SHARED_ROOT}/common/`:共享模型/数据/代码快照(多版本 verl / 公共数据) - - `${SHARED_ROOT}/user/`:用户自定义代码(例如 `reward_fn_path` 指向这里) - - v1.1 默认策略:先假设“所有用户可写”(后续 v3 再做权限与隔离)。 - -4) **可排障基础** - - 每个 job 目录必须有: - - `config/`:提交命令、JobSpec 快照、关键 env_vars - - `logs/`:Ray job logs + hydra logs(如有) - - `checkpoints/`:按 `save_freq` 控制频率(默认每 10 step) - - 提供“失败快照”能力:收集 `ray status` / `ray job list` / `ray list nodes` / `ray list actors`(最少其中 2 项)写入 job 目录。 - - v1.1 submitter 默认落盘: - - `${SHARED_ROOT}/jobs//config/job_spec.json` - - `${SHARED_ROOT}/jobs//config/runtime_env.json` - - `${SHARED_ROOT}/jobs//config/submit_cmd.txt` - - `${SHARED_ROOT}/jobs//logs/ray_job_submit.out` - - `${SHARED_ROOT}/jobs//debug/ray_status_{pre,post}.txt` - - `${SHARED_ROOT}/jobs//debug/ray_job_list_post.txt` - -### 2.2 Workload 扩展(至少新增 1 个) - -v1.1 需要新增并验收通过两个 workload(都要跑通闭环): - -- **GRPO on Ray**(推荐优先,复用 PPO 入口,通过算法配置切换) - - 基于 `python -m verl.trainer.main_ppo` - - 通过配置覆盖:`algorithm.adv_estimator=grpo`(以及必要的 rollout 参数) - - - **SFT on Ray(Ray-native)** - - 入口:`python -m verl.trainer.sft_trainer_ray` - - 参考实现:`verl/verl/trainer/sft_trainer_ray.py`(内部会 `ray.init()`) - - 需要确保 `ray.init()` 连接已有集群: - - 优先:`runtime_env.env_vars.RAY_ADDRESS=auto`(配合 `ray job submit`) - - 兜底:在 v1.1 的 launcher 脚本里显式 `ray.init(address="auto")` 再调用 trainer(避免依赖 Ray 的 env var 行为差异) - - 重要细节:Ray Job 的 entrypoint(driver)默认不分配 GPU,因此 SFT driver 侧不要强依赖 CUDA: - - 推荐:`trainer.device=cpu`(driver 只做 orchestration;训练由 Ray workers 占 GPU) - ---- - -## 3. v1.1 关键设计点 - -### 3.1 多版本代码与自定义逻辑(为 v3.1 铺路,但 v1.1 先做最小验证) - -已确定优先方案(A):通过 **Ray Job 的 `runtime_env.env_vars`** 注入 `PYTHONPATH`。 - -- `code_path`(例如 `${SHARED_ROOT}/common/code/verl/`) -- 提交 job 时设置: - - `runtime_env.env_vars.PYTHONPATH = ":$PYTHONPATH"` - -并约定: - -- `reward_fn_path` 可指向 `${SHARED_ROOT}/user/code/...` 下用户自定义代码 -- 与 `code_path` 一样,必须通过 `runtime_env.env_vars` 确保该路径可被 import(例如把 `${SHARED_ROOT}/user/code` 也加入 `PYTHONPATH`) - -v1.1 中至少做一次“代码覆盖验证”: - -- 在 code_path 下放一个可识别的 `verl` 版本标识(例如 `verl.__version__` 打印差异) -- 提交 job 并在日志中确认 import 的是 code_path 的版本(而不是镜像内默认安装) - -v1.1 的最小落地方式(已实现): - -- 提供代码快照脚本:`src/mvp/v1.1/scripts/31_snapshot_verl_code.sh` - - 会把 `/workspace/verl`(挂载的 repo)复制到 `${SHARED_ROOT}/common/code/verl//` - - 并写入 `${code_path}/mvp_marker.py`,用于在 Ray job logs 中验证“选用的是哪份 code_path” -- submitter 会在 entrypoint 前运行 preflight: - - 打印 `verl.__file__` 与 `mvp_marker.MARKER` - - 由此确认 job 粒度的 PYTHONPATH 生效,且不同 job 可指向不同 `code_path`(多版本共存) - -### 3.2 Checkpoint 策略(磁盘保护) - -- 默认:`save_freq=10`(每 10 step 保存一次) -- 对于 step 数已知的短任务(例如 29 steps),可以通过配置把 `save_freq` 调整为 10/15/29(按需求权衡) -- 作业目录按 `submission_id` 隔离,方便清理与归档 - ---- - -## 4. v1.1 交付物清单(代码 + 文档) - -### 4.1 代码(建议落点) - -在 `src/mvp/` 下新增 v1.1 级别的提交器与模板(或在 `src/mvp/v1` 原地演进但要保持 v1 可回归): - -- `src/mvp/v1.1/` - - `docker-compose.yaml`(与 v1 互不干扰的容器名/网络名) - - `scripts/`(Ray 启动/prepare 保留 bash;submit 通过 SDK 工具执行) - - `py/`(工程化提交层:YAML + Ray Python SDK) - - `py/configs/`(Ray 基础配置) - - `py/jobspecs/`(训练 JobSpec) - - `py/run.py`(入口) - -此外,为了对齐 dev 环境约束(远程机固定目录): - -- 远程机目录必须新增:`argus@h1:/home2/argus/infra/mvp/v1.1/` -- 该目录内需包含 v1.1 的全部内容(compose + scripts + README),可由本 repo 的 `src/mvp/v1.1/` 同步过去 - -### 4.2 文档 - -- `specs/mvp/v1.1/v1.1_action.md`:开发、部署、测试、验收流程(可复现) -- 更新 `specs/mvp/mvp_roadmap.md`:保持路线图与落地一致(按需) - ---- - -## 5. v1.1 验收标准(DoD) - -### 5.1 Hardening DoD - -- [ ] 所有提交均由 head 执行 `ray job submit`,且显式 `--submission-id=` -- [ ] 共享根路径由 `SHARED_ROOT` 控制(dev/prod 可切换),脚本无硬编码 -- [ ] 每个 job 的输出目录为:`${SHARED_ROOT}/jobs//` -- [ ] checkpoint 不会“每 step 保存”导致爆盘:默认 `save_freq=10` -- [ ] job 失败时,`${SHARED_ROOT}/jobs//config/` 中有足够信息定位(命令、env、ray 状态快照) - - [ ] v1.1 测试前会清理 v1 的遗留容器/进程(避免端口、容器名、Ray session 干扰) - -### 5.2 Workload DoD(GRPO + SFT 都必须) - -GRPO(必须): - -- [ ] `algorithm.adv_estimator=grpo` 的 job 可提交并进入 RUNNING -- [ ] job 能跑完最小训练步数(可设 `total_epochs=1` 或 `total_training_steps`) -- [ ] 输出目录内有日志与至少 1 次 checkpoint(或明确不保存并说明原因) - -SFT(必须): - -- [ ] `sft_trainer_ray` 可连接集群并跑到至少 1 个 step(推荐最小训练步数/epoch) -- [ ] 输出目录与 checkpoint 策略同 v1.1 规范(落盘到 `${SHARED_ROOT}/jobs//...`) diff --git a/specs/mvp/v1.1/sdk_submit_refactor.md b/specs/mvp/v1.1/sdk_submit_refactor.md deleted file mode 100644 index 9c6412b..0000000 --- a/specs/mvp/v1.1/sdk_submit_refactor.md +++ /dev/null @@ -1,148 +0,0 @@ -# MVP v1.1 工程化重构方案:Ray Python SDK 提交层(YAML Config + YAML JobSpec) - -本文档把 v1.1 的“代码工程化”目标落到一个明确的设计:**保留现有 scripts**(Ray 集群构建、数据准备、模型准备、代码快照),将“任务提交机制”重构为 **Ray Python SDK**(`ray.job_submission.JobSubmissionClient`)驱动的 Python 工具层。 - -> 约束(已确认) -> 1) 基础配置用 YAML,JobSpec 也用 YAML。 -> 2) 工具必须在 **head 容器**执行(从 head 发起提交,满足“在 head 提交”的要求)。 -> 3) 训练参数组织保持与现在一致:仍然使用 **Hydra overrides** 方式构造 entrypoint。 -> 4) 不使用 `requests` 直连 HTTP API(只用 Ray SDK)。 - ---- - -## 1. 当前 Ray SDK 能力验证(关键前提) - -在 head 容器(`mvp11-ray-head`)中验证: - -- Ray 版本:`2.51.1` -- `JobSubmissionClient.submit_job` 支持以下关键字段: - - `submission_id` - - `runtime_env` - - `entrypoint_num_cpus` - - `entrypoint_num_gpus` - - `entrypoint_resources`(用于强制 driver 落 worker) - -因此 v1.1 可以“纯 SDK”完成提交,不需要 `requests` fallback。 - ---- - -## 2. 系统分层(不动 scripts,只重构提交层) - -### 2.1 scripts(保留) - -`src/mvp/v1.1/scripts/` 继续负责: - -- 容器生命周期:`01_up.sh` / `02_down.sh` -- Ray 启动:`20_start_head.sh` / `21_start_workers.sh` -- 数据/模型准备:`30_prepare_data_and_model.sh` -- 代码快照:`31_snapshot_verl_code.sh`(生成 `${SHARED_ROOT}/common/code/verl//`) - -scripts 可以新增一个“薄封装”脚本,负责 `docker exec` 进 head 容器并运行 Python 提交器,但 scripts 不再拼 `ray job submit ...` CLI 字符串。 - -### 2.2 Python 工具层(新增) - -在 `src/mvp/v1.1/py/` 新增提交工具层: - -- 读取 Ray 基础配置(YAML) -- 读取训练 JobSpec(YAML) -- 用 Ray Python SDK 提交/查询/停止/拉日志 -- 将 job 级别产物落盘到:`${SHARED_ROOT}/jobs//...` - ---- - -## 3. 输入定义:两份 YAML - -### 3.1 Ray 基础配置(RayConfig YAML) - -这份配置是“稳定可复用”的,描述 cluster 与 driver placement 等通用信息。 - -字段建议: - -- `address`: `http://127.0.0.1:8265`(从 head 容器内部视角) -- `shared_root`: `/private` -- `entrypoint_num_cpus`: `1` -- `entrypoint_resources`: `{"worker_node": 1}`(强制 driver 使用 worker 才有的资源) -- `runtime_env.env_vars`: HF cache / endpoint 等通用环境变量 -- `user_code_path`: `${shared_root}/user/code`(可选,默认值也可) - -### 3.2 训练 JobSpec(JobSpec YAML) - -这份配置是“一次训练”语义,描述 workload + 训练参数 + code_path 多版本等。 - -字段建议: - -- `workload`: `ppo|grpo|sft` -- `submission_id`: 可选(不填则生成;但最终必须显式传给 SDK) -- `code_path`: `${shared_root}/common/code/verl/`(多版本关键字段) -- `model_id` -- 数据路径:`train_file` / `val_file`(按 workload) -- 训练参数:`nnodes` / `n_gpus_per_node` / `total_training_steps` / `save_freq` / `test_freq` - -注意(SFT 的 driver 设备选择): - -- Ray job 的 entrypoint(driver)默认不分配 GPU(我们通常不设置 `entrypoint_num_gpus`)。 -- `sft_trainer_ray.py` 的 driver 会用 `trainer.device` 做张量统计;若设置为 `cuda` 且 driver 无 GPU,会报: - - `RuntimeError: No CUDA GPUs are available` -- 因此 v1.1 的 SFT JobSpec 默认应设置:`trainer.device=cpu`(训练 workers 仍会占用 GPU)。 - ---- - -## 4. Python 提交器的职责(tool class) - -建议实现 `RayJobTool`(或类似命名),能力: - -### 4.1 submit(核心) - -输入:`RayConfig + JobSpec` -输出:`submission_id` - -实现要点: - -- `client = JobSubmissionClient(address)` -- 生成/确定 `submission_id` -- `runtime_env` 合并逻辑: - - 合并 config 与 jobspec 的 `env_vars` - - 强制注入多版本: - - `PYTHONPATH = "::$PYTHONPATH"` -- 构造 entrypoint(保持 hydra overrides 风格): - - PPO/GRPO:`python3 -m verl.trainer.main_ppo ...` - - SFT:`python3 -m verl.trainer.sft_trainer_ray ...` -- 强制 driver 落 worker: - - `entrypoint_resources=config.entrypoint_resources` - - `entrypoint_num_cpus=config.entrypoint_num_cpus` -- 落盘产物: - - `${shared_root}/jobs//config/{ray_config.yaml,jobspec.yaml,submit_payload.json}` - - `${shared_root}/jobs//logs/submit.out` - - `${shared_root}/jobs//debug/{ray_status_pre,ray_job_list_post}.txt`(可用 SDK 或 `ray status` 采集) - -### 4.2 status / stop / logs / list - -- `status(submission_id)` -- `stop(submission_id)` -- `logs(submission_id)`(可支持 tail) -- `list()` - ---- - -## 5. `run.py` 入口(必须在 head 容器执行) - -建议入口: - -- `python3 /workspace/mvp/v1.1/py/run.py --config --jobspec --action submit` -- `--action` 支持:`submit|status|stop|logs|list` - -host 侧执行方式(由 scripts 薄封装): - -- `docker exec mvp11-ray-head python3 /workspace/mvp/v1.1/py/run.py ...` - ---- - -## 6. 验收口径(工程化部分) - -1) **SDK 提交**:不使用 `ray job submit` CLI,改用 `JobSubmissionClient.submit_job`。 -2) **driver 仍强制在 worker**:SDK 提交时 `entrypoint_resources={"worker_node":1}` 生效。 -3) **多版本共存验证**: - - 通过 `31_snapshot_verl_code.sh` 生成 `codeA/codeB` 两份 code_path - - 通过两份 JobSpec 分别指向不同 `code_path` - - 在 job logs 中看到不同的 marker(例如 `mvp_marker.MARKER`) - diff --git a/specs/mvp/v1.1/v1.1_action.md b/specs/mvp/v1.1/v1.1_action.md deleted file mode 100644 index cd72a7f..0000000 --- a/specs/mvp/v1.1/v1.1_action.md +++ /dev/null @@ -1,333 +0,0 @@ -# MVP v1.1 行动文档(实施方案 / 部署测试 / 验收口径) - -本文档面向“把 v1 跑通的实验脚本,升级为可长期回归的 v1.1 最小系统”,并给出**开发改造 → 部署测试 → 验收**的可复现流程。 - -> v1.1 的核心约束(来自讨论结论) -> - 仍然必须通过 **head 节点执行 `ray job submit`** 提交任务。 -> - 训练/driver **必须落在 worker**(head 不跑训练)。 -> - 多版本 `verl` 共存:同一镜像不变,必须通过 **Ray Job `runtime_env.env_vars` 注入 `PYTHONPATH`** 让 job 粒度选择代码版本。 -> - 存储只考虑 NFS:dev 环境我们自己 mount;生产环境容器内统一看到 `/private/`。 - ---- - -## 1. 目标与非目标 - -### 1.1 目标(v1.1 必须做到) - -1) **可回归**:同一环境连续跑多次 PPO 回归,不互相覆盖,输出按 submission id 归档。 -2) **可扩展**:新增并验收通过 2 个 workload(**GRPO + SFT**)并跑通闭环。 -3) **可排障**:每个 job 目录包含完整的提交快照、关键 env、Ray 状态快照与日志入口。 -4) **可多版本共存**:同一 Ray 集群内,不同 job 通过 `PYTHONPATH` 选择不同 `verl` 代码快照。 - -### 1.2 非目标(v1.1 不做) - -- 不做平台 API/队列/多租户/RBAC(这是 v2/v3)。 -- 不做复杂调度(拓扑、IB 域、NUMA、Gang 等自动化策略)。 - ---- - -## 2. 运行环境约定(dev / prod 一致抽象) - -### 2.1 拓扑(单机 3 容器) - -- `mvp-ray-head`:无 GPU,`ray start --head --num-cpus=0 --num-gpus=0`(控制面 only) -- `mvp-ray-worker-0`:4 GPU -- `mvp-ray-worker-1`:4 GPU - -### 2.2 “head 不跑训练”的硬约束实现(必须) - -1) **head CPU=0**:从资源层面阻断默认 task/driver 落到 head。 -2) **worker 自定义资源标签**:worker 启动时带 `--resources='{"worker_node": 100}'`。 -3) **ray job submit 强制 entrypoint 落 worker**:提交时必须带: - - `--entrypoint-resources='{"worker_node": 1}'` - - `--entrypoint-num-cpus=1`(显式声明 driver 需要的 CPU) - -> 验证口径:`ray job list` 的 `driver_info.node_ip_address` 必须是 worker 的 IP,而不是 head IP。 - -### 2.3 共享存储(NFS)与路径(关键) - -- 生产环境:容器内共享根路径固定为 `/private/`(算力平台统一挂载 NFS)。 -- 开发环境:docker compose 也应把宿主机共享目录挂载到容器内的 `/private/`,从而做到 dev/prod 一致。 - -统一约定(容器内视角): - -- `SHARED_ROOT=/private` -- Job 输出:`${SHARED_ROOT}/jobs//` - -建议的共享目录结构(v1.1 新增 `common/` 与 `user/`): - -- `${SHARED_ROOT}/datasets/`:通用数据(例如 gsm8k parquet) -- `${SHARED_ROOT}/hf/`:HuggingFace cache(模型/分词器/权重) -- `${SHARED_ROOT}/jobs/`:按 submission id 归档的作业目录(强制) -- `${SHARED_ROOT}/outputs/`:临时/非强约束输出(不建议长期依赖) -- `${SHARED_ROOT}/ray/`:Ray 调试痕迹(可选,通常 Ray 默认写 `/tmp/ray`) -- `${SHARED_ROOT}/common/`:所有用户可读写共享区(模型/数据/代码快照) - - `${SHARED_ROOT}/common/models/`:可复用基础模型(可用软链指向 hf cache 或 snapshot) - - `${SHARED_ROOT}/common/datasets/`:共享数据(或与 `datasets/` 统一规划) - - `${SHARED_ROOT}/common/code/`:代码快照(多版本 `verl` / 自定义 reward) -- `${SHARED_ROOT}/user/`:用户自定义内容(默认所有用户可写) - - `${SHARED_ROOT}/user/code/`:reward_fn 等自定义 Python 代码 - ---- - -## 3. 开发实施方案(代码改造清单) - -> v1.1 建议新增 `src/mvp/v1.1/`(保持 v1 可回归不被破坏)。 - -### 3.1 JobSpec(最小标准化) - -v1.1 的工程化目标是把“提交机制”迁移到 Ray Python SDK,因此输入拆为两份 YAML: - -1) Ray 基础配置(YAML):address / entrypoint resources / runtime_env 等 -2) 训练 JobSpec(YAML):workload 语义与训练参数(仍由 Hydra overrides 组织) - -训练 JobSpec(YAML)至少包含: - -- `submission_id`:可空;为空时由 submitter 生成(但最终必须显式传给 `ray job submit --submission-id`) -- `workload`:`ppo` / `grpo` / `sft`(v1.1 必须 `ppo` + `grpo` + `sft`) -- `shared_root`:默认 `/private`(容器内路径) -- `code_path`:`verl` 代码快照目录(用于多版本共存) -- `reward_fn_path`(可选):指向 `${shared_root}/user/code/...` 下的 Python 文件或模块入口 -- `model` / `dataset`:必须指向共享存储的持久化路径(避免每次下载/生成) -- `ray`:`address=http://127.0.0.1:8265`(从 head 容器内部视角) -- `resources`: - - `entrypoint_resources={"worker_node":1}` - - `entrypoint_num_cpus=1` -- `trainer_overrides`:训练参数覆盖(v1.1 默认 `total_epochs=1`、`save_freq=10`) -- `env_vars`:会被透传到 `runtime_env.env_vars`(必须包含 `PYTHONPATH` 注入) - -交付物(v1.1 SDK 方式): - -- `src/mvp/v1.1/py/configs/dev.yaml`(Ray 基础配置示例) -- `src/mvp/v1.1/py/jobspecs/{ppo,grpo,sft}.yaml`(训练 JobSpec 示例) -- `src/mvp/v1.1/py/run.py`(入口:使用 Ray Python SDK 提交/查询/停止/拉日志) -- 设计文档:`specs/mvp/v1.1/sdk_submit_refactor.md` - -### 3.2 多版本 `verl` 共存(必须) - -原则:**镜像固定不变**;job 粒度通过 `PYTHONPATH` 选择 `verl` 代码快照。 - -提交时必须注入(runtime_env): - -- `PYTHONPATH=":$PYTHONPATH"`(`CODE_PATH` 放最前面) - -并要求 job 在日志中打印一行确认 import 来源,例如: - -- `python -c "import verl,inspect; print(verl.__file__)"`(或训练入口启动时打印) - -v1.1 具体实现(可复现): - -- 先用 `src/mvp/v1.1/scripts/31_snapshot_verl_code.sh` 生成代码快照目录 `${SHARED_ROOT}/common/code/verl//` - - 该目录里会包含一个 `mvp_marker.py`(`MARKER=`) -- 提交 job 时让 `code_path` 指向该快照目录;submitter 会在 entrypoint 前打印: - - `MVP_PRECHECK_VERL_FILE`(验证 import 来源) - - `MVP_PRECHECK_MARKER`(验证选择的 code_path) - -### 3.3 `submit_job` 工具(组装 ray job submit) - -新增一个提交器(建议 Python,避免复杂 bash quoting): - -- 输入:JobSpec JSON -- 产物: - - 生成/确定 `submission_id` - - 创建 `${SHARED_ROOT}/jobs//config/`、`logs/`、`checkpoints/` - - 写入 `config/job_spec.json`(原样快照) - - 写入 `config/runtime_env.json`(最终用于 submit 的 JSON) - - 写入 `config/submit_cmd.txt`(最终命令行) -- 执行:在 **head 容器内**运行 `ray job submit ...` - -### 3.4 可排障:debug bundle(强制落盘) - -在 job 生命周期的关键节点收集并落盘(至少 2 类): - -- `ray status` -- `ray job list` -- `ray list nodes` -- `ray list actors` - -建议落盘到: - -- `${SHARED_ROOT}/jobs//debug/`(每次收集带时间戳文件名) - -### 3.5 Workload 扩展:GRPO(v1.1 新增闭环) - -优先用与 PPO 相同入口 `python -m verl.trainer.main_ppo`,仅通过配置切换算法: - -- `algorithm.adv_estimator=grpo` -- 其余保持最小可跑:`total_epochs=1`、`save_freq=10` - -### 3.6 Workload 扩展:SFT on Ray(v1.1 必须新增闭环) - -#### 3.6.1 入口与参考实现 - -- 入口:`python -m verl.trainer.sft_trainer_ray` -- 参考代码:`verl/verl/trainer/sft_trainer.py`(非 Ray 版本)与 `verl/verl/trainer/sft_trainer_ray.py`(Ray 版本) - -> v1.1 要验收的是 “SFT on Ray”,因此默认使用 `sft_trainer_ray.py`。 - -#### 3.6.2 连接已有 Ray 集群(必须) - -`sft_trainer_ray.py` 内部直接调用 `ray.init()`,为了确保它连接到**已有集群**(head+workers),v1.1 约定: - -- 提交 job 时通过 `runtime_env.env_vars` 注入:`RAY_ADDRESS=auto` - -如果发现 `ray.init()` 未按预期读取 `RAY_ADDRESS`(Ray 版本差异风险),v1.1 需要提供一个 launcher 兜底: - -- 由 launcher 先显式 `ray.init(address="auto")`,再调用 SFT trainer 逻辑 - -#### 3.6.3 SFT 数据格式(parquet schema) - -`sft_trainer_ray` 默认使用 `MultiTurnSFTDataset`,parquet 中至少需要: - -- `messages` 列:list[dict],dict 至少含 `role`/`content` - -v1.1 的 `prepare` 阶段需要生成并持久化 SFT 数据,例如: - -- `${SHARED_ROOT}/datasets/gsm8k_sft/train.parquet` -- `${SHARED_ROOT}/datasets/gsm8k_sft/val.parquet`(可选) - -单条样本的 `messages` 形态示例: - -- `[{ "role": "user", "content": "" }, { "role": "assistant", "content": "" }]` - -> 注意:SFT parquet 不能直接复用 PPO/RL 的 parquet(schema 不同)。 - -#### 3.6.4 重要细节:SFT Ray Driver 不应依赖 GPU - -在 `ray job submit` 模式下,我们的 entrypoint(driver)默认 **不会分配 GPU**(我们只指定了 `--entrypoint-num-cpus=1`,没有指定 `--entrypoint-num-gpus`)。 - -而 `verl/verl/trainer/sft_trainer_ray.py` 的 driver 逻辑里会用 `trainer.device` 来创建 `torch.tensor(..., device=...)` 做统计,如果设置为 `cuda` 且 driver 没有 GPU,会触发: - -- `RuntimeError: No CUDA GPUs are available` - -因此 v1.1 的 SFT on Ray 验收默认要求: - -- `trainer.device=cpu`(driver 只做 orchestration;真正训练仍由 Ray 的 TrainingWorker/资源池占用 GPU) - -### 3.7 v1.1 脚本化交付(必须独立完整) - -`src/mvp/v1.1/` 需要像 v1 一样提供一套完整脚本,确保 v1.1 可独立运行、可回归: - -- `src/mvp/v1.1/docker-compose.yaml`(容器名建议与 v1 区分,避免冲突) -- `src/mvp/v1.1/scripts/00_prereq_check.sh`(含 GPU/目录/NFS/verl 代码检查) -- `src/mvp/v1.1/scripts/01_up.sh` / `02_down.sh`(起停) -- `src/mvp/v1.1/scripts/20_start_head.sh` / `21_start_workers.sh` -- `src/mvp/v1.1/scripts/30_prepare_data_and_model.sh`(包含 PPO 数据 + SFT 数据) -- `src/mvp/v1.1/scripts/40_submit_ppo_epoch1.sh` -- `src/mvp/v1.1/scripts/41_submit_grpo_epoch1.sh` -- `src/mvp/v1.1/scripts/42_submit_sft_minimal.sh` -- `src/mvp/v1.1/scripts/50_status.sh` -- `src/mvp/v1.1/scripts/31_snapshot_verl_code.sh`(多版本 code snapshot) -- `src/mvp/v1.1/scripts/43_submit_jobspec.sh`(通过 JobSpec 提交) -- `src/mvp/v1.1/scripts/12_install_py_deps.sh`(安装 PyYAML 等依赖) -- `src/mvp/v1.1/scripts/44_submit_sdk.sh`(通过 Ray Python SDK + YAML 提交) - ---- - -## 4. 部署与测试流程(dev 环境) - -> dev 环境以远程机目录为例:`argus@h1:/home2/argus/infra/mvp`。v1.1 的所有内容要求放在: -> -> - `argus@h1:/home2/argus/infra/mvp/v1.1/` -> -> 并在该目录中通过脚本使用 `docker exec` 协调容器。 - -### 4.0 清理 v1 环境(必须先做) - -v1 已在 `argus@h1` 部署过容器与 Ray。为保证 v1.1 的可重复测试,开始 v1.1 前必须清理 v1: - -1) 停止并删除 v1 容器(推荐用 v1 的 down 脚本) -2) 确认 `docker ps` 中不再有 v1 的 `mvp-ray-head/mvp-ray-worker-*` - -v1.1 的脚本里也提供了一个 best-effort 清理脚本:`src/mvp/v1.1/scripts/03_cleanup_v1_legacy.sh`(远程目录中同名脚本)。 - -### 4.1 环境准备(一次性 / 幂等) - -1) 目录检查(远程机): - - `${WORKDIR}/shared/` 存在并具备上述子目录(含 `common/`、`user/`) -2) `verl` 代码目录检查: - - `${WORKDIR}/verl` 不存在则执行 `git clone https://github.com/volcengine/verl.git` -3) GPU 可用性检查: - - 设备存在(例如 0-7 可见),并按 worker 容器分配(每个 worker 4 GPU) -4) 模型与数据持久化路径: - - 模型与数据必须落在 `${SHARED_ROOT}` 下;若已存在则跳过下载/生成 - - SFT parquet 同样必须落在 `${SHARED_ROOT}` 下;若已存在则跳过生成 - -### 4.2 启动 Ray 集群(每次测试) - -1) `docker compose up -d` -2) head:`ray start --head --num-cpus=0 --num-gpus=0 ...` -3) workers:`ray start --address=:6379 --resources='{"worker_node":100}' ...` -4) 验证:`ray status` 显示 1 head + 2 worker,且 head `CPU:0 GPU:0` - -### 4.3 提交 PPO 回归(必须跑 2 次) - -1) 生成 JobSpec(可用模板 + 覆盖项) -2) 在 head 容器内执行 submitter(或直接 `ray job submit`) -3) 验证要点: - - `ray job list`:driver node 是 worker - - `${SHARED_ROOT}/jobs//` 下存在 `config/`、`logs/`、`checkpoints/` - - checkpoint 每 10 step 产生(例如 `global_step_10`) - -### 4.4 提交 GRPO(新增 workload 验收) - -同 PPO,但覆盖 `algorithm.adv_estimator=grpo`,确保能进入 RUNNING 并完成最小步数。 - -### 4.5 提交 SFT on Ray(新增 workload 验收,必须) - -1) 确认 `${SHARED_ROOT}/datasets/gsm8k_sft/train.parquet` 已存在(由 v1.1 prepare 生成)。 -2) 通过 head 容器执行 `ray job submit` 提交 `python -m verl.trainer.sft_trainer_ray`。 -3) 关键约束: - - `runtime_env.env_vars.RAY_ADDRESS=auto`(连接已有集群) - - `--entrypoint-resources='{"worker_node": 1}'`(driver 落 worker) - - `PYTHONPATH=:$PYTHONPATH`(多版本 verl) -4) 最小化训练配置建议(避免 OOM/耗时过长): - - `trainer.total_epochs=1` - - `trainer.total_training_steps=10~30` - - `trainer.save_freq=10` - - `trainer.nnodes=2`、`trainer.n_gpus_per_node=4`(用满 8 卡做一次最小分布式验证) - - `data.train_files=${SHARED_ROOT}/datasets/gsm8k_sft/train.parquet` - - `trainer.default_local_dir=${SHARED_ROOT}/jobs//checkpoints` - -### 4.6 工程化验证:JobSpec + 多版本共存(v1.1 必须) - -1) 生成两个 code snapshot(不同 `CODE_ID`): - - `CODE_ID=codeA ./scripts/31_snapshot_verl_code.sh` - - `CODE_ID=codeB ./scripts/31_snapshot_verl_code.sh` -2) 分别修改/复制 JobSpec 模板,使 `code_path` 指向不同 snapshot: - - `${SHARED_ROOT}/common/code/verl/codeA` - - `${SHARED_ROOT}/common/code/verl/codeB` -3) 用 JobSpec 提交(必须从 head): - - `./scripts/43_submit_jobspec.sh /workspace/mvp/v1.1/templates/ppo.json`(示例) -4) 在 Ray job logs 中验证: - - `MVP_PRECHECK_MARKER` 打印为对应的 `codeA`/`codeB` - - `MVP_PRECHECK_VERL_FILE` 指向 `${SHARED_ROOT}/common/code/verl/...` 而不是镜像内 site-packages - ---- - -## 5. 验收标准(Definition of Done) - -### 5.1 Hardening DoD(全部必选) - -- [ ] 提交必须来自 head:能在 head 容器内看到 `ray job submit ...` 的提交记录 -- [ ] driver 不在 head:`ray job list` 的 `driver_info.node_ip_address` ∈ worker IP,且 ≠ head IP -- [ ] 输出目录按 submission id 隔离:`${SHARED_ROOT}/jobs//` 不复用、不覆盖 -- [ ] 数据/模型持久化:再次提交时不重复下载/生成(有 “skip if exists” 的日志) -- [ ] checkpoint 策略有效:默认 `save_freq=10`,不会每 step 保存爆盘 -- [ ] debug bundle 落盘:`${SHARED_ROOT}/jobs//debug/` 至少包含 2 类 Ray 状态快照 -- [ ] 多版本共存验证通过:日志中能确认 `verl` import 来源来自 JobSpec 指定的 `code_path` - -### 5.2 Workload DoD(GRPO + SFT 都必须) - -- [ ] GRPO job 能提交、RUNNING、完成最小训练步数 -- [ ] GRPO job 产物目录满足与 PPO 相同的目录规范与 debug 规范 -- [ ] SFT job 能提交、连接已有集群并跑到至少 1 个 step(建议最小步数/epoch) -- [ ] SFT job 产物目录满足与 PPO 相同的目录规范与 debug 规范 - ---- - -## 6. 生产环境部署注意事项(v1.1 需要考虑但不强制在 dev 全量模拟) - -- 容器由算力平台创建:我们只负责 SSH 进去纳管(启动 ray / 提交 job / 收集产物)。 -- 容器内共享路径为 `/private`:所有脚本必须以 `SHARED_ROOT=/private` 工作,不得写死 `/mnt/shared`。 -- 认证仅内部 token:在 submitter 中把 token 作为 env var 透传(不写入日志明文)。 diff --git a/specs/mvp/v1/mvp_plan.md b/specs/mvp/v1/mvp_plan.md deleted file mode 100644 index 026e458..0000000 --- a/specs/mvp/v1/mvp_plan.md +++ /dev/null @@ -1,120 +0,0 @@ -# MVP 计划(V1) - -本文档目标:把当前“口述/实验记录”整理成**可复现、可验收**的 MVP 计划,并明确下一步最小闭环。 - -## 1. 背景与目标 - -我们要验证的最小闭环是: - -1) 在“Head(CPU 容器)+ Worker(GPU 容器)”的 Ray Cluster 上,能够跑通一次 `verl` 的 PPO 训练。 -2) 训练所需的 **数据集 / 模型缓存 / 训练产物(checkpoint)/ 日志** 不落在容器临时文件系统里,而是落在**共享存储(NFS)**,容器重启后可继续使用。 -3) 所有步骤能写成一套**清晰命令/脚本**,新人可照着复现。 - -## 2. 环境与假设 - -- 机器:H20 机器(具体规格由算力平台提供) -- 访问方式:通过 `ssh h1a` 远程登录(进入算力平台/宿主访问入口) -- 容器:算力平台可申请 CPU 容器(对外暴露端口)与若干 GPU 容器(可 SSH 互通) -- 共享存储:所有容器可挂载同一套 NFS(在 `specs/hl_design_v2.md` 中假设为 `/mnt/shared`) - -## 3. 已验证现状(现有实验) - -目录 `ray_in_docker/` 已经做过一次可运行的实验(偏“本地/示例级别”): - -- 用 `docker-compose` 起了 2 个 `verl` 镜像容器: - - `verl-head`:作为 Ray Head(Dashboard 端口 `8265`) - - `verl-worker`:作为 Ray Worker -- 在容器中执行: - - 下载 GSM8K 数据集(`examples/data_preprocess/gsm8k.py`) - - 拉取 HuggingFace 模型(示例:`Qwen/Qwen2.5-0.5B-Instruct`) - - `ray start --head` + `ray start --address=...` - - 通过 `ray job submit ... python -m verl.trainer.main_ppo ...` 提交 PPO 训练任务(见 `ray_in_docker/ray_example/ppo_train.sh`) - -结论:**训练脚本可以跑通**。 - -## 4. 当前主要问题(从实验到平台化 MVP 的差距) - -1) **数据 / 模型 / 输出落在容器内**:容器重启/替换后不可复用;也不利于多人共享与审计。 -2) **缓存路径不规范**:HuggingFace cache、Ray 临时目录、Hydra 输出目录等可能分散在容器默认路径。 -3) **可复现不足**:缺少明确的目录规范、统一的启动/提交流程、验收口径。 -4) Ray 节点**打标签/亲和性调度**的方法未固化:需要明确是否统一用 `ray start --resources`,以及命名规范如何设计。 - -## 5. MVP V1:最小闭环定义 - -以 `specs/hl_design_v2.md` 的方向为准,但 V1 **只做最小可运行原型**,暂不做完整 Web/调度系统。 - -### 5.1 目录规范(统一落到 NFS) - -约定所有容器统一挂载 NFS 到 `/mnt/shared`,并在其中固定目录结构: - -- `/mnt/shared/code/`:代码(可选:按版本/分支隔离) -- `/mnt/shared/datasets/`:数据集(如 `gsm8k/`) -- `/mnt/shared/hf/`:HuggingFace 缓存(设置 `HF_HOME=/mnt/shared/hf`) -- `/mnt/shared/ray/`:Ray 运行期临时目录(可选:设置 `RAY_TMPDIR=/mnt/shared/ray/tmp`) -- `/mnt/shared/outputs/`:训练输出根目录(Hydra/日志/ckpt 统一落这里) - - `/mnt/shared/outputs/logs//` - - `/mnt/shared/outputs/checkpoints//` - -### 5.2 最小集群形态 - -- 1 个 Head(CPU 容器) - - 跑 `ray start --head --dashboard-host=0.0.0.0` - - 暴露 `8265` 给 Desktop/用户查看 Job 状态 -- 1~2 个 Worker(GPU 容器) - - 跑 `ray start --address=:6379` 加入集群 - - (可选)通过 `--resources='{\"gpu_pool_a\": 1}'` 给节点打标签 - -### 5.3 最小训练任务 - -- 目标任务:跑通一次 `verl.trainer.main_ppo`(以 GSM8K 为例) -- 要求: - - `data.train_files` / `data.val_files` 指向 `/mnt/shared/datasets/...` - - HuggingFace 模型下载缓存落到 `/mnt/shared/hf` - - 训练输出(Hydra outputs、checkpoint、stdout/stderr)落到 `/mnt/shared/outputs/...` - -建议在提交命令里显式覆盖 Hydra 输出目录(示例,具体目录名按需调整): - -- `hydra.run.dir=/mnt/shared/outputs/logs/${JOB_TAG}` - -## 6. 实施步骤(Checklist) - -### 6.1 一次性准备 - -- [ ] 确认所有容器已挂载 NFS 到同一路径:`/mnt/shared` -- [ ] 在 `/mnt/shared/` 下创建目录:`datasets/ hf/ outputs/ ray/` -- [ ] 在所有容器中设置/注入环境变量(推荐写入统一脚本): - - `HF_HOME=/mnt/shared/hf` - - `HF_ENDPOINT=https://hf-mirror.com`(如需) - - `RAY_TMPDIR=/mnt/shared/ray/tmp`(可选) - -### 6.2 启动集群(Head + Worker) - -- [ ] 在 Head 容器启动 Ray Head(并记录 `head_ip:6379`) -- [ ] 在每个 Worker 容器执行 `ray start --address=...` 加入集群 -- [ ] 在 Head 上通过 `ray status` / Dashboard 验证节点已注册 - -### 6.3 准备数据与模型 - -- [ ] 数据集下载到:`/mnt/shared/datasets/gsm8k/` -- [ ] 模型缓存落到:`/mnt/shared/hf/`(拉取一次即可多任务复用) - -### 6.4 提交训练任务 - -- [ ] 用 `ray job submit --address=http://:8265 ...` 提交 PPO 训练 -- [ ] 训练日志与 checkpoint 在 `/mnt/shared/outputs/` 可见 - -## 7. 验收标准(V1) - -- [ ] Ray Head/Worker 能稳定加入同一集群(Dashboard 可见) -- [ ] PPO 训练任务可提交并跑通(至少完成若干 step/epoch) -- [ ] 数据集、HF 缓存、训练输出均在 `/mnt/shared/` 下可复用(容器重启后仍在) -- [ ] 有一份“从零到跑通”的命令清单(或脚本)可复现 - -## 8. 未决问题(记录待补齐) - -- [ ] Ray 节点标签/亲和性调度:是否统一用 `ray start --resources`,以及命名规范如何设计 -- [ ] RL workload 的 Driver 放置策略:先按 `verl` 默认即可,后续再按 `specs/hl_design_v2.md` 收敛到“Driver-on-Head / Placement Group”等模式 - -## 9. 下一步(进入 V2) - -当 V1 达到“可复现 + 产物可落盘”的验收标准后,下一阶段工作见:`specs/mvp_plan_v2.md`。 diff --git a/specs/mvp/v1/v1_action.md b/specs/mvp/v1/v1_action.md deleted file mode 100644 index 31ae03d..0000000 --- a/specs/mvp/v1/v1_action.md +++ /dev/null @@ -1,111 +0,0 @@ -# MVP V1 远程实验行动文档(待确认后执行) - -## 1. 任务复述(我理解的需求) - -你希望我在远程机器 `argus@h1` 上,进入目录 `/home2/argus/infra/mvp`,把 MVP V1 的“原本流程”**手动完整跑一遍并验证**。要求: - -1) 在宿主机上编写脚本,脚本通过 `docker exec` 在容器内执行命令,负责协调启动顺序(先 head、后 worker)。 -2) 集群拓扑改为: - - 1 个 Ray Head:**没有 GPU**,并且 Head 的 Ray 资源 `CPU=0`(防止 Ray 把训练任务调度到 head)。 - - 2 个 Ray Worker:各自 **4 GPU**(总 8 GPU)。 -3) PPO 训练需要“轻量化”,把 `total_epochs` 改为 `1`。 -4) 先在本地仓库 `src/mvp/v1/` 写好脚本与 compose 文件;再拷贝到远程目录执行与验证。 -5) 在你确认这份行动文档没问题之前,我**不执行**远程操作。 - -## 2. 本地已准备的文件(在本仓库内) - -- `src/mvp/v1/docker-compose.yaml`:3 容器(head + 2 worker),head 不使用 nvidia runtime;worker0/1 各限制 4 GPU。 -- `src/mvp/v1/scripts/`:宿主机脚本(内部全部用 `docker exec`) - - `01_up.sh`:起容器 - - `20_start_head.sh`:启动 Ray head(`--num-cpus=0 --num-gpus=0`) - - `21_start_workers.sh`:启动 Ray worker 加入集群 - - `30_prepare_data_and_model.sh`:准备 GSM8K 数据与预下载模型 - - `40_submit_ppo_epoch1.sh`:提交 PPO(`trainer.total_epochs=1`,并设置 `nnodes=2, n_gpus_per_node=4`) - - `run_all.sh`:按顺序一键执行 - -## 3. 远程环境前置条件(需要你确认/保证) - -在 `argus@h1` 上: - -- Docker 可用,且有 `docker compose` 插件(Compose v2)。 -- NVIDIA runtime 可用(worker 容器需要 `runtime: nvidia`),宿主机有至少 8 张 GPU。 -- 不强制要求提前准备 `./verl`:脚本会在宿主机侧检查 `${PWD}/verl`,如果不存在会自动执行: - - `git clone https://github.com/volcengine/verl.git` - -此外本实验默认写入持久化目录:`/home2/argus/infra/mvp/shared`(会自动创建)。 - -## 4. 拷贝到远程(我执行前会再次征求你确认) - -从本地(本机)同步到远程: - -1) 同步脚本与 compose: - - `rsync -av ./src/mvp/v1/ argus@h1:/home2/argus/infra/mvp/src/mvp/v1/` - - `rsync -av ./specs/mvp/v1_action.md argus@h1:/home2/argus/infra/mvp/specs/mvp/v1_action.md` -2) `verl/` 默认不需要同步(远程会 clone)。如果你更希望固定版本/避免网络波动,也可以手动同步: - - `rsync -av --delete ./verl/ argus@h1:/home2/argus/infra/mvp/verl/` - -## 5. 远程执行步骤(在宿主机上) - -在远程机器执行: - -1) 进入目录: - - `cd /home2/argus/infra/mvp` -2) 确保脚本可执行(首次同步后需要做一次): - - `chmod +x ./src/mvp/v1/scripts/*.sh` -3) 启动容器: - - `./src/mvp/v1/scripts/01_up.sh` -4) 安装 editable 版 `verl`(保证 `python -m verl...` 可用): - - `./src/mvp/v1/scripts/10_install_verl_editable.sh` -5) 启动 Ray Head(禁止调度到 head): - - `./src/mvp/v1/scripts/20_start_head.sh` -6) 启动两个 Ray Worker 加入集群: - - `./src/mvp/v1/scripts/21_start_workers.sh` -7) 准备数据 + 预下载模型(落到 `./shared`): - - `./src/mvp/v1/scripts/30_prepare_data_and_model.sh` -8) 提交 PPO(`total_epochs=1`,必须用 `ray job submit` 在 head 提交;通过 `--entrypoint-resources` 强制 driver 调度到 worker): - - `./src/mvp/v1/scripts/40_submit_ppo_epoch1.sh` -9) 观察状态: - - `./src/mvp/v1/scripts/50_status.sh` - - 打开 Ray Dashboard:`http://:8265` - -也可以一键跑: -- `./src/mvp/v1/scripts/run_all.sh` - -## 6. 验收与验证点(执行时我会逐项检查) - -1) Head 节点无 GPU:在 head 容器内 `nvidia-smi` 应不可用或无设备(worker 内可见 4 张)。 -2) Head 的 Ray 逻辑资源为 `CPU=0, GPU=0`:head 不应承载训练任务调度资源(通过 `ray start --num-cpus=0 --num-gpus=0`)。 -3) 集群节点数量正确:`ray status` 中应看到 1 head + 2 worker。 -4) PPO driver 不在 head:`ray job list` 里该 `submission_id` 的 `driver_info.node_ip_address` 应该是 worker 的 IP(`172.19.0.3/172.19.0.4`),不能是 head(`172.19.0.2`)。 -5) PPO 训练只跑 1 个 epoch:提交参数包含 `trainer.total_epochs=1`。 -6) checkpoint 落盘:`/mnt/shared/jobs//checkpoints/` 有产物(脚本通过 `trainer.default_local_dir` 强制指向该目录;不设置 `trainer.default_hdfs_dir`)。 -7) 数据与缓存落盘:`/home2/argus/infra/mvp/shared/` 下出现 datasets/hf/jobs 等目录。 - -补充(磁盘保护): -- checkpoint 不要每步保存(会非常占空间);当前脚本默认 `trainer.save_freq=10`(每 10 step 保存一次)。 - -## 10. 目录命名约定(submission id) - -- 脚本默认会显式指定 `ray job submit --submission-id=$SUBMISSION_ID`,并使用同一个值作为输出目录名: - - 输出目录:`/mnt/shared/jobs/$SUBMISSION_ID/` -- 你可以在提交时自定义 ID(推荐这样便于检索): - - `SUBMISSION_ID=my_run_20251219_001 ./src/mvp/v1/scripts/40_submit_ppo_epoch1.sh` - -## 7. 风险点与兜底 - -- 如果 `runtime: nvidia` 在该环境不生效:需要改成 compose 的 `gpus:` 写法(我会按远程 docker 版本调整)。 -- 如果 Ray Jobs 的 driver 必须在 head 启动(Ray 机制如此):这不影响“训练任务不调度到 head”,但 head 仍会有一个 job driver 进程。 -- 如果 `verl` 在镜像内已安装但版本不匹配:脚本会优先 `pip install -e /workspace/verl` 以保证行为一致。 - -## 8. 你需要确认的 3 个问题(你已确认,我按此执行) - -1) `verl/`:脚本会在远程自动 `git clone https://github.com/volcengine/verl.git`(如你希望固定版本,可改成同步或 checkout tag/commit)。 -2) GPU:`0-7` 可用(worker0 用 `0-3`,worker1 用 `4-7`)。 -3) PPO:用满 8 GPU(`nnodes=2, n_gpus_per_node=4`)。 - -## 9. 你新增的关键要求(我已纳入脚本) - -- 数据与模型必须落在 `/mnt/shared`(由宿主机 `./shared` bind mount 提供),并且具备**幂等**: - - 数据:如果 `train.parquet/test.parquet` 已存在则跳过下载。 - - 模型:优先检测本地 cache(`HF_HOME=/mnt/shared/hf`);存在则跳过,否则才下载。 -- 提交 job 时显式注入 `HF_HOME/HUGGINGFACE_HUB_CACHE/TRANSFORMERS_CACHE`,确保训练使用持久化缓存与数据路径。 diff --git a/specs/mvp/v2.0/v2_api.md b/specs/mvp/v2.0/v2_api.md deleted file mode 100644 index 3e859b7..0000000 --- a/specs/mvp/v2.0/v2_api.md +++ /dev/null @@ -1,194 +0,0 @@ -# MVP v2.0 API 设计(最小可用) - -v2.0 的 API 目标是:把 v1.1 的“脚本提交”变成“服务化提交”,并在服务侧实现队列/重试/状态聚合。 - -约束: -- 内部 token 鉴权(简单即可)。 -- Ray Job 提交必须使用 **Ray Python SDK**(`JobSubmissionClient`),不使用 `requests` 手写 HTTP。 -- 输出与状态必须落盘到 NFS(容器内 `/private`)。 - ---- - -## 1. 鉴权 - -- Header:`Authorization: Bearer ` -- v2.0 不做用户体系与权限隔离;token 只是“防误用”。 -- 配置建议:复用 `src/mvp/v1.1/py/configs/dev.yaml` 并在 `v2.auth.token_env` 指定 token 环境变量名。 - -## 1.1 运行位置(dev 示例) - -- 服务进程运行在 **Ray head 容器**(便于访问 Ray Job server)。 -- 宿主机侧用脚本控制(`docker exec`): - - `src/mvp/v2.0/scripts/20_start_api.sh` - - `src/mvp/v2.0/scripts/21_stop_api.sh` - - `src/mvp/v2.0/scripts/22_status_api.sh` -- 远程机目录约定(示例):`argus@h1:/home2/argus/infra/mvp/v2/`,容器内挂载到 `/workspace/mvp/v2/`。 - ---- - -## 2. 资源与 ID 约定 - -### 2.1 task_id(服务层主 ID) - -- 格式建议:`mvp2----` - - 示例:`mvp2-ppo-20251223-143201-7f3a` - -### 2.2 ray_submission_id(attempt 级 ID) - -- 由 service 派生:`--a` - - 示例:`mvp2-ppo-20251223-143201-7f3a--a01` - -好处: -- Ray 的 submission id 自带 task_id,可直接从 Ray dashboard 反查到服务侧任务。 -- `/private/jobs//...` 目录天然隔离且可读。 - ---- - -## 3. JobSpec(请求体) - -v2.0 **要求 JobSpec 使用 v1.1 同款 YAML**(字段与语义保持一致),服务端接收 YAML 文本并解析后入库(同时原样保存 `jobspec_yaml` 便于审计/复现)。 - -最小字段(示例 YAML): - -```yaml -workload: "ppo" -submission_id: "" # v2.0 服务端会忽略/覆盖(由 task_id 派生 ray_submission_id) -code_path: "/private/common/code/verl/verl_repo" -model_id: "Qwen/Qwen2.5-0.5B-Instruct" -train_file: "/private/datasets/gsm8k/train.parquet" -val_file: "/private/datasets/gsm8k/test.parquet" -nnodes: 2 -n_gpus_per_node: 4 -total_epochs: 1 -total_training_steps: 10 -save_freq: 10 -test_freq: -1 -trainer_device: null # 仅 sft 使用(通常 "cpu") -``` - -说明: -- `trainer_device` 仅对 `sft` 生效(通常为 `cpu`,避免 driver 无 GPU)。 -- `val_file` 可为 `null`(例如 SFT)。 - ---- - -## 4. API 端点 - -### 4.1 提交任务 - -`POST /api/v2/tasks` - -Request body: -- **raw JobSpec YAML**(与 v1.1 jobspec YAML 结构一致) - -Headers: -- `Content-Type: application/yaml`(或 `text/yaml`) - -Response: -```json -{ - "task_id": "mvp2-ppo-20251223-143201-7f3a", - "state": "QUEUED" -} -``` - -### 4.2 查询任务(聚合状态) - -`GET /api/v2/tasks/{task_id}` - -Response(示例): -```json -{ - "task_id": "mvp2-ppo-20251223-143201-7f3a", - "workload": "ppo", - "state": "RUNNING", - "desired_resources": {"nnodes": 2, "n_gpus_per_node": 4, "total_gpus": 8}, - "latest_attempt": { - "attempt_no": 1, - "ray_submission_id": "mvp2-ppo-20251223-143201-7f3a--a01", - "ray_status": "RUNNING", - "start_time": "2025-12-23T14:32:10+08:00" - }, - "error_summary": null -} -``` - -### 4.3 列出 attempts - -`GET /api/v2/tasks/{task_id}/attempts` - -Response: -```json -{ - "task_id": "mvp2-ppo-20251223-143201-7f3a", - "attempts": [ - { - "attempt_no": 1, - "ray_submission_id": "mvp2-ppo-20251223-143201-7f3a--a01", - "ray_status": "FAILED", - "failure_kind": "INSUFFICIENT_RESOURCES", - "message": "Total available GPUs 0 is less than total desired GPUs 8", - "start_time": "...", - "end_time": "..." - } - ] -} -``` - -### 4.4 取消任务 - -`POST /api/v2/tasks/{task_id}:cancel` - -行为: -- 若 task 处于 `SUBMITTED/RUNNING`:调用 Ray Jobs SDK `stop_job(ray_submission_id)` 并标记 `CANCELED` -- 若处于 `QUEUED/PENDING_RESOURCES`:直接标记 `CANCELED`(不提交) - -Response: -```json -{"task_id":"...","state":"CANCELED"} -``` - -### 4.5 获取日志 - -`GET /api/v2/tasks/{task_id}/logs?attempt=latest&tail=2000` - -返回: -- `text/plain`(直接透传 Ray Job logs tail) - -说明: -- v2.0 先用 Ray SDK `get_job_logs()`。 -- 若需要更稳定的归档,可在 scheduler 定期抓取并落盘(v2.1+)。 - -### 4.6 列出队列(运维/调试) - -`GET /api/v2/queue` - -Response: -```json -{ - "pending": [{"task_id":"...","state":"PENDING_RESOURCES","next_run_at":"..."}], - "running": [{"task_id":"...","ray_submission_id":"..."}] -} -``` - ---- - -## 5. 错误码(最小) - -- `400`:jobspec 缺字段/非法 -- `401`:token 不正确 -- `404`:task 不存在 -- `409`:状态冲突(例如已终态又 cancel) -- `500`:服务内部错误 - ---- - -## 6. SQLite 持久化(API 可见性) - -v2.0 服务端使用 SQLite 持久化保存: -- tasks(`task_id`、`state`、`jobspec_yaml`、`next_run_at`、`latest_attempt_no` 等) -- attempts(`ray_submission_id`、`ray_status`、失败原因等) - -因此: -- `GET /api/v2/tasks/{task_id}` 的数据来自 SQLite(再叠加 Ray 状态同步的结果)。 -- 进程重启后,队列可恢复,`PENDING_RESOURCES` 的任务会在 `next_run_at` 到期后继续尝试提交。 diff --git a/specs/mvp/v2.0/v2_plan.md b/specs/mvp/v2.0/v2_plan.md deleted file mode 100644 index 4b0a27e..0000000 --- a/specs/mvp/v2.0/v2_plan.md +++ /dev/null @@ -1,306 +0,0 @@ -# MVP v2.0 开发计划(服务化入口 + 队列调度 + Ray Jobs SDK) - -目标:在 v1.1(脚本 + Ray Jobs SDK)已验收通过的基础上,交付一个**可独立运行的最小“服务层”**: -- 用户通过 **HTTP API** 提交训练任务(PPO/GRPO/SFT)。 -- 服务层分配一个**人类易读的任务 ID**(`task_id`),并把任务放入队列。 -- 后台调度器在资源满足时再向 Ray 集群提交 Ray Job,并持续追踪 Ray Job 状态。 -- 针对 `verl` 的 **fail-fast 资源预检查**(资源不足直接 `ValueError` 失败)做“服务级重试/排队”,避免用户反复手工提交。 - -> 约束继承 v1.1:head 不跑训练;driver 必须落到 worker;共享存储只考虑 NFS(容器内 `/private`)。 - ---- - -## 1. 背景:为什么 v2.0 需要“服务层调度” - -在 v1.1 中我们通过 Ray Job 提交 `verl` 训练任务。`verl` PPO/GRPO 在初始化 worker 时会创建资源池,并做一次 fail-fast 的资源检查: -- 触发点:`ResourcePoolManager.create_resource_pool()` 末尾调用 `_check_resource_available()` -- `_check_resource_available()` 使用 `ray._private.state.available_resources_per_node()` 统计“可用 GPU/NPU”,如果不足则直接抛异常: - - `ValueError: Total available GPUs 0 is less than total desired GPUs 8` - -这是一种合理的选择(避免 Ray 层面无限 pending/卡死),但会带来一个平台侧问题: -- 当集群暂时没有足够资源时,用户提交会“立刻失败”,需要手动重试。 - -因此 v2.0 的服务层要提供: -- **队列 + gang 约束**:资源不满足则任务在服务层 pending(不提交到 Ray)。 -- **状态追踪**:一旦提交到 Ray,持续获取 Ray Job 状态并回传给用户。 -- **资源不足的“自动重试”**:即使发生 race(提交时资源够、启动时被抢走),也能识别该类失败并延迟重试。 - ---- - -## 2. v2.0 交付范围(Scope) - -### 2.1 必做(MVP v2.0) - -1) **HTTP API**(内部 token): - - 提交任务、查询任务、取消任务、拉取日志(最小可用)。 -2) **任务队列与调度器**: - - FIFO(先到先服务),无配额/公平性(留给 v3+)。 - - gang:按 `nnodes` + `n_gpus_per_node` 的固定资源需求“全有才提交”。 -3) **Ray Jobs SDK 集成**(不使用 `requests` 自己拼 HTTP): - - 通过 `ray.job_submission.JobSubmissionClient` submit/status/stop/logs。 -4) **可观测/可排障最小集**: - - 每个 task/attempt 落盘配置、提交载荷、Ray 返回的 `submission_id`、关键日志。 -5) **失败策略**: - - 识别 “资源不足 fail-fast” 类失败 → 转为 `PENDING_RESOURCES` 并延迟重试。 - - 其他失败保持 `FAILED`(不自动重试,避免掩盖错误)。 - -### 2.2 不做(v2.0 不实现) - -- 多租户/配额/优先级/公平性调度(v3)。 -- Pipeline(多 job 串联)(v3+)。 -- 完整 UI(v3+,v2.0 可只提供 OpenAPI/Swagger)。 -- K8s 编排(明确不做,仍是 Native Ray)。 - ---- - -## 2.3 工程原则(开闭原则 / 复用 v1.1) - -v2.0 研发遵循开闭原则(Open/Closed Principle): -- **对扩展开放**:新增“服务层(API + scheduler + SQLite)”能力以支持排队、重试、状态聚合。 -- **对修改关闭**:尽量不改动 v1.1 已经稳定可用的 Ray Jobs SDK 提交链路代码。 - -落地方式: -- 将 `src/mvp/v1.1/py/mvp_v11/` 作为“成熟可用提交层”,原样拷贝到 `src/mvp/v2.0/py/mvp_v11/` 供 v2.0 复用。 -- v2.0 的新增功能全部在新模块实现(例如 `src/mvp/v2.0/py/mvp_v2/`),通过组合/封装来调用 `mvp_v11`,避免在旧代码中掺杂平台逻辑。 - ---- - -## 3. 总体架构(v2.0) - -### 3.1 组件 - -- **mvp-api**(HTTP Server) - - 接收 JobSpec(结构化字段保持与 v1.1 一致的语义) - - 生成 `task_id` 并写入持久化 - - 提供 query/cancel/logs - -- **mvp-scheduler**(后台调度器,可与 api 同进程也可拆进程) - - 轮询队列:对 `PENDING_RESOURCES` 的任务做资源判断 - - 资源满足 → 调用 Ray Jobs SDK 提交 → 记录 `ray_submission_id` - - 对 `SUBMITTED/RUNNING` 的任务持续同步 Ray Job 状态 - - 如果 Ray Job 失败且命中资源不足模式 → 延迟重试 - -> 部署建议:v2.0 先在 **head 容器**内运行该服务(dev/prod 行为一致;生产环境只能 ssh 进入容器纳管)。 - -### 3.4 dev 环境目录约定(示例) - -以当前远程开发机为例(`argus@h1`): -- 宿主机目录:`/home2/argus/infra/mvp/v2/` -- 容器内挂载:`/workspace/mvp/v2/` -- 共享 NFS:容器内统一为 `/private/`(与 v1.1 保持一致) - -> 注意:服务脚本(`v2/scripts/*.sh`)应在**宿主机**执行,通过 `docker exec` 控制 head 容器;训练 driver 仍通过 Ray entrypoint_resources 强制落到 worker。 - -### 3.2 与 Ray/容器的关系 - -- 服务进程运行在 head(或等价能访问 head 的 Job server 地址)。 -- 提交时仍使用 v1.1 的强约束: - - head:`--num-cpus=0 --num-gpus=0` - - worker:`--resources='{\"worker_node\": 100}'` - - job entrypoint:`entrypoint_resources={\"worker_node\": 1}` 强制 driver 落 worker - ---- - -## 3.3 配置约定(复用 v1.1 dev.yaml 并扩展) - -v2.0 的服务层(API + scheduler)建议复用 v1.1 已存在的 RayConfig 文件: -- `src/mvp/v1.1/py/configs/dev.yaml` - -原因: -- 其中已包含 v1.1 运行所需的 Ray 基础配置(Ray Job server address、entrypoint_resources、runtime_env 等),v2.0 也需要同样的信息来提交 Ray Jobs。 - -扩展方式: -- 在该 YAML 中新增一个顶层 `v2:` section,存放 v2 服务专属配置(API 监听、SQLite 路径、scheduler 间隔等)。 -- v1.1 submitter 只读取 `address/shared_root/entrypoint_* /runtime_env/user_code_path`,会忽略 `v2:` 之类的额外字段;因此不会破坏 v1.1。 - -最小新增项建议(示例): -- `v2.api.host` / `v2.api.port` -- `v2.auth.token_env`(内部 token 环境变量名) -- `v2.sqlite.db_path`(建议 `/private/common/db/mvp_v2.sqlite3`) -- `v2.scheduler.tick_s` / `v2.scheduler.retry_interval_s` / `v2.scheduler.max_running_tasks` - ---- - -## 4. 核心数据模型(Task / Attempt) - -### 4.1 Task(用户视角的任务) - -- `task_id`:**人类易读**且唯一,例如: - - `mvp2-ppo-20251223-143201-7f3a` -- `workload`:`ppo|grpo|sft` -- `jobspec`:提交参数(**保持 v1.1 的 jobspec YAML 字段与语义**;服务端解析 YAML 后入库) -- `state`:见第 5 节状态机 -- `created_at` / `updated_at` -- `latest_attempt`:指向当前 attempt -- `attempts[]`:历史尝试列表 -- `error_summary`:面向用户的简短错误(最后一次失败原因) - -### 4.2 Attempt(一次真实的 Ray Job 提交) - -- `attempt_no`:从 1 开始递增 -- `ray_submission_id`:建议派生自 task_id: - - `ray_submission_id = --a01` - - 好处:Ray 侧输出目录天然可读、可追溯 -- `status`:Ray Job 状态(PENDING/RUNNING/SUCCEEDED/FAILED/STOPPED) -- `start_time` / `end_time` -- `exit_code`(如可取) -- `failure_kind`(枚举): - - `INSUFFICIENT_RESOURCES`(匹配 “Total available GPUs … less than total desired …”) - - `USER_ERROR`(配置/数据路径错误等) - - `RUNTIME_ERROR`(代码异常) - - `UNKNOWN` - ---- - -## 5. 状态机(服务侧) - -建议最小状态集: - -- `QUEUED`:已入队,尚未进行资源判断 -- `PENDING_RESOURCES`:资源不足,等待(服务侧 pending,不提交 Ray) -- `SUBMITTING`:正在向 Ray 提交 attempt -- `SUBMITTED`:Ray 已接受 submission(拿到 `ray_submission_id`) -- `RUNNING`:Ray Job RUNNING -- `SUCCEEDED`:任务成功(终态) -- `FAILED`:任务失败(终态,除非命中“资源不足重试策略”) -- `CANCELED`:用户取消(终态) - -关键转换: -- `QUEUED -> PENDING_RESOURCES`:资源不足 -- `QUEUED/PENDING_RESOURCES -> SUBMITTING`:资源满足 -- `SUBMITTING -> SUBMITTED`:提交成功 -- `SUBMITTED -> RUNNING`:Ray 状态推进 -- `SUBMITTED/RUNNING -> SUCCEEDED|FAILED`:Ray 终态 -- `FAILED (INSUFFICIENT_RESOURCES) -> PENDING_RESOURCES`:进入延迟重试(attempt_no+1) - ---- - -## 6. 调度策略(v2.0) - -### 6.1 资源计算(对齐 verl 的“可用资源”口径) - -由于 verl 使用 `ray._private.state.available_resources_per_node()` 做“可用资源”统计, -v2.0 的 scheduler 应该尽量使用相同口径,避免: -- 我们认为够了 → 实际 verl 认为不够(仍 fail-fast) -- 我们认为不够 → 实际够了(浪费) - -策略(建议): -1) scheduler 周期性获取 per-node 可用 GPU -2) 计算 total_available_gpus = sum(node_gpu_available) -3) 任务需求 total_required_gpus = nnodes * n_gpus_per_node -4) 如果 `total_available_gpus < total_required_gpus` → `PENDING_RESOURCES` - -注意:v2.0 先只做总量判断;节点级分配(保证每个 node 恰好 n_gpus_per_node)可作为 v2.1+(资源池/标签/节点纳管)增强点。 - -### 6.2 排队与并发 - -- 默认 FIFO。 -- 并发度:允许同时跑多个任务,但必须保证资源足够。 - - 简化实现:如果任务默认都吃满 8 卡,则 scheduler 实际上一次只能跑一个。 - - 若未来支持小任务(1*1、1*4),可以自然并发。 - -### 6.3 重试策略(资源不足) - -当出现下面模式时判定为 `INSUFFICIENT_RESOURCES`: -- Ray Job `status=FAILED` -- `JobDetails.message` 或 `job logs` 中匹配: - - `Total available GPUs` 且 `less than total desired` - -处理: -- 将 task 置为 `PENDING_RESOURCES` -- `next_run_at = now + 60s`(固定间隔;v2.1 可改指数退避) -- attempt_no++ 后重提(新 submission id) - ---- - -## 7. SQLite 持久化(队列/状态/attempt) - -v2.0 引入一个**最小但可恢复的持久化层**:使用 SQLite 保存任务队列与状态,确保: -- api/scheduler 进程重启后,队列不丢; -- task/attempt 历史可追溯; -- 能实现“服务侧 pending + 延迟重试”的确定性行为。 - -### 7.1 存放位置 - -建议路径(容器内): -- `DB_PATH=/private/common/db/mvp_v2.sqlite3` - -说明: -- v2.0 默认单实例服务(单 writer),SQLite 足够。 -- 生产环境若 NFS 上的 SQLite 有锁/性能风险,v2.1+ 再演进到 Postgres/Redis;v2.0 先以“可回放/可恢复”为第一目标。 - -### 7.2 表设计(建议最小集合) - -- `tasks` - - `task_id` (PK) - - `workload` - - `state`(服务侧状态机) - - `jobspec_yaml`(原始 YAML 文本,原样落盘便于审计/复现) - - `created_at`, `updated_at` - - `next_run_at`(用于 `PENDING_RESOURCES` 的延迟重试) - - `error_summary` - - `latest_attempt_no` - -- `attempts` - - `task_id` (FK) - - `attempt_no` - - `ray_submission_id` - - `ray_status` - - `failure_kind` - - `message`(截断后的关键信息) - - `start_time`, `end_time` - -- `events`(可选,但非常利于排障) - - `id` (PK) - - `task_id` - - `ts` - - `event_type`(STATE_TRANSITION / SUBMIT / RAY_STATUS_SYNC / RETRY_SCHEDULED 等) - - `payload_json` - -### 7.3 调度循环(与 SQLite 的交互) - -scheduler 每个 tick 做三件事: -1) **挑选可运行任务**(FIFO + next_run_at): - - `state IN ('QUEUED','PENDING_RESOURCES') AND next_run_at <= now` -2) **资源判断**(对齐 verl 的可用资源口径): - - 不满足:更新 `state='PENDING_RESOURCES'`,并写入 `next_run_at=now+60s` -3) **提交 Ray Job 并追踪**: - - 提交成功:写入 `attempts` 并更新 `tasks.latest_attempt_no`、`state='SUBMITTED'` - - 周期性同步 Ray 状态:`SUBMITTED/RUNNING -> SUCCEEDED/FAILED` - - 若失败命中资源不足模式:`FAILED -> PENDING_RESOURCES` + 计划下次重试 - ---- - -## 8. 接口与验收(DoD) - -### 8.1 API 能力(最小集合) - -详见 `specs/mvp/v2.0/v2_api.md`。 - -### 8.2 验收口径(DoD) - -1) API 提交 PPO/GRPO/SFT,返回 `task_id`,并在 NFS 上创建任务目录。 -2) 当集群忙(GPU 不足)时: - - task 状态为 `PENDING_RESOURCES`(不是 FAILED) - - 一旦资源释放,任务自动变为 `SUBMITTED/RUNNING` -3) 当 race 导致触发 verl fail-fast: - - attempt 标记为 `INSUFFICIENT_RESOURCES` - - task 回到 `PENDING_RESOURCES`,并在 60s 后自动重试 -4) 通过 API 查询 task 能看到: - - 当前 state - - 最新 attempt 的 `ray_submission_id` - - attempt 历史(至少包含开始/结束/失败原因) -5) Cancel 能停止正在运行的 Ray Job(调用 Ray Jobs SDK stop) - ---- - -## 9. v2.0 交付物建议(目录) - -`specs/mvp/v2.0/`(本目录): -- `v2_plan.md`:总体设计与开发计划(本文件) -- `v2_api.md`:API 详细定义(请求/响应/字段/错误码) - -代码建议位置(后续实现时): -- `src/mvp/v2.0/` - - `py/`:API server + scheduler - - `scripts/`:启动/停止/查看状态(仍沿用 v1.1 的 compose/cluster 逻辑) diff --git a/specs/mvp/v2.5/README.md b/specs/mvp/v2.5/README.md deleted file mode 100644 index ebd49fd..0000000 --- a/specs/mvp/v2.5/README.md +++ /dev/null @@ -1,15 +0,0 @@ -# MVP v2.5(Design)— User Management & Stateless Ray Node Pool - -本目录基于 `specs/mvp/mvp_roadmap_v2.md` 与 `specs/mvp/image/roadmap_v2.5.png` 的 v2.5 规划, -给出一份**可落地、可验证、可迭代实现**的详细方案设计文档集合。 - -v2.5 的核心变化: -- 在 v2.0 的任务队列/调度/重试基础上,引入 **User Management**(多用户隔离、目录隔离、token)。 -- 引入 **Stateless Ray Node Pool**:worker 节点/容器不再需要平台显式下发 head 地址,通过共享存储(GPFS/NFS)完成服务发现与自愈连接(watchdog)。 - -文档: -- `specs/mvp/v2.5/v2.5_design.md`:总体架构、关键机制(head IP file / watchdog / 用户隔离 / 任务流)。 -- `specs/mvp/v2.5/v2.5_api.md`:API 设计(用户、任务、队列、日志)与鉴权约定。 -- `specs/mvp/v2.5/v2.5_acceptance.md`:开发/部署/验收流程与可验证标准。 -- `specs/mvp/v2.5/v2.5_summary.md`:v2.5 已实现内容总结(本次迭代做了什么、验收结果、已知限制)。 -- `specs/mvp/v2.5/v2.5_container_design.md`:将 stateless pool 固化到单镜像(head/worker 复用 + supervisor 守护)的设计与验证流程。 diff --git a/specs/mvp/v2.5/notices.md b/specs/mvp/v2.5/notices.md deleted file mode 100644 index 6b4a2cf..0000000 --- a/specs/mvp/v2.5/notices.md +++ /dev/null @@ -1,3 +0,0 @@ -# 记录问题 -1. task 、 submission id 里加上 user name -2. 补全端到端测试用例,各种正常和异常用例,边界情况测试 \ No newline at end of file diff --git a/specs/mvp/v2.5/v2.5_acceptance.md b/specs/mvp/v2.5/v2.5_acceptance.md deleted file mode 100644 index 74e2953..0000000 --- a/specs/mvp/v2.5/v2.5_acceptance.md +++ /dev/null @@ -1,67 +0,0 @@ -# MVP v2.5 开发/部署/验收标准 - -本文件定义 v2.5 的“可验证闭环”,确保每个里程碑可验收。 - ---- - -## 1. 开发交付物(Deliverables) - -### 1.1 代码交付(建议) - -- API Server 增强:user management + task 关联 user_id + 鉴权隔离 -- SQLite schema 迁移:新增 users/tokens,tasks 增加 user_id -- Ray Head service discovery:head.json 写入与心跳刷新 -- Worker bootstrap + watchdog: - - dev:以脚本方式提供(docker compose 场景) - - prod:以容器 command/entrypoint 方式可注入 - -### 1.2 文档交付 - -- 目录结构与 GPFS 路径约定 -- API 文档(含用户与多租户隔离) -- 运维 SOP:head 重启、worker 自愈、如何排障 head.json - ---- - -## 2. 部署流程(Dev 环境可验证) - -### 2.1 启动顺序(推荐) - -1) 启动 head(包含 API server + Ray head) -2) head 写入 `/private/ray/discovery//head.json` -3) 启动若干 worker(无须指定 head 地址) -4) worker 自动读取 head.json 并加入集群 -5) 通过 API 创建用户并获取 token -6) 使用 user token 提交 PPO/GRPO/SFT - ---- - -## 3. 验收标准(Acceptance Criteria) - -### 3.1 Stateless Ray Node Pool - -- A1:在 worker 启动时不传 head 地址,worker 能在 `T<=60s` 内加入集群(ray status 可见) -- A2:head 容器重启(IP 变化或 Ray 重启)后: - - head.json 更新 - - worker watchdog 在 `T<=60s` 内自动重连 -- A3:head 设置 `--num-gpus=0 --num-cpus=0`,训练 driver 不会跑到 head(可通过 Ray dashboard/日志验证) - -### 3.2 User Management - -- U1:admin 可创建用户并签发 token(token 仅返回一次) -- U2:用户 A 提交的 task,用户 B 无法查询/取消/获取日志(API 返回 404 或 403,按设计约定) -- U3:仅隔离 jobs 输出:任务输出落在 `/private/users//jobs//...`,不同用户互不覆盖 -- U4:训练输入(verl 代码、HF cache、datasets)统一使用 `/private/common/...`(v2.5 不做输入隔离) - -### 3.3 Task Flow(继承 v2.0) - -- T1:PPO/GRPO/SFT 三种 workload 都能成功提交并跑通(dev 规模可用 epoch=1/steps=10) -- T2:资源不足时任务不会“直接失败不可恢复”,而是进入 `PENDING_RESOURCES` 并按间隔重试(与 v2.0 同逻辑) - ---- - -## 4. 回归用例(最小集合) - -1) 创建用户 alice/bob,分别提交 sft,验证隔离与输出目录 -2) 启动 head + 2 workers,提交 ppo/grpo,验证 driver 落 worker -3) 重启 head(或修改 head.json 指向新 IP),验证 worker watchdog 自动重连 diff --git a/specs/mvp/v2.5/v2.5_api.md b/specs/mvp/v2.5/v2.5_api.md deleted file mode 100644 index 2a37650..0000000 --- a/specs/mvp/v2.5/v2.5_api.md +++ /dev/null @@ -1,109 +0,0 @@ -# MVP v2.5 API 设计(User + Task + Queue) - -v2.5 在 v2.0 API 基础上,新增 **User Management** 与多租户隔离。 - -约束: -- 仍使用内部 token(API key); -- 不引入外部 IAM; -- TaskSpec 仍为 YAML(沿用现有结构化字段)。 - ---- - -## 1. Auth - -Header: -- `Authorization: Bearer ` - -服务端行为: -- 将 `api_token` 映射到 `user_id` -- 之后的 task 操作默认仅作用于该 `user_id` - -Admin token(可选): -- 支持额外配置 `MVP_ADMIN_TOKEN`(或 user.role=admin) -- admin 可跨用户查询/取消(用于运维)。 - ---- - -## 2. User Management - -### 2.1 创建用户(admin) - -`POST /api/v2/users` - -Request(JSON): -```json -{"user_id":"alice","display_name":"Alice"} -``` - -Response: -```json -{"user_id":"alice","state":"ACTIVE"} -``` - -### 2.2 为用户签发 token(admin) - -`POST /api/v2/users/{user_id}/tokens` - -Response(只返回一次明文 token): -```json -{"user_id":"alice","token":"mvp_u_..."} -``` - -### 2.3 禁用用户(admin) - -`POST /api/v2/users/{user_id}:disable` - ---- - -## 3. Task Management(多租户) - -### 3.1 提交任务 - -`POST /api/v2/tasks` - -Body: -- `Content-Type: application/yaml` -- raw TaskSpec YAML(训练语义字段;不含 user_id) - -Response: -```json -{"task_id":"mvp25-ppo-20251225-170001-2a3f","state":"QUEUED"} -``` - -服务端 side effects: -- 记录 tasks.user_id(由 token 得到) -- 计算输出目录:`/private/users//jobs//...` - -### 3.2 查询任务(仅本人) - -`GET /api/v2/tasks/{task_id}` - -若 task 不属于当前 user: -- 返回 `404`(避免泄露存在性) - -### 3.3 取消任务(仅本人) - -`POST /api/v2/tasks/{task_id}:cancel` - ---- - -## 4. Queue/Debug - -### 4.1 查看队列(本人视角) - -`GET /api/v2/queue` - -返回该 user 的 pending/running 列表。 - -### 4.2 管理员查看全局队列(admin) - -`GET /api/v2/admin/queue` - ---- - -## 5. Logs - -`GET /api/v2/tasks/{task_id}/logs?attempt=latest&tail=2000` - -行为与 v2.0 一致:透传 Ray Job logs tail。 - diff --git a/specs/mvp/v2.5/v2.5_container_design.md b/specs/mvp/v2.5/v2.5_container_design.md deleted file mode 100644 index 653ea76..0000000 --- a/specs/mvp/v2.5/v2.5_container_design.md +++ /dev/null @@ -1,202 +0,0 @@ -# MVP v2.5 — Stateless Ray Node Pool 容器固化设计 - -目标:把 v2.5 的 **stateless pool(head discovery + worker watchdog)** 能力固化到一个可复用镜像中,避免依赖宿主机脚本在容器内 `docker exec` 启动/守护进程。**同一个镜像同时供 head/worker 复用**,通过环境变量区分角色。 -约束:**API server 代码与镜像解耦**,短期仍按现状“宿主机代码挂载到 head 容器,在 head 容器内启动 API”,不把 API 代码打进本镜像。 - ---- - -## 1. 背景(现状与痛点) - -当前 `src/mvp/docker-compose.yaml` 里 head/worker 都基于 `verlai/verl:sgl055.latest`,容器启动后 `command: sleep infinity`,再由宿主机脚本完成: -- head:`ray start --head ...` + `head_publisher`(写 `head.json`) -- worker:`worker_watchdog`(读取 `head.json`,自动加入/重连 ray 集群) - -现状问题: -- 启动流程依赖宿主脚本 `docker exec`,易受权限/路径/人为操作影响; -- “守护”目前是 bash while-loop,出现异常时排障成本高; -- 未来生产环境容器可能由算力平台拉起,我们只能 SSH 纳管,更需要把“自启动 + 自愈”放到容器内部。 - ---- - -## 2. v2.5 容器固化目标与非目标 - -### 2.1 目标 -- **一个镜像复用**:head/worker 统一镜像,通过 `ARGUS_ROLE=head|worker` 区分。 -- **supervisor 守护**:无论 head/worker,都使用 `supervisord` 守护关键进程: - - watchdog 崩溃 → supervisor 自动重启 watchdog - - ray 节点崩溃 → watchdog/或 supervisor 触发自动恢复(见 3.2 进程模型) -- **与共享存储对齐**:容器内统一挂载根路径 `/private`;discovery 文件写到共享存储。 -- **最小内置代码**:镜像只内置 stateless pool 相关 python 脚本(discovery/publisher/watchdog/entrypoint),不把 API 服务代码打进镜像。 - - **远端构建**:镜像构建必须在开发/运行机器(例如 `argus@h1`)上完成,本机不要求具备 `verlai/verl:*` 基础镜像。 - -### 2.2 非目标(本迭代不做) -- 不把 API server 打包进本镜像(后续可做单独 `argus-api` 镜像)。 -- 不改变 v2.5 TaskSpec 约束(仍使用 `/private/common/...` 公共资源;用户隔离只隔离 jobs)。 -- 不在本迭代引入 K8s/operator/autoscaler;只固化容器自启动/自愈。 - ---- - -## 3. 设计方案 - -### 3.1 单镜像架构概览 - -新增一个镜像(示例名): -- `argus/argus-ray-node:v2.5` - -该镜像: -- `FROM verlai/verl:sgl055.latest`(通过 build-arg 可切换 base) -- 内置: - - `argus_raypool`(或复用现有 `argus.ray.*` 子集)脚本: - - `discovery.py`:head record 读写(head.json) - - `head_publisher.py`:head 写入 head.json(带 TTL/刷新) - - `worker_watchdog.py`:worker 读取 head.json,自动加入/重连 - - (可选)`head_watchdog.py`:把 “ray head + publisher” 组装成一个可恢复的 watchdog - - `/usr/local/bin/argus-entrypoint.sh`:根据 role 生成 supervisor 配置并启动 supervisor - - supervisor 配置模板(或运行时生成) - -### 3.2 进程模型(确保“ray 崩/ watchdog 崩都能恢复”) - -用户新增要求:head/worker 均要 supervisor 守护 watchdog;ray 节点崩溃或 watchdog 崩溃都要自动恢复。 - -推荐进程组织(避免 “ray start” 后台化导致 supervisor 无法感知): - -#### A) Head 容器(ARGUS_ROLE=head) -由 supervisor 启动 **两个 program**: -1) `argus_head_watchdog`(推荐实现为 python 或 bash,内部用 `ray start --head --block` 前台运行) - - 关键点:`ray start --head --block` 让 Ray 进程前台阻塞,watchdog 作为父进程能感知退出码 - - ray 崩 → `ray start --block` 返回 → watchdog 退出非 0 → supervisor 重启 watchdog → ray 自动重启 -2) `argus_head_publisher` - - 定期刷新 `head.json`(TTL/refresh) - - publisher 崩 → supervisor 自动重启 - -> 备选:把 publisher 逻辑合并进 `argus_head_watchdog`(一个进程同时跑 ray + publisher 线程),减少 supervisor program 数量;但拆分更易观测与定位问题。 - -#### B) Worker 容器(ARGUS_ROLE=worker) -由 supervisor 启动 **一个 program**: -1) `argus_worker_watchdog` - - 轮询读取 `head.json`,并以 `ray start --address=:6379 --block` 方式加入集群 - - 只要 ray 进程退出(ray 崩/被 stop),`--block` 结束,watchdog 进入下一轮重连/重启 - - watchdog 自己异常退出 → supervisor 自动重启 watchdog - -> 注意:当前仓库里的 `worker_watchdog.py` 是 “`ray start` 非 block + 仅在 head addr 变化时重启”。容器固化建议升级为 “`--block` + 监测 ray 退出” 模式,否则 supervisor 很难准确感知 ray 的生命周期。 - -### 3.3 配置与环境变量(Role 驱动) - -镜像入口只依赖环境变量,不依赖宿主脚本参数。 - -建议环境变量清单(含默认值): -- `ARGUS_ROLE`:`head` / `worker`(必填) -- `ARGUS_SHARED_ROOT`:默认 `/private` -- `ARGUS_CLUSTER_NAME`:默认 `argus-ray` -- `ARGUS_HEAD_IP_FILE`:默认 `${ARGUS_SHARED_ROOT}/ray/discovery/${ARGUS_CLUSTER_NAME}/head.json` -- `ARGUS_RAY_PORT`:默认 `6379` -- `ARGUS_DASHBOARD_PORT`:默认 `8265`(head) -- `ARGUS_TTL_S`:默认 `60`(head publisher) -- `ARGUS_REFRESH_S`:默认 `10`(head publisher) -- `ARGUS_POLL_S`:默认 `5`(worker watchdog) -- `ARGUS_NODE_IP`:默认空;若空则 entrypoint 自动探测容器 IP -- `ARGUS_WORKER_RESOURCES_KV`:默认 `worker_node=100`(用于 driver 强制落 worker 的自定义资源) -- `ARGUS_RAY_EXTRA_ARGS`:可选,传递额外 `ray start` 参数 -- `ARGUS_LOG_DIR`:默认 `${ARGUS_SHARED_ROOT}/common/logs`(落到共享目录便于排障) - -### 3.4 Dockerfile / entrypoint / supervisor 设计 - -#### Dockerfile(建议路径) -在仓库新增(后续实现时): -- `src/mvp/images/argus-ray-node/Dockerfile` -- `src/mvp/images/argus-ray-node/entrypoint.sh` -- `src/mvp/images/argus-ray-node/supervisord.conf.tmpl`(可选) -- `src/mvp/images/argus-ray-node/py/argus_raypool/*.py`(仅 stateless pool 子集) - -Dockerfile 关键动作: -- `FROM verlai/verl:sgl055.latest`(可 `ARG BASE_IMAGE=...`) -- 安装 supervisor: - - Debian/Ubuntu 基底:`apt-get update && apt-get install -y supervisor` - - 设定 `CMD ["supervisord","-n","-c","/etc/supervisor/supervisord.conf"]` -- 拷贝 python 脚本到 `/opt/argus/raypool` 并设置 `PYTHONPATH=/opt/argus` -- 拷贝 entrypoint 到 `/usr/local/bin/argus-entrypoint.sh` -- `ENTRYPOINT ["/usr/local/bin/argus-entrypoint.sh"]` - -entrypoint.sh 逻辑: -- 探测容器 IP(如 `hostname -i` 或 `ip route get 1.1.1.1`) -- 根据 `ARGUS_ROLE` 生成 supervisor 配置: - - head:启动 `head_watchdog` + `head_publisher` - - worker:启动 `worker_watchdog` -- 配置 supervisor: - - `autorestart=true` - - `startretries` 合理配置 - - stdout/stderr 指向 `${ARGUS_LOG_DIR}/...` 或直接 stdout(便于 `docker logs`) - -### 3.5 与 API server 的关系(保持解耦) -API server 仍按现状(短期方案): -- **代码存放在宿主机**,通过 volume mount 挂载到 head 容器(例如 `/workspace/mvp`)。 -- **在 head 容器内启动 API**(例如用脚本 `docker exec argus-ray-head ... python3 /workspace/mvp/py/server.py`)。 -- 关键点:即使 API 进程跑在 head 容器里,也仍视作“独立于 ray node 镜像的业务代码”,后续可独立演进为单独的 `argus-api` 镜像。 -- 只要 API 能访问 Ray job server(通常 `http://127.0.0.1:8265` 在 head 容器视角)即可。 - -未来(非本迭代)可将 API server 单独做 `argus-api` 镜像,按相同 `/private` 共享目录运行。 - ---- - -## 4. docker-compose 调整建议(后续实现) - -当前 compose 的变化点(概念上): -- `image: verlai/verl:sgl055.latest` → `image: argus/argus-ray-node:v2.5` -- `command: sleep infinity` 移除(镜像自带 entrypoint) -- head service 增加: - - `ARGUS_ROLE=head` - - 暴露 dashboard 端口保持 `8265:8265` -- worker service 增加: - - `ARGUS_ROLE=worker` - - `ARGUS_WORKER_RESOURCES_KV=worker_node=100` -- volumes 仍需要: - - `../../shared:/private`(共享存储) - - `../../verl:/workspace/verl`(verl 代码/依赖按现状) - ---- - -## 5. 验证与回归流程(落地后怎么验收) - -### 5.1 构建镜像 -1) **在远端 `argus@h1` 构建**(本机不要求具备基础镜像): - - `cd /home2/argus/infra/mvp/src/mvp` - - `docker build -t argus/argus-ray-node:v2.5 -f images/argus-ray-node/Dockerfile .` -2) 也可以使用 compose build(推荐,和实际运行一致): - - `docker compose -f docker-compose.yaml build --no-cache` - -### 5.2 基础连通性(stateless pool 验证) -1) `docker compose up -d` -2) 验证 head 写入: - - 共享目录存在 `head.json`:`${ARGUS_SHARED_ROOT}/ray/discovery/${ARGUS_CLUSTER_NAME}/head.json` -3) 验证 worker 自动加入: - - 在 head 容器内 `ray status` 能看到 worker 节点加入 - - Dashboard Nodes 页面能看到 head + worker - -### 5.3 故障注入(supervisor 自愈验证) -1) watchdog 崩溃: - - `pkill -f worker_watchdog`(或 kill 对应 PID) - - 期望:supervisor 自动拉起 watchdog;worker 最终重新加入集群 -2) ray 节点崩溃(worker): - - `ray stop --force` 或 kill raylet - - 期望:watchdog 重新执行 `ray start ... --block`,worker 恢复 -3) ray 节点崩溃(head): - - kill head ray 前台进程(由 watchdog 启动) - - 期望:supervisor 重启 head_watchdog;head 恢复并重写 head.json;workers 自动重连 - -### 5.4 端到端任务回归(与 v2.5 API 协作) -沿用现有 v2.5 E2E: -- `src/mvp/scripts/run_all_v25_api.sh` -- `src/mvp/scripts/run_e2e_v25_cases.sh` - -验收标准: -- PPO/GRPO/SFT 均能在 worker 上运行,head 不跑训练 -- API 的 task_id / submission_id 正常携带用户名 -- 资源不足可转 `PENDING_RESOURCES` 并按周期重试 - ---- - -## 6. 风险点与对策 - -- **ray start 后台化**:如果继续后台启动,supervisor 不易感知 ray 崩溃。对策:使用 `ray start --block`(推荐)。 -- **IP 探测不稳定**:不同环境(compose/平台)容器 IP 获取方式不同。对策:entrypoint 做多策略探测并允许 `ARGUS_NODE_IP` 显式覆盖。 -- **日志可观测性**:建议同时支持写到 `/private/common/logs`(共享)以及 stdout(`docker logs`)。 diff --git a/specs/mvp/v2.5/v2.5_design.md b/specs/mvp/v2.5/v2.5_design.md deleted file mode 100644 index 8ae30ad..0000000 --- a/specs/mvp/v2.5/v2.5_design.md +++ /dev/null @@ -1,255 +0,0 @@ -# MVP v2.5 详细设计方案(User Management + Stateless Ray Node Pool) - -本文目标:把 `mvp_roadmap_v2.md` 中 v2.5 的思路落到**可工程化实现**的设计层,包括: -- API Server 内新增 user management; -- Ray node pool 变为无状态(worker 自发现 head、自动加入、watchdog 自愈); -- 仍保持 v2.0 的“任务管理层”语义:Task/Attempt、队列、资源判断、Ray Job 提交与状态同步; -- 所有共享数据/状态统一落在 GPFS(dev 环境可先用 NFS),容器内路径统一为 `/private/`。 - -> 术语说明:文中“GPFS”代表生产共享存储;dev 环境可用 NFS,但容器内仍以 `/private/` 访问。 - ---- - -## 1. 目标与非目标 - -### 1.1 v2.5 目标(Must) - -1) **User Management(最小多租户)** -- 支持创建/禁用用户; -- 为每个用户签发内部 token(API key),用于认证与隔离; -- 用户隔离(v2.5 先做最小闭环,仅隔离 **jobs 输出** 与 API 可见性): - - 用户只能看到/操作自己的 Task; - - 训练输出(job root、checkpoints、日志归档等)按 user 目录落盘; - - 训练输入(verl 代码、HF cache、datasets)统一使用 `common/`(v2.5 不支持用户自定义代码/模型/数据集隔离)。 - -2) **Stateless Ray Worker Node Pool** -- worker 容器启动时无需被平台告知 head 地址; -- worker 通过 GPFS 读取 **Head IP File** 自动连接 Ray head; -- worker 内部 watchdog 监控 head 地址变化,发生变化时自动 `ray stop` + `ray start` 重连; -- worker 尽量不依赖本地持久化状态(宕机/替换后可无感重建)。 - -3) **保持 v2.0 的 Task 管理行为** -- Task/Attempt 模型不变(或向后兼容扩展); -- 对齐 verl 的 fail-fast 行为:资源不足时服务侧 pending + 重试; -- Ray Job 提交仍通过 Ray Python SDK(JobSubmissionClient)。 - -### 1.2 v2.5 非目标(Not Now) - -- 完整 WebUI(留到 v3.0)。 -- 公平调度/配额/优先级(留到 v3.x)。 -- 完整生产级 IAM(留到 v4+),v2.5 仅内部 token。 -- K8s 原生编排(本阶段不要求,但设计需能适配“算力平台拉起容器,只能 ssh 进去纳管”的模式)。 - ---- - -## 2. 总体架构(对应 roadmap v2.5) - -### 2.1 组件划分 - -**控制面(Control Plane)** -- **API Server** - - user management - - task management(队列/调度/重试/状态聚合) - - Ray Job Tool(Ray Client) - - VerlTaskSpec(TaskSpec YAML,沿用 v2.0/v2.1 格式) - - 与 Ray head 在同一台/同一容器是推荐形态(便于访问 dashboard / job server) -- **Ray Head(有状态)** - - 启动后把 head 地址写入 GPFS 的 Head IP File,用于 worker 服务发现 - -**数据面(Data Plane)** -- **Ray Workers(无状态节点池)** - - stateless bootstrap:从 GPFS 读取 head 地址自动加入集群 - - watchdog:持续 watch head 地址文件变化并自愈重连 - -**共享存储(GPFS)** -- 统一数据路径:数据、模型 cache、代码、任务输出、以及 head 服务发现文件。 - -### 2.2 v2.5 的控制反转(IoC) - -与 v2.0/手工集群的关键差异: -- v2.0:平台脚本/运维显式启动 worker 并指定 `--address=`。 -- v2.5:worker 自己从 GPFS 读取 `head_ip_file`,无需平台维持 worker 列表与 SSH 连接池。 - ---- - -## 3. GPFS 目录结构(容器内 `/private`) - -建议在 v2.5 固化以下目录(与现有 v2.0 兼容扩展): - -``` -/private/ - ray/ - discovery/ - / - head.json # Head IP File(服务发现) - head.json.lock # 可选:写入锁(v2.5 可先不实现) - users/ - / - jobs/ # /private/users//jobs//* - outputs/ # 训练输出聚合(按需要) - common/ - code/ # 平台/公共代码快照(verl code snapshot 等) - datasets/ # 公共数据集 - hf/ # 公共 HF cache(dev 复用) - db/ # sqlite - logs/ # API 日志、平台日志 -``` - -说明: -- `common/`:平台默认目录(v2.5 先默认所有用户可写;后续再加 ACL/只读)。 -- `users//...`:用户隔离主边界(最小多租户的关键)。 - ---- - -## 4. Head IP File(服务发现)设计 - -### 4.1 文件路径 - -- `head_ip_file = /private/ray/discovery//head.json` -- ``:由配置指定(例如 `argus-ray`),允许同一 GPFS 上存在多个环境/集群。 - -### 4.2 文件内容(JSON) - -建议采用 JSON(易扩展): - -```json -{ - "cluster_name": "argus-ray", - "head_ip": "10.0.0.12", - "gcs_port": 6379, - "dashboard_port": 8265, - "job_server_url": "http://10.0.0.12:8265", - "updated_at": "2025-12-25T17:00:00Z", - "expires_at": "2025-12-25T17:01:00Z" -} -``` - -关键点: -- `updated_at`:便于排障与可观测; -- `expires_at`:避免 worker 读取到“陈旧 head 地址”后无限重连; -- `job_server_url`:对外可直接用于 Ray Job Tool 配置(便于无脑接入)。 - -### 4.3 写入策略(原子更新) - -Head 写入时必须保证 worker 读取不会读到半文件: -- 写临时文件 `head.json.tmp`; -- `fsync`(可选); -- `rename(head.json.tmp -> head.json)`(原子替换)。 - -### 4.4 心跳与 TTL - -Head 进程需周期性刷新 `head.json`: -- 建议 `ttl_s=60`,刷新周期 `refresh_s=10`; -- 若 head 进程异常退出,worker 读取到过期文件可进入“等待模式”而非无限重连。 - ---- - -## 5. Stateless Worker Bootstrap + Watchdog - -### 5.1 启动序列(worker 容器内) - -1) 启动脚本读取 `head.json`: - - 若文件不存在:sleep + 重试(直到存在) - - 若存在但 `expires_at` 已过期:sleep + 重试(直到变为新鲜) -2) 解析 `head_ip:gcs_port` 并执行: - - `ray stop --force || true` - - `ray start --address=: --resources='{"worker_node": 100, ...}' ...` -3) 启动 watchdog 进程(同容器): - - 轮询/监听 `head.json` 的内容变化 - - 一旦 `head_ip` 或 `gcs_port` 改变,触发 `ray stop` + `ray start` 重连 - -### 5.2 Watchdog 策略(最小可用) - -v2.5 推荐“简单且稳”的实现: -- polling 间隔 `watch_s=5`; -- 对比 `head.json` 的 `updated_at` 或 hash; -- 若发现变更:执行重连; -- 若连续多次重连失败:指数退避(v2.5 可先固定退避,v2.6 再增强)。 - -### 5.3 资源标签(driver 强制落 worker) - -继续沿用 v2.0 的思路: -- worker 启动时 `--resources='{"worker_node": 100}'` -- head 不包含 `worker_node` 资源 -- Ray job submit 时设置 entrypoint_resources:`{"worker_node": 1}` - -### 5.4 GPU/CPU 的“无状态”约束 - -- worker 是否有 GPU 由底层算力平台决定(生产上平台会为容器挂载 GPU); -- worker 启动脚本不应硬编码 GPU 编号,只依赖 `NVIDIA_VISIBLE_DEVICES`/平台注入; -- head 推荐 `--num-gpus=0 --num-cpus=0`,避免训练调度到 head。 - ---- - -## 6. User Management 设计(最小多租户) - -### 6.1 数据模型(SQLite) - -新增两张表(示意): -- `users` - - `user_id`(PK) - - `display_name` - - `state`(ACTIVE/DISABLED) - - `created_at` -- `api_tokens` - - `token_hash`(PK) - - `user_id`(FK) - - `created_at` - - `last_used_at` - -并在 `tasks` 表增加: -- `user_id`(FK) - -### 6.2 鉴权策略 - -内部 token 模式: -- `Authorization: Bearer ` -- 服务端将 token 映射到 `user_id` -- 后续所有 task 查询/取消/日志默认 scope 到该 `user_id` - -管理员能力(v2.5 最小实现): -- 额外配置一个 admin token(或把特定 user 标记为 admin) -- admin 可 list all users/tasks(用于运维排障)。 - -### 6.3 用户目录隔离(路径约束) - -核心原则(v2.5 版): -- **输出**:必须落在 `/private/users//jobs/...`(服务端统一计算,不允许用户任意指定输出根) -- **输入**:统一使用 `/private/common/...`(v2.5 不支持用户自定义 verl 代码、也不做 hf/datasets 的用户隔离) - -服务端处理策略(最小可用): -- 解析 TaskSpec 后,对输入路径字段做白名单前缀校验(必须是 `/private/common/...`;拒绝 `../` 与越界路径); -- 输出目录统一由服务端计算:`job_root = /private/users//jobs//`。 - ---- - -## 7. TaskSpec(VerlTaskSpec YAML)在 v2.5 的扩展点 - -v2.5 **不扩展 TaskSpec**:保持与 v2.0/v2.1 的 YAML 结构化字段与语义一致。 - -v2.5 的“用户语义”仅体现在服务端的补齐/约束: -- user_id 由 token 推导(用户不需要在 YAML 里写 user_id); -- 服务端派生 `ray_submission_id`(由 task_id/attempt 派生); -- 服务端统一计算输出目录 `job_root=/private/users//jobs//...`; -- v2.5 不支持用户自定义 verl 代码路径(因此 runtime_env 不需要注入用户 code 目录)。 - ---- - -## 8. 迁移与兼容性 - -v2.5 设计需满足: -- 现有 v2.0 的“手工启动 worker”仍可运行(作为 dev fallback); -- 在不改镜像的前提下,worker watchdog 可以以“容器启动命令/entrypoint”方式注入(dev 用 scripts;生产由算力平台指定 command)。 - ---- - -## 9. 风险与对策(v2.5) - -1) **GPFS 上 head.json 一致性/延迟** -- 对策:原子 rename + TTL;watchdog polling。 - -2) **Ray head 重启后 job server URL 变化** -- 对策:head.json 内写入 `job_server_url`,Ray Job Tool 可读取该文件更新 address(v2.6 可做动态 reload)。 - -3) **Worker 重连期间任务波动** -- 对策:服务侧调度器对齐 verl 的资源 fail-fast;任务失败可归因并排队重试。 diff --git a/specs/mvp/v2.5/v2.5_dev_plan.md b/specs/mvp/v2.5/v2.5_dev_plan.md deleted file mode 100644 index ce2bad6..0000000 --- a/specs/mvp/v2.5/v2.5_dev_plan.md +++ /dev/null @@ -1,229 +0,0 @@ -# MVP v2.5 开发计划(TDD 驱动) - -本文是 v2.5 的**工程化开发计划**,强调“先写测试,再写实现”(TDD),并将每个里程碑拆成**可独立验收**的小闭环。 - -输入依据: -- 路线图:`specs/mvp/mvp_roadmap_v2.md` -- v2.5 设计:`specs/mvp/v2.5/v2.5_design.md` -- v2.5 API 草案:`specs/mvp/v2.5/v2.5_api.md` -- v2.5 验收:`specs/mvp/v2.5/v2.5_acceptance.md` - -v2.5 约束(已确认): -- **不扩展 TaskSpec**:沿用 v2.0/v2.1 的 YAML 结构化字段与语义。 -- **不支持自定义 reward function / 不支持用户自定义 verl 代码**。 -- 训练输入(verl 代码、HF cache、datasets)统一使用 `/private/common/...`。 -- 多用户隔离 v2.5 **先只隔离 jobs 输出目录**:`/private/users//jobs//...`。 - ---- - -## 0. TDD 规范(所有功能都遵循) - -### 0.1 测试分层 - -1) **单元测试(fast)** -- 纯 Python 逻辑:DB、鉴权、ID、路径派生、head.json 解析/TTL、watchdog 决策逻辑。 -- 目标:不依赖真实 Ray、不依赖 docker、不依赖网络。 - -2) **组件测试(中等)** -- FastAPI 路由:使用 `fastapi.testclient.TestClient`(现有 v2.0 已采用)。 -- 目标:验证 auth/权限隔离、API 行为、状态机。 - -3) **端到端(慢/手工或脚本)** -- 在 `argus@h1` 上通过 scripts/compose 跑一次“head publish → worker auto-connect → API submit”闭环。 -- 目标:验证无状态 worker + watchdog 的真实行为。 - -### 0.2 测试约定 - -- 测试目录:`src/mvp/py/tests/` -- 新增功能必须先补齐测试用例,并让其在未实现时失败(红)。 -- 实现最小改动让测试变绿(绿)。 -- 重构/去重复(重构)。 - -> 注:现有测试通过 `src/mvp/py/tests/conftest.py` 注入 ray stub,确保单测不依赖真实 ray 包;v2.5 新增模块也应复用此模式。 - ---- - -## 1. 里程碑拆分(v2.5 = 4 个可验证闭环) - -### M1:User 表/Token 表 + 基础鉴权(不影响现有内部 token 兼容) - -**目标** -- 引入 user/token 的持久化与鉴权映射(token → user_id)。 -- 兼容现有 `Authorization: Bearer ` 的“单租户模式”,避免一次性破坏 v2.0 用法: - - v2.5 可以先支持两种 token 模式: - - legacy:环境变量 `MVP_INTERNAL_TOKEN`(全局单租户); - - user token:DB 内签发 token(多用户)。 -- admin 能创建用户、签发 token、禁用用户。 - -**TDD 用例(先写测试)** - -单测: -- `test_user_db_create_disable()` - - 创建用户 ACTIVE;禁用后状态变为 DISABLED;重复创建返回冲突或幂等(按最终约定)。 -- `test_token_hashing()` - - 签发 token 时 DB 中只保存 hash,不保存明文。 - -API 测试(TestClient): -- `test_admin_create_user_and_issue_token()` - - admin token 可创建用户并签发 token(明文 token 只返回一次)。 -- `test_disabled_user_token_rejected()` - - 用户被禁用后,使用旧 token 调用 API 返回 401/403。 - -**实现落点(建议模块)** -- `argus.service.auth`:token 校验与 user_id 解析(兼容 legacy 模式) -- `argus.service.db`:新增 `users`、`api_tokens` 表与 CRUD -- `argus.service.app`:新增 user 管理 endpoints(admin scope) -- `configs/dev.yaml`:补充 admin token/env 相关配置(保持 YAML 风格) - -**验收点** -- `v2.5_acceptance.md`:U1 可通过自动化 API 测试覆盖。 - ---- - -### M2:Task 绑定 user_id + API 可见性隔离(仍不改 TaskSpec) - -**目标** -- 提交 task 时由 token 推导 `user_id`,写入 `tasks.user_id`。 -- task 查询/取消/日志默认只允许 owner;他人访问返回 404(避免泄露存在性)。 -- queue 默认只返回当前用户队列;admin 可查询全局队列(可选)。 - -**TDD 用例(先写测试)** - -单测: -- `test_tasks_table_has_user_id()`:创建任务必须落 `user_id`,且 `list_queue(user_id=...)` 只返回该用户任务。 - -API 测试: -- `test_task_visibility_isolated()` - - user A 创建 task;user B 查询 `/api/v2/tasks/{id}` 返回 404; - - user B cancel/logs 也返回 404。 -- `test_queue_isolated()` - - A/B 各自创建 task;`GET /api/v2/queue` 只看到自己的。 - -**实现落点** -- `argus.service.app`:为 task endpoints 增加 user scope -- `argus.service.db`:tasks 表增加 user_id 字段、索引、按 user 过滤的查询方法 -- `argus.service.scheduler`:pick_next_runnable_task 等仍按“全局 FIFO”或“按 user FIFO” - - v2.5 先保持“全局 FIFO”最简单(但 API queue 视角是按 user 过滤)。 - -**验收点** -- `v2.5_acceptance.md`:U2 可通过 API 测试覆盖。 - ---- - -### M3:Jobs 输出目录按 user 隔离(只改输出,不改输入) - -**目标** -- Ray Job 的 job_root 目录由服务端统一计算到: - - `/private/users//jobs//...` -- TaskSpec 内与输入相关的路径字段必须是 `/private/common/...`(v2.5 输入统一 common)。 -- 任何用户无法通过 TaskSpec 指定输出写到非 user jobs 目录(避免越权写)。 - -**TDD 用例(先写测试)** - -单测: -- `test_job_root_derivation_per_user()` - - 给定 user_id 与 ray_submission_id,派生 job_root 固定且正确。 -- `test_reject_non_common_inputs()` - - TaskSpec 中 train_file / val_file / code_path / hf 路径等若不以 `/private/common/` 开头则拒绝(HTTP 400)。 - -API 测试: -- `test_job_dir_written_under_user_jobs()` - - 提交 task 后,在 DB 或 submit payload 中能看到 job_root 在 user jobs 下(可通过 mock RayJobTool.submit 捕获 spec)。 - -**实现落点(建议最小侵入)** -- 在 service 层派生 `job_root` 并注入到 RayJobTool/builders(而不是让用户从 TaskSpec 指定)。 -- RayJobTool `_job_dir()` 改为接收“job_root 生成器”或直接接收 `job_root` 参数(由服务层提供)。 - - 目标:保持 RayJobTool 的职责清晰:提交 Ray job;路径策略由 service 决定。 - -**验收点** -- `v2.5_acceptance.md`:U3/U4 可通过 API/单测覆盖。 - ---- - -### M4:Stateless Ray Node Pool(head.json + worker watchdog)+ 端到端脚本验证 - -**目标** -- head 启动后持续写入 `/private/ray/discovery//head.json`(包含 TTL)。 -- worker 容器内运行 watchdog(或启动脚本 + watchdog),无需平台显式传 head 地址: - - 读取 head.json(存在且未过期)→ `ray start --address=:` - - head.json 变化 → `ray stop` + `ray start` 重连 -- 在 dev 环境(docker compose)提供一键脚本复现(e2e)。 - -**TDD 用例(先写测试)** - -单测(不跑真实 ray): -- `test_head_json_read_validate_ttl()` - - 文件不存在/过期 → 返回“不可用” - - 未过期 → 返回 head 地址 -- `test_watchdog_decision_on_change()` - - head_ip 变化 → 触发重连动作 - - only updated_at 变化(地址不变)→ 不重连(或按策略重连,需确定) - -组件/脚本级测试(可选): -- 如果 watchdog 用 Python 实现,可对“执行命令”层做 stub(不真正跑 `ray start`),只验证会调用什么命令。 - -端到端脚本(手工/慢): -- 提供脚本 `scripts/run_all_v25_stateless.sh`(命名示例): - 1) 起 head(Ray head + API) - 2) 启动 head publisher(写 head.json) - 3) 起 2 个 worker(每个 4 GPU),worker 只跑 watchdog,不传 head 地址 - 4) `ray status` 显示 1 head + 2 worker 且 GPU=8 - 5) 通过 API 创建用户/签发 token,提交 PPO/GRPO/SFT - 6) 重启 head(或更新 head.json 指向新地址)验证 worker 自动重连 - -**实现落点(建议实现策略)** - -为了可测试性(TDD),推荐把“读 head.json/判定 TTL/生成 ray start 命令”做成 Python 模块: -- `argus.ray.discovery`:read/write head.json(原子写、TTL) -- `argus.ray.worker_watchdog`:watch loop(polling + change detection),执行命令可注入(便于单测 stub) - -脚本层保持薄: -- `scripts/` 负责 docker exec / compose 编排与进程守护; -- watchdog 进程由容器内 python 模块运行(更可测、更易移植到生产平台的 entrypoint/command)。 - -**验收点** -- `v2.5_acceptance.md`:A1/A2/A3 主要通过 e2e 脚本 + dashboard/日志验证。 - ---- - -## 2. 回归策略(确保 v2.0 不被破坏) - -在 v2.5 过程中保留并持续回归以下用例(至少单测覆盖): -- 旧的内部 token 模式仍可访问 `GET /api/v2/queue` 与提交 task(若决定保留兼容)。 -- scheduler 的“资源不足 → PENDING_RESOURCES → 延迟重试”行为不变(现有 `test_scheduler.py` 覆盖)。 -- `ray entrypoint_resources` 强制 driver 落 worker(继续使用 `worker_node` 自定义资源)。 - ---- - -## 3. 交付清单(代码/脚本/文档) - -### 3.1 代码 -- user/tokens:DB schema + auth + API endpoints -- tasks:绑定 user_id + 权限隔离 -- job_root:按 user jobs 输出目录派生(输入仍 common) -- discovery/watchdog:head.json + worker 自愈 - -### 3.2 scripts(dev e2e) -- head:启动 Ray head + head publisher -- workers:以无状态方式启动(不传 head addr)+ watchdog -- `run_all`:一键跑通(含 API submit + 查询 + cancel + 观察队列) - -### 3.3 文档 -- 更新 `specs/mvp/v2.5/*`(设计/API/验收/开发计划) -- 补充 `src/mvp/README.md` 的 v2.5 使用方式(如需要) - ---- - -## 4. 关键待确认点(开始实现前必须定稿) - -1) **legacy token 是否继续兼容** -- 方案 A:保留 `MVP_INTERNAL_TOKEN`(单租户)+ 新增 user token(多租户) -- 方案 B:v2.5 直接切换到 user token(破坏兼容,但更清晰) - -2) **调度公平性** -- v2.5 先全局 FIFO(简单);后续 v3 再引入 per-user 公平调度/配额。 - -3) **head.json 的生产写入者** -- 方案 A:与 API 同进程线程(最少组件) -- 方案 B:独立进程(更独立、易运维) - diff --git a/specs/mvp/v2.5/v2.5_e2e_test_cases.md b/specs/mvp/v2.5/v2.5_e2e_test_cases.md deleted file mode 100644 index 2e8472e..0000000 --- a/specs/mvp/v2.5/v2.5_e2e_test_cases.md +++ /dev/null @@ -1,132 +0,0 @@ -# MVP v2.5 端到端测试用例(正常/异常/边界) - -本用例集目标:覆盖 v2.5 的关键能力与边界条件(User + jobs 隔离 + stateless node pool + API 队列调度)。 - -约束(v2.5 已确认): -- TaskSpec 不扩展;不支持 reward_fn;不支持用户自定义 verl 代码。 -- 输入统一 `/private/common/...`;用户隔离先只隔离 `/private/users//jobs/...` 输出。 - ---- - -## 0. 环境前置 - -远端目录示例: -- `argus@h1:/home2/argus/infra/mvp/src/mvp/` - -共享目录(宿主机): -- `/home2/argus/infra/mvp/shared/` - -容器内路径约定: -- `/private` 为共享存储挂载点 - -需要: -- GPU 0-7 可用 -- 3 容器:head(无 GPU)+ 2 worker(各 4 GPU) - ---- - -## 1. 正常用例(Happy Path) - -### HP-1:v2.5 全链路(PPO → GRPO → SFT,串行) - -步骤: -1) `cd /home2/argus/infra/mvp/src/mvp/scripts` -2) `MVP_INTERNAL_TOKEN= RESET_DB=1 ./run_all_v25_api.sh` - -期望: -- Ray dashboard 显示 3 nodes(head+2 workers),GPU 总数 8。 -- 3 个 task 最终为 `SUCCEEDED`。 -- 输出目录存在且按用户隔离: - - `/private/users//jobs//{config,logs,checkpoints,debug}` - -### HP-2:Driver 不在 head 跑 - -验证点(任选一种): -- Ray job 的 driver node IP 不等于 head 容器 IP; -- 或日志/调度信息显示 entrypoint_resources 生效(driver 在 worker)。 - ---- - -## 2. 异常用例(Error Cases) - -### E-Auth-1:缺 token - -请求: -- `GET /api/v2/queue` 不带 `Authorization` 头 - -期望: -- 返回 401(missing bearer token) - -### E-Auth-2:无效 token - -请求: -- `Authorization: Bearer ` - -期望: -- 返回 401(invalid token) - -### E-Auth-3:用户禁用后拒绝访问 - -步骤: -1) admin 创建用户 `bob` 并签发 token -2) admin 禁用 `bob` -3) 用 bob token 请求 `/api/v2/queue` - -期望: -- 返回 403(user disabled) - -### E-Isolation-1:跨用户访问 task 资源(不泄露存在性) - -步骤: -1) alice 提交 task 得到 `task_id` -2) bob 查询 `/api/v2/tasks/{task_id}` - -期望: -- 返回 404(task not found) - -### E-Input-1:输入路径不在 /private/common(v2.5 约束) - -请求: -- 提交 taskspec 但 `train_file` 或 `code_path` 不以 `/private/common/` 开头 - -期望: -- 返回 400,并给出具体字段错误(例如 `train_file must start with /private/common/`)。 - ---- - -## 3. 边界用例(Boundary) - -### B-Queue-1:资源不足时不提交 Ray(PENDING_RESOURCES) - -步骤: -1) 构造任务需求 `nnodes=3` 且 `n_gpus_per_node=4`(total 12 GPU) -2) 提交后轮询状态 - -期望: -- task 进入 `PENDING_RESOURCES`(服务侧 pending,不向 Ray submit) -- 具备 `next_run_at` - -### B-Cancel-1:任务取消(QUEUED/RUNNING) - -步骤: -1) 提交一个较长 steps 的任务(确保有机会 RUNNING) -2) 调用 `POST /api/v2/tasks/{task_id}:cancel` - -期望: -- task state 为 `CANCELED` -- attempt 中 `ray_status` 最终为 `STOPPED`(或 Ray 侧停止) - ---- - -## 4. 可执行回归脚本 - -见: -- `src/mvp/scripts/run_e2e_v25_cases.sh` - -脚本覆盖: -- HP-1 -- E-Auth-1/E-Auth-2/E-Input-1 -- E-Isolation-1 -- B-Queue-1 -- B-Cancel-1(best-effort) - diff --git a/specs/mvp/v2.5/v2.5_summary.md b/specs/mvp/v2.5/v2.5_summary.md deleted file mode 100644 index deb52fa..0000000 --- a/specs/mvp/v2.5/v2.5_summary.md +++ /dev/null @@ -1,92 +0,0 @@ -# MVP v2.5 迭代总结(已落地) - -本文档总结 v2.5 在 v2.0/v2.1/v2.2…基础上完成的能力、实现点、验收方式与已知限制,便于回顾与后续版本迭代对齐。 - -## 目标与边界 - -v2.5 的核心目标: -- 引入 **User Management(用户管理)**:基于 token 的鉴权与任务级隔离(“只隔离 jobs”)。 -- 引入 **Stateless Ray Node Pool(无状态 Ray worker 池)**:worker 不依赖平台下发 head 地址,自动发现并连接/自愈。 -- 保持 **TaskSpec(v1.1 同款 YAML 格式)不扩展**:本迭代不支持 reward function、自定义 verl 代码等。 - -明确不做(v2.5 约束): -- 不支持 TaskSpec 扩展(例如 `reward_fn_path` 等)。 -- 不支持用户自定义 verl/hf/dataset 的隔离或自定义路径:**统一使用 `/private/common/...`** 的公共资源。 -- 用户隔离仅覆盖 **任务与产物目录**(jobs),不覆盖 HF cache、datasets 等公共缓存。 - -## 关键能力(对外表现) - -### 1) 多用户鉴权与任务隔离 -- API 仍使用内部 `Authorization: Bearer ` 方式: - - 管理员 token 来自环境变量 `MVP_INTERNAL_TOKEN`(admin)。 - - 业务用户 token 由管理员通过 API 下发并持久化到 SQLite。 -- 用户隔离策略: - - 非管理员用户只能查询/取消/拉取日志 **自己的 task**;跨用户访问返回 404(不泄露存在性)。 - - 训练产物落盘隔离:Ray job 目录统一写入 `/private/users//jobs//...`。 - -### 2) task_id / submission_id 带用户名 -- 新任务 ID 规则:`mvp2----` -- Ray submission id(attempt)规则:`--aNN`,因此自然包含用户名。 -- 作用:Dashboard/日志/落盘目录可读性更强,便于按用户追踪和审计。 - -### 3) “无状态 worker 池”与 head 地址发现 -- Head 在共享存储写入 **head 地址文件**(例如 `head.json`),worker 通过 watchdog: - - 轮询发现 head 地址 - - 自动 `ray start --address ...` 加入集群 - - 掉线后自动重连(watchdog 自愈) -- 达成效果:在生产环境中,即使 worker 容器由算力平台创建(只提供 SSH 纳管),也能通过共享存储实现连接与自愈。 - -### 4) 任务调度:队列 + Ray Job 提交 + 状态回传 -- API 提交任务后进入 SQLite 队列,由后台 scheduler 逐个提交到 Ray(默认 `max_running_tasks=1`)。 -- Scheduler 持续轮询 Ray job 状态并回写任务状态(RUNNING/SUCCEEDED/FAILED/CANCELED)。 -- 资源不足的“可重试失败”处理: - - 针对 VERL 的 fail-fast(`Total available GPUs ... is less than total desired GPUs ...`)或集群资源不足, - 任务进入 `PENDING_RESOURCES` 并设置 `next_run_at`,按 `retry_interval_s` 周期重试。 - -## 关键实现点(工程化落地) - -### 存储与目录约定(容器内视角) -- 共享根路径统一为 `/private`(对齐生产挂载)。 -- v2.5 强约束:TaskSpec 的以下字段必须以 `/private/common/` 开头: - - `code_path` / `train_file` / `val_file` -- 公共目录(示例): - - `/private/common/hf`:HF 缓存 - - `/private/common/datasets`:训练数据(必要时通过 symlink 指向已有缓存目录复用下载) - - `/private/common/db/mvp.sqlite3`:队列与用户信息(SQLite) - - `/private/common/logs`:API / watchdog 日志 - - `/private/users//jobs/...`:用户作业产物(隔离) - -### Ray 拓扑与“head 不跑训练” -- Head 启动为管理节点(CPU/GPU=0),避免训练任务落到 head。 -- Worker 节点具备 GPU(示例:2 个 worker * 每个 4 GPU)。 -- driver 通过 `entrypoint_resources`(例如 `worker_node: 1`)强制落 worker。 - -### 部署脚本与可重复执行 -提供完整脚本链路,覆盖: -- 清理 legacy 环境、起停容器、启动 Ray head -- head discovery publisher、worker watchdog 启动与状态检查 -- 数据/模型/代码准备(幂等、可复用已有下载) -- 启动 API server(并支持 RESET_DB) -- API 方式连续提交 PPO/GRPO/SFT 并等待完成 - -代表性脚本: -- `src/mvp/scripts/run_all_v25_api.sh`:v2.5 happy-path 端到端(含重建集群、准备资源、起 API、提交 3 类任务) -- `src/mvp/scripts/run_e2e_v25_cases.sh`:在 happy-path 基础上增加鉴权/隔离/输入校验/资源不足/取消等用例 - -## 验收与测试(已通过) - -### 单元测试(本机 venv) -- `.venv/bin/python -m pytest` -- 覆盖率阈值:>= 90% - -### 远端端到端(h1) -- 在 `argus@h1:/home2/argus/infra/mvp/src/mvp/scripts` 执行: - - `MVP_INTERNAL_TOKEN=mvp-dev-token RESET_DB=1 ./run_e2e_v25_cases.sh` -- 结果:happy-path(PPO/GRPO/SFT)完成,且异常/边界用例验证通过(鉴权、跨用户隔离、输入校验、资源不足转 PENDING_RESOURCES、取消任务等)。 - -## 已知问题与后续建议 - -- `max_running_tasks=1` 会让队列中的任务在前序 RUNNING 时保持 QUEUED,这在“资源不足”边界测试里需要显式清空/取消前序任务,或接受该行为作为设计的一部分。 -- 当前仍是 SQLite 单点;后续若要 HA/水平扩展,可在 v2.6+ 引入更强的持久化与多副本(例如 Postgres/etcd)。 -- API server / watchdog 目前以脚本方式守护;后续可进一步统一为 systemd/supervisor(或平台侧守护)并补齐健康检查与告警。 - diff --git a/specs/mvp/v3.0/README.md b/specs/mvp/v3.0/README.md deleted file mode 100644 index b338179..0000000 --- a/specs/mvp/v3.0/README.md +++ /dev/null @@ -1,15 +0,0 @@ -# MVP v3.0(Design)— WebUI + 用户数据上传/下载(SFTPGo)→ 首个可发布版本 - -本目录基于: -- `specs/mvp/mvp_roadmap_v2.md`(总体路线图) -- `specs/mvp/image/roadmap_v3.0.png`(v3.0 迭代图) -- 当前已落地的 v2.5(User Mgmt + Stateless Ray Node Pool) - -目标是在 v2.5 的基础上补齐 **用户数据闭环**(上传→训练可见→产物下载)以及最小可用的 **WebUI**,形成“可发布”的 v3.0 版本。 - -文档: -- `specs/mvp/v3.0/v3.0_design.md`:总体架构与关键机制(WebUI、SFTPGo、数据/权限模型、任务流)。 -- `specs/mvp/v3.0/v3.0_api.md`:v3.0 API 扩展设计(UI、数据、SFTPGo 管理、权限约束)。 -- `specs/mvp/v3.0/v3.0_acceptance.md`:部署/升级/验收流程与可验证标准(含故障注入与回归清单)。 -- `specs/mvp/v3.0/v3.0_dev_plan.md`:TDD 驱动的工程化开发计划(里程碑拆分、测试分层、E2E 验收)。 -- `specs/mvp/v3.0/v3.0_progress.md`:实施进展记录(每个里程碑完成后追加记录)。 diff --git a/specs/mvp/v3.0/v3.0_acceptance.md b/specs/mvp/v3.0/v3.0_acceptance.md deleted file mode 100644 index fe710e5..0000000 --- a/specs/mvp/v3.0/v3.0_acceptance.md +++ /dev/null @@ -1,55 +0,0 @@ -# MVP v3.0 — 部署与验收流程(草案) - -## 0) 环境前提 -- Ray 集群:延续 v2.5 的 head + stateless worker(自动 join) -- 共享存储:容器内挂载 `/private`(dev/prod 对齐) -- API server:宿主机代码挂载到 head 容器,在 head 容器内启动 -- 新增:SFTPGo 服务(建议容器化部署) - -## 1) 部署步骤(高层) - -1) 部署/升级 Ray 节点镜像(沿用 v2.5 的 `argus/argus-ray-node:v2.5` 或更高版本) -2) 启动 Ray 集群(compose 或平台创建容器) -3) 启动/配置 SFTPGo(挂载 `/private`) -4) 启动 API server(head 容器内) -5) 启动 WebUI(由 API server 托管) - -## 2) 验收用例(必须通过) - -### A. 用户与凭据 -1) admin 创建用户 `alice`,签发 API token -2) 系统联动在 SFTPGo 创建 `alice`(home=/private/users/alice) -3) `alice` 使用 token 登录 WebUI(或调用 `/api/v2/me` 成功) - -### B. 上传数据闭环(核心) -1) `alice` 通过 SFTP 上传数据集到 `/private/users/alice/datasets/...` -2) `alice` 通过 WebUI/API 提交任务,TaskSpec 引用该路径 -3) Ray worker 读取该数据,任务 RUNNING 并最终 SUCCEEDED - -### C. 下载产物闭环 -1) 训练完成后,产物落到 `/private/users/alice/jobs//...` -2) `alice` 通过 SFTP 下载 checkpoints/logs 成功 -3) (新增)`alice` 将需要长期保留的权重从 `jobs//...` 移动到 `models/`,确认移动后可长期存在 - -### C2. Jobs 回收站与自动清理(3 天移入回收站,7 天后永久删除) -1) 将 `jobs_trash_after_days`/`jobs_purge_after_days` 配置为较小值(例如分钟级,用于验证) -2) 训练完成进入 terminal 状态 -3) 等待 API server 内置 janitor 扫描周期后,确认对应 `jobs/` 被移动到 `trash/jobs/` -4) 在回收站窗口内,把某个文件从 `trash/jobs/` 移动到 `models/`,确认移动成功 -5) 等待超过 `jobs_purge_after_days` 后,确认 `trash/jobs/` 被永久删除 -6) 确认已移动到 `models/` 的文件不被删除 - -### D. 安全隔离(必须) -1) `bob` 不能通过 API 查询 `alice` 的 task(404) -2) `bob` 不能提交引用 `/private/users/alice/...` 的 TaskSpec(400/403) -3) `bob` 通过 SFTP 无法访问 `/private/users/alice/...`(chroot 生效) - -## 3) 故障注入(推荐通过) -1) kill worker watchdog 或 raylet → worker 自动恢复并重新加入集群 -2) 重启 head 容器 → head 重新写 `head.json`,worker 自动重连 -3) SFTPGo 重启 → 不影响 Ray 集群;用户可重新连接上传/下载 - -## 4) 回归清单(与 v2.5 一致) -- 任务队列、重试(INSUFFICIENT_RESOURCES → PENDING_RESOURCES → retry) -- PPO/GRPO/SFT 三种 workload 均可跑通 -- head 不跑训练(driver 强制落 worker) diff --git a/specs/mvp/v3.0/v3.0_api.md b/specs/mvp/v3.0/v3.0_api.md deleted file mode 100644 index 67f113b..0000000 --- a/specs/mvp/v3.0/v3.0_api.md +++ /dev/null @@ -1,109 +0,0 @@ -# MVP v3.0 — API 扩展设计(基于 v2.5) - -v3.0 的原则是:**尽量复用 v2.5 API**,只增量增加 “数据闭环” 与 “WebUI 支持” 所需的最小接口。 - -## 1) 认证与权限 - -沿用 v2.5: -- Header:`Authorization: Bearer ` -- admin token:来自 `MVP_INTERNAL_TOKEN` -- 普通用户 token:由 admin 颁发并持久化在 SQLite - -权限规则: -- 非 admin:只能访问自己的 task、自己的数据空间(`/private/users//...`)。 -- 跨用户访问返回 404(不泄露存在性)。 - -## 2) 用户与 SFTPGo 联动(管理员接口) - -### 2.1 创建用户(复用 v2.5) -`POST /api/v2/users` -- v3.0 行为:成功后,**可选**联动创建 SFTPGo 用户 - - v3.0 默认启用联动:创建 SFTPGo 用户 + 生成一次性密码(password 认证) - - v3.0 仅保留该方案(方案 A):不做外部认证/SSO 集成(留到更后续版本) - - `data.sftpgo.admin_api_base` 推荐形如:`http://argus-sftpgo:8080/api/v2`(包含 `/api/v2` 前缀) - -### 2.2 下发 token(复用 v2.5) -`POST /api/v2/users/{user_id}/tokens` - -### 2.3 禁用用户(复用 v2.5) -`POST /api/v2/users/{user_id}:disable` -- v3.0 行为:联动禁用 SFTPGo 用户(可选) - -### 2.4 SFTP 凭据管理(新增,管理员或用户自助) -(具体由你确认 v3.0 需要“用户自助”还是“管理员操作”) - -#### 重置 SFTP 密码(管理员) -`POST /api/v2/users/{user_id}/sftp:reset_password` -- 返回:一次性密码(只返回一次,服务端不保存明文) -> v3.0 先只做 password 方案;SSH public key 作为后续版本可选增强(不在 v3.0 范围)。 - -## 3) 用户自助信息(新增) - -### 3.1 获取当前用户信息 -`GET /api/v2/me` -- 返回示例: -```json -{ - "user_id": "alice", - "is_admin": false, - "paths": { - "home": "/private/users/alice", - "datasets": "/private/users/alice/datasets", - "models": "/private/users/alice/models", - "code": "/private/users/alice/code", - "jobs": "/private/users/alice/jobs", - "trash_jobs": "/private/users/alice/trash/jobs" - }, - "retention": { - "jobs_trash_after_days": 3, - "jobs_purge_after_days": 7 - }, - "sftp": { - "host": "h1.example.internal", - "port": 2022, - "username": "alice" - } -} -``` - -## 3.2 Jobs Retention 提示(新增) -为了支撑 WebUI 展示与用户预期管理,可在 `/api/v2/me` 或单独接口返回: -- `jobs_trash_after_days`:默认 3 -- `jobs_purge_after_days`:默认 7 -- `jobs_root`:`/private/users//jobs` -- `trash_jobs_root`:`/private/users//trash/jobs` -- `recommendations`:提示用户把需要长期保存的产物移动到 `models/` 或 `datasets/` - -## 4) 数据浏览/下载(可选,v3.0 最小化) - -说明:上传/下载主通道仍是 SFTP。 -WebUI 如果要提供“快速浏览/查看”,可实现只读接口(避免实现大文件上传/断点等复杂逻辑)。 - -### 4.1 列目录 -`GET /api/v2/files?path=/private/users/alice` -- 权限:path 必须在 `/private/common/` 或 `/private/users//` 下 -- 返回:文件列表(name/type/size/mtime) - -### 4.2 下载文件(小文件为主) -`GET /api/v2/files:download?path=/private/users/alice/jobs/.../logs/...` -- 返回:流式下载 -- 大文件仍建议走 SFTP - -## 5) TaskSpec 路径校验升级(v3.0 关键) - -v2.5:仅允许 `/private/common/...` -v3.0:允许 `/private/common/...` 与 `/private/users//...` - -应用字段(至少): -- `train_file` / `val_file` -- `code_path`:仍仅允许 `/private/common/...`(v3.0 不支持执行用户 code) -- 本地模型路径字段(如果引入):允许 `/private/users//models/...` - -## 6) WebUI 路由(新增) - -由 API server 托管: -- `GET /ui`:主页面 -- `GET /ui/login`:token 登录页 -- 静态资源:`/ui/static/...` - -WebUI 的所有操作均调用同源 API(不额外开 CORS)。 diff --git a/specs/mvp/v3.0/v3.0_design.md b/specs/mvp/v3.0/v3.0_design.md deleted file mode 100644 index 4edf84b..0000000 --- a/specs/mvp/v3.0/v3.0_design.md +++ /dev/null @@ -1,358 +0,0 @@ -# MVP v3.0 详细设计方案(基于 v2.5) - -## 0. 结论摘要(v3.0 要交付什么) - -v3.0 = v2.5 + **WebUI** + **用户数据上传/下载(SFTPGo)**,形成第一个可对外发布的版本: -- 用户可以通过 **SFTP** 上传数据/模型/代码(至少数据),落到 GPFS(容器内 `/private`)并对 Ray worker 可见。 -- 用户可以通过 API/WebUI 提交训练任务,任务读取自己上传的数据。 -- 用户可以下载训练产物(checkpoints/logs 等),最小闭环跑通。 - -## 1. 范围与原则 - -### 1.1 继承 v2.5 的前提(不回退) -- **Stateless Ray Node Pool**:head 写 `head.json`,worker watchdog 自动 join/自愈。 -- **User Management**:token 鉴权、任务可见性隔离(跨用户 404 不泄漏)。 -- **作业产物隔离**:Ray job 目录落到 `/private/users//jobs//...`。 -- **API server 短期运行方式**:代码在宿主机,挂载到 head 容器,在 head 容器内启动(保持现状)。 - -### 1.2 v3.0 新增目标 -1) **Data Management(SFTPGo)** - - 提供用户上传/下载入口(SFTP 为主)。 - - 数据落到 GPFS(dev 环境 NFS/GPFS,生产环境 GPFS),训练 job 在 worker 容器内可直接读取。 -2) **WebUI** - - 用户可视化创建任务、查看队列/状态/日志、查看“数据路径约定”和自己的 SFTP 信息。 - - 目标是 “可用而非豪华”,支持核心工作流。 -3) **权限闭环** - - 用户只能使用自己目录下的数据(`/private/users//...`)或公共目录(`/private/common/...`)。 - - 防止用户提交任务读取其他用户的文件路径。 - -### 1.3 v3.0 明确不做(留给 v3.5) -- 不做 “自定义 reward function / 自定义 verl 代码 / 多版本 verl 共存”(路线图 v3.5)。 -- 不做复杂 Serving/训推一体(路线图 v3.5)。 -- 不做 IB 网络/拓扑优化(路线图 v3.5)。 -- 不做系统级可观测性平台(路线图 v4.0)。 - -## 2. 架构概览 - -参考 `roadmap_v3.0.png`,v3.0 的控制面与数据面: - -### 2.1 控制面(Control Plane) -- **API Server(FastAPI)** - - v2.5 的任务队列/调度/重试 + 用户管理能力继续复用 - - 新增:数据管理能力(与 SFTPGo 对接) + WebUI -- **WebUI** - - 通过 API 使用 token 登录 - - 提供任务/日志/数据入口(不直接运行训练) -- **Ray Head(状态节点)** - - 仍在 head 容器内(或单独节点) - - job server/dashbaord 提供 job submit/status/logs 能力 - -### 2.2 数据面(Data Plane) -- **GPFS(容器内挂载 `/private`)** - - 存放 common 与 users 两大根目录 -- **Ray Worker Node(无状态)** - - 自动连接 head,执行训练 - - 读取 `/private/users//...` 的数据 - -### 2.3 新增组件:SFTPGo(Data Management) -- 作为独立服务运行(容器化优先),后端存储使用 **filesystem**(GPFS 挂载路径)。 -- 用户的 home directory 指向 `/private/users/`(或其子目录)。 - -## 3. 存储与目录规范(v3.0 统一约定) - -### 3.1 目录层级 -统一以容器内 `/private` 作为根路径(dev/prod 对齐): -- `/private/common/`:公共资源 - - `hf/`:HF cache - - `datasets/`:公共数据集(可选) - - `code/`:公共代码(例如公共 verl repo snapshot) - - `db/`:SQLite(队列、用户、token) - - `logs/`:API/supervisor/watchdog 日志 -- `/private/users//`:用户空间(v3.0 重点) - - `datasets/`:用户上传的数据集(推荐) - - `models/`:用户保存/上传的本地模型(允许;也用于“把 job 产物移动到长期保存目录”) - - `code/`:用户上传的代码(v3.0 **不支持执行**;仅存放/下载) - - `jobs/`:训练任务产物(已在 v2.5 落地) - - `tmp/`:临时文件(可选) - -### 3.2 Jobs Retention(两段式:3 天移入回收站,7 天后永久删除) -v3.0 引入 **jobs 目录两段式保留策略**: -- 第 1 阶段(soft-delete):job 结束后 **3 天**,将该 job 目录从 `jobs/` **移动到用户回收目录**; -- 第 2 阶段(hard-delete):进入回收目录后再过 **7 天**,从回收目录 **永久删除**。 - -目录约定(建议): -- jobs 根目录:`/private/users//jobs//...` -- 回收目录:`/private/users//trash/jobs//...` - -计时规则: -- 以 job 进入 terminal 状态(SUCCEEDED/FAILED/CANCELED)的结束时间为起点; -- “3 天”用于从 `jobs/` 移入 `trash/jobs/`; -- “7 天”用于从 `trash/jobs/` 永久删除(即总共最多 10 天窗口)。 - -用户保留关键产物的方式(无需 keep 标记): -- 在 “3 天窗口”内把需要长期保存的文件从 `jobs//...` **移动/复制**到 `models/`(例如权重)或 `datasets/`(例如评估输出数据); -- 即便已被移动到回收目录,用户仍可在 “7 天窗口”内从 `trash/jobs//...` 把需要的文件移到 `models/` / `datasets/`; -- janitor 只管理 `jobs/` 与 `trash/jobs/`,不会触碰 `models/` 与 `datasets/`。 - -这里的“清理程序”我们称为 **janitor**: -- 定义:一个后台清理执行器,按固定周期扫描“已结束且已过期”的 job 目录并删除 -- v3.0 目标:实现“3 天移入回收站 + 7 天后删除”这一条产品规则(不提供 keep/延长保留标记) - -实现建议(按你的偏好): -- **janitor 作为 API server 内置后台线程**运行: - - 优点:天然可访问 SQLite(任务状态、结束时间、user_id、ray_submission_id),并能把清理结果写回 events 表用于审计 - - 部署更简单:不额外引入 cronjob/独立服务 -- 删除/移动动作建议 **直接在 GPFS/NFS 文件系统上操作**(API server 运行在 head 容器,已挂载 `/private`): - - 第 1 阶段:`os.rename`(同文件系统原子移动)把 `jobs/` 移到 `trash/jobs/`; - - 若跨文件系统(理论上不应发生),则降级为 copy+delete; - - 移动前做严格路径前缀校验(必须在 `.../users//jobs/` 下)。 - - 第 2 阶段:对 `trash/jobs/` 执行递归删除(例如 `shutil.rmtree`),同样做路径前缀校验(必须在 `.../users//trash/jobs/` 下)。 - - 为什么不依赖 SFTPGo API:SFTPGo 只是用户访问协议层(SFTP/Web),目录物理就在同一份文件系统;文件系统直连更简单、也不依赖 SFTPGo 在线。 -- 如果你强烈希望“通过 SFTPGo API 删除”: - - 可以作为可选实现/补充(例如用于统一审计或未来接入配额/策略),但不建议作为唯一手段(SFTPGo 停机不应阻塞清理)。 - -### 3.3 用户在 SFTPGo 内移动/整理文件(确认点) -支持用户在 SFTPGo 中进行“移动/重命名/整理”(例如把权重从 `jobs/` 移动到 `models/`): -- 前提:SFTPGo 用户权限允许对其 home 目录进行 `rename/mkdir/remove` 等操作(v3.0 默认可写)。 -- 行为:用户可以把 `jobs/` 下某些文件移动到 `models/` 或 `datasets/`,用于长期保存权重/评估产物等。 -- 与 retention 的关系:只要文件被移动出 `jobs/`,就不会被 jobs 清理逻辑删除。 - -### 3.4 路径权限规则(API 侧校验) -v2.5 约束是 “只允许 `/private/common/...`”。 -v3.0 需要升级为: -- 允许: - - `/private/common/...` - - `/private/users//...` -- 禁止: - - 任何其他绝对路径(例如 `/private/users/other/...`、`/etc/...`) - -并把该规则应用到 TaskSpec 的相关字段(至少): -- `train_file` / `val_file` -- `code_path`:仍仅允许 `/private/common/...`(v3.0 不支持执行用户 code) -- 本地模型路径字段:允许 `/private/users//models/...`(确认:v3.0 允许) - -## 4. SFTPGo 方案设计(Data Management) - -### 4.1 运行形态 -推荐用容器运行 SFTPGo(与 Ray/API 解耦),挂载同一份 `/private`: -- `sftpgo` 容器挂载 `../../shared:/private` -- 对外暴露: - - SFTP 端口(建议 2022) - - WebAdmin/API 端口(建议 8081,仅内网或管理员访问) - -#### 4.1.1 镜像来源(现成 Docker 镜像) -SFTPGo 有现成可用的 Docker 镜像(无需自建): -- v3.0 推荐优先使用官方/上游发布的 `sftpgo` 镜像作为运行基座 -- 我们在 v3.0 里不需要定制 SFTPGo 代码,只需要: - - 正确挂载 GPFS/NFS(容器内 `/private`) - - 配置管理员账号(用于 API server 联动创建/禁用用户、重置密码) - - 配置每用户 home/chroot - -> 注意:具体镜像名/tag 在不同环境可能有差异(官方/镜像仓库策略会变动)。落地时建议在 `argus@h1` 上 `docker search sftpgo` 或由你们内部镜像仓库提供固定版本;v3.0 设计只要求“使用现成镜像”,不强依赖某个 tag。 - -#### 4.1.2 docker-compose 服务草案(示意) -下面给出一个**示意**(最终以实际镜像名/tag 与你们端口规划为准): - -```yaml -services: - sftpgo: - image: sftpgo/sftpgo:latest # 示例:使用现成镜像 - container_name: argus-sftpgo - ports: - - "2022:2022" # SFTP - - "8081:8080" # WebAdmin/API(建议仅内网/管理员) - volumes: - - ../../shared:/private - - ../../shared/common/sftpgo:/var/lib/sftpgo # 持久化 SFTPGo 元数据(可选/建议) - environment: - # 管理员账号/密码(示意,具体变量名以镜像文档为准) - SFTPGO_ADMIN_USERNAME: "admin" - SFTPGO_ADMIN_PASSWORD: "${SFTPGO_ADMIN_PASSWORD}" -``` - -与 v3.0 的配合点: -- API server 使用 `data.sftpgo.admin_api_base` + admin 凭据联动创建用户 -- 用户 home/chroot 统一指向 `/private/users/` - -### 4.2 用户隔离 -每个用户在 SFTPGo 中的 home dir 绑定到: -- `/private/users/`(chroot),用户只能读写自己的目录。 - -### 4.3 用户创建与凭据管理(两种实现,建议先做 A) - -**方案 A(v3.0 推荐):API Server 负责“联动创建 SFTPGo 用户”** -- 在 v2.5 的 `POST /api/v2/users` 成功后: - - API server 调用 SFTPGo 管理 API 创建同名用户 - - 设置 home dir = `/private/users/` - - 设置权限(默认可写;是否只读可配置) -- 认证方式: - - v3.0 最小可用:用户名+密码(确认:v3.0 先 password;API 生成一次性密码,用户首次登录后要求改密) - - 或:SSH public key(WebUI 允许上传 public key,API 写入 SFTPGo) - -**方案 B(更强但复杂):SFTPGo 外部认证** -- SFTPGo 把认证委托给 API server(token/SSO),SFTP 也走内部 token。 -- 复杂度高,建议 v3.0 不做,放到 v3.5 或更后。 - -### 4.4 用户上传/下载体验 -用户通过 SFTP 上传: -- `datasets/...`(训练数据) -- `models/...`(本地模型,可选) -下载: -- `jobs//...`(checkpoints/logs) - -WebUI/文档提供 “路径如何写进 TaskSpec” 的指引。 - -## 5. WebUI 方案设计(最小可用) - -### 5.1 目标页面 -v3.0 WebUI 采用“**多子页面 + 侧边导航栏**”而不是把所有功能挤到单页: -- 原因:信息密度更可控,后续可扩展(v3.5+)且不会把一个页面做成“巨型表单/巨型列表”。 -- 实现仍保持轻量:服务端渲染(或静态 HTML + 少量 JS),不引入复杂前端工程。 - -信息架构(IA)建议如下: -1) **登录页**(`/ui/login`) - - 用户粘贴 token(管理员发放),浏览器保存(localStorage/sessionStorage) - - 提供“退出登录/清空 token” -2) **任务列表页**(`/ui/tasks`) - - 默认列表:最近 N 条任务(按 created_at 倒序) - - 支持过滤:workload、state(QUEUED/RUNNING/SUCCEEDED/FAILED/CANCELED)、时间范围 - - 支持快捷操作:进入详情、取消任务 -3) **新建任务页**(`/ui/tasks/new`) - - 两种模式(二选一,均可实现): - - **YAML 直接提交**:上传/粘贴 TaskSpec YAML(最省开发) - - **表单生成 YAML**:选择 workload,填写核心字段(train/val/model/nnodes/gpus),生成 YAML 预览后提交 - - 提交后跳转到任务详情页 -4) **任务详情页**(`/ui/tasks/{task_id}`) - - 顶部:task_id、workload、state、created_at、updated_at、error_summary - - Attempt 卡片:latest attempt_no、ray_submission_id、ray_status、start/end - - 操作区:取消任务(若非 terminal)、刷新状态、复制路径/ID - - 链接到日志页与产物提示(SFTP 路径) -5) **任务日志页**(`/ui/tasks/{task_id}/logs`) - - 默认 tail=2000,可选 200/1000/5000 - - 提供“自动刷新(每 3~5 秒)”开关(简单轮询即可) -6) **数据页**(`/ui/data`) - - 显示 SFTP 连接信息(host/port/username) - - 显示用户目录约定: - - home:`/private/users/` - - datasets:`/private/users//datasets` - - models:`/private/users//models` - - jobs:`/private/users//jobs` - - trash/jobs:`/private/users//trash/jobs` - - 明确 retention:jobs 结束后 3 天移入回收站,回收站 7 天后删除;重要文件请移到 `models/` 或 `datasets/` -7) **(仅管理员可见)用户管理页**(`/ui/admin/users`,可选但很有价值) - - 创建用户、禁用用户、签发 token、重置 SFTP 密码(方案 A) - -### 5.2 页面组织与导航(建议) -侧边栏导航(普通用户): -- Tasks(列表) -- New Task(新建) -- Data(SFTP/目录说明) - -管理员侧边栏额外增加: -- Admin / Users - -### 5.3 大致示意图(wireframe) - -下面是一个粗略示意(非最终 UI,仅表达信息结构与布局): - -``` -┌──────────────────────────────────────────────────────────────────────┐ -│ Argus MVP v3.0 [user: alice] │ -├───────────────┬──────────────────────────────────────────────────────┤ -│ Side Nav │ /ui/tasks │ -│ │ │ -│ • Tasks │ [Filter] workload=all state=all [Search task_id] │ -│ • New Task │ │ -│ • Data │ Task List │ -│ • Admin(*) │ ┌────────────────────────────────────────────────┐ │ -│ │ │ task_id workload state ... │ │ -│ │ │ mvp2-alice-ppo-... ppo RUNNING ... │ │ -│ │ │ mvp2-alice-sft-... sft SUCCEEDED... │ │ -│ │ └────────────────────────────────────────────────┘ │ -│ │ [View] [Cancel] │ -└───────────────┴──────────────────────────────────────────────────────┘ -``` - -任务详情页(示意): -``` -┌──────────────────────────────────────────────────────────────────────┐ -│ /ui/tasks/{task_id} │ -├──────────────────────────────────────────────────────────────────────┤ -│ task_id: mvp2-alice-ppo-... state: RUNNING workload: ppo │ -│ created_at: ... updated_at: ... │ -│ error_summary: (empty) │ -│ │ -│ latest_attempt: a01 ray_submission_id: ...--a01 ray_status: RUNNING │ -│ [Open Logs] [Cancel Task] [Refresh] │ -│ │ -│ Artifacts (SFTP paths): │ -│ jobs/: /private/users/alice/jobs// │ -│ trash/: /private/users/alice/trash/jobs// │ -│ tip: move important files to /private/users/alice/models/ │ -└──────────────────────────────────────────────────────────────────────┘ -``` - -### 5.2 技术取舍(建议:不引入 Node 构建) -为了降低部署复杂度,建议 v3.0 WebUI 以 “服务端渲染 + 少量 JS/HTMX” 或 “纯静态 HTML+fetch” 实现: -- 由 API server 提供静态资源(FastAPI StaticFiles) -- 页面调用同源 API,避免跨域与复杂前端构建链 - -## 6. API 扩展设计(概览) - -v3.0 可以保持 `/api/v2/...` 不变,增量加: -- SFTPGo 集成管理端点(管理员): - - 创建/禁用用户时联动 SFTPGo - - 重置 SFTP 密码 / 更新 SSH key -- 用户数据端点(可选,最小化): - - `/api/v2/me`:返回 user_id、SFTP 信息(host/port/home) - - `/api/v2/files`:仅用于浏览/下载(上传仍走 SFTP) - -详细见 `specs/mvp/v3.0/v3.0_api.md`。 - -## 7. 配置与部署(v3.0 新增项) - -在 `configs/dev.yaml` 基础上扩展一组 `data` 配置(示意): -```yaml -data: - shared_root: "/private" # 通常与 ray.shared_root 一致 - user_root: "/private/users" # 用户空间根目录 - allow_common_prefix: "/private/common/" - allow_user_prefix_template: "/private/users/{user_id}/" - - sftpgo: - enabled: true - host: "127.0.0.1" - sftp_port: 2022 - admin_api_base: "http://127.0.0.1:8081/api/v2" - admin_user: "admin" - admin_password_env: "SFTPGO_ADMIN_PASSWORD" # 仅 head 容器内可读 - - retention: - jobs_trash_after_days: 3 - jobs_purge_after_days: 7 - trash_root_template: "/private/users/{user_id}/trash/jobs" - janitor_interval_s: 3600 # 每小时扫一次(可配置) -``` - -## 8. 风险点与对策 - -1) **路径逃逸/越权读取** - - 必须在 API 提交任务时校验路径前缀 - - SFTPGo 必须 chroot 到用户 home -2) **大文件上传稳定性** - - 优先用 SFTP(断点续传/可靠性更好) -3) **用户 token 与 SFTP 凭据的生命周期** - - token 走 v2.5 SQLite - - SFTP 凭据建议独立(密码/SSH key),并提供 reset 流程 -4) **GPFS/NFS 权限** - - 确保 `/private/users/` 目录权限可被 SFTPGo 写入且 worker 可读 - -## 9. 已确认结论(来自你的反馈) -1) 允许用户上传并在训练时使用自定义数据集:允许(`/private/users//datasets/...`)。 -2) 允许用户上传并在训练时使用本地模型路径:允许(`/private/users//models/...`)。 -3) v3.0 不允许执行用户自定义代码(不注入 `PYTHONPATH` 作为可执行 code path)。 -4) SFTPGo 认证方式:v3.0 先 password。 -5) WebUI:按“简单最小必要功能”做(token 粘贴登录优先)。 - -## 10. 待确认问题(需要你给结论) -(已确认)jobs 清理执行主体:v3.0 采用 **API server 内置 janitor 后台线程**。 diff --git a/specs/mvp/v3.0/v3.0_dev_plan.md b/specs/mvp/v3.0/v3.0_dev_plan.md deleted file mode 100644 index 9a14b4b..0000000 --- a/specs/mvp/v3.0/v3.0_dev_plan.md +++ /dev/null @@ -1,232 +0,0 @@ -# MVP v3.0 开发计划(TDD 驱动) - -本文是 v3.0 的**工程化开发计划**,强调“先写测试,再写实现”(TDD),并将每个里程碑拆成**可独立验收**的小闭环。 - -输入依据: -- 路线图:`specs/mvp/mvp_roadmap_v2.md` -- v3.0 设计:`specs/mvp/v3.0/v3.0_design.md` -- v3.0 API:`specs/mvp/v3.0/v3.0_api.md` -- v3.0 验收:`specs/mvp/v3.0/v3.0_acceptance.md` -- 现状基线:v2.5(Task queue + User mgmt + Stateless ray pool + 单镜像节点守护) - -v3.0 已确认约束: -- 允许用户数据集路径:`/private/users//datasets/...` -- 允许用户本地模型路径:`/private/users//models/...` -- **不允许执行用户自定义代码**(不注入 user code 到 PYTHONPATH;`code_path` 仍只允许 `/private/common/...`) -- SFTPGo 先用 **password** 方案(方案 A:API 联动创建/管理 SFTPGo 用户) -- jobs retention:**3 天移入回收站(trash/jobs),再 7 天永久删除**;不提供 keep/延长保留标记 -- janitor:**API server 内置后台线程**;删除/移动采用**文件系统直接操作**(不依赖 SFTPGo API) - ---- - -## 0. TDD 规范(所有功能都遵循) - -### 0.1 测试分层 - -1) **单元测试(fast)** -- 纯 Python 逻辑:路径策略、SFTPGo client、retention 计算、文件移动/删除策略(用临时目录)。 -- 不依赖真实 Ray、不依赖 docker、不依赖网络。 - -2) **组件测试(中等)** -- FastAPI 路由(含 WebUI 路由):`fastapi.testclient.TestClient` -- mock/stub SFTPGo client 与 ray client - -3) **端到端(慢)** -- 在 `argus@h1` 通过 docker compose + scripts: - - Ray 集群自动起来(head+2 worker) - - SFTPGo 服务可用 - - 上传数据 → 提交训练 → 下载产物 → jobs 回收站/清理 - -### 0.2 代码与测试约定 -- 测试目录:`src/mvp/py/tests/` -- 新功能必须先补齐测试用例,并让其在未实现时失败(红) -- 最小实现让测试变绿(绿) -- 再做重构(重构) -- 覆盖率:继续沿用当前阈值(>= 90%) - ---- - -## 1. 里程碑拆分(v3.0 = 5 个可验证闭环) - -### M1:TaskSpec 路径策略升级(允许 user datasets/models;code_path 仍仅 common) - -**目标** -- API submit 时的路径校验从 v2.5 的 “仅 `/private/common/`” 升级为: - - `train_file` / `val_file`:允许 `/private/common/...` 与 `/private/users//...` - - 本地模型路径:允许 `/private/users//models/...`(不改变 YAML 结构,见实现建议) - - `code_path`:仍仅允许 `/private/common/...` -- 阻止越权路径(`/private/users/other/...`)与非 `/private/...` 路径。 - -**实现建议(不扩展 TaskSpec)** -- `model_id` 字段保持不变: - - 若 `model_id` 以 `/private/` 开头 → 视作本地模型路径 - - 否则视作 HuggingFace repo id(如 `Qwen/...`) - -**TDD 用例(先写测试)** -- 单测: - - `test_paths_allow_common_and_own_user_prefix()` - - `test_paths_reject_other_user_prefix()` - - `test_model_id_local_path_allowed_only_under_users_models()` - - `test_code_path_still_common_only()` -- API 测试: - - `test_submit_accepts_user_datasets_paths()` - - `test_submit_rejects_cross_user_paths_404_or_400()`(按约定返回 400/403) - -**验收点** -- `v3.0_acceptance.md` 的 D 类安全隔离用例可由 API 测试覆盖。 - ---- - -### M2:SFTPGo 集成(方案 A:用户联动创建 + password) - -**目标** -- 引入 `data management (SFTPGo)`: - - admin 创建用户时联动创建 SFTPGo 用户(home=/private/users/,chroot) - - password 模式:生成一次性密码(reset/create)并返回给 admin(明文只返回一次) -- 提供用户自助信息: - - `GET /api/v2/me` 返回 SFTP 连接信息、目录约定、retention 提示。 - -**实现建议** -- 新增 `SFTPGoAdminClient`(同步调用): - - 通过 `urllib` 或 `httpx`(建议 `urllib`,减少依赖;禁止 hard-code requests 使用) - - 支持:create user / disable user / reset password(最小集合) -- API server 启动时校验配置(enabled 时必须具备 admin 密码 env)。 -- 同步创建用户目录结构(文件系统): - - `/private/users//{datasets,models,code,jobs,trash/jobs}`(最小必需) - -**TDD 用例(先写测试)** -- 单测: - - `test_sftpgo_client_builds_correct_requests()`(不发真实网络;mock urlopen) - - `test_user_dirs_created_on_user_create()`(tmp dir 断言目录存在) -- API 测试: - - `test_create_user_calls_sftpgo_client()`(stub client,断言调用参数) - - `test_me_returns_sftp_info_and_paths()`(含 trash/jobs 与 TTL 字段) - -**验收点** -- `v3.0_acceptance.md` 的 A 类(用户/凭据)与 B 类(上传闭环前置)覆盖。 - ---- - -### M3:WebUI(最小可用,多页面 + 侧边栏) - -**目标** -- WebUI 由 API server 托管(同源,无额外 CORS): - - `/ui/login`:token 粘贴登录(localStorage) - - `/ui/tasks`:任务列表 + 过滤(最小) - - `/ui/tasks/new`:YAML 提交(优先)+(可选)表单生成 YAML - - `/ui/tasks/{task_id}`:详情页 - - `/ui/tasks/{task_id}/logs`:日志 tail + 可选自动刷新 - - `/ui/data`:SFTP 信息 + 目录/retention 提示 - - (可选)`/ui/admin/users`:管理员用户管理(若时间允许,强烈建议) - -**实现建议** -- 先不引入 Node 构建: - - HTML 模板可用最简单的字符串拼接或 Jinja2(若引入 jinja2,则补齐依赖与测试) - - 页面通过 fetch 调用 `/api/v2/...`,并复用 token header - -**TDD 用例(先写测试)** -- 组件测试(TestClient): - - `test_ui_routes_render_200()` - - `test_ui_contains_sidebar_links()`(简单断言文本包含导航链接) - - `test_ui_tasks_detail_shows_ids()`(包含 task_id、state、ray_submission_id) - -**验收点** -- WebUI 能完成:登录→创建任务→查看任务→查看日志→看到 data 页提示。 - ---- - -### M4:Jobs Retention janitor(3 天移入 trash,7 天后 purge) - -**目标** -- API server 内置 janitor 后台线程: - - 周期性扫描 DB 中 terminal tasks - - 到期后执行: - - move:`/private/users//jobs/` → `/private/users//trash/jobs/` - - purge:递归删除 `/private/users//trash/jobs/` - - 全程严格 path 校验,禁止越界删除 - - 清理操作记录到 DB events(审计) - -**实现建议(数据与状态)** -- 需要稳定的时间锚点与幂等: - - 使用 attempts.end_time 作为 job 结束时间(latest attempt) - - 在 tasks 表新增字段(或新表)记录: - - `trashed_at`(首次成功 move 时间) - - `purged_at`(成功删除时间) - - `trash_path`(可选) - - 幂等:重复运行不会报错(目录不存在视为已处理) - -**TDD 用例(先写测试)** -- 单测(用 tmpdir 构造 jobs/trash 目录): - - `test_janitor_moves_job_to_trash_after_threshold()` - - `test_janitor_purges_trash_after_threshold()` - - `test_janitor_never_touches_models_or_datasets()` - - `test_janitor_path_escape_rejected()`(恶意 path 不可删) -- API/组件测试: - - `test_me_includes_retention_fields()`(jobs_trash_after_days/jobs_purge_after_days) - -**验收点** -- `v3.0_acceptance.md` 的 C2 用例可按“把阈值调小到分钟级”完成验证。 - ---- - -### M5:端到端(h1)— SFTP 上传→训练→产物下载→回收站/清理 - -**目标** -- 在 `argus@h1` 落一个一键脚本(或手册)跑通: - 1) `docker compose up -d` 拉起 Ray(head+2 worker)+ SFTPGo - 2) admin 创建用户 alice(联动创建 SFTPGo 用户 + password) - 3) alice 通过 SFTP 上传: - - 数据集到 `/private/users/alice/datasets/...` - - (可选)本地模型到 `/private/users/alice/models/...` - 4) alice 通过 API/WebUI 提交任务引用上述路径 - 5) 任务成功后: - - 从 `jobs/` 下载 logs/checkpoints - - 把权重移动到 `models/`,验证不会被清理 - 6) 把 retention 配置调小,验证 jobs→trash→purge - -**交付建议** -- 新增脚本(命名示例): - - `scripts/run_all_v30_api.sh` - - `scripts/run_e2e_v30_cases.sh` -- 新增 `docker-compose.yaml` 中的 `sftpgo` service(或 `docker-compose.v30.yaml` 叠加文件) - -**验收点** -- `v3.0_acceptance.md` 全部 MUST 用例通过。 - ---- - -## 2. 风险与测试关注点 - -1) **权限与路径逃逸** -- path policy 必须覆盖:train/val/model_id(local)/output dirs(jobs/trash) -- 所有删除/移动必须做 prefix 校验 - -2) **并发与竞态** -- janitor 只处理 terminal tasks,避免清理正在写入的目录 -- move 使用同文件系统 `os.replace`(原子) - -3) **SFTPGo 可用性** -- SFTPGo 不在线不应影响训练与 API 核心功能(除了用户创建联动) -- janitor 不依赖 SFTPGo(文件系统直连) - ---- - -## 3. 交付清单(代码/配置/脚本/文档) - -### 3.1 代码 -- Path policy(v3.0) -- SFTPGoAdminClient + user create/disable/reset password 联动 -- `/api/v2/me` 扩展(SFTP/目录/retention) -- WebUI 路由与静态资源 -- janitor(trash+purge)后台线程 + DB 记录 - -### 3.2 配置 -- `configs/dev.yaml` 增加 `data.sftpgo`、`data.retention` 段(详见设计文档) - -### 3.3 scripts / compose -- compose 增加 `sftpgo`(或新增 overlay compose 文件) -- v3.0 e2e 脚本(上传/下载/清理验证) - -### 3.4 文档 -- 更新 `specs/mvp/v3.0/*` 与 `src/mvp/README.md`(运行方式、路径约定、SFTP 操作、retention 解释) - diff --git a/specs/mvp/v3.0/v3.0_progress.md b/specs/mvp/v3.0/v3.0_progress.md deleted file mode 100644 index 49ebfe6..0000000 --- a/specs/mvp/v3.0/v3.0_progress.md +++ /dev/null @@ -1,154 +0,0 @@ -# MVP v3.0 进展记录(milestone log) - -本文档用于记录 v3.0 按 `specs/mvp/v3.0/v3.0_dev_plan.md` 实施过程中的里程碑完成情况。 -约定:每完成一个里程碑,追加一条记录,包含**日期**、**完成内容**、**涉及文件**、**验证方式/结果**、**待办/风险**。 - ---- - -## M1:Path policy + tests(已完成) - -- 日期:2025-12-30 -- 范围:按 v3.0 路径策略升级 API submit 的路径校验(不扩展 TaskSpec YAML 结构)。 -- 完成内容: - - `code_path`:仍只允许 `/private/common/...`(v3.0 不执行 user code)。 - - `train_file`/`val_file`:允许 `/private/common/datasets/...` 或 `/private/users//datasets/...`。 - - `model_id`:若以 `/private/` 开头则视为本地路径,仅允许: - - `/private/common/models/...` 或 - - `/private/users//models/...` - 否则仍按 HuggingFace repo id(如 `Qwen/...`)处理。 - - 拒绝跨用户路径(例如 `bob` 提交 `/private/users/alice/datasets/...`)。 - - 拒绝本地模型路径不在 `models/`(例如指向 `jobs/`)。 -- 涉及文件: - - `src/mvp/py/argus/service/app.py` - - `src/mvp/py/tests/test_users.py` -- 验证方式与结果: - - 本地单测:`.venv/bin/python -m pytest -q` - - 结果:全部通过(`54 passed`),覆盖率阈值保持 `>= 90%`。 -- 待办/风险: - - `model_id=/private/...` 的“本地模型路径语义”需要在用户文档/WebUI 中明确提示(避免误用)。 - - 后续 M2/M3 需要把该路径策略同步到 UI 表单/提示文本(避免用户填错路径)。 - ---- - -## M2:SFTPGo 集成(方案 A:用户联动创建 + password)(已完成) - -- 日期:2025-12-30 -- 范围:SFTPGo(Data Management)最小集成 + 用户自助信息 `/api/v2/me` + 用户目录结构落盘。 -- 完成内容: - - 新增 `data` 配置段: - - `data.user_root`:用户数据根目录(默认 `/private/users`) - - `data.sftpgo`:SFTPGo 可选联动(enabled/host/sftp_port/admin_api_base/admin_user/admin_password_env) - - `data.retention`:jobs 过期策略配置(3 天移入 trash,7 天 purge;janitor 在 M4 实现) - - 新增 `SFTPGoAdminClient`(`urllib` 实现,不使用 `requests`): - - `create_user` / `disable_user` / `reset_password`(最小集合) - - API server 增强: - - `POST /api/v2/users`:创建 DB user + 同步创建目录结构(`datasets/models/code/jobs/trash/jobs`) - - 当 `data.sftpgo.enabled=true` 时,创建用户会联动调用 SFTPGo admin API,并返回一次性密码(明文仅返回一次,服务端不保存) - - `POST /api/v2/users/{user_id}:disable`:禁用用户(SFTPGo 禁用 best-effort) - - `POST /api/v2/users/{user_id}/sftp:reset_password`:管理员重置一次性密码(SFTPGo enabled 才允许) - - `GET /api/v2/me`:返回当前用户的目录约定、retention 提示,以及(可选)SFTP 连接信息 - - 同步更新 `src/mvp/configs/dev.yaml`:补齐 v3.0 相关 `data.*` 配置(默认关闭 sftpgo)。 -- 涉及文件: - - `src/mvp/py/argus/service/config.py` - - `src/mvp/py/argus/service/sftpgo.py` - - `src/mvp/py/argus/service/app.py` - - `src/mvp/py/tests/test_sftpgo.py` - - `src/mvp/py/tests/test_users.py` - - `src/mvp/py/tests/test_app.py` - - `src/mvp/py/tests/test_service_config.py` - - `src/mvp/configs/dev.yaml` - - `specs/mvp/v3.0/v3.0_api.md` -- 验证方式与结果: - - 本地单测:`.venv/bin/python -m pytest -q` - - 结果:全部通过(`62 passed`),覆盖率 `90.11%`(阈值 `>= 90%`)。 -- 待办/风险: - - M2 仅做了“API 侧联动 + 单测”,未在真实 SFTPGo 容器上端到端验证(按计划在 M5 完成)。 - - 目录创建依赖文件系统权限:生产部署时需确保 API/head 容器对 `/private/users` 可写。 - ---- - -## M3:WebUI(最小可用,多页面 + 侧边栏)(已完成) - -- 日期:2025-12-30 -- 范围:API server 托管最小 WebUI(同源,不引入 Node 构建),用于登录/提交/查看任务与日志、查看 data 信息。 -- 完成内容: - - 新增 UI 路由(HTML+少量 JS): - - `/ui`(重定向到 tasks) - - `/ui/login`:token 粘贴并写入浏览器 localStorage(key=`mvp_token`) - - `/ui/tasks`:任务队列列表(调用 `/api/v2/queue`) - - `/ui/tasks/new`:提交 TaskSpec YAML(POST `/api/v2/tasks`) - - `/ui/tasks/{task_id}`:任务详情(GET `/api/v2/tasks/{task_id}`,支持 cancel) - - `/ui/tasks/{task_id}/logs`:日志查看(GET `/api/v2/tasks/{task_id}/logs`,可选自动刷新) - - `/ui/data`:展示 `/api/v2/me` 返回的路径/SFTP/retention 信息 - - 统一侧边栏导航:Tasks / New Task / Data / Login。 - - UI 不做服务端 session:所有 API 调用均由浏览器带 `Authorization: Bearer `(localStorage 注入)。 -- 涉及文件: - - `src/mvp/py/argus/service/ui.py` - - `src/mvp/py/argus/service/app.py` - - `src/mvp/py/tests/test_ui.py` -- 验证方式与结果: - - 本地单测:`.venv/bin/python -m pytest -q` - - 结果:全部通过(`65 passed`),覆盖率 `90.53%`(阈值 `>= 90%`)。 -- 待办/风险: - - WebUI 当前为“骨架+API 驱动”,不做复杂交互与大文件下载;上传/下载仍以 SFTP 为主(按设计)。 - - Starlette TestClient 的 `allow_redirects` 有弃用告警(不影响功能,可在后续清理)。 - ---- - -## M4:Jobs Retention janitor(3 天移入 trash,7 天后 purge)(已完成) - -- 日期:2025-12-30 -- 范围:API server 内置后台线程,对“已结束 attempt”的 job 目录执行保留策略(文件系统直连,不依赖 SFTPGo)。 -- 完成内容: - - 新增 `JobsJanitor`: - - 以 `attempts.end_time` 为基准计算 TTL(从 job 结束开始算) - - `>= 3 天 && < 7 天`:把目录从 `.../jobs/` 移动到 `.../trash/jobs/` - - `>= 7 天`:确保目录进入 trash 后删除(`shutil.rmtree`) - - 对缺失目录、异常移动/删除为 best-effort(不影响服务主流程) - - DB 增强:新增查询 `list_ended_attempts_before()`,用于 janitor 扫描候选 attempt。 - - API server 启动时启动 janitor 线程(可通过 `data.retention.janitor_interval_s` 控制;<=0 视为关闭)。 -- 涉及文件: - - `src/mvp/py/argus/service/janitor.py` - - `src/mvp/py/argus/service/db.py` - - `src/mvp/py/argus/service/app.py` - - `src/mvp/py/tests/test_janitor.py` -- 验证方式与结果: - - 本地单测:`.venv/bin/python -m pytest -q` - - 结果:全部通过(`75 passed`),覆盖率 `90.72%`(阈值 `>= 90%`)。 -- 待办/风险: - - M4 只做“逻辑 + 单测”,实际 `/private/users/...` 的权限与在 `argus@h1` 的行为验证放到 M5(端到端)。 - ---- - -## M5:端到端(h1)— SFTPGo compose + v3.0 E2E 脚本(已完成:交付脚本/配置) - -- 日期:2025-12-30 -- 范围:补齐 h1 端到端所需的 compose/service、配置与一键脚本(实际运行/验收由你在 `argus@h1` 执行)。 -- 完成内容: - - SFTPGo 集成到 `docker compose`: - - 新增 `argus-sftpgo` service(SFTP 2022;Admin API/UI 8080→host 8081,避免与 MVP API 8080 冲突) - - 同挂载 `../../shared:/private`,并持久化元数据到 `../../shared/common/sftpgo` - - SFTPGoAdminClient 实装(对齐 upstream OpenAPI): - - `GET /api/v2/token`(BasicAuth)获取 admin token - - `POST /api/v2/users` 创建用户(含 `permissions: {"/":["*"]}`) - - `PUT /api/v2/users/{username}` 禁用/重置密码 - - 新增 v3.0 dev 配置:`configs/dev_v30.yaml`(启用 `data.sftpgo` 并配置 `admin_api_base=http://argus-sftpgo:8080/api/v2`) - - 新增 v3.0 一键脚本: - - `scripts/run_all_v30_api.sh`:起 Ray+SFTPGo、启动 API、创建用户并提交 PPO/GRPO/SFT(引用 user dataset 路径) - - `scripts/run_e2e_v30_cases.sh`:最小 E2E runner(HP-1) - - API 启动脚本增强:`scripts/60_start_api.sh` 支持透传 `SFTPGO_ADMIN_PASSWORD` 到 head 容器内的 API 进程。 -- 涉及文件: - - `src/mvp/docker-compose.yaml` - - `src/mvp/configs/dev_v30.yaml` - - `src/mvp/scripts/run_all_v30_api.sh` - - `src/mvp/scripts/run_e2e_v30_cases.sh` - - `src/mvp/scripts/60_start_api.sh` - - `src/mvp/py/argus/service/sftpgo.py` - - `src/mvp/py/tests/test_sftpgo.py` - - `src/mvp/README.md` - - `specs/mvp/v3.0/v3.0_api.md` -- 验证方式与结果: - - 本地单测:`.venv/bin/python -m pytest -q` - - 结果:全部通过(`75 passed`),覆盖率 `90.35%`(阈值 `>= 90%`)。 -- 待办/风险: - - 需要你在 `argus@h1` 实跑 `scripts/run_all_v30_api.sh` 完成真正的 SFTP 上传/下载与 retention 验收(按 `v3.0_acceptance.md`)。 diff --git a/specs/mvp/v3.0/v3.0_summary.md b/specs/mvp/v3.0/v3.0_summary.md deleted file mode 100644 index c952025..0000000 --- a/specs/mvp/v3.0/v3.0_summary.md +++ /dev/null @@ -1,166 +0,0 @@ -# MVP v3.0 迭代总结(Ray + SFTPGo + API + WebUI) - -本文总结 v3.0 迭代最终落地的功能、架构、运行方式、验收点与已知限制,便于后续评审、交接与继续迭代。 - -相关更详细文档: -- `specs/mvp/v3.0/v3.0_design.md` -- `specs/mvp/v3.0/v3.0_api.md` -- `specs/mvp/v3.0/v3.0_dev_plan.md` -- `specs/mvp/v3.0/v3.0_acceptance.md` -- `specs/mvp/v3.0/v3.0_progress.md` - ---- - -## 1. 目标与范围 - -v3.0 作为“第一版可发布”的最小闭环,主要新增: -- **WebUI**:最小可用的人机界面(登录、任务提交与查看、数据入口、管理员入口)。 -- **用户管理**:基于内部 token 的用户体系(admin 与普通用户),支持创建用户与签发 token。 -- **数据管理入口(SFTPGo)**:用户通过 SFTP/WebClient 上传下载自己的数据;同时暴露只读的共享数据/缓存目录(common)用于复用。 -- **保持训练闭环**:仍通过 Ray Job 提交到集群执行(PPO/GRPO/SFT 三类 workload 都验证)。 - -明确不做(本迭代保持最小): -- 不支持用户自定义训练代码(TaskSpec 的 `code_path` 固定走 common 下的 verl snapshot 策略)。 -- 不做复杂资源排队优化/多集群/多租隔离策略(目前隔离粒度主要在用户 jobs 目录层)。 - ---- - -## 2. 系统架构(最终形态) - -核心组件: -- **Ray 集群(容器)** - - `argus-ray-head`:head 节点(无 GPU/不跑训练),提供 Ray Dashboard 与 Job Server。 - - `argus-ray-worker-0/1`:worker 节点(有 GPU),承载训练任务。 - - worker 以 “stateless + watchdog 自动连接 head” 的方式加入集群。 -- **API Server(运行在 head 容器内)** - - 读取 YAML 配置(dev/prod),维护任务队列(sqlite),并周期性调度将任务提交到 Ray。 - - 同时承载 WebUI(`/ui`)。 -- **SFTPGo(容器)** - - 提供 SFTP(端口 `2022`)与 Web Client/Admin(端口 `8081` 映射到容器 8080)。 - - 用户 home 为 `/private/users/`,默认可读写。 - - 额外提供 `/common/*` 共享只读入口(见第 4 节)。 -- **共享存储(NFS/GPFS 等挂载到容器内 `/private`)** - - `/private/common`:共享缓存(hf、datasets、models、db、logs 等)。 - - `/private/users/`:用户隔离目录(jobs/datasets/models/code/trash 等)。 - ---- - -## 3. 任务与调度(Task / Ray Job) - -### 3.1 Task(平台概念) -- 用户向 API 提交 TaskSpec(YAML),平台分配 `task_id`(可读、包含用户名)。 -- `task_id` 对应内部状态机与重试逻辑;底层每次提交 Ray Job 会产生 attempt 与 `ray_submission_id`。 - -### 3.2 Ray Job(Ray 概念) -- 真正执行训练的 driver 通过 Ray Job 运行在集群 worker 上(避免 head 承载训练)。 -- head 节点通过 `--num-cpus=0` / 自定义资源等策略避免调度到 head。 - -### 3.3 VERL 资源预检查的处理 -- VERL 在创建资源池时会做 fail-fast 资源预检查(如“可用 GPU 不足”直接报错退出)。 -- v3.0 延续 v2.x 的策略:服务端识别失败原因并按策略重试/回退(具体见 scheduler 实现与 v2.5/3.0 文档)。 - ---- - -## 4. 数据管理(SFTPGo)与 common 只读目录 - -### 4.1 用户目录(读写) -- 用户通过 SFTP/WebClient 访问自己的 home:`/private/users/` -- 目录结构(至少):`datasets/ models/ code/ jobs/ trash/ common/` - -### 4.2 common 只读(方案 A:Virtual Folder) -本迭代采用 SFTPGo 的 Virtual Folder + 路径权限覆盖,实现用户可读共享目录但不可写。 - -最终对外暴露为: -- `/common/datasets`(只读) - - **mapped_path 指向真实目录 `/private/datasets`**(避免 `/private/common/datasets` 中大量 symlink 导致的 WebClient “权限不足/越界”问题) -- `/common/hf`(只读) - - mapped_path 指向 `/private/hf` - -备注: -- `/private/common/datasets` 内部存在 symlink(如 `gsm8k -> /private/datasets/gsm8k`),如果虚拟目录映射到 symlink 根目录,SFTPGo 会把 symlink 跳转视为“逃逸 root”,导致点击进入时报权限不足;因此选择直接映射到真实目录根。 - ---- - -## 5. WebUI(最小可用) - -入口: -- `/ui/login`:粘贴 token(存 browser `localStorage`) -- `/ui/tasks`:任务列表(Running/Pending/Completed),Completed 支持分页 -- `/ui/tasks/new`:提交任务(PPO/GRPO/SFT 三套样例可一键填充) -- `/ui/data`:展示当前用户名、支持重置 SFTPGo 密码并复制;提供跳转到 SFTPGo WebClient;提示 FileZilla 等客户端用法 -- `/ui/admin`:管理员入口(创建用户、签发 token、用户列表) -- 导航栏提供 Ray Dashboard 快捷跳转(当前 IP 的 `:8265`) - -关于 admin 页面权限: -- admin 页面本身可访问,但其数据请求必须携带 admin token;否则会在页面内显示 401/403/错误信息(满足“需要先提供 admin token 才能看到内容”)。 - ---- - -## 6. API(v3.0 新增/强化点) - -核心接口(节选): -- 认证: - - Bearer token:`MVP_INTERNAL_TOKEN`(admin)或用户 token(由 admin 签发) -- 用户管理(admin): - - `POST /api/v2/users` 创建用户(并初始化用户目录) - - `GET /api/v2/users` 获取用户列表(包含最新 token、创建/更新时间等) - - `POST /api/v2/users/{user_id}/tokens` 签发用户 token -- 任务: - - `POST /api/v2/tasks` 提交 TaskSpec(YAML) - - `GET /api/v2/tasks` 任务列表(支持 states/limit/offset,用于 Completed 分页) - - `GET /api/v2/tasks/{task_id}`、`POST /api/v2/tasks/{task_id}:cancel`、`GET /api/v2/tasks/{task_id}/logs` - - `GET /api/v2/queue`(运行中/待调度概览) -- 数据/SFTP: - - `GET /api/v2/me` 返回用户路径信息、SFTP 连接信息,并 best-effort 对齐 SFTPGo 用户配置 - - `POST /api/v2/me/sftp:reset_password` 用户自助重置 SFTPGo 密码(一次性返回明文) - -安全取舍说明(当前为内网/开发优先): -- 为了 Admin WebUI “可查看并复制 token”,数据库持久化存储了 `token_plain`(明文 token)。 - - 这在生产场景通常不建议;未来可改为只展示“重置/重新签发”而不回显明文,或只回显一次。 - ---- - -## 7. 持久化与清理 - -- 任务队列:sqlite(WAL 模式) -- SFTPGo:自带 sqlite db(容器挂载持久化目录) -- Jobs 目录清理策略(服务端 janitor): - - job 结束后 3 天移动到回收目录(trash) - - 回收目录再保留 7 天后删除 - ---- - -## 8. 运行方式与脚本 - -开发/验收脚本: -- `src/mvp/scripts/run_all_v30_api.sh`:端到端拉起(Ray + SFTPGo + API),并通过 API 提交 PPO/GRPO/SFT,等待完成并验收 -- 其他脚本用于启动/停止 API、准备数据与模型、探测服务就绪等(详见 scripts 目录与 README) - -典型端到端(示例参数): -- `MVP_INTERNAL_TOKEN=my-dev-token` -- `SFTPGO_ADMIN_PASSWORD=my-dev-sftpgo-admin` -- 支持 `RESET_DB/RESET_SFTPGO` 用于测试环境重置 - ---- - -## 9. 验证结果(已跑通) - -在 `argus@h1` 环境中已完成端到端验证: -- Ray 集群可用(head + 2 worker) -- API server + WebUI 可用 -- SFTPGo(admin + 普通用户)可用 -- 通过 API 连续提交 PPO/GRPO/SFT 三种任务均能完成(SUCCEEDED) -- 用户可以登录 SFTPGo WebClient/SFTP,访问自己的目录,并访问 `/common/datasets`、`/common/hf` 的只读内容 - -同时本地单测通过: -- pytest 全绿 -- 覆盖率阈值 >= 90% - ---- - -## 10. 已知限制 & 后续可改进 - -- WebUI 当前为最小版,交互与权限提示仍偏“工程化”而非产品化(后续可增强错误提示、搜索筛选、任务详情聚合等)。 -- token 明文持久化仅适合内网/开发场景;生产建议改为一次性展示或支持撤销/轮换策略。 -- SFTPGo 虚拟目录目前保留了历史遗留映射(例如 `/common/models` 可能残留),后续可在升级脚本中做一次性清理与迁移。 - diff --git a/specs/mvp/v3.5/README.md b/specs/mvp/v3.5/README.md deleted file mode 100644 index c6df997..0000000 --- a/specs/mvp/v3.5/README.md +++ /dev/null @@ -1,7 +0,0 @@ -# MVP v3.5 - -本目录包含 v3.5 的需求与设计(精简版): - -- `requirement.md`:需求补充说明(来源于讨论) -- `roadmap_v3.5.png`:架构草图(Advanced Task + Resume + IB + Serving) -- `v3.5_design.md`:详细设计方案(基于 v3.0;当前迭代仅聚焦 Advanced TaskSpec + Custom Reward,Serving/IB/Resume/多版本 verl 暂缓) diff --git a/specs/mvp/v3.5/note.md b/specs/mvp/v3.5/note.md deleted file mode 100644 index c68bdfd..0000000 --- a/specs/mvp/v3.5/note.md +++ /dev/null @@ -1,3 +0,0 @@ - -1. node management(v3.5 引入的接口骨架:通过 SSH/平台能力管理 head/worker 节点生命周期;先做最小可用 --- 这个是干嘛的? -2. \ No newline at end of file diff --git a/specs/mvp/v3.5/requirement.md b/specs/mvp/v3.5/requirement.md deleted file mode 100644 index 56520f6..0000000 --- a/specs/mvp/v3.5/requirement.md +++ /dev/null @@ -1,40 +0,0 @@ - -v3.5 版本是在v3.0的基础上进行功能扩展: -1. 支持自定义命令,不走固定的TaskSpec模板,用户直接提供调用verl 的python命令,如下,这个灵活度更高,需要用户自己把握文件路径,用户使用 $HOME,服务层替换为用户自己的/private/users//路径,使用$COMMON 则替换为/private/ - -``` -PYTHONUNBUFFERED=1 python3 -m verl.trainer.main_ppo \ - data.train_files=$HOME/data/gsm8k/train.parquet \ - data.val_files=$HOME/data/gsm8k/test.parquet \ - data.train_batch_size=256 \ - data.max_prompt_length=512 \ - data.max_response_length=512 \ - actor_rollout_ref.model.path=Qwen/Qwen2.5-0.5B-Instruct \ - actor_rollout_ref.actor.optim.lr=1e-6 \ - actor_rollout_ref.actor.ppo_mini_batch_size=64 \ - actor_rollout_ref.actor.ppo_micro_batch_size_per_gpu=4 \ - actor_rollout_ref.rollout.name=vllm \ - actor_rollout_ref.rollout.log_prob_micro_batch_size_per_gpu=8 \ - actor_rollout_ref.rollout.tensor_model_parallel_size=1 \ - actor_rollout_ref.rollout.gpu_memory_utilization=0.4 \ - actor_rollout_ref.ref.log_prob_micro_batch_size_per_gpu=4 \ - critic.optim.lr=1e-5 \ - critic.model.path=Qwen/Qwen2.5-0.5B-Instruct \ - critic.ppo_micro_batch_size_per_gpu=4 \ - algorithm.kl_ctrl.kl_coef=0.001 \ - trainer.logger=console \ - trainer.val_before_train=False \ - trainer.n_gpus_per_node=1 \ - trainer.nnodes=1 \ - trainer.save_freq=10 \ - trainer.test_freq=10 \ - trainer.total_epochs=15 -``` - -2. 支持自定义的奖励函数方法,你参考 verl 项目 [text](../../../verl) 里的示例,设计方案 - -3. 支持codepath指定用户上传到自己user路径下的 verl版本代码 - -4. 断点续训:支持某个已经complete(成功或者fail或者stopped)的任务task,从最后一个保存的checkpoint 继续训练,参数应该保持不变,你确认一下是不是对应一个新的ray job,或者分析一下verl 是否已经有类似的功能支持。 - -5. 支持训练走NCCL,使用RoCEv2和Infiband网络,调研一些verl怎样支持,需要哪些配置。 \ No newline at end of file diff --git a/specs/mvp/v3.5/roadmap_v3.5.png b/specs/mvp/v3.5/roadmap_v3.5.png deleted file mode 100644 index 779e05beae8b88d26270a59774811196f9d7ab15..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 100850 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%0AX3 zsivmpwD7~JsoLA~?>{TrnSO50#}6MY>i_-u`1p9gob9an^ZO4MwFJyI%WdP6)e_*i zwIy@%?Afnhy#kG@oSE_P{rmkTFE8zim2vNvv(3D;gwu`&5IAW@z&MV-KuZu z>+4$^wN;6Eo@Vf}4?q9>`}=!!UB6qu+~52E|4odT8jwaK0N{_*p# zt&P5Y>(-?3X14uRUj;c>W}D~xd3go>)$sN8b#`*9`}K19t5;d->dWQpekhull$@HP zDXivmAb#(gH*bocpG!?o|NZNioK*=&y{GAZ#k;#oU*F&VzgOD)&)>i5zO#-zEpm2p zN=i;P&%L$en$Y^E%iFSV$nd$p?I^gSIMpk9Th7VHAH&wgND2siILvQVxY= zn-6kuawcw!sQ&f_G)~ebs$El4Bf)d*%uM6@9}nB_+==-le6b)Z$B7Paxq_nqIBdU{&n&O4xdARVpP^5*T^@HG*jxy7=@E8aKx!waU(H{b9| zn^ja*fleK&{B-2z&6`)Rem&I6owA>w7t}pkdK!0mks~>wkZLUwyYA=Bv~72jcfHUD{Oq{G7Oc+@JIH|2{uB$he*X^sQ1^(TLG9>;WgpM{=s5al#taFY72A`K_wC!aPft(piD-a|P-OPW4ccwJHgSjt>mnn00lP_jJ9L>$Ys!^5@y?{C&UQSvNW;O!NS)S+YJXq*-o@g0<;s;6Vc(~ErMkMh=H}{lAKkQR)1^)Oy<&@Y#;8qR zxy)3+3ABIHBr_;7a^~K>pkn~keP%3p%8<%iesrpbO254QzfY(2U*8tBQ)&sge0S65 zpP!#EUApw{?(*=z7gU8h+sqA&jf-z?N?o~fW!7u=Ua75xkKH~A3wF9JT)5CY|6a=G zoA+xz`$j~}_-1UCp&-;*VKXo4CP&kc=kx3D+__UA`}FPY?cL(~`|AJidu8_R+qcbW zXJ^^fRyEsyD780Q8Z>kAWaX(|)+H|vBp7^qcXxN`>ubTw{VJ=gPe1+i>QxpucQ=2X z18-f^)~#EmcI~{TuBe!JZjL33dJ%8*x=ygq@+c^1Wm4m`}YQ|^zreD*_I=D^EaR3krbo5 zckhO;kMq6fDrNem&E$vc>fgJh>`ZsY%$qjt*_$^p+nsuTe_DC%)6=3#H@CK(J1d*F zJ6-#f9XdTgLUN%xxOni1`rghmH3EQeIK`Ym+T4iKxy!!oNp-vZ5Q`4_^ z<#z4kw)6bV`nmaf#M`}9U$fra*jW4P%gv3+?#<%I_UzdstnL>Q8d|tBrpCJQ+1c5T z{|9MJO-)UmIdkUQ+uQ%QL~qGn_LEnn`{@5apZk5(et$Zxe>G2AU##2L$LB-6X@%zM zYR3Ny4jnr5_4W1R$BwO9`~Bm`n>&k_H#aw%ffBXVziS*UP5f><=a(&1UK_dj*_D;S zpk<(6zWmu@%fP@R;(OTmZpHt9wNX*CeAJAMjX!_*u;RC~hk#32nVDP;sFK}R`+FI; zhuzE&Ez$0yB04kTrc9r1U-xInu3fW^Chgq0)6&Z7+TYM=r=L!pI#oDT{^mxbaAEJ(^ZlwqollB(wzjtJ<62 z^59@d?(J=%x%NS+GWi{5@vDECR75@c@aFsddU=BchsUBj<9y2x*8KVLaYy0fX?n3% z+1J(_yKBs9`e><-ijZyHpB-z~@F+fc_3GB9RPU{^nLlGMg9gcLDn5V~a$ndf$gpeS z5z`Y9H*em|Tqm&MW{%CmIp?~*aPEj%_bpU)ae8j<-QDH+XK!za(BX~En@27~JA>cua=a5MbS0Gpnao_>96_Vp`QLO%6fVt5hT zyj)eTDg?YVDpYp*TVq~XD-r*r>jE@XggRHRUTyZ>l#%Teq)Rn%;=~*?>HBHADk@6? z)&8+ENXUexq%7HYnt{Q9!AI@#*|TeR?5Ozh;bE_xyg9>sx7n9B<=)=r>gw9e#%r`= zUZa?p*kbqoylZP_dZ^sml-m7F`VO=6@f4%Id-gCfGvD7=Yn^jrL*?gZhBGg;@iE9A zJo1YH0vtFm7%)Sa3{w~$NMuQKVWCbJPEOA4`S<@lpI^Ue z^X9LyG7Jn12YwXpjFAU{`S0%TE`NV7_Wn^u1_tM(GY@ZqCU>&0>+x!CdUkg9_Po2d zPM%y@`uZBARrRRAVwa900|P_CjweNxetv#sWo2n#keK+8-Td{vy}S4C|NrFVl|MuAaVr{rdUy=dWD3^4)1rC`+hrjF>ZX zCTMl*?(+Bl{(ir&G|}U0q~3Jv%1=)!KR+|gzZVm)%EG|#%6Quc9Yw{&%gcP%$L$S@ zefi{xh=9O_)#2;k-Q67>8ToQ`4k&WMVpPM&vTzu%%;E^N!ay)Jh5viCxa3=RJz3%=!CUl$v_Jo zzrMb%v5UX23JTBz?z3&HzirLFe&)=Xb+NmzZA$g76=!E)_;NDf@a88^o^%SUD<6Ah z23rfDCBmgPx$@_yr=UqIs0qs_c&I!+*6Z!>UtU_ex8&udnKNhZ^JZaSs7jtNSNi_m zYH=y4uH{c-HzY6~Nn>DOXn6SOV}*O4Oy=cfzF}e4+IXeEfYSd3_2x74bYpf1+<$cD z+BGqLO;8eSaIF6N3Ur>0(~DPESHFAr?w1}P1H+58uP4Uk)EQwE5MmSK8t09z1<`xc&Ccn=iN9fK+GbY}>XC)FXFVcwFsbylYbKIVHSHNj~+}>3yR&3a`=@Qs=%Xu_ysy{qnjC)YD^TKAq7vgpdcW#=o@ebgrZ>5lJ? zIdJ-i=AHv7Qa2QGl@B~E+FkZ`)}%>A|Ns4UY-W48+k$~%L2#SMyuB44nekp2Usp0oo7tZg7w8sHm$uSFkZGkap%ee{WA^v-pB^R=*jgj|1IA7 zZ)2O&!hi=Ui$k=omPeK}D($VQt*QC;_BQ){K?Vk1NuLU}$tS(My+3Z+zI}TgH#0+6 zU?AhenSufwELL@{Gkw}#&z)7Qyn}oGt4&$Q+;ndS#hbDHlDe`qL`#%+;_0VP(pH`R zn)@O1Xu#WL(ckso?eJcg`Q`h=W-e~-($7w_O5fd)RQ&SgWw1mY$f?bo=ZlJpPNeGV z>)TFaVF*f1UAnKEL8|fHVdJ7W;T@ZW7xdlUo)4Oc(?9uSS59uOtgI|I7uTlEn|GJI zT=f1C14F|*37^$jm6eup8Q0gzPCtD$Kat^pmX_9+Se6SMKEA%Cf4Y<=a_9%-`tdoW zhlYl7D8Bl0Xj|4*u9ZF63=9mj3}$@jd2{{Yg9i)lPhxOrdNZ@|LhZLTyLL(GU%7Ve z)sLl&EBN`&YfQ3r=9oEirs7n6ZU%-6Ee~7Mb)&Xi$oFJWaI8p^DX|Zgy}46xQ+k6{ zLC|!oo5mdH85q8#7(A4${I2fq?*4Zg3xiNeo(Z4POrPWHJ+4`ln%!q+;1%jV+TnH6 zxVX4@$)#zG3=AfT1`j1IEm*9~nO-%#nOWHIfrsJC`FP5&~7qPn^|+@>m?^9gSx7f9W$mwlC-nAoUb!_07@ z|6yzT1Y71Sj5m!RFZlgS!*UK=S{_S?^V|GlVSYa-~E>X?K&}n7A=?4?{^hgGV zyCBy@Ulh2K#xT|4yvbuwLrvvXOS;$6p!=>23=Fmgdp__;U1BIba5F!=Pc8@90y8Q0yY+nr-*^JVN)H*!%y8s;J6Vt=Fgn`%Uud<* zx+~>|R}E+SOykcm+G9}V~p3` zBXy>oixW)CW0~SQ_XE$SbfcL*8X{dTi(b9TS{M-VcmEOIi{&4`Hk?hHJ!3|Jh0Le* zx16s|%{nc^$L?Nb@lE;vCcBoJZ^BGYX0v?B&AClv-otIVul^Jee)n$O_uW#j_7y8z ze&bMyuiRxp_R z2dUUhKK(Q_G*nDXOp2-J%9Se%7AQnV-{uzAv#_wpxVJE9<&@J;mn~bCQ?_?HN0S2R z28>r%SFerUK5N#jRkpL|&);A0@X$i%_H#1~n-3;DdH%fq_uK79j~-pNY?;!;6`M9q zx^wCD>DM7TRkgQkQdqQjadC06vy+pQ&2fg*Ky{nL zqQO=FUQB*Cb00U;mt}kQ$Xwi7$s`d}$^y#T8lv-Ltx8UuKK=T|#l=$FD!;vn%+1aH z{q61AwQHsCEDX`o)z#g)b?em$*R`~@t*gJ~L`BWYTI0HE-MYGukB&Y(-0tn|E$CEO zSO^+|U$aI>L*u}0ZWbnYclYx0?}Ey1FZOEl?OSy~;Z6UfY16_&LqlU@ed8vdK6UEb zo14WS9yrFw-xpMN%elQx*VZ<6_WKi`pP!H4QxO;uF=Ni0n3xzIRx^S%{XZkY}y5hsvbv>+1|>o{8L? zmU&smTcE{5<<*UiiyahJa=x%`>Q5z*1JXU+u8GlhiQxOvlep3P3@ zc0N5lz4dW>XW3S7Yi~b3QQ7^~vpZj0zt5HCm30*G^z`IVyee_;%9Sf;&#qmtfI)G} zJP_EIe4I~hvZREBMe?zpb91dHzuyqF5;RKi?Ck8fZ{7$vsj8~3(mk@f?5&h#(UNui zoPWBlau<}$lVUMXcKp_J?nAzn?QHc1#nkg3{Hem};9H;O2Jh?(XuxfB){? zyLao&eOtC{*|aI>^OS@2e?GE1W&HT?P-@#mucfA@rW}fm4iDbHfB)o3N^Z^Efp%_3qAM_uQo`SH7I48!aO%E9exw+%I-p&dl!aZl{Giik_aDVVL~u z>uYzv(g4W7a+5+A7!>^7UHSQ0UtgcHTTjOIb#wdp*;h1u=;2yWtbBHF{eL8lWH>)p)kd>$%7?(WA;v#%XFdi3wN+xgCIJQt5&WGF4TZ>-huq37AXz18jFFDm~r zbDU@RA+n=b*;VUHR`LDm)28{&FgSSX)T;{%ou55>mVbZW-nzfLR(BA3geTIC^`Y?;MN5!)?43dJ`T!N}BU^Reywzo~Gu{N8S3byqoq`e0+3wcllha z(xBIJk&%&}0xg?2e_k$|DSU8$y@6@Rw10m-pD%uXj+3Qnm%3+Y=+p?EZ=XJG+PLvx z_L;M1+j&7JXl+P8Kkw{3TWceuOGl3$y?=kdb30!Jv)%mj&p*$dGskY5gx69dd;9+n z54ZQr*?#)=P0k>pp>1Z)mL+F(tlj#pZW>EeFZ&*u+qmyRV>-vNc^9WDhPoHXYk|wl z!#9ohp3iJF&A#Tdb>i2LkB`rsIWzzMzN1^8U%7H+(ITb#`g)^@t^!An^-4c}^r($T z^3#ipi`)6-fBpP<^!V}T&z`M%w{69WjOXX(ZcaP<>GNl4+o~_;=30N;pwx2V_xJbO z+S+g5zI`n{r|kE)+?ENOH*aojZGH9Y%o!iE*}2)-w=>x9SG@{oF zTw5O>zdiH++uPekMMdxKDh*y6*5$HDTt7}lMPBu3-Quymj=BFk-p-#U!76%^|xb;f8=FOilq2Se(l?$EQL4)Wv za{d}3r=Awo*az=nT=!DWu0{ehwmjQB|KFpdpu4hUt;^or+dKPBOW6GfTQ+SnvN2d$ z|Nmc>^pht~OfJ5?Vkhrv=c{$NJov<^Q&Ag}T4&FWzRNq$rm{)k*52yxoxJ%3jSBUlV9tp!oxAXU_%6l!n^y$+l{%;f3^ap70aC7gj{H*45;^9{?O`sTtksomxzQ~bW}D|nPSN#0k z)~#EAXfIBDo_~LzuD<^H^XKnx$qdfP(Yf~wH0{5;+`J=&4+m zSH`O~b?K|z5)%^@1vox^`sAW?@$T;O$B!QiI#vAYl{U`wR_ICd3sny@!oP7Ry zXG~sQ-98VMRnZ&wmA(#3OG^Wdos_*@wM))l|K)=R37MHUr@TL|-gK^a*29-#ix)3u zW@6g+_uK7VH?@`q{rvRQyJbRzj#&3mi|bjLnJ-_wc=7b<)5nh&&pLF}Md{+}>+5Z8 zZMXJE2L%NcY7ZI;I{oz1&(F_~A3xsS((-_T$6O$0XOXIzS=p5p zf!WvBZQZmfNJFIj{k`7a-caj}szRX2s;OR2w`5*EbM~zCoyu-8-K^|vetEl^udlAM za*MUJwSD?o)9RF{@o|5Q-t^N?Lo{^r(iWx9)@ey+X#UVMPa|;W6(OHB{43hHOeH2o z=$t!!`u2`O<^JP`n|~L+>N%O>H{WjVpPA>+ovZuy=H?8;FLk;%d%ZK9!>x` zVy4m2>({rZo}MOaU3TS8OXG8n($dna`<5O)e*F3C_51DW|NVJ&b@k>=o2Kc<=cT1B z+veN+Gtt}I+iZ62&rhlH^7DJ8%^%&)+8m*ipPye}|6g1`E+jN`;={-w5SX-o|NjM! z&0B8nY;ItHIv zY3$?cJ9o~Uc{Y_s`S;L~P-(UAP z1V%^iE_rz={rtR#yhoA>OG>^xIXQXts#Q(R&CC7guM0bO>C&Y&YjouL!y_YS&YwSj z!h{KP=J?F5ejpXb8g=~B=g;E$aXkXJ_SNooP&je&WG8qXq_}?E9J|`8xHvf{4;7)O z&!3mSz4i6?`~CbpJa4Y73~qLu?xQyO^iz4$$;%xSZtN<3eQK(9rOmyG%I-F{w&rZ628&i%u-+2-Q=3Shu z__yf5ncjvhji80<98OwOwM4q^+_}>$ZT{=$PgQmG`#X!Df4^VFRR(-q^GB6X5QSC zdfIQU)ylVf^6&5a{q1dcclYb7tHqrgBE3*Y)@Pc(k~$+e*V| zyIsn81smosHvbu0(iv*3x=ebDciu@mJ4>;pskvF*XGVhn7bmBuw>PNe_WgeS`ZDb- zclYBcQ~xh6FXwmCu(tkvXJ_%vn>Y9E+t6}=FJ0* zWM5k=U6+xUSNGw8;~wA4OiibbvuWSo-ZruYPPzrVY?*qvWrfBmxB@-1!?6J}?r2%Y@(_4Ucw0lRnZ{P_z6xLBGhKR>JedNn+F zna{zg9<5FvH+J@2xe{VF+gHHF)6>(@(Xp`bRr*rzFDz_sZ$CcMIDOx*SF0yY zn)Kqui^9jpT3cEkC}nOgR-3$X=btIA`_x4^&len>axVG&iVH_YUWm7(e{tzNwRBoS zmVkq)$jS?!EB5TI{vH+{9vvC^P-*7u+47b}E;?eLfBxBJdQ{Q5O~$68;O3@OQ0Z9u zN+j-NiqZZ*pH3g`7Jsa0&eWK2c9tnld8Q}gojK-YWxQ>(E%G4HCXShup0(z*He@1H;4Uj04KCWYHR zG%D)Vg9j64&yJ3Y>N?LmhwJp&v%1>amu-ZTBO`C_EPf6eiJdpEPhgg1vD(imD_6eU zS^WIY-Mg=U$FB_8m2eQWYWDrDt*0+vo_sWkSIR^~K|w)HO-)HjNlQyhNomo+KL&L_ z-re23X_L_>vD_Jug;nY2=k3k9ss(DiffiPsTzpOKXOH~8+TUR+LXt;9dQ~=k5aB%k z;tpus2wds#=-Vt#ca~b9*41O{%u%@W&Mwh|zw*3}B^WRjjM)H z91F|e-vjkP{J%F@o7}o_qrgIjoxPpST6>;#dEVhR-Y3pxvwPFa-`w53ef|3N&!R&% zN9gEHpFMrLdC?P(`1trwV$U@-HNBQ@0$(+<>);=Q`RBK9-(LUs*H`xBPj!EPot7*u@>f?@zPlkUb*R^l?Qfr9`ps3<8xLBrx_XLc>DzP&BComW~+ zTH1RXQ$=OvT-)kv7cU0tPFS7&<;6u)Q`7jGkF9Ih>drp`7<=li|fP-zqhJ&e?A`n`T03FOVh5ka=h>E zT)ASRrsk$JF(NuTyD~t;(a+9v)w?wHt9`8lnKxB1|K&*>&BA~&Z!eE4vFjDcLgIq0GR;*G zI5$CSy1+cfRgE>>g$JevN|{}fHZhz1_8AB)OKe_tnqNBgljI@eu7(dh4i#?2ZC9dr z9!f5ddevjgJfAuJ{DWIe8GUc=cud?ac&Y4}+s23=9)Ab5xrt@la%t}6=5n-$P+EQR%?LOyrK3*A%4`*ka|I#~g zyz!0XS;?U1ZZ<0#+ITY?HZ7QxD^sw}VfuBkMu&jl;KiG#GdoD9lrwaJO5^4aYXU>U z!oosAwq#xPy3hKPhpY1ERZ3|No>O7h>(IX@_R(GOD$o#1%Q?~x+Ua!dEq&C^K zv|Ugb4D_a-epv9qsQvK6qMd4LYEgY((l+0G;`hP+(f(WS4;DxURj?VGGp%a8@Ar7Y z?>94N&Xn9Y-JIcy=yAo@!^oM zggny<=1u9x9KR=@H@Ux6l40+HwC8Sn5(>;G{+3CpV6!)zfBxXXh0B&L+p*)u;ls}N zQ-5;YD#`ov`~80V9rI46Y>Ln^o4xki_h#*zIos-t16dqT*t_J~Itp;LGX0-=`YC7; ziQMTm%%H)yLOX$ZjISEN?mX9B!t;=91wscc^MPnFq?a2=ko6_f>chKK z&3R?Wv!_pAt_qk^@c!Oj&<@ti&n2{-U+wOc232ua7$43oJW#3-Tb8Gi|CEP;HBiMS z`0Tuw+f}UC=1NP)rll?0*ZrYz3(t9h*zBVM^8z_a@>oKcA(~FiV{AZD|4>q4wu+R^ z&zIlc9#F7ZEHEQNK7h9+{TSo*#xF+S&b(MYpXtHm%y?&0qm<`vMJ5TLRY?aA9t54r z$gya{hJvfBLjV2yw>ka1o{r9yXZPpZR&Pr?J1hPCyp`+LtXt>j;ZgDL&(3H6MZ1qm z>Fs23{PW>3zjGUproR61>?cK_^L`#ZdNgVBlhktbZ+P4m$#d8`sv4y9~Zm# zzq`Kv{>#hDUq6eT>Xn+6^$N5+e|!G?2@@9l3i0$jd2X(Cb5oO&vhwE5n?tXEe|NX~ z_qVqk3(uT6vtfgQz5V{F+TmQSPG^t*usl&&WisbaiC>gNZAF?#^7#*)9)~^WFr+&2 z9kF<^uUNVA*@3xd8Ce5WGM#U~nR!m@PSDCND^{%7w(Z-+#qNoTiL9)w91E|nk7s9L zVPR!eY}vGV^Y+}^(pW2B_Qi_~eSLki*}Vc@etvQL zYIeR-(AL*q54wpZ`#PV!j*iZnl`AzhH9NbyZf(z(kL!G2v254vuCA_*4$w~ImI>Y6 z-C4CphK7cqrNHl1EG>WD*;#zNPxkeloyJZpR;>appgud>9CRL$aXR0Pg_fMTZ$hay|^#*B-L zdU|;N?Dtyw>FjLtu&^*?w;qM^AOHUTUa~}`Wy1db`*-fFtX=#fyeUMn+m%r>6Opaw`-)5O+&oa#xlb4@Ad-m*^GjEn` zl)UtAdE>m~^945RL$rE--&@!=#kP5-G-K(5jgk{=jrpo%s@Wb&E>P%dN#AmI-pe<~ z*kbgq-@0XGX*u&?!kb%LSLff~_ayk^$BzpaF4T?M($U%Z@yiz%j@Z3brRU~Yf?9|B zYOQCV73)5F^ypEh#s;5>f-D8U zJUKbp%*@Pd>8AsY%sY4PG)_D7;oCPoUESX9ZfA~ODbrWW=hqzyKeu4P0<>|m`}BrIYTooql@j=FO$c1YhNzg{=ix_UY%J7cXA)$yzJD-4s3FdG>s^JIj0W?(=+7qkL2F}9 zPF5Fm+MIT_sHEh|hh4hS+f>#!zI^%e;>C;0mMu$7O*Jz!+1^*4So3V;VQ$ayLbQo_4W1szu#`3p05A<_wUaYHhk^M(@#G?KY#tSt&cxe zR4`SwT=@0%^>V+ttHNeTo98{4ZQb75`t|MY?R)mv7#dzYb}a46iomS*mv$6BE+}`G zy|AxX`EJ(HRS##bUAwl9`*I1-`eNm~el8Ba7B;KbC)*n6{0Nudl+KVKk~z8UT(8xG zM~|8Wq--iSWcmF2@$vC={dm2Y9TR%oE?v5GZjNQMz^U`+_t*co`(?ho<-K6f_4QF( zy%q*kR8{dwoB4e1zIE$XR8*8w3rCYh>8p_3++0`Jqxb9o>xyt~&$+2I{dD;HxZdo0 zK`Xax*%D&v{@t;xtZdq}X`t2LS5{8G6+CU)G#k0~k()uwgtD)#u`GEp;nmW(l_6>> zDiIM8F0QUSckP;IU9M+nc=7b<*FQc!&dbZIkZyEH$j?8YV8F&Nw`TM0#o3pO+|NfD zT1H&l(LNtkKhFi_jSpvz9dohv zM4{zapR9M^k5!;+FeXn9&dYoE^78WYb1W|}^Od%nU;pgPOjd5OJNxVFFD>x|E$a8? zYfnx~11*6Ct+Kv9)$1u}4epwV#JoJa%u6aYB45uoMMp+zPV}hy{%&vfbv?c5yUX6* zs{H(HZ{6Qrd-lX=O+A%jWW%5G{M_90b1WxM2Z8d3hg$Xb|Cw}$x%uFQzpYWf!0_oUQxiWBxl{R7e?|4n+lOgQ%`w|u|Noz%p<(g!b9>9)-rAadUBKyn-ERqkNE1kaUL;;_Bo|>9ksr;-N zGiJ=3$;rZGY-}7H91L22TmLZ6Y*$XR%JEo-=WY&;XJ?sSE*BIC>OA!#jPdHzk5-nJ z3$4VJqN8tb&AzS|wPnSQ9TK2Lue)l0m)UUS-rSVBaN)x5@9t*b-?w-B_V3@`-oCyj z^6{%zyUO0)>ged`leONKb2Di6^|>~cpO$)0KXvNVp~Hu*%irbX=l}oo)LU=*@6-DG zS8T2Jn_=LnH~sy+y}v=r==EZqI3gn=Knn)Hy}5aIw)yefAAZ(USO31gKK^>{s^YS; zG^3doYd(GX^5=2C{h~#S`eZDf@&sgL=1iFaIwtAMmoGbupGQSTo=n-)($ezdM@5rD z-T%Me8JXF(WL@QYxotDE&zg97BOBv)1qUV^GOjuo$h?BHJzZGM=R&z7gA>QY6{7VT z^EXdErsdxZT3le%#j`{Gu<@>~4lg&|v&^|+psuc-o}Rw-t8LYn9p&%iTwPiFj|b0X z$$oKR;SOPCr;dXOJragY{%h(#KRdf+%a*O#*Rw2>r_G)X3Pvt2u7WGiA3P{{c&L>> z?_}EM<-W5)M^~&2iHeNO%*>4Z9+vs+*|Xo@-|K5=tf*FKX6LW_^n`P!n6a^O^!B{F zkB)Z7@2lyIzjfzM&G~t@tHaiUu1@a~)jm-VUDE#{rtkB!v#+nNo}Sfzd>LDC^Og3V z1HHcw@ao$%-wtBdlCUnzDJv^GyZ=bi#t0p=cipWM4Gj$+e*Rfw7q1}jp~9xoVL{dI ztIOQ3iGmhlNEsV%=D(*I@jb)3cyZtHc~{F{CU1<0Vtd8nILEsD+?_jr7U!{E+f!L= z^mi$*-t^Upzkhu@mSFJ8t>@acYj<~-tIJ14MuJlM*;%HUnVCj2&zw1P=I~)>)6V0M zKknJPcdP!Z=a=^tE9Yh(Jr?`eXwQc;JM8%rG`8j4{q@s&;_0VGGkMC(r+6(*+3(&X z!{4^s;@aEGE51#6m9Tl&|F41EtN88z8*DwEV)UBNd$qNKZ|)JPcL!Je3V5q&Hv8=3 zj|Dt#$C7`|o!oq8-b2d^3=8ACxvL4zAJNVKAd7S(?`wk_9IrInV*hwXU(pCHfK@Q$H2drXNlwE}U+z=c2eu(8#ac!{72w|Of|b_ao$+=2t+ zqN3#o%MTpl+1c6E)z!7rmvWj)EWKQlRQov1L)XOM8)(Vs0?rvbFJ^cw4O$qGk(wI% z{X&aVVpdj`uW#?{+0m=R)^4%?_U-NM)unk;JXEf)i``xHl&kxwlzm;ze7jnnDlbdE zcIByF(sy_c881%pnBL&_=FW-`t*KtBc{77GL@ItZXP?mB8h`nLo&66jtJ@6=n@)n# z{hkJaOaByqzL%2Ay0`xp+p7P5d27A}9G>;7?BC4ion{-nTSMKI888?Ju__ z{?`}lKKii0?#J|4eqR5~&C#-RY#11LGpxUz;mDe=s;Vj|D0q39@8|E|&!0Fk!?HNd z(b2J>0Cd#HNd_MsvHyQQpKs@vSNq?6{IPE2rj%P-GFR;tds_7K>+9?Fzu#^@b?TH| z?Ju9XR-)_WZL7At5)o`|ZQY!H-p}9vIRE3vkHgnQ7^a_-+4L%-KrR@$vEcUoV$yhp&5cfB*f12N@Mz1dhxy&F+)8?<=1@cW&*+N3Pk~ z*>>~azk21hZ%%+l%&wBms;Vjvj}x0xPjhi`rJb2k`0dTjkB^VvzH#Hl!ynSl&C3~c z)vvXG=!rVra~-Cx39J#XS-J0UD*>YFF$|Aj2XwO?n?>g z9yV5fai`TFu@%4Iq_4jvY z6Aaw?WOi13d}Lew?ahsikB`gO-`Skb-+$b?^wpJ*kB`gB%9`iiy0S6Zz2(B~?fJ|7 z=j%=M(9+gEIo-PM&yTs*ZAB`s~@Wyu0LGnwK-CobQ>T7|S%H z*Kp&$2pu<$jW^${S)W%a(@>8$*Diw`~Ix{7V!4{@~ORV5|;f`-=nuQs59Gp z$FiXEh5Npyv_6}B-&1Iv+{&;?TUI7yt}C6GZSp?y@Md8(9}ho2J$?QEf0);BoBv=; z76mt&u9R$#`gKN3sYWzw%^?QR1fl>7t25KBw)B+8vZnUpZ)0~BxvmWHn`2S<_0`px zGiR#%%{g)I+%bPkYis3}V?C0Wm;1{XRm=5@OG(X|Hf`FRIddjYe*EHvgs^aOV&cZ~ z_xH}twN`GK;`Q|6V)u`>E8pMUeSLMfK6q6?0sqO`-`^nn6=Qant=+Y&>f9VlHrvm2 z&9yO^((@$q+C$$;Ub?<7@YuYEA9&hTcbwf3c#3TWs28VM79Aa(%`(^Dq4q=j?JMPn z&YnKKdhOby%KRUjUKPFFza&U==bFmot?BkNGXErWZOYrXG0$q_JNrq}CNFoV>?p7n z^s}tnaJA=bT6TtA@X~F2U)f)~+jAOJk_Zb6=gHd0t$$ZE+bmbW$<);J*|TTA>ds%e zXlA3FtroQMibJ;M(W6HzB+Aauv#tO0(cNrzZhrpz7cU}0LR7@MS(zLQ3k{uCxOR(4 zl?6pcMn**3SRZfi@9)3o*~P`~pkbS>2SHnnzrDFRZQ3;d`F6TmT3r16>sPF>sQjej zDDdsuH|_9spi}iP%V!8TZA|}a_+rV5X*@5p&u8_V>rMH#rtlQYinVLjtkEpfo_tcl z#yDvg=XozLuUY2#c`WKdwYIMI4;Mbm5LkX{>r3T;`_o+he)wYZBtExn#m}p}i)y!n zR{jPU+XP=IO{)F0NnxUgkFW37=o$Xa{zx;Yu2`$n?~B&-0kTVPahxe z4>fMNdiCmT^L)@b9!ENbZ*R?>K701+D%o>q&&F=a2n-Fq`u%?W{CV^0zP`G8<;s

+|UR`N%7i(#0 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 v3.5 本轮按已确认的精简 scope:**只聚焦 Advanced TaskSpec + Custom Reward(方式 A:用户在 command 里写 overrides)**。Serving/IB/断点续训/多版本 verl 等能力本轮仍不做。 - -## 1. TaskSpec / 任务语义 - -### 1.1 新增 Advanced TaskSpec(自定义 command) - -- 新增 `kind: advanced` 的 TaskSpec 类型: - - 用户可提交任意 bash `command`,不再局限于平台内置 PPO/GRPO/SFT 模板。 - - `workload` 不再要求用户填写,也不做 infer;平台内部统一按 `"advanced"` 做任务分类与 task_id 命名(避免未来训练类型扩展带来的限制)。 -- 支持 `$HOME` 宏替换(服务端提交前展开): - - `$HOME` → `/private/users/` - - `$HOME/common/datasets` → `/private/datasets` - - `$HOME/common/hf` → `/private/hf` -- `command` 校验(best-effort,面向内部可信用户): - - 要求包含 `python3 -m verl.`(允许 `verl.trainer.*` / `verl.model_merger` 等)。 - - 不做强沙箱;主要防止明显误用导致的不可预期行为。 - -### 1.2 Custom Reward(方式 A) - -- 平台不新增 reward 专用字段、不扩展 TaskSpec schema。 -- 用户通过在 `command` 里写 VERL 原生 overrides 来注入 reward: - - `custom_reward_function.path=...` - - `custom_reward_function.name=...` - - `custom_reward_function.reward_kwargs=...`(如需) -- 平台侧仅做: - - 基础路径/宏展开($HOME) - - best-effort 的字符串校验(不做深度 AST 解析) - -## 2. WebUI(New Task 体验增强,仍兼容 YAML) - -- `New Task` 页面新增 **YAML 模式 / 表单模式**切换: - - 表单模式只覆盖 **5 个模板**:PPO / GRPO / SFT / Advanced / Model Merge。 - - 表单模式实时生成 YAML 预览;Submit 时提交生成 YAML;可一键切回 YAML 模式继续手工编辑。 -- `Advanced example`: - - 示例命令改为多行、可读性更好。 - - 补齐 PPO 常见 fail-fast 所需的关键 overrides(例如 actor micro batch),避免用户“照抄即失败”。 -- 新增 `Model merge example`(Advanced command 形式): - - 使用 `python3 -m verl.model_merger merge ...` - - 支持用 `$HOME/jobs//...` 访问训练产物目录。 - -## 3. SFTPGo / common 目录可读性(配合 v3.5 的 $HOME/common 语义) - -> 这些变更主要用于保证 v3.5 所定义的 `$HOME/common/{datasets,hf}` 语义在 SFTPGo WebClient/客户端下可用。 - -- `/common/datasets` 与 `/common/hf` 作为 SFTPGo virtual folders 暴露为只读共享目录: - - 允许 list + download(用于浏览与下载/查看内容;仍不允许 upload/rename/delete)。 - - 权限规则覆盖到子路径(避免“能进目录但文件不可读”的情况)。 -- API 调用 SFTPGo admin API 的连通性增强: - - dev 环境下避免依赖容器内 DNS(部分 head 容器环境存在临时解析失败),改为通过 docker bridge 网关 + 映射端口访问 admin API。 -- API 启动脚本确保注入 `SFTPGO_ADMIN_PASSWORD`(与 compose 默认值保持一致),避免 Reset Password 走到 401。 - -## 4. 兼容性与行为变化 - -- **完全兼容 v3.0 的 PPO/GRPO/SFT TaskSpec YAML**(原有字段与提交方式不变)。 -- 新增能力不会影响 ray/node management(仍按 v3.0:head 发布 discovery、worker watchdog join/self-heal)。 -- Advanced 任务不会进入 PPO/GRPO/SFT 的语义约束;平台仅负责: - - 资源字段(`nnodes` / `n_gpus_per_node`)用于队列调度与提交 gate - - 将 `command` 作为 Ray job entrypoint 执行 - -## 5. 已知限制(v3.5 不做) - -- 不提供“可视化” reward 配置面板(仅方式 A:用户自己写 command)。 -- 不支持 per-job 自定义 verl 代码快照/多版本共存(本轮不做 code_path 选择)。 -- 不支持断点续训一键 resubmit / IB(RDMA) / model serving(按 roadmap 后续版本推进)。 - diff --git a/specs/mvp/v3.5/v3.5_design.md b/specs/mvp/v3.5/v3.5_design.md deleted file mode 100644 index f85edbc..0000000 --- a/specs/mvp/v3.5/v3.5_design.md +++ /dev/null @@ -1,366 +0,0 @@ -# MVP v3.5 详细设计方案(进一步精简版,基于 v3.0) - -> 背景:v3.0 已具备 WebUI + API server + 用户/任务隔离 + SFTPGo 数据管理 + Stateless Ray cluster(head + worker node pool)。 -> -> v3.5 本轮 **只做 2 件事**: -> 1) Advanced Task:支持用户提交自定义训练命令(command) -> 2) Custom Reward:支持用户通过 VERL 原生 `custom_reward_function.*` 方式注入 reward(仅方式 A:用户自己写命令) -> -> 明确不做(从上一版设计中移除):(3) 自定义 verl 版本/代码路径、(4) 断点续训、(5) IB/RoCEv2 网络支持、(6) Model Serving。 - ---- - -## 0. 继承 v3.0 的不变点(重要约束) - -1) **Node management 不变** -- v3.5 不新增/不修改 node management 机制;仍按 v3.0 现状运行(head 写 discovery、worker watchdog 自动 join、自愈)。 - -2) **Head 不跑训练** -- 所有训练/Serving driver 通过 Ray entrypoint placement 强制落在 worker(例如 `entrypoint_resources={"worker_node": 1}`)。 - -3) **SFTPGo 的 “common” 目录约定变更** -- 不再使用 `$COMMON` 宏。 -- 在 SFTPGo 中,把共享只读资源映射到用户 home 下的固定目录(用户在 SFTP/WebClient 看到的是 `$HOME/common/...`): - - `$HOME/common/datasets` → 容器内真实路径 `/private/datasets`(只读) - - `$HOME/common/hf` → 容器内真实路径 `/private/hf`(只读) - -> 这里的 `$HOME` 指:`/private/users/`(容器内路径)。 - ---- - -## 1. v3.5 需求范围(精简后) - -### 1.1 In scope - -**A. Advanced TaskSpec(自定义命令)** -- 用户提交 `command`(多行 shell 或单行) -- 平台做 `$HOME` 宏替换 -- 平台做 best-effort 安全检查(路径/关键参数),然后提交为 Ray job - -**B. Custom Reward(仅方式 A)** -- 用户在 `command` 里显式写 hydra overrides: - - `custom_reward_function.path=...` - - `custom_reward_function.name=...` - - `custom_reward_function.reward_kwargs.*=...`(可选) -- 平台不提供结构化 reward 字段(不做方式 B),只做检查(校验 path 合法) - -### 1.2 Out of scope(本轮不做) -- 自定义 verl 版本/代码路径(仍使用平台内置/公共 verl 代码快照) -- 断点续训(resume from checkpoint) -- IB/RoCEv2 网络专门支持(NCCL/RDMA env 先不引入平台) -- Model Serving(暂缓,后续单独设计迭代) - ---- - -## 2. Advanced TaskSpec 设计 - -### 2.1 为什么需要 Advanced Task - -v3.0 的 Basic TaskSpec(ppo/grpo/sft)通过平台模板生成固定 overrides,适合“快速跑通”。 -但科研/调参场景需要更高自由度:用户希望直接写 `python3 -m verl.trainer.main_ppo ...` 并自行控制每个 override。 - -### 2.2 Advanced TaskSpec(建议 schema) - -建议新增一种 TaskSpec 类型,通过 `kind: advanced` 区分: - -```yaml -kind: advanced - -# 资源(平台调度与预检查用;仍需要) -nnodes: 2 -n_gpus_per_node: 4 - -# 自定义命令(用户负责写对 VERL 的参数/路径) -# 平台会对 $HOME 做宏替换;其余保持原样 -command: | - PYTHONUNBUFFERED=1 python3 -m verl.trainer.main_ppo \ - data.train_files=$HOME/datasets/gsm8k/train.parquet \ - data.val_files=$HOME/datasets/gsm8k/test.parquet \ - actor_rollout_ref.model.path=Qwen/Qwen2.5-0.5B-Instruct \ - trainer.nnodes=2 \ - trainer.n_gpus_per_node=4 \ - trainer.total_epochs=1 \ - trainer.save_freq=10 \ - +ray_kwargs.ray_init.address=auto -``` - -### 2.3 `$HOME` 宏替换规则 - -仅支持 `$HOME`(v3.5 移除 `$COMMON`): -- `$HOME` → `/private/users/` - -用户如果要用共享数据/缓存: -- 共享数据:`$HOME/common/datasets/...` -- 共享 HF 缓存:`$HOME/common/hf/...`(通常不需要写进 command,但可用于 debug) - -#### 2.3.1 重要说明:SFTPGo “virtual folder” 与训练进程看到的“真实路径” - -在 SFTPGo 中,`$HOME/common/datasets` / `$HOME/common/hf` 是 **SFTP 虚拟目录映射**(virtual folder),它们映射到容器内真实路径: -- `$HOME/common/datasets` ↔ `/private/datasets` -- `$HOME/common/hf` ↔ `/private/hf` - -训练进程(Ray worker 上的 python 进程)看到的是 **容器内真实文件系统**,它并不会理解 SFTPGo 的 virtual folder。 - -因此,为了让用户能沿用 WebClient 里看到的路径语义(写 `$HOME/common/...`),服务层在提交 Advanced command 前需要做 **路径宏映射**: - -- `"$HOME/common/datasets"` → `"/private/datasets"` -- `"$HOME/common/hf"` → `"/private/hf"` -- 其余 `"$HOME"` → `"/private/users/"` - -这样用户写的 command 能在训练进程里正确读到文件。 - -### 2.4 服务层检查(best-effort,强约束 + 弱约束) - -> 目标:在不“解析完整 shell”的前提下,尽可能避免跨用户读文件与明显错误的任务。 - -**强约束(必须通过,否则 400)** -1) `nnodes`、`n_gpus_per_node` 必须存在(用于队列/资源预检查/placement) -2) `command` 必须包含一个明确的 python entry: - - 建议最低要求:包含 `python3` 且包含 `-m verl.trainer.`(防止随意执行系统命令) -3) 路径隔离校验(字符串/正则级别): - - 展开 `$HOME`(含 `$HOME/common/*` 映射到 `/private/*`)后: - - 禁止出现 `/private/users/` 下 “非当前用户”的路径(例如 `/private/users/bob/...`) - - 对 `data.train_files=...`、`data.val_files=...`(若出现)做 allowlist: - - 允许(用户目录):`/private/users//datasets/...` - - 允许(共享目录):`/private/datasets/...` - - 对 `custom_reward_function.path=...`(若出现)做 allowlist: - - 允许:`/private/users//code/...`(用户自行上传) - -**弱约束(warning,不阻塞)** -- 未检测到 `data.train_files=`/`data.val_files=`(可能是用户写成了别的 key 或使用了 config file) -- 未检测到 `+ray_kwargs.ray_init.address=auto`(v3.0/v3.5 推荐加,但用户可自行负责) - -> 说明:Advanced command 本质上属于“内部可信用户”能力,v3.5 不做强沙箱;安全检查以 best-effort 为主。 - ---- - -## 3. Custom Reward(仅方式 A:用户自己写) - -### 3.1 VERL 原生机制(本仓库 `verl/` 已调研) - -VERL PPO trainer 配置里支持: -- `custom_reward_function.path` -- `custom_reward_function.name` -- `custom_reward_function.reward_kwargs` - -对应实现位置: -- 配置模板:`verl/verl/trainer/config/ppo_trainer.yaml` -- 加载逻辑:`verl/verl/trainer/ppo/reward.py:get_custom_reward_fn` -- 典型 reward manager:`verl/verl/workers/reward_manager/naive.py` 会调用 `compute_score(...)` - -### 3.2 用户写法(示例) - -用户上传 `$HOME/code/reward.py`,在 command 里加: - -```bash -custom_reward_function.path=$HOME/code/reward.py \ -custom_reward_function.name=compute_score -``` - -函数签名建议(与 `naive` reward manager 参数对齐): - -```python -def compute_score(*, data_source: str, solution_str: str, ground_truth: str, extra_info=None, **kwargs): - ... -``` - -### 3.3 平台侧只做检查(不做字段扩展) - -v3.5 限定 reward 注入方式为 “用户写 command”,平台只做: -- 展开 `$HOME` -- 若检测到 `custom_reward_function.path=`,校验 path 在 `$HOME/code/` 下 -- 不尝试解析/合并 reward_kwargs(用户自己写) - ---- - -## 4. 服务层与 SFTPGo 的映射修改(你提出的关键点) - -v3.0 时代平台允许用户引用: -- `/private/common/datasets/...` -- `/private/common/hf/...` - -但现在 common 以 **SFTPGo virtual folder** 的形式呈现给用户(用户看到 `$HOME/common/...`,真实路径是 `/private/...`),因此 v3.5 的服务层需要做两件事: - -1) **用户侧语义(写 TaskSpec/command)** -- 共享 datasets(只读):`$HOME/common/datasets/...` -- 共享 hf cache(只读):`$HOME/common/hf/...` - -2) **运行时真实路径(提交到 Ray 前展开)** -- `$HOME/common/datasets/...` → `/private/datasets/...` -- `$HOME/common/hf/...` → `/private/hf/...` - -同时保留用户自有目录: -- 用户 datasets:`$HOME/datasets/...` -- 用户 models:`$HOME/models/...` -- 用户 code(reward):`$HOME/code/...` - -> 这部分主要影响: -> - Advanced command 检查(allowlist) -> - WebUI/Data 页面文案(告诉用户共享数据在哪里) - -> 兼容性建议:为了不影响 v3.0 期间已经习惯使用 `/private/common/datasets/...` 的用户/历史任务, -> v3.5 实现阶段建议 **同时接受**: -> - `/private/common/datasets/...`(旧路径语义,仍可读) -> - `/private/datasets/...`(真实路径语义,推荐) -> - Advanced command 里写的 `$HOME/common/datasets/...` 会先映射到 `/private/datasets/...` - ---- - -## 5. 验收标准(精简版) - -### 5.1 Advanced command -- 提交一个 Advanced PPO command(train/val 使用 `$HOME/common/datasets/...` 或 `$HOME/datasets/...`) -- 确认: - - 任务从 QUEUED → SUBMITTED/RUNNING - - driver 在 worker 上(head 不跑训练) - - 训练能正常跑至少若干 step - -### 5.2 Custom reward(方式 A) -- 用户上传 `$HOME/code/reward.py` -- 在 command 中设置 `custom_reward_function.path=$HOME/code/reward.py` -- 确认训练日志出现 `using customized reward function ...` - ---- - -## 6. 待确认问题(需要你拍板/补充) - -1) Advanced command 的“强约束”是否需要更严格? - - 目前建议要求包含 `python3 -m verl.trainer.`,否则拒绝。 - - 你是否允许用户跑非 verl 的命令(例如自定义评估脚本)? - -2) `$HOME/common/datasets` 与 `$HOME/common/hf` 两个映射目录在平台侧是否需要“强制只读”语义? - - 例如:TaskSpec 校验允许读取但禁止写入(目前设计是 best-effort 字符串级校验)。 - ---- - -## 7. 基于现有源码的改动点分析(实现清单) - -本节按当前 v3.0 已上线的源码结构(`src/mvp/py/argus/...`)逐文件列出 v3.5 需要的具体改动点,并评估对现有能力的影响面。 - -### 7.1 TaskSpec/模型层(解析与兼容) - -**现状** -- Basic TaskSpec 由 `argus.ray.models.JobSpec.from_dict()` 解析:`src/mvp/py/argus/ray/models.py` -- API `/api/v2/tasks` 直接 `JobSpec.from_dict(obj)`,并基于字段做路径校验:`src/mvp/py/argus/service/app.py` -- Scheduler 同样假定 jobspec_yaml 能解析为 `JobSpec`:`src/mvp/py/argus/service/scheduler.py` - -**v3.5 需要新增** -1) 新增 `AdvancedTaskSpec` 数据结构(建议放在 `src/mvp/py/argus/ray/models.py`): - - 必填:`kind: advanced`、`workload`(建议仍要求 ppo/grpo/sft,用于 task_id 命名与 UI 分类)、`nnodes`、`n_gpus_per_node`、`command` - - 可选:`submission_id`(由服务层 override) -2) 新增 “union 解析”: - - 新增 `parse_taskspec(obj: dict) -> Basic(JobSpec) | Advanced(AdvancedTaskSpec)` - - 兼容策略:如果没有 `kind` 字段,则 **默认按 v3.0 Basic JobSpec 解析**(保证老客户端无感)。 - -### 7.2 Builder 层(把 TaskSpec 转为可执行 argv) - -**现状** -- `src/mvp/py/argus/ray/builders.py:build_training_argv(spec: JobSpec, ...)` 只支持模板化 PPO/GRPO/SFT。 - -**v3.5 需要新增** -1) 新增 `build_advanced_argv(command: str) -> list[str]` - - 推荐实现:返回 `["bash", "-lc", ""]` - - 原因:用户 command 允许 `ENV=... python3 ... \` 多行以及 shell 语法,`bash -lc` 兼容性最好。 -2) Driver entrypoint 复用: - - 仍通过 `argus.ray.driver_entrypoint` 执行(统一 job_dir、日志与退出码)。 - -### 7.3 RayJobTool 层(runtime_env 与提交) - -**现状** -- `src/mvp/py/argus/ray/ray_job_tool.py:RayJobTool.submit(spec: JobSpec, ...)`: - - runtime_env 的 `PYTHONPATH` 由 `spec.code_path` 决定 - - entrypoint 固定为 driver_entrypoint + builder 生成 argv - -**v3.5 需要新增** -1) 扩展 submit 支持 AdvancedTaskSpec: - - 方案 A(最小侵入):新增 `submit_advanced(...)` 方法,参数为 `command` + `job_dir` + `submission_id` + `nnodes/n_gpus...` - - 方案 B(统一接口):新增内部抽象 `SubmitPlan`(包含 `runtime_env` + `entrypoint` + `artifacts`),Basic/Advanced 都生成 plan,再走同一 submit 逻辑。 -2) runtime_env 的 code path: - - 因 v3.5 本轮不做“自定义 verl code_path”,建议仍固定使用公共快照(例如 `/private/common/code/verl/verl_repo`)。 - - 为减少散落常量,建议在 config 增加 `ray.verl_code_path`(或 `service.verl_code_path`),RayJobTool 统一读取。 -3) runtime_env 的用户代码目录(可选增强): - - VERL 的自定义 reward 函数是通过 `custom_reward_function.path` 以“文件路径”动态 import 的,理论上不依赖 `PYTHONPATH`。 - - 但用户的 `reward.py` 可能会 `import` 自己目录下的其他模块;为了提升易用性,可将 - `/private/users//code` 追加到 job 的 `PYTHONPATH`。 - - 这需要 RayJobTool.submit/submit_advanced 能感知 `user_id`(由 Scheduler 传入),属于小改动但要注意兼容性。 - -### 7.4 API Server(提交校验、宏替换、spec 展示) - -**现状** -- `POST /api/v2/tasks`:只支持 Basic JobSpec 且强校验 `code_path/train_file/val_file/model_id` 前缀:`src/mvp/py/argus/service/app.py` -- `/api/v2/tasks/{task_id}/spec`:返回 resolved 的 Basic JobSpec(补默认值/补 submission_id):`src/mvp/py/argus/service/app.py` - -**v3.5 需要新增/修改** -1) `POST /api/v2/tasks` 分流: - - `kind != advanced`:走原 Basic 流程(兼容 v3.0) - - `kind == advanced`:走 Advanced 解析 + 校验 -2) Advanced command 宏替换与映射(核心): - - 实现 `expand_command(user_id, command)`: - - 先把 `$HOME/common/datasets` → `/private/datasets` - - 再把 `$HOME/common/hf` → `/private/hf` - - 再把其余 `$HOME` → `/private/users/` - - 校验使用 “展开后的 command” -3) reward 注入检查(仅方式 A): - - 若发现 `custom_reward_function.path=...`: - - 校验展开后的 path 前缀必须是 `/private/users//code/` -4) `/api/v2/tasks/{task_id}/spec`: - - 需要支持返回 AdvancedTaskSpec 的 resolved 版本: - - 展示时可选择“原始 command”(含 `$HOME`)或“展开后的 command”(建议都展示:raw + expanded) - -### 7.5 Scheduler(队列与提交) - -**现状** -- `src/mvp/py/argus/service/scheduler.py` 假定 jobspec_yaml 一定是 Basic JobSpec,并调用 `tool.submit(spec2, ...)`。 - -**v3.5 需要新增** -1) Scheduler 的 `_parse_jobspec` 替换为 `parse_taskspec`(支持 Basic/Advanced)。 -2) `_submit_one` 根据 spec 类型调用: - - Basic:保持现状 `tool.submit(JobSpec, ...)` - - Advanced:调用 `tool.submit_advanced(...)`(或统一 SubmitPlan) - -### 7.6 WebUI(最小改动) - -**现状** -- `src/mvp/py/argus/service/ui.py` 的 New Task 页面只提供 Basic YAML 模板。 - -**v3.5 需要新增** -- 增加 “Advanced Task” 模板按钮: - - `kind: advanced` - - `workload: ppo|grpo|sft`(用于 UI 分类与 task_id) - - `nnodes/n_gpus_per_node` - - `command: | ...`(带中文注释) -- Data 页面文案更新: - - 明确共享目录在 `$HOME/common/datasets`、`$HOME/common/hf`(并解释会映射到 `/private/datasets`、`/private/hf`) - ---- - -## 8. 对现有功能的兼容性影响评估 - -### 8.1 API/TaskSpec 兼容 -- 兼容策略:**没有 `kind` 字段的 YAML 一律按 v3.0 Basic JobSpec 解析**。 - - 现有脚本/客户端(提交 ppo/grpo/sft 的 YAML)无需修改。 -- AdvancedTaskSpec 是新增能力,不影响既有任务状态机/DB。 - -### 8.2 路径策略变更的影响 -风险点:v3.0 的 Basic 任务/模板大量使用 `/private/common/datasets/...`。 - -建议: -- v3.5 实现阶段先保持 “双栈兼容”: - - Basic 继续接受 `/private/common/datasets/...`(旧) - - 同时接受 `/private/datasets/...`(新/真实路径) -- Advanced command 允许用户写 `$HOME/common/datasets/...`,服务层展开为 `/private/datasets/...`(避免虚拟目录不可见问题)。 - -### 8.3 任务执行/调度兼容 -- Scheduler 队列/并发控制(`max_running_tasks`)保持不变。 -- 资源预检查仍只依赖 `nnodes/n_gpus_per_node`,AdvancedTaskSpec 不改变资源模型。 - -### 8.4 安全边界变化 -- Advanced command 引入后,平台从“结构化参数”变成“执行用户命令”,安全边界变宽。 -- 缓解措施(best-effort): - - 强约束要求命令包含 `python3 -m verl.trainer.` - - 基础路径隔离校验(禁止跨用户路径) - - reward 文件路径限制在 `$HOME/code` - -### 8.5 数据库兼容 -- DB schema 不强制变更:仍复用 `tasks.jobspec_yaml` 存储原始 YAML。 -- 若后续需要更强查询/过滤,再考虑增加 `tasks.kind` 字段(可选增量迁移)。 diff --git a/specs/mvp/v3.5/v3.5_dev_plan.md b/specs/mvp/v3.5/v3.5_dev_plan.md deleted file mode 100644 index b05682c..0000000 --- a/specs/mvp/v3.5/v3.5_dev_plan.md +++ /dev/null @@ -1,200 +0,0 @@ -# MVP v3.5(精简版)开发计划(TDD) - -> 目标:在 v3.0 已有能力基础上,仅新增两项能力: -> 1) **Advanced TaskSpec(自定义 command)** -> 2) **Custom Reward(方式 A:用户自己在 command 里写 `custom_reward_function.*`)** -> -> 设计依据:`specs/mvp/v3.5/v3.5_design.md`(本计划不再扩展 scope)。 - ---- - -## 0. 范围与约束 - -### 0.1 In scope -- 新增 `kind: advanced` 的 TaskSpec:用户提供 `command`,平台做 `$HOME` 宏替换与 best-effort 校验,再提交 Ray Job。 -- Custom Reward:平台仅做 **reward path 校验**(方式 A),不新增结构化字段。 -- `$HOME/common/*` 路径语义支持(关键):用户在 SFTPGo/WebClient 看到的路径能被训练进程正确读取。 - -### 0.2 Out of scope(本轮不做) -- 自定义 verl 版本/代码路径(多版本共存) -- 断点续训(resume from checkpoint) -- IB/RoCEv2/NCCL 专项支持 -- Model Serving -- Node management 改造(v3.0 的 stateless head/worker/watchdog/supervisor 机制保持不变) - -### 0.3 关键路径映射(必须保持一致) -> 说明:SFTPGo 的 `$HOME/common/...` 是 **virtual folder**,训练进程看不到该虚拟路径。 - -提交 Advanced command 前必须展开/映射: -- `$HOME/common/datasets` → `/private/datasets`(只读语义) -- `$HOME/common/hf` → `/private/hf`(只读语义) -- 其余 `$HOME` → `/private/users/` - -并且为兼容历史用法(v3.0): -- Basic TaskSpec 仍接受 `/private/common/datasets/...`、`/private/common/hf/...`(不强制迁移)。 - ---- - -## 1. 测试策略(TDD) - -### 1.1 单元测试优先级 -1) **解析与兼容**:`kind: advanced` 能解析;无 `kind` 仍按 Basic 解析,旧用法不破坏。 -2) **宏替换正确性**:`$HOME` / `$HOME/common/*` 映射严格按约定展开。 -3) **best-effort 校验**:拒绝明显危险/跨用户路径;对 reward path 做 allowlist。 -4) **提交链路**:Scheduler 能识别 Advanced spec 并调用对应的提交方法,确保 submission_id/目录规范不变。 -5) **WebUI/API**:New Task 模板与 `/spec` 展示完整 resolved spec(包含展开后的 command)。 - -### 1.2 本地运行方式 -- 复用已有 `.venv`,执行:`.venv/bin/python -m pytest` -- 若环境没有 pip,使用 uv 的方式参考 v3.0 约定(不在本计划重复)。 - ---- - -## 2. 里程碑划分(每个里程碑可独立验证) - -> 约定:每个里程碑先写测试(失败),再实现代码使测试通过;里程碑结束跑一遍 `pytest`。 - -### M1 — TaskSpec 模型与解析(兼容优先) -**目标** -- 引入 AdvancedTaskSpec 数据结构与 union parser,同时保证 v3.0 Basic 行为不变。 - -**新增/修改(建议位置)** -- `src/mvp/py/argus/ray/models.py` - - 新增 `AdvancedTaskSpec` - - 新增 `parse_taskspec(obj: dict) -> JobSpec | AdvancedTaskSpec` - - 兼容策略:缺省 `kind` → 走 `JobSpec.from_dict` - -**测试(先写)** -- `src/mvp/py/tests/test_models.py` - - `test_parse_taskspec_basic_no_kind_compat()` - - `test_parse_taskspec_advanced_smoke()` - - `test_parse_taskspec_advanced_requires_command_nnodes_gpus()` - -**验收** -- `pytest -q` 通过;旧测试不修改或仅做最小必要更新。 - ---- - -### M2 — Advanced command 展开与校验(核心能力) -**目标** -- 实现 command 展开(含 `$HOME/common/*` 映射)与 best-effort 强约束校验。 - -**实现点(建议新增模块)** -- `src/mvp/py/argus/service/command_expand.py`(或放在 `argus/service/validation.py`) - - `expand_advanced_command(user_id: str, command: str) -> str` - - `validate_advanced_command(user_id: str, expanded_command: str) -> None`(失败抛 `ValueError`) - -**强约束(与设计文档一致)** -- 必须包含 `python3` 且包含 `-m verl.trainer.`(否则 400) -- 禁止出现 `/private/users//...`(跨用户路径) -- 若检测到 `data.train_files=`/`data.val_files=`: - - 只允许 `/private/users//datasets/...` 或 `/private/datasets/...` - - (兼容)允许 `/private/common/datasets/...`(旧路径) -- 若检测到 `custom_reward_function.path=`: - - 只允许 `/private/users//code/...`(展开后校验) - -**测试(先写)** -- 新增:`src/mvp/py/tests/test_advanced_command.py` - - `test_expand_maps_home_common_datasets_to_private_datasets()` - - `test_expand_maps_home_common_hf_to_private_hf()` - - `test_expand_maps_home_to_private_users()` - - `test_validate_rejects_cross_user_paths()` - - `test_validate_requires_verl_trainer_entry()` - - `test_validate_allows_reward_path_under_user_code()` - - `test_validate_rejects_reward_path_outside_user_code()` - -**验收** -- 单测覆盖映射/校验的正反例;错误信息可读(用于 API 400 detail)。 - ---- - -### M3 — Ray 提交链路支持 Advanced(Builder/Tool/Scheduler) -**目标** -- Advanced spec 能进入 scheduler 队列并提交为 Ray job(driver 仍落 worker)。 - -**代码改动点(建议)** -- `src/mvp/py/argus/ray/builders.py` - - 新增 `build_advanced_argv(command: str)`:返回 `["bash","-lc", expanded_command]` -- `src/mvp/py/argus/ray/ray_job_tool.py` - - 新增 `submit_advanced(...)`(或统一成内部 submit plan) - - runtime_env:继续注入公共 verl code path(本轮不支持用户自定义 verl 代码) - - 可选:把 `/private/users//code` 加入 `PYTHONPATH`,提升 reward 代码 `import` 体验 -- `src/mvp/py/argus/service/scheduler.py` - - 使用 `parse_taskspec` 分流 Basic/Advanced - - Advanced 调用 `tool.submit_advanced(...)` - -**测试(先写)** -- `src/mvp/py/tests/test_builders.py` - - `test_build_advanced_argv_uses_bash_lc()` -- `src/mvp/py/tests/test_scheduler.py` - - 新增一个 `kind: advanced` 的任务,断言 scheduler 调用了 `submit_advanced` - - 断言 job_dir/submission_id 规则不变(仍按 `/private/users//jobs/`) -- `src/mvp/py/tests/test_ray_job_tool.py` - - 断言 advanced 提交时 entrypoint 是 driver_entrypoint + `bash -lc ...` - -**验收** -- 单测跑通;Scheduler tick 能完成 Advanced 任务从 QUEUED → SUBMITTED(mock Ray)。 - ---- - -### M4 — API & WebUI(最小功能闭环) -**目标** -- WebUI/HTTP API 能提交 Advanced Task,并在详情页看到 resolved spec(含完整 command)。 - -**API 改动点** -- `src/mvp/py/argus/service/app.py` - - `POST /api/v2/tasks`:支持 `kind: advanced` - - 保存 raw YAML(保持与 Basic 一致) - - 对 Advanced:展开 command + 校验(失败返回 400) - - `GET /api/v2/tasks/{task_id}/spec`: - - 返回 resolved spec(建议同时返回 raw + expanded,或 YAML 中直接给 expanded) - -**WebUI 改动点** -- `src/mvp/py/argus/service/ui.py` - - New Task 页面新增 Advanced 模板(含中文注释) - - 文案强调共享目录:`$HOME/common/datasets`、`$HOME/common/hf` - -**测试(先写)** -- `src/mvp/py/tests/test_app.py` - - `test_create_task_advanced_ok()`(最小 valid command) - - `test_create_task_advanced_rejects_invalid_command()` - - `test_task_spec_endpoint_includes_expanded_command()` -- `src/mvp/py/tests/test_ui.py` - - 断言页面包含 Advanced 示例块 - -**验收** -- `pytest` 通过;浏览器可提交 Advanced YAML 并看到 expanded command。 - ---- - -### M5 — 端到端验证(远端 argus@h1) -**目标** -- 在真实 Ray cluster + VERL 环境下验证 Advanced 与 Custom Reward(方式 A)。 - -**步骤(手工验收脚本化可选)** -1) 启动 v3.0/v3.5 统一的 compose + API(沿用现有 `run_all` 脚本体系) -2) 用户(如 `alice`)通过 SFTP 上传 reward 代码到: - - `$HOME/code/reward.py`(真实路径 `/private/users/alice/code/reward.py`) -3) 通过 WebUI 或 curl 提交 Advanced task: - - `command` 中包含: - - `custom_reward_function.path=$HOME/code/reward.py` - - `custom_reward_function.name=compute_score` - - `data.train_files=$HOME/common/datasets/gsm8k/train.parquet` - - `data.val_files=$HOME/common/datasets/gsm8k/test.parquet` -4) 检查: - - 任务状态从 QUEUED → RUNNING → SUCCEEDED/FAILED(有日志) - - driver 不在 head 上跑(dashboard 验证) - - 日志出现 “custom reward” 生效的提示(按 VERL 实际日志关键字确认) -5) 回归:提交 Basic ppo/grpo/sft 任务仍可运行(确保兼容性) - -**验收** -- Advanced task 能跑至少若干 step,且 reward 注入生效。 -- Basic 任务兼容不回退。 - ---- - -## 3. 风险点与边界(明确写进 PR/变更说明) -- Advanced command 只做 best-effort 校验,不做完整 shell AST 解析;复杂命令可能存在漏检/误判(后续可扩展)。 -- `$HOME/common/*` 是“用户侧语义”,服务层必须映射到真实路径,否则训练必然 FileNotFound。 -- 校验策略(强约束)如果后续要允许非 VERL 命令,需要调整规则并补测试(本轮默认拒绝)。 - diff --git a/specs/mvp/v3.6/README.md b/specs/mvp/v3.6/README.md deleted file mode 100644 index fc220f4..0000000 --- a/specs/mvp/v3.6/README.md +++ /dev/null @@ -1,9 +0,0 @@ -# MVP v3.6 - -本目录包含 v3.6 的需求与设计: - -- `Snipaste_2026-01-05_10-56-34.png`:v3.6 架构草图(在 v3.5 基础上增加 Weights & Biases;其余模块保持不变) -- `requirements.md`:需求要点(W&B + Evaluation 模板) -- `wandb.md`:W&B local server 的前期调研与资料(license、部署方式、VERL 配置要点等) -- `v3.6_design.md`:v3.6 详细设计方案(基于 v3.5) -- `v3.6_progress.md`:v3.6 里程碑进度记录 diff --git a/specs/mvp/v3.6/Snipaste_2026-01-05_10-56-34.png b/specs/mvp/v3.6/Snipaste_2026-01-05_10-56-34.png deleted file mode 100644 index 8e889e2396f451cf621d45dc0d17e716aaca3943..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 72243 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 设计基线:当前线上已具备 v3.5 能力(PPO/GRPO/SFT + Advanced TaskSpec + SFTPGo 数据管理 + WebUI)。 -> v3.6 的架构草图见:`specs/mvp/v3.6/Snipaste_2026-01-05_10-56-34.png` - -## 0. 目标与范围 - -### 0.1 v3.6 目标 - -1) **Weights & Biases(W&B)集成** -- 训练/任务运行时自动打点到 W&B local server。 -- 采用“共享 W&B 账号(license 只支持 1 user) + 为每个 MVP 用户创建独立 project”的方式隔离可视化与检索体验。 -- 平台提供 W&B 的跳转链接、以及每个 task 对应 run 的可定位信息(最小闭环)。 - -2) **New Task 增加 Evaluation 模板** -- 在 New Task 页面提供一个最小可用的 “Evaluation” 任务模板(用于离线评估/打分),并能把结果落到 job 输出与(可选)W&B。 - -### 0.2 非目标(v3.6 不做) - -- 不引入新的 node management 机制;保持 v3.5 的 head discovery + worker watchdog stateless pool。 -- 不做 Serving/IB/RDMA/断点续训/多版本 verl code_path 等(仍按 v3.5 的范围)。 -- 不做多租户安全隔离(W&B API Key 注入属于内部可信环境)。 - ---- - -## 1. W&B local server(部署与连通) - -> 资料参考:`specs/mvp/v3.6/wandb.md`。**文档中 license/token 属敏感信息,v3.6 设计不在代码/文档里写死。** - -### 1.1 部署方式(dev/h1) - -建议在 `src/mvp/docker-compose.yaml` 新增 `wandb` 服务(与现有 ray_head / sftpgo 同一 compose network): - -- 镜像:`wandb/local:latest` -- 容器端口:`8080` -- 宿主机端口:建议 `8090:8080`(避免和 MVP API `8080`、SFTPGo `8081` 冲突) -- 持久化:挂载到 NFS/共享目录(例如 `/private/common/wandb`)以持久化 runs/artifacts -- 首次启动后由管理员在 W&B System Admin 页面粘贴 license(见 `wandb.md`) - -### 1.1.1 持久化策略(必须) - -v3.6 约定 **W&B server 的元数据必须持久化**(否则会丢 license/账号/API key、历史 runs/project 索引等): - -- W&B server 数据目录(`/vol`)挂载到共享目录(NFS):例如 `/private/common/wandb:/vol` -- 这部分数据由平台/管理员长期保留(不跟随单个 job 清理) - -与之相对,**每个 Ray job 对应的本地 W&B run 文件**放在 job 目录下(见 §2.3 的 `WANDB_DIR`),并由现有 janitor 随 job 一起清理: - -- `WANDB_DIR=/private/users//jobs//wandb` -- janitor 对 job 的策略是“结束后 3 天移入回收站、7 天后删除”,因此该目录会被一并处理 - -> 说明:W&B 的最终“事实数据”在 server 侧持久化(runs/metrics/可视化);job 目录下的 `WANDB_DIR` 更像运行期缓存/临时文件与调试材料。 - -### 1.2 容器内访问 W&B 的 base_url - -在 v3.5 经验中,Ray head 容器对 docker 内部 DNS 名称解析不稳定(`Temporary failure in name resolution`)。 -为避免再次踩坑,v3.6 统一采用 **“docker bridge 网关 + host 映射端口”** 的方式让容器访问 W&B: - -- `WANDB_BASE_URL=http://172.22.0.1:8090`(其中 `172.22.0.1` 为 `mvp_argus-ray-net` 网关) - -> 注意:如果未来 dev 环境 network 网段变化,需要把网关地址做成配置项(见 §2)。 - ---- - -## 2. 平台侧 W&B 集成(API/Scheduler/Ray Job runtime_env) - -### 2.1 配置设计(YAML) - -在 `configs/dev.yaml`(以及生产配置)中新增一段 W&B 配置,建议结构: - -```yaml -tracking: - wandb: - enabled: true - base_url: "http://172.22.0.1:8090" - api_key_env: "WANDB_API_KEY" - entity: "" # 可选;verL 通过 env WANDB_ENTITY 读取 - project_suffix: "_project" # 例如 alice_project - # 可选:代理(verL 支持 trainer.wandb_proxy) - proxy: null -``` - -平台读取 `api_key_env` 对应的环境变量,并在 job 维度注入 `WANDB_API_KEY`。 -**不在配置文件中存明文 API KEY**(避免泄露)。 - -### 2.2 项目/命名规范(共享账号 + user project) - -由于 W&B local license 限制 “最多 1 user”,v3.6 采用: - -- **同一个 W&B 账号**(同一个 `WANDB_API_KEY`) -- 每个 MVP user 使用不同 project: - - `project_name = + project_suffix` - - 示例:`alice_project` -- 每个 Ray job attempt 对应一个 run: - - `experiment_name = `(保证 attempt 唯一;也便于从 dashboard 反查) - -verL 内部 `wandb.init(project=project_name, name=experiment_name, entity=$WANDB_ENTITY)`(见 `verl/utils/tracking.py`)。 - -### 2.3 Ray Job 注入(runtime_env env_vars) - -当 `tracking.wandb.enabled=true` 时,在 scheduler 提交 ray job 时,统一注入: - -- `WANDB_BASE_URL`(来自配置) -- `WANDB_API_KEY`(来自 env `tracking.wandb.api_key_env`) -- `WANDB_ENTITY`(可选) -- `WANDB_MODE=online`(默认在线;可在 dev/离线时切换) -- `WANDB_DIR=/private/users//jobs//wandb`(保证每个 job 的本地 run 文件落到对应 job 目录;便于随 job 一起被 janitor 清理) - -> 对 Advanced TaskSpec:平台无法替用户改 command,但仍可注入上述 env,让用户在 command 中自行启用 wandb。 - -### 2.4 verL 训练任务自动开启 wandb logger - -对平台内置 workload(PPO/GRPO/SFT),平台将 hydra overrides 改为: - -- `trainer.logger=[console,wandb]`(替代 v3.5 的 `trainer.logger=console`) -- `trainer.project_name=_project` -- `trainer.experiment_name=` -- 可选:如果配置了 `tracking.wandb.proxy`,注入 `trainer.wandb_proxy=...` - -兼容性说明: -- `trainer.logger` 在 verL 的 ppo/sft config 中本身是 list(示例为 `["console","wandb"]`),因此不会破坏 verL 配置解析。 -- 现有 v3.5 的 checkpoint/log dir 仍按 job_dir 注入,不依赖 `trainer.default_local_dir`。 - -### 2.5 数据库存储与 API 输出(最小闭环) - -v3.6 需要让用户能在 WebUI/Task 详情中 “点一下跳转到 W&B”: - -建议在 DB(sqlite)里新增 attempt 级字段(或 metadata JSON): - -- `wandb_project`:如 `alice_project` -- `wandb_run_name`:如 `` -- `wandb_base_url`:如 `http://:8090` -- `wandb_url`:拼出来的最终链接(若 W&B local 的 URL 结构不稳定,可只存前 3 项,由前端拼接) - -API 侧在: -- `GET /api/v2/tasks/` 的 `latest_attempt` 增加 `wandb` 字段(或顶层增加 `tracking` 字段) -- `GET /api/v2/me` 增加 `wandb` 信息(base_url、project_name),便于页面展示 “Open W&B” - -> W&B local 的 URL 路径结构需要在接入时确认;若不确定,先只提供 base_url + project/run 名称,用户可在 W&B UI 搜索。 - ---- - -## 3. WebUI 变更(v3.6) - -### 3.1 Data / Login 页 - -- 在 Data 或 Login 页新增: - - “Open W&B” 链接(跳转到 `tracking.wandb.base_url` 的 Web UI) - - 展示当前用户的 project 名称(例如 `alice_project`),并提供 Copy 按钮 - -### 3.2 Tasks / Task Detail - -- Task list 无需大改;Task detail 页面增加: - - W&B run 信息(project / run name / link) - - 若任务失败,W&B 仍可用于查看已上报的中间日志(对训练类任务有价值) - -### 3.3 New Task 增加 Evaluation 模板 - -New Task 页面新增一个 “Evaluation example”: - -#### 方案 A(推荐,最小改动):作为 Advanced TaskSpec 模板 - -- 直接提供 `kind: advanced` 的模板,command 运行 verL 自带评估入口: - - `python3 -m verl.trainer.main_eval data.path=... custom_reward_function.path=... +ray_kwargs.ray_init.address=auto` -- 优点:不需要扩展 TaskSpec schema / scheduler 逻辑 -- 缺点:Evaluation 在平台侧不可结构化(仍属于 advanced) - -#### 方案 B(更产品化):新增内置 workload: evaluation(后续可选) - -若希望在任务分类/队列中把 evaluation 作为一类“内置任务”,可新增: - -```yaml -workload: evaluation -code_path: /private/common/code/verl/verl_repo -nnodes: 1 -n_gpus_per_node: 0 -data_path: $HOME/common/datasets/<...>.parquet -response_key: responses -data_source_key: data_source -reward_model_key: reward_model -custom_reward_path: $HOME/code/reward.py # 可选 -custom_reward_name: compute_score # 可选 -``` - -平台把它编译成 `verl.trainer.main_eval` 的 hydra overrides + ray init address;并可选择把结果解析后上报 W&B。 - -v3.6 建议先落地 **方案 A**(模板即可),方案 B 作为 v3.7+ 的演进。 - ---- - -## 4. 验收标准(v3.6) - -### 4.1 W&B(训练任务) - -- 提交 PPO/GRPO/SFT 任一任务: - - W&B local server 能看到对应 project(如 `alice_project`) - - 能看到 run 名称为该任务 attempt 的 `ray_submission_id` - - run 内能持续刷新 metrics(至少包含 loss/step 等 verL 默认上报) -- WebUI: - - 能打开 W&B UI 链接 - - Task detail 能展示 project/run(或至少可检索信息) - -### 4.2 Evaluation 模板 - -- New Task 中出现 “Evaluation example” -- 复制模板提交后: - - 任务能在 Ray 上运行(CPU 即可,`+ray_kwargs.ray_init.address=auto` 连接集群) - - 输出 metrics(`main_eval.py` 默认 print dict) - - (可选)若用户在 command 里启用 wandb,则能在对应 project 下看到评估 run - ---- - -## 5. 兼容性影响评估 - -- 对现有 v3.5 功能: - - 默认行为改变:PPO/GRPO/SFT 会默认多一个 logger(wandb),并对外发起 HTTP 请求到 W&B server。 - - 若 W&B server 不可用/配置缺失: - - 建议行为:平台自动降级为 `trainer.logger=[console]` 并在 task 状态中给出 warning(避免训练直接失败)。 - - 初版也可选择 fail-fast:缺少 `WANDB_API_KEY` 时拒绝开启 wandb(由配置开关控制)。 -- 对资源/存储: - - W&B server 自身会写入一定量数据(license 限制 10GB);需配合 retention 策略做清理(v3.6 先手动,后续可自动)。 - - job 目录下的 `WANDB_DIR` 会随 jobs retention 被清理;不会无限增长。 - ---- - -## 6. 已确认的落地约定 - -- W&B server 对外端口:`8090` -- Project 命名:`_project`(不使用 `WANDB_ENTITY`) -- Evaluation:先只提供 **Advanced 模板**(New Task 页面提供示例即可) - ---- - -## 7. 运维与验收流程(dev/h1) - -### 7.1 启动服务(docker compose) - -1) 启动/重启 compose(Ray head/worker + SFTPGo + W&B): - -```bash -cd /home2/argus/infra/mvp/src/mvp -docker compose up -d -``` - -2) 访问 UI: -- MVP WebUI:`http://:8080/ui` -- Ray Dashboard:`http://:8265` -- SFTPGo Web:`http://:8081/web/` -- W&B Web:`http://:8090` - -> W&B 容器数据目录已挂载到共享盘:`/private/common/wandb`(容器内 `/vol`)。 - -### 7.2 初始化 W&B(管理员一次性操作) - -1) 打开 `http://:8090/system-admin` 粘贴 license(详见 `specs/mvp/v3.6/wandb.md`)。 -2) 进入 W&B UI 创建/登录到共享账号(license 只支持 1 user)。 -3) 在 W&B UI 的用户设置页面生成 API Key(通常位于 “User Settings / API Keys”)。 - -### 7.3 启动 API server(需要注入 WANDB_API_KEY) - -平台不会把 `WANDB_API_KEY` 写入配置文件;必须在启动 API server 时通过环境变量提供。 - -示例(在宿主机): - -```bash -export MVP_INTERNAL_TOKEN="my-dev-token" -export WANDB_API_KEY="...从 W&B UI 复制..." -cd /home2/argus/infra/mvp/src/mvp/scripts -./60_start_api.sh -``` - -> 说明:`./60_start_api.sh` 会把 `WANDB_API_KEY` 透传给 head 容器内运行的 API server。 - -### 7.4 验收(最小闭环) - -1) 在 WebUI Login 页面能看到 W&B 区块(Open W&B + project copy)。 -2) 提交一个 PPO/GRPO/SFT 任务(任意一个即可): - - W&B project 为 `_project`(如 `alice_project`) - - run name 为该 attempt 的 `ray_submission_id` -3) 提交 Evaluation 模板(Advanced)能在 Ray 上运行并输出评估结果(stdout / logs)。 diff --git a/specs/mvp/v3.6/v3.6_dev_plan.md b/specs/mvp/v3.6/v3.6_dev_plan.md deleted file mode 100644 index d0fa1e3..0000000 --- a/specs/mvp/v3.6/v3.6_dev_plan.md +++ /dev/null @@ -1,194 +0,0 @@ -# MVP v3.6(基于 v3.5)开发计划(TDD) - -> 设计依据:`specs/mvp/v3.6/v3.6_design.md` -> 本计划默认已确认: -> 1) W&B host 端口:`8090`;2) project:`_project`;3) evaluation 先做 Advanced 模板;4) 不使用 `WANDB_ENTITY`。 - -## 总体原则 - -- **TDD**:每个里程碑先补齐单测(或契约测试)再实现功能;保证覆盖率门槛不回退。 -- **最小闭环**:先做到“可用+可验证”,再做体验优化;不做超出 v3.6 scope 的扩展。 -- **配置不落盘敏感信息**:`WANDB_API_KEY` 只能来自运行环境变量,不写入仓库配置文件。 - ---- - -## Milestones - -### M1:配置层(tracking.wandb)与解析 - -**目标** -- 在服务配置中新增 `tracking.wandb`,支持开关、base_url、api_key_env。 -- 不引入 `WANDB_ENTITY`(保持为空即可)。 - -**开发任务** -- 在 `src/mvp/py/argus/service/config.py`: - - 新增 `TrackingConfig/WandbConfig` dataclass(或等价结构)。 - - `V2Config.from_root_dict()` 解析 `tracking.wandb.*`(缺省为 disabled)。 - - 校验:`enabled=true` 时 `base_url` 不能为空;`api_key_env` 默认 `WANDB_API_KEY`。 - -**测试(先写)** -- `test_config_parses_wandb_defaults`:没有 tracking 字段时,默认 disabled。 -- `test_config_parses_wandb_enabled`:enabled=true 能读到 base_url/api_key_env。 -- `test_config_rejects_empty_base_url_when_enabled`:enabled=true 且 base_url 空时报错(或记录 warning,取决于实现选择)。 - -**验收** -- 仅通过 config 即能决定是否启用 W&B,且不会破坏 v3.5 现有配置解析。 - ---- - -### M2:Ray Job runtime_env 注入(WANDB_* env) - -**目标** -- 当 `tracking.wandb.enabled=true` 时:平台在 job 粒度注入 `WANDB_BASE_URL/WANDB_API_KEY/WANDB_MODE/WANDB_DIR` 等 env。 -- `WANDB_API_KEY` 从 API server 进程环境变量中读取:`os.environ[api_key_env]`。 - -**开发任务** -- 在 scheduler / ray job builder(`src/mvp/py/argus/service/scheduler.py` 或 `src/mvp/py/argus/ray/builders.py`): - - 构造 job runtime_env.env_vars 的 merge 逻辑: - - 现有 `ray.runtime_env.env_vars` 为基础; - - 追加 W&B env(不覆盖用户显式指定的同名变量,或按“平台优先”策略二选一并写清楚)。 - - 注入: - - `WANDB_BASE_URL=` - - `WANDB_API_KEY=` - - `WANDB_MODE=online` - - `WANDB_DIR=/private/users//jobs//wandb`(本地 run 文件随 job 一起由 janitor 清理) - -**测试(先写)** -- `test_scheduler_injects_wandb_env_when_enabled`: - - mock env 中存在 `WANDB_API_KEY`; - - 提交一个内置任务(ppo/sft 任意),断言构造出来的 runtime_env 含以上 env_vars。 -- `test_scheduler_sets_wandb_dir_under_job_dir`: - - 断言 `WANDB_DIR` 位于该 attempt 的 job 目录下(而不是 common 目录),避免无法跟随 job retention 清理。 -- `test_scheduler_does_not_inject_wandb_env_when_disabled`。 -- `test_scheduler_wandb_missing_api_key_behaviour`: - - enabled=true 但缺少 env 时的行为: - - 方案 A(推荐):**自动降级**为 console(不注入 wandb),并在 task/attempt message 记录 warning; - - 或方案 B:fail-fast(返回 500/400)。 - - 需在实现前确认采用哪种策略;建议 v3.6 选 A 提升可用性。 - -**验收** -- 任意内置任务提交后,在 Ray job runtime_env 中能看到 `WANDB_*`。 - ---- - -### M3:内置训练任务自动开启 wandb logger(PPO/GRPO/SFT) - -**目标** -- 当 W&B enabled 时,平台默认把内置训练任务改成 `trainer.logger=["console","wandb"]`,并设置 project/run 命名。 - -**开发任务** -- 在 job 构建(PPO/GRPO/SFT 的 overrides 生成处): - - 将 `trainer.logger` 从 `console` 改为 list:`[console,wandb]`(hydra 语法按现有实现方式拼接)。 - - `trainer.project_name=_project` - - `trainer.experiment_name=` - - 保持 v3.5 的 job_dir/checkpoint/log dir 注入方式不变。 - -**测试(先写)** -- `test_job_overrides_include_wandb_logger_when_enabled`: - - 断言 entrypoint/overrides 包含 `trainer.logger=[console,wandb]`(或等价写法)。 - - 断言包含 `trainer.project_name=_project`、`trainer.experiment_name=`。 -- `test_job_overrides_keep_console_only_when_wandb_disabled_or_missing_key`。 - -**验收** -- 训练任务 run 会自动出现在 W&B 对应 project 下(E2E 验证在 M6)。 - ---- - -### M4:API 输出与 WebUI 链接(最小闭环) - -**目标** -- 用户可以在 UI 里“知道去哪看 W&B”,以及知道本 task 对应哪个 project/run。 - -**开发任务** -- API: - - `GET /api/v2/me` 增加 `wandb` 信息(仅当 enabled 时返回): - - `base_url` - - `project_name`(`_project`) - - `GET /api/v2/tasks/{task_id}`(或 attempt 结构)增加 `wandb_project` / `wandb_run_name`(run_name=ray_submission_id)。 -- WebUI: - - Login/Data 页增加 “Open W&B” 链接(跳 `base_url`),展示 project_name + Copy。 - - Task detail 增加 wandb 字段展示(project/run/可点击链接或可复制文本)。 - -**测试(先写)** -- `test_me_includes_wandb_when_enabled`(mock config + env)。 -- `test_task_detail_contains_wandb_fields_when_enabled`(mock task/attempt)。 -- `test_ui_contains_wandb_link`(渲染 HTML 断言包含 base_url/project_name 字样)。 - -**验收** -- WebUI 能一键跳转 W&B;Task detail 能定位到 run。 - ---- - -### M5:New Task 增加 Evaluation 模板(Advanced) - -**目标** -- New Task 页面增加一个 Evaluation 模板按钮/示例(先按 Advanced TaskSpec 提供)。 - -**开发任务** -- 在 `src/mvp/py/argus/service/ui.py`: - - YAML 模式增加 “Evaluation example”。 - - 表单模式本轮可选(不要求): - - 如果要支持:把 evaluation 作为 advanced 模板的一种预填 command(仍 `kind: advanced`)。 -- 模板建议使用 verL 自带入口: - - `python3 -m verl.trainer.main_eval ... +ray_kwargs.ray_init.address=auto` - - `data.path=$HOME/common/datasets/...`(按 v3.5 的宏规则) - -**测试(先写)** -- `test_ui_new_task_contains_evaluation_example`:断言页面包含 `main_eval` 与关键字段。 - -**验收** -- 用户复制 evaluation 模板可提交成功并在 Ray 上运行(E2E 在 M6)。 - ---- - -### M6:端到端(dev/h1)部署与验收流程 - -> 里程碑 M6 以脚本/手工步骤为主;不强制写 e2e 自动化测试。 - -**部署任务** -- compose 增加 `wandb` 服务: - - `wandb/local:latest` - - host 端口 `8090:8080` - - 数据挂载到 `/private/common/wandb:/vol` 持久化(W&B 元数据/账号/API key/历史 runs) -- API 启动方式: - - 在宿主机 export:`WANDB_API_KEY=<从 W&B UI 生成的 key>` - - 启动 API(确保 env 透传到容器内) -- 首次初始化: - - 打开 `http://:8090/system-admin` 粘贴 license(管理员操作) - -**验收用例** -1) **训练类任务自动打点** - - 用 alice 提交一个 SFT(或 PPO)任务(内置 workload) - - 在 W&B UI 中看到 project:`alice_project` - - run name 为 `ray_submission_id`,metrics 可见 -2) **Advanced task 可手动打点** - - 提交一个 Advanced(用户自己写 command)并在 command 中启用 `trainer.logger=["console","wandb"]`(如需) - - 确认 env 注入生效(W&B 记录出现) -3) **Evaluation 模板** - - 用 New Task 的 Evaluation example 提交 - - 任务成功运行并输出 metrics(stdout/logs) - - (可选)如果 evaluation 也启用 wandb,则能出现在对应 project 下 - -**回归** -- v3.5 的三类任务(ppo/grpo/sft)在 W&B disabled 或缺少 key 时仍可跑通(至少 console 输出不受影响)。 - -**Retention 联动检查** -- 提交一个短任务生成 `WANDB_DIR`,结束后确认: - - `WANDB_DIR` 位于 `/private/users//jobs//wandb` - - janitor 运行后该目录会随 job 一起进入 trash / 被 purge(与 jobs retention 一致) - ---- - -## 交付物清单(v3.6) - -- 文档: - - `specs/mvp/v3.6/v3.6_design.md`(已存在,必要时补充操作流程) - - `specs/mvp/v3.6/v3.6_dev_plan.md`(本文) -- 代码(预期变更点): - - `src/mvp/py/argus/service/config.py` - - `src/mvp/py/argus/service/scheduler.py` / `src/mvp/py/argus/ray/builders.py` / `src/mvp/py/argus/ray/ray_job_tool.py` - - `src/mvp/py/argus/service/app.py`(/me 与 task detail 输出) - - `src/mvp/py/argus/service/ui.py`(Open W&B + Evaluation template) - - `src/mvp/docker-compose.yaml`(wandb service) - - `src/mvp/configs/dev.yaml`(tracking.wandb 配置) - - `src/mvp/scripts/*`(API 启动时 env 透传,必要时补充) diff --git a/specs/mvp/v3.6/v3.6_progress.md b/specs/mvp/v3.6/v3.6_progress.md deleted file mode 100644 index 7f681c8..0000000 --- a/specs/mvp/v3.6/v3.6_progress.md +++ /dev/null @@ -1,42 +0,0 @@ -# MVP v3.6 进度记录 - -> 基线:v3.5 已完成(Advanced TaskSpec + Custom reward(方式A)+ WebUI + SFTPGo + stateless ray node pool)。 -> 本文件用于记录 v3.6 每个 milestone 的完成情况与关键改动点。 - -## M1(完成) - -- 新增 `tracking.wandb` 配置解析与校验(enabled/base_url/api_key_env)。 - -## M2(完成) - -- Ray job 维度注入 `WANDB_*` env(含 `WANDB_BASE_URL/WANDB_API_KEY/WANDB_MODE/WANDB_DIR`),缺少 key 时降级并记录 warning。 - -## M3(完成) - -- PPO/GRPO/SFT 内置训练任务在 wandb 可用时自动追加 overrides: - - `trainer.logger=[console,wandb]` - - `trainer.project_name=_project` - - `trainer.experiment_name=` - -## M4(完成) - -- API 输出增加 W&B 定位信息: - - `/api/v2/me` 返回 `wandb.{enabled,base_url,project_name}` - - `/api/v2/tasks/{task_id}` 在 `latest_attempt.wandb` 返回 `{base_url,project_name,run_name}` -- WebUI: - - Login 页面增加 W&B 区块(跳转 8090、copy project) - - Task detail 页面增加 W&B 区块(copy run) - -## M5(完成) - -- WebUI New Task 增加 Evaluation 模板(Advanced): - - 使用 `python3 -m verl.trainer.main_eval ... +ray_kwargs.ray_init.address=auto` - - 以占位符路径示例(用户替换 `/`) - -## M6(完成) - -- `docker-compose.yaml` 集成 W&B local server: - - host 端口 `8090` - - 持久化目录 `/private/common/wandb`(容器内 `/vol`) -- dev 配置新增 `tracking.wandb` 默认开启(缺 key 自动降级并记录 warning)。 -- API 启动脚本支持把 `WANDB_API_KEY` 从宿主机透传到 head 容器中的 API server。 diff --git a/specs/mvp/v3.6/v3.6_summary.md b/specs/mvp/v3.6/v3.6_summary.md deleted file mode 100644 index 818bb4d..0000000 --- a/specs/mvp/v3.6/v3.6_summary.md +++ /dev/null @@ -1,126 +0,0 @@ -# MVP v3.6 迭代研发总结(基于 v3.5) - -> 时间基线:2026-01(H20 dev 环境:`argus@h1:/home2/argus/infra/mvp`) -> v3.6 架构草图:`specs/mvp/v3.6/Snipaste_2026-01-05_10-56-34.png` - -## 1. 迭代目标回顾 - -v3.6 在 v3.5(WebUI + API server + Ray stateless node pool + SFTPGo + Advanced TaskSpec)基础上,新增两块能力: - -1) **Weights & Biases(W&B)local server 集成** -- 训练任务(PPO/GRPO/SFT)默认可写入 W&B。 -- 采用“共享 W&B 账号 + 按用户拆分 project(`_project`)”的隔离策略。 - -2) **New Task 增加 Evaluation 示例** -- New Task 页面新增一个最小可用的 evaluation 模板(以 Advanced command 方式运行 `verl.trainer.main_eval`)。 - -## 2. 交付内容(代码/配置/脚本) - -### 2.1 部署形态(docker compose) - -v3.6 在 `src/mvp/docker-compose.yaml` 新增 W&B 服务: - -- 服务名:`wandb`(容器名:`argus-wandb`) -- 宿主机端口:`8090:8080` -- 持久化:`../../shared/common/wandb:/vol` -- 同 network:`argus-ray-net`(便于 Ray 容器内访问) - -### 2.2 平台配置(YAML) - -在 `src/mvp/configs/dev.yaml` 增加/启用 W&B 配置: - -```yaml -tracking: - wandb: - enabled: true - base_url: "http://172.22.0.1:8090" - api_key_env: "WANDB_API_KEY" - project_suffix: "_project" -``` - -说明: -- `base_url` 采用 docker bridge 网关 + 宿主机映射端口的方式,规避容器内 DNS 偶发解析失败问题。 -- 不在 config 中写明文 key,统一通过启动 API server 时注入 `WANDB_API_KEY`。 - -### 2.3 Ray Job runtime_env 注入(核心) - -v3.6 在**每个 Ray job attempt**提交时注入两类环境变量: - -1) **始终注入(无论是否启用 W&B)**:便于 Advanced command 在不改模板的情况下能运行 -- `MVP_TRAINER_LOGGER`:`console` 或 `[console,wandb]` -- `MVP_WANDB_PROJECT`:`_project`(例如 `alice_project`) -- `MVP_WANDB_RUN`:``(每次 attempt 唯一) - -2) **当 W&B 有效启用时注入** -- `WANDB_BASE_URL` -- `WANDB_API_KEY` -- `WANDB_MODE=online` -- `WANDB_DIR=/wandb`(例如 `/private/users/alice/jobs//wandb`) - -降级策略: -- 当 `tracking.wandb.enabled=true` 但缺少 `WANDB_API_KEY` 时,平台会**降级为 console**(并在 attempt.message 中记录 warning),避免训练失败。 - -### 2.4 WebUI 变更 - -1) **Login 页面** -- 增加 “Open W&B” 跳转(指向 `tracking.wandb.base_url`) - -2) **New Task 页面** -- 新增 **Evaluation example** -- Advanced example 更新为 v3.6: - - `command: |` 内不再包含任何注释(避免 YAML/命令解析报错) - - W&B 参数不再让用户手填,改为引用平台注入的 `${MVP_*}` env: - - `trainer.logger=${MVP_TRAINER_LOGGER}` - - `trainer.project_name=${MVP_WANDB_PROJECT}` - - `trainer.experiment_name=${MVP_WANDB_RUN}` - -> 备注:driver 日志里会打印 `MVP_DRIVER_EXEC: bash -lc '...'`,此处看到 `${MVP_*}` 仍是“未替换”的字符串是正常现象;变量替换发生在 `bash` 执行阶段,而不是打印 argv 阶段。 - -### 2.5 启动脚本 - -`src/mvp/scripts/60_start_api.sh` 支持将宿主机的 `WANDB_API_KEY` 透传进 head 容器内启动的 API server: - -- 宿主机设置:`export WANDB_API_KEY=...` -- 启动 API:脚本会 `docker exec -e WANDB_API_KEY=...` 进入 head 容器启动 `python3 /workspace/mvp/py/server.py` - -## 3. 用户侧操作流程(v3.6) - -### 3.1 一次性初始化(只在首次启用/清空 /vol 时需要) - -1) 打开 W&B UI:`http://:8090` -2) 在 System Admin 页面粘贴 license 完成初始化 -3) 生成并记录 `WANDB_API_KEY`(local key) -4) 以后启动 API server 时注入该 key(`WANDB_API_KEY=...`) - -只要保留 `shared/common/wandb`(即 `/vol` 持久化目录),重建容器无需再次进入 8090 配置。 - -### 3.2 日常使用 - -1) WebUI 登录:`http://:8080/ui/login`(输入 user token) -2) New Task 提交任务:`http://:8080/ui/tasks/new` -3) 到 Tasks 查看状态/日志:`/ui/tasks` 与 task detail -4) 打开 W&B:`http://:8090`,在 `_project` 下查看 runs/metrics - -## 4. 验收结果(本迭代应达成) - -1) PPO/GRPO/SFT 任一任务运行后: -- W&B local server 可见对应 project(如 `alice_project`) -- run name 与 `ray_submission_id` 对齐(便于追踪每次 attempt) - -2) Evaluation 示例: -- 可作为 Advanced 任务提交并在 Ray 上执行 `verl.trainer.main_eval` -- 支持用户在 command 内自行加入 reward overrides(平台不做封装) - -## 5. 已知限制与后续建议 - -1) **W&B 初始化自动化** -- 当前:首次仍需在 8090 页面粘贴 license、生成 key(更稳、侵入最小)。 -- 若需要“从零部署也完全免页面操作”,可进一步调研 W&B local 的可用管理 API/启动参数(自动注入 license + 自动创建 key)。 - -2) **Advanced command 的自由度** -- 平台只负责: - - `$HOME` 宏替换 - - runtime_env env_vars 注入 - - 任务队列与 Ray job 提交 -- command 的语义正确性仍由用户负责(例如 PPO 必需的 micro batch 等参数)。 - diff --git a/specs/mvp/v3.6/wandb.md b/specs/mvp/v3.6/wandb.md deleted file mode 100644 index c7ddeda..0000000 --- a/specs/mvp/v3.6/wandb.md +++ /dev/null @@ -1,70 +0,0 @@ - -# License - -License: -eyJhbGciOiJSUzI1NiIsImtpZCI6InUzaHgyQjQyQWhEUXM1M0xQY09yNnZhaTdoSlduYnF1bTRZTlZWd1VwSWM9In0.eyJjb25jdXJyZW50QWdlbnRzIjoxLCJ0cmlhbCI6ZmFsc2UsIm1heFN0b3JhZ2VHYiI6MTAsIm1heFRlYW1zIjowLCJtYXhVc2VycyI6MSwibWF4Vmlld09ubHlVc2VycyI6MCwibWF4UmVnaXN0ZXJlZE1vZGVscyI6MiwiZXhwaXJlc0F0IjoiMjAyNy0wMS0wNVQwMjoxMjo1MC4zMjRaIiwiZGVwbG95bWVudElkIjoiYzNmN2Y5N2ItMzAxOS00Nzk2LTkxYTgtZDUyMjc1NDBiMTI1IiwiZmxhZ3MiOltdLCJjb250cmFjdFN0YXJ0RGF0ZSI6IjIwMjYtMDEtMDVUMDI6MTI6NTAuMzI0WiIsImFjY2Vzc0tleSI6IjYxMGM5NjliLTk4ZWEtNGRhNS1iYzU1LWM2MzVlZWNhNzc0OCIsInNlYXRzIjoxLCJ2aWV3T25seVNlYXRzIjowLCJ0ZWFtcyI6MCwicmVnaXN0ZXJlZE1vZGVscyI6Miwic3RvcmFnZUdpZ3MiOjEwLCJleHAiOjE3OTkxMTUxNzAsIndlYXZlTGltaXRzIjp7IndlYXZlTGltaXRCeXRlcyI6bnVsbCwid2VhdmVPdmVyYWdlQ29zdENlbnRzIjowLCJ3ZWF2ZU92ZXJhZ2VVbml0IjoiTUIifX0.VADnc0PExWhGDAxMIbu0vlmPN423B398of4HFl6BMJ1vqGA9H1ESElOZfk0VQ0YnYgwZc_CZF9k0HRyfCBgRhtRKyB1PpGnaKT_kKNVQryykWRpNhnpDqhmTa-wfTUBXNxhu1ktNPKBFNaEbaYuPsLN_aXPGW0dDwp6coGnGEXEqdRmuvekE6ytu7t6IA6flYs35WqCojvvjAmfBdovo2zPTfmlqKeaz7GPrApMo9JBpmb1a6bZEjCoRhhUx_k-v2rbvE3hd9ix9_UMZ6siJ5IKtNuXy_cprcCXXIFVUMcfTnt78RRXY0jCRMQqWkNq9ZGF0Mgcjsh3ts9xSxPgWnw - -# License 限制 -Add License to your Local Instance -Create up to 0 teams -Create up to 1 users -Store up to 10 GB of data -Create up to 2 Registered Models - -Quickstart -On a machine with Docker and Python installed, run: -1 pip install wandb --upgrade -2 wandb server start -Generate a free license from the Deployer. -Add it to your W&B Server's localhost's settings. -Paste the license in the /system-admin page on your localhost - -# docker 部署 - -deployment: -version: "3.8" - -services: - wandb: - image: wandb/local:latest - container_name: wandb-local - ports: - - "8080:8080" - volumes: - - wandb_data:/vol - restart: unless-stopped - -volumes: - wandb_data: - - - -# 连接方式: -方式 B:环境变量(适合容器/批处理/CI) - -通过 ray job的runtime_env来设置环境变量 - -export WANDB_BASE_URL=http://<服务器IP或域名>:8080 -export WANDB_API_KEY=<你的API_KEY> - - -官方文档说明可以用 WANDB_BASE_URL + WANDB_API_KEY 代替 wandb login --host .. - - -# verl配置: -在 verl 里打开 wandb(你只需要配 trainer) - -verl 的配置里,最关键是这三个字段:trainer.logger、trainer.project_name、trainer.experiment_name。文档里也写了 logger 用于 console + tracking(tracking 会初始化 wandb)。 -veRL Documentation -+1 - -推荐写法(新版本): - -trainer: - logger: ["console", "wandb"] - project_name: my_project # 用argus的用户名_project ,譬如 alice_project - experiment_name: exp_001 # 用 task id 作为实验名 - - - - diff --git a/specs/mvp/v3.7/v3.7_design.md b/specs/mvp/v3.7/v3.7_design.md deleted file mode 100644 index 436aed9..0000000 --- a/specs/mvp/v3.7/v3.7_design.md +++ /dev/null @@ -1,215 +0,0 @@ -# MVP v3.7 设计方案:切换 `verlai/verl:vllm011.latest` + 默认 rollout=vllm - -## 0. 背景与目标 - -当前 dev/h1 环境的 Ray 节点镜像基于 `verlai/verl:sgl055.latest`,并且平台内置 PPO/GRPO 的默认参数中写死了: - -- `actor_rollout_ref.rollout.name=sglang` - -v3.7 的目标是: - -1. **Ray 节点镜像切换到 vLLM 版本** - - 基础镜像改为 `verlai/verl:vllm011.latest` - - 构建并打标:`argus/argus-ray-node:vllm011.latest` - - 构建在远端 `argus@h1` 上完成(本地没有 verlai 基础镜像) -2. **端到端跑通 v3.0 API 流程** - - 通过 `src/mvp/scripts/run_all_v30_api.sh` 完整 E2E -3. **内置训练任务默认使用 vLLM rollout** - - 提交 VERL 训练任务时将 `actor_rollout_ref.rollout.name` 从 `sglang` 改为 `vllm` - -> 备注:本迭代是“替换默认 backend”而非“新增能力”,尽量保持对 v3.6 功能兼容(W&B、SFTPGo、Advanced TaskSpec、stateless pool 等不改协议)。 - ---- - -## 1. 现状梳理(源码定位) - -### 1.1 Ray 节点镜像与 compose - -- Dockerfile:`src/mvp/images/argus-ray-node/Dockerfile` - - 当前 `ARG BASE_IMAGE=verlai/verl:sgl055.latest` -- Compose:`src/mvp/docker-compose.yaml` - - `ray_head.build.args.BASE_IMAGE: verlai/verl:sgl055.latest` - - `ray_head.image / worker.image: argus/argus-ray-node:v2.5` - -### 1.2 默认 rollout.name=sglang 的位置 - -平台内置 PPO/GRPO 参数由 Ray job 入口构建器生成: - -- `src/mvp/py/argus/ray/builders.py` - - `build_training_argv()` 中写死了: - - `actor_rollout_ref.rollout.name=sglang` - -WebUI 的 Advanced 示例也包含 rollout.name(用于指导用户): - -- `src/mvp/py/argus/service/ui.py` - - Advanced example 中当前为 `actor_rollout_ref.rollout.name=sglang`(需要同步改成 vllm,避免用户 copy/paste 走错) - -### 1.3 `run_all_v30_api.sh` 依赖默认参数 - -`src/mvp/scripts/run_all_v30_api.sh` 提交 PPO/GRPO/SFT 的 TaskSpec(YAML)时 **不会显式携带 rollout.name**,因此是否能切到 vllm,依赖平台默认值(builders)是否变更。 - ---- - -## 2. 方案设计 - -### 2.0 已确认决策(来自评审) - -1) **compose 移除 build**:允许移除 `ray_head.build`,强制使用远端已构建镜像。 -2) **全量切换 vllm**:不保留 sglang 作为可选项(v3.7 默认全部切到 vllm)。 -3) **backend 名称**:确认 VERL backend 名为 `vllm`(即 `actor_rollout_ref.rollout.name=vllm`)。 - -### 2.1 镜像策略(vllm011) - -#### 2.1.1 Dockerfile 修改 - -目标: -- 默认基础镜像改为 `verlai/verl:vllm011.latest` - -改动点: -- `src/mvp/images/argus-ray-node/Dockerfile` - - `ARG BASE_IMAGE=verlai/verl:vllm011.latest` - -说明: -- 仍保留 `BASE_IMAGE` build arg,便于未来热切换不同基础镜像(而不是把镜像写死在 compose)。 - -#### 2.1.2 镜像 tag - -构建产物镜像: -- `argus/argus-ray-node:vllm011.latest` - -> 注意:该 tag 用于表达“运行时依赖的 vllm 版本线”,而不是 MVP 功能版本(v3.7)。 - -#### 2.1.3 compose 复用新镜像(避免每次重建) - -目标:E2E 时尽量避免每次 `docker compose up` 都 build。 - -建议修改 `src/mvp/docker-compose.yaml`: -- `ray_head.image: argus/argus-ray-node:vllm011.latest` -- `ray_worker_0.image: argus/argus-ray-node:vllm011.latest` -- `ray_worker_1.image: argus/argus-ray-node:vllm011.latest` - -并采用:**移除 `ray_head.build`**(强制使用已构建镜像),避免每次 `docker compose up` 触发 build。 - ---- - -### 2.2 训练默认参数切换到 vllm - -目标:平台内置 PPO/GRPO 的默认 rollout backend 从 sglang 切到 vllm。 - -改动点: -- `src/mvp/py/argus/ray/builders.py` - - 将 `actor_rollout_ref.rollout.name=sglang` 替换为 `actor_rollout_ref.rollout.name=vllm` - -影响范围: -- PPO、GRPO(两者都走 `verl.trainer.main_ppo`) -- 对 SFT 不影响(SFT 走 `verl.trainer.sft_trainer_ray`) - -兼容性评估: -- `run_all_v30_api.sh` 会受益:无需修改 TaskSpec,即可自动切换。 -- 若未来仍需支持 sglang,可考虑在 v3.7 之后引入“配置驱动”的默认值(见 §2.4 可选增强)。 - ---- - -### 2.3 WebUI/模板同步(避免误导用户) - -目标:New Task 页面的 Advanced example 也应默认 vllm,避免用户 copy 后手工改参数。 - -改动点: -- `src/mvp/py/argus/service/ui.py` - - Advanced example 中 `actor_rollout_ref.rollout.name=vllm` - -> 注意:该模板仅用于 UX 指导;实际生效仍由用户提交的 command 决定。 - ---- - -### 2.4 可选增强(不强制,供评审) - -为避免后续再硬编码切换,可引入“平台训练默认值”配置(可选): - -- 在 `configs/dev.yaml` 增加: - ```yaml - verl_defaults: - rollout_backend: "vllm" # 或 "sglang" - ``` -- `builders.py` 从配置读取默认值,而非写死。 - -本次 v3.7 的最低交付可以先不做该增强,只做硬替换;若你希望后续支持 A/B 切换,再纳入。 - ---- - -## 3. 远端部署/迁移步骤(argus@h1) - -> 本节是“计划步骤”,评审通过后再执行。 - -### 3.1 同步代码到远端目录 - -远端目录约定: -- `argus@h1:/home2/argus/infra/mvp/src/mvp`(compose 与 scripts) - -将本地变更 rsync 到远端后再进行构建/拉起。 - -### 3.2 在远端构建镜像(只在 h1) - -在 `argus@h1` 执行(示例命令): - -```bash -cd /home2/argus/infra/mvp/src/mvp -docker build \ - -f images/argus-ray-node/Dockerfile \ - --build-arg BASE_IMAGE=verlai/verl:vllm011.latest \ - -t argus/argus-ray-node:vllm011.latest \ - . -``` - -### 3.3 清理旧环境并用新镜像拉起 - -```bash -cd /home2/argus/infra/mvp/src/mvp -docker compose down -docker compose up -d -``` - -验证: -- `docker ps` 中 `argus-ray-head/worker` 的 image 为 `argus/argus-ray-node:vllm011.latest` -- Ray dashboard 可访问:`http://:8265` - -### 3.4 E2E:跑 `run_all_v30_api.sh` - -```bash -cd /home2/argus/infra/mvp/src/mvp -MVP_INTERNAL_TOKEN=my-dev-token \ -WANDB_API_KEY=... \ -./scripts/run_all_v30_api.sh -``` - -验收关键点: -- PPO/GRPO/SFT 全部成功(或至少 PPO/GRPO 不卡在 rollout backend 初始化阶段) -- 任一 PPO/GRPO 的 driver logs / hydra overrides 中能看到: - - `actor_rollout_ref.rollout.name=vllm` - ---- - -## 4. 风险与排查要点 - -### 4.1 vLLM backend 在 VERL 的参数兼容性 - -平台默认传入的这些参数当前是为 sglang 写的: -- `actor_rollout_ref.rollout.tensor_model_parallel_size=1` -- `actor_rollout_ref.rollout.gpu_memory_utilization=0.4` - -vLLM rollout 是否接受/需要额外参数(例如 tokenizer、engine 配置),需要在 E2E 中观察: -- 如果 vLLM rollout 初始化报错,可能需要补充 vllm 特定 overrides(属于 v3.7 的后续修复项)。 - -### 4.2 镜像依赖差异 - -更换 base image 可能带来: -- Python/Ray/依赖版本差异 -- CUDA/NCCL 依赖差异 - -建议: -- 在 v3.7 评审通过后,优先跑最小 PPO(epochs=1、steps=10)验证 vllm backend 能启动并完成。 - ---- - -## 5. 待确认问题(请你评审时确认) -已完成评审确认(见 §2.0),无额外待确认项。 diff --git a/specs/mvp/v3.7/v3.7_dev_plan.md b/specs/mvp/v3.7/v3.7_dev_plan.md deleted file mode 100644 index 61b0f58..0000000 --- a/specs/mvp/v3.7/v3.7_dev_plan.md +++ /dev/null @@ -1,122 +0,0 @@ -# MVP v3.7 开发计划(TDD) - -> 目标:切换 Ray 节点基础镜像到 `verlai/verl:vllm011.latest`,并将平台内置 PPO/GRPO 默认 rollout backend 全量切到 `vllm`,最后在远端 `argus@h1` 通过 `run_all_v30_api.sh` 跑通端到端。 - -## M0 - 基线确认(不改行为) - -**目的**:确认当前 v3.6 baseline 可跑(避免把历史问题混入 v3.7)。 - -- [ ] 本地单测全绿:`.venv/bin/python -m pytest` -- [ ] 远端 h1 当前环境可跑(可选):`./scripts/run_all_v30_api.sh`(或至少能启动 Ray+API) - -**验收**: -- 单测通过,coverage ≥ 90%(现有门槛) - ---- - -## M1 - 训练默认参数切换到 vllm(TDD) - -**目的**:在不碰镜像/compose 的前提下,先把“默认 rollout=sglang”替换为 vllm,并用单测锁定行为。 - -### 1.1 新增/更新单测(先写测试) - -- [ ] `src/mvp/py/tests/test_builders.py` - - 新增断言:PPO/GRPO 的 argv 中包含 `actor_rollout_ref.rollout.name=vllm` - - 且不再包含 `actor_rollout_ref.rollout.name=sglang` - -- [ ] `src/mvp/py/tests/test_ui.py` - - New Task Advanced example 模板包含 `actor_rollout_ref.rollout.name=vllm`(避免用户 copy/paste 走错默认) - -> 这两条测试先写出来,预期先失败(red)。 - -### 1.2 实现改动(让测试变绿) - -- [ ] `src/mvp/py/argus/ray/builders.py` - - 将 `actor_rollout_ref.rollout.name=sglang` 改为 `...=vllm` - -- [ ] `src/mvp/py/argus/service/ui.py` - - Advanced example 中同样改为 `...=vllm` - -### 1.3 回归测试 - -- [ ] `.venv/bin/python -m pytest` - -**验收**: -- 单测全绿(coverage ≥ 90%) -- 平台内置 PPO/GRPO 构建出的 command/overrides 默认 rollout backend 为 vllm - ---- - -## M2 - 镜像与 compose 切换(远端构建为主) - -**目的**:完成镜像切换与环境拉起,确保 Ray stateless pool 正常工作。 - -### 2.1 Dockerfile 默认 base image 切换 - -- [ ] `src/mvp/images/argus-ray-node/Dockerfile` - - `ARG BASE_IMAGE=verlai/verl:vllm011.latest` - -### 2.2 docker-compose 强制使用新镜像(移除 build) - -- [ ] `src/mvp/docker-compose.yaml` - - 移除 `ray_head.build` 段(强制走 `image:`) - - `ray_head.image / ray_worker_0.image / ray_worker_1.image` 统一改为: - - `argus/argus-ray-node:vllm011.latest` - -### 2.3 远端构建镜像(h1) - -在 `argus@h1:/home2/argus/infra/mvp/src/mvp`: - -- [ ] `docker build -f images/argus-ray-node/Dockerfile -t argus/argus-ray-node:vllm011.latest .` - -### 2.4 清理旧 compose 并拉起 - -- [ ] `docker compose down` -- [ ] `docker compose up -d` -- [ ] 验证: - - `docker ps` 看到 `argus-ray-head/worker` 正常运行 - - Ray dashboard:`http://:8265` 可访问,节点数 1 head + 2 worker - -**验收**: -- h1 环境成功使用新镜像拉起 Ray 集群(head 无 GPU、worker 各 4 GPU 的配置仍保持) - ---- - -## M3 - 端到端验证(run_all_v30_api.sh) - -**目的**:验证在新镜像 + 默认 vllm rollout 下,API 提交的训练任务能跑通闭环。 - -### 3.1 同步代码到远端 - -- [ ] rsync `src/mvp` 到 `argus@h1:/home2/argus/infra/mvp/src/mvp` - -### 3.2 执行 E2E - -在 h1: - -- [ ] `./scripts/run_all_v30_api.sh`(确保环境变量按脚本要求设置:`MVP_INTERNAL_TOKEN`、可选 `WANDB_API_KEY` 等) - -### 3.3 核心检查点 - -- [ ] PPO/GRPO/SFT 任务整体流程可执行(至少 PPO/GRPO 不因 rollout backend 初始化失败) -- [ ] 任一 PPO/GRPO 的 Ray job logs / submit payload / hydra overrides 中可确认: - - `actor_rollout_ref.rollout.name=vllm` - -**验收**: -- `run_all_v30_api.sh` 端到端成功(或若 PPO/GRPO 因 vllm 参数差异失败,需在本 milestone 内补齐必要 overrides 并重新跑通) - ---- - -## 风险与回滚策略 - -### 风险 - -- vLLM rollout 可能对部分参数(如 batch/并发/显存利用率)有不同约束,导致训练启动失败。 -- base image 切换导致 ray/依赖版本差异。 - -### 回滚 - -回滚到 v3.6 / sglang 的最小动作: -- `docker-compose.yaml` 恢复旧镜像 tag -- `builders.py` 恢复 rollout.name=sglang - diff --git a/specs/mvp/v3.7/v3.7_summary.md b/specs/mvp/v3.7/v3.7_summary.md deleted file mode 100644 index c00bf26..0000000 --- a/specs/mvp/v3.7/v3.7_summary.md +++ /dev/null @@ -1,121 +0,0 @@ -# MVP v3.7 迭代总结:切换 vLLM rollout + `verlai/verl:vllm011.latest` - -> 基线版本:v3.6(W&B + SFTPGo + WebUI/API + Ray stateless pool + Advanced TaskSpec) -> 验证环境:`argus@h1:/home2/argus/infra/mvp` - -## 1. 目标与结果 - -### 1.1 本次目标 - -1) Ray 节点镜像切换到 vLLM 版本: -- base image:`verlai/verl:vllm011.latest` -- 构建镜像 tag:`argus/argus-ray-node:vllm011.latest` - -2) 平台内置 PPO/GRPO 默认 rollout backend 全量切换: -- `actor_rollout_ref.rollout.name=sglang` → `actor_rollout_ref.rollout.name=vllm` - -3) 端到端验证: -- 使用 `src/mvp/scripts/run_all_v30_api.sh` 在 h1 上跑通 E2E(通过 API 提交 PPO/GRPO/SFT) - -### 1.2 实际结果(验收) - -- h1 上已成功构建并使用新镜像拉起(head + 2 worker): - - `docker ps` 显示 `argus-ray-head/worker-*` 使用 `argus/argus-ray-node:vllm011.latest` -- `run_all_v30_api.sh` 端到端跑通: - - PPO/GRPO/SFT 任务均 `SUCCEEDED` -- 在 job submit payload 中验证关键点: - - `actor_rollout_ref.rollout.name=vllm` - - `HF_HUB_OFFLINE=1`(见 §3.2) - ---- - -## 2. 代码与配置改动点 - -### 2.1 训练默认参数(sglang → vllm) - -- `src/mvp/py/argus/ray/builders.py` - - 将 PPO/GRPO 默认参数中的 `actor_rollout_ref.rollout.name` 固定为 `vllm` -- `src/mvp/py/argus/service/ui.py` - - New Task → Advanced example 同步改为 `actor_rollout_ref.rollout.name=vllm`(避免用户 copy/paste 走错) - -并用单测锁定行为(TDD): -- `src/mvp/py/tests/test_builders.py` -- `src/mvp/py/tests/test_ui.py` - -### 2.2 镜像与 compose(强制用预构建镜像) - -- `src/mvp/images/argus-ray-node/Dockerfile` - - 默认 `ARG BASE_IMAGE=verlai/verl:vllm011.latest` -- `src/mvp/docker-compose.yaml` - - 移除 `ray_head.build`(避免每次 `docker compose up` 触发 build) - - head/worker 统一使用 `image: argus/argus-ray-node:vllm011.latest` - ---- - -## 3. E2E 遇到的问题与修复 - -### 3.1 问题:vLLM 初始化触发 HF mirror 429 - -在切换到 vLLM rollout 后,PPO/GRPO 任务启动阶段出现: -- `huggingface_hub.errors.HfHubHTTPError: 429 Too Many Requests` -- 请求来源:`https://hf-mirror.com/api/models//tree/main?...` - -原因要点: -- 传入模型为 repo id(`Qwen/Qwen2.5-0.5B-Instruct`)时,vLLM 会调用 HF API 获取 repo tree/file list; -- 多进程/多 replica 并发会瞬间放大请求,导致 mirror 限流; -- 即便本地 cache 已存在,repo id 路径仍可能触发远端检查。 - -### 3.2 修复:禁用 HF Hub 联网 + 使用本地 snapshot path - -1) 在 Ray job runtime_env 注入离线开关: -- `src/mvp/configs/dev.yaml` -- `src/mvp/configs/dev_v30.yaml` - -新增: -```yaml -HF_HUB_OFFLINE: "1" -``` - -2) E2E 脚本提交任务时,`model_id` 改为本地 snapshot 目录,避免 repo id: -- `src/mvp/scripts/run_all_v30_api.sh` - - 在 head 容器内用 `snapshot_download(..., local_files_only=True)` 解析本地路径 - - 用该路径作为 `model_id:` 提交 PPO/GRPO/SFT - -> 结果:E2E 任务不再触发 HF mirror 429,PPO/GRPO/SFT 全部跑通。 - ---- - -## 4. 远端部署/操作记录(h1) - -### 4.1 构建镜像(h1 上执行) - -在 `argus@h1:/home2/argus/infra/mvp/src/mvp`: - -```bash -docker build -f images/argus-ray-node/Dockerfile \ - --build-arg BASE_IMAGE=verlai/verl:vllm011.latest \ - -t argus/argus-ray-node:vllm011.latest . -``` - -### 4.2 拉起环境(compose) - -```bash -docker compose down -docker compose up -d -``` - -### 4.3 E2E - -```bash -export MVP_INTERNAL_TOKEN=my-dev-token -export SFTPGO_ADMIN_PASSWORD=my-dev-sftpgo-admin -./scripts/run_all_v30_api.sh -``` - ---- - -## 5. 已知影响与注意事项 - -1) **vLLM rollout 更敏感于模型加载路径与联网行为**:建议默认离线(`HF_HUB_OFFLINE=1`)并优先使用本地 snapshot path。 -2) **镜像切换可能带来依赖差异**:后续若遇到 rollout 相关参数兼容问题,应以 vLLM 的配置要求为准逐项调整(保持小步快跑)。 - diff --git a/specs/mvp/v3.8/Snipaste_2026-01-08_17-17-57.png b/specs/mvp/v3.8/Snipaste_2026-01-08_17-17-57.png deleted file mode 100644 index 3ec8be70cdfa42f862affca3cd2275519acb6eda..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 413025 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

m~gbB&}EXN28b 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 z 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 z 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�VeY2vHlbeTobsfDAOC$nlpe*{Phg#QNRZIqm| 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 z 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≫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 -``` - -#### 2. 编写部署脚本 (`serve_medium_llm.py`) -使用 **Builder Pattern** 定义配置并构建应用。以下示例配置了一个典型的 70B 模型部署: - -```python -# serve_medium_llm.py -from ray.serve.llm import LLMConfig, build_openai_app -import os - -llm_config = LLMConfig( - model_loading_config=dict( - model_id="my-llama-3.1-70b", - model_source="meta-llama/Llama-3.1-70B-Instruct", - ), - accelerator_type="A100-40G", # 或 L40S - deployment_config=dict( - autoscaling_config=dict( - min_replicas=1, # 最小副本数 - max_replicas=4, # 最大副本数,实现动态扩展 - ) - ), - runtime_env=dict(env_vars={"HF_TOKEN": os.environ.get("HF_TOKEN")}), - engine_kwargs=dict( - max_model_len=32768, # 上下文长度 - tensor_parallel_size=8, # 在单节点的 8 个 GPU 间拆分权重 - ), -) - -# 使用 Builder Pattern 构建应用 -app = build_openai_app({"llm_configs": [llm_config]}) -``` - -#### 3. 启动部署 -在终端运行以下命令启动服务: -```bash -serve run serve_medium_llm:app -``` -部署过程通常需要几分钟,包括配置集群、启动 vLLM 服务器以及下载模型权重。 - -#### 4. 发送请求测试 -服务启动后,可以通过符合 OpenAI 标准的接口进行访问。 -```python -from openai import OpenAI - -client = OpenAI(base_url="http://localhost:8000/v1", api_key="FAKE_KEY") -response = client.chat.completions.create( - model="my-llama-3.1-70b", - messages=[{"role": "user", "content": "解释一下什么是量子纠缠?"}], - stream=True -) -for chunk in response: - if chunk.choices.delta.content: - print(chunk.choices.delta.content, end="", flush=True) -``` - ---- - -### 三、 性能与并发优化建议 - -* **提高并发量**:可以通过降低 `max_model_len` 来减少 KV 缓存所需的显存,从而显著提升每个副本支持的最大并发请求数。 -* **监控指标**:通过 Ray Serve LLM 仪表盘监控 **TTFT(首字延迟)**、**TPOT(单字延迟)** 和 **Token 吞吐量** 来评估服务性能。 -* **精度折衷**:对于资源受限的场景,可以使用**量化模型**(如 FP8)来减少模型内存占用,为 KV 缓存留出更多空间,进而提高并发能力。 - -**比喻理解**: -部署**中型 LLM** 就像是在一个大型车间里组装一台复杂的精密机器(模型权重)。**Builder Pattern** 是你的“全自动组装线”,你只需设定好机器的参数(Config),生产线就会自动帮你把零件固定好并接通电源。而 **vLLM 和张量并行** 就像是让 8 个熟练工人(GPU)共同抬起这台沉重的机器,每个人只负责自己那一部分的力气,从而让机器能够平稳地运转。 \ No newline at end of file diff --git a/specs/mvp/v3.8/requirements.md b/specs/mvp/v3.8/requirements.md deleted file mode 100644 index aaaa642..0000000 --- a/specs/mvp/v3.8/requirements.md +++ /dev/null @@ -1,8 +0,0 @@ - -1. 通过ray serve(后端vllm)来动态拉起llm,支持多模型application部署, -2. 默认一个模型只有一个replica,用户配置可以多个 -3. 用户可以删除(下线)模型 -4. 可以指定模型用几张卡 -5. 通过WebUI来进行配置,查看当前部署的模型列表,以及可以查看详情 -6. 模型路径可以使用common,也可以用户自己指定user路径 -7. \ No newline at end of file diff --git a/specs/mvp/v3.8/v3.8_api.md b/specs/mvp/v3.8/v3.8_api.md deleted file mode 100644 index 813f2a9..0000000 --- a/specs/mvp/v3.8/v3.8_api.md +++ /dev/null @@ -1,224 +0,0 @@ -# MVP v3.8 API Reference(Serving) - -> 说明:本节为 v3.8 新增的 **Model Serving** API(Ray Serve LLM / vLLM)。 -> 认证:Serving 管理 API 复用现有 MVP API 的认证方式(`Authorization: Bearer `)。 -> 推理:对外 OpenAI endpoint **不做鉴权**(v3.8 约定)。 - -## 0. 基本信息 - -### 0.1 Base URLs - -- MVP API server:`http://:8080` -- Ray Serve OpenAI ingress(固定端口 8000):`http://:8000/v1` - -### 0.2 认证 - -所有 `/api/v2/serve/*` 接口要求: - -``` -Authorization: Bearer -``` - -其中 `user_token` 由管理员通过 `/api/v2/users//tokens` 颁发(沿用现有机制)。 - -### 0.3 命名规则:`model_id = user_id-YYYYMMDDHHMM-` - -- 用户提交时填写 `model_id`(语义为 suffix,例如 `qwen-0.5b`) -- 平台生成前缀: - - `prefix = "-"` -- 平台实际对外暴露的 OpenAI model 名称为: - - `model_id = "-"` - - 示例:`alice-202601061235-qwen-0.5b` - -## 1. 数据结构 - -### 1.1 ServingSpec(YAML) - -请求体建议使用 YAML(与 TaskSpec 一致),示例: - -```yaml -model_id: qwen-0.5b # 必填:suffix(平台自动加 user_id- 前缀) -model_source: $HOME/common/hf/.../ # 必填:本地路径或 repo id;平台做 $HOME 宏替换与路径校验 -num_replicas: 1 # 可选,默认 1 -gpus_per_replica: 1 # 可选,默认 1 -# engine_kwargs: # 可选:vLLM 参数透传(白名单/黑名单由实现决定) -# max_model_len: 8192 -# gpu_memory_utilization: 0.9 -``` - -说明: -- `accelerator_type` 不在 ServingSpec 中暴露;由平台配置(`dev.yaml` 的 `serving.llm.accelerator_type`)统一注入到 Ray Serve LLM 的 `LLMConfig.accelerator_type`(dev/h1: `H20`)。 - -#### 宏替换 - -- `$HOME` → `/private/users/` -- `$HOME/common/hf` → `/private/hf` -- `$HOME/common/datasets` → `/private/datasets`(serving 不强依赖,但保留一致语义) - -#### 路径校验(v3.8 约定) - -`model_source` 允许: - -- `/private/hf/...`(common) -- `/private/users//...`(user) - -拒绝: - -- 其它用户目录 -- 非 `/private` 下路径 -- 空路径或包含 `..` 的可疑路径 - -### 1.2 ServingModel(响应体,JSON) - -```json -{ - "model_key": "svc-alice-20260106-123000-abcd", - "user_id": "alice", - "model_id": "alice-202601061235-qwen-0.5b", - "model_id_suffix": "qwen-0.5b", - "model_id_prefix": "alice-202601061235", - "model_source": "/private/hf/hub/models--.../snapshots/", - "num_replicas": 1, - "gpus_per_replica": 1, - "total_gpus": 1, - "state": "RUNNING", - "endpoint": { - "openai_base_url": "http://:8000/v1", - "model": "alice-202601061235-qwen-0.5b" - }, - "error_summary": null, - "created_at": "2026-01-06T12:30:00Z", - "updated_at": "2026-01-06T12:31:02Z" -} -``` - -## 2. 管理 API(MVP API server) - -### 2.1 Create / Upsert model - -`POST /api/v2/serve/models` - -#### Request - -- Header: `Content-Type: application/yaml` -- Body: ServingSpec(YAML) - -#### Response (202) - -```json -{ - "model_key": "svc-alice-20260106-123000-abcd", - "state": "QUEUED" -} -``` - -语义: -- 创建新模型(若 suffix 不存在) -- 或更新已有模型(若同一用户同一 suffix 已存在):更新 replicas/gpu 等配置,进入 `QUEUED` 等待 reconciler apply - -### 2.2 List models (current user) - -`GET /api/v2/serve/models` - -#### Response (200) - -```json -{ - "items": [ ... ServingModel ... ], - "openai_base_url": "http://:8000/v1" -} -``` - -### 2.3 Get model detail - -`GET /api/v2/serve/models/{model_key}` - -#### Response (200) - -```json -{ - "model": { ... ServingModel ... }, - "resolved_spec_yaml": "model_id: ...\nmodel_source: ...\n", - "events": [ - { "event_type": "DEPLOY_REQUESTED", "created_at": "...", "payload": {...} } - ], - "serve_status": { - "app_name": "argus_llm_app", - "app_status": "RUNNING" - } -} -``` - -### 2.4 Scale replicas (PATCH) - -`PATCH /api/v2/serve/models/{model_key}` - -#### Request (JSON) - -```json -{ "num_replicas": 2 } -``` - -#### Response (200) - -```json -{ "model_key": "...", "state": "QUEUED" } -``` - -> v3.8 只支持修改 `num_replicas`(以及可选 engine_kwargs);`gpus_per_replica` 若修改,可能触发重新部署。 - -### 2.5 Delete / Undeploy model - -`DELETE /api/v2/serve/models/{model_key}` - -#### Response (200) - -```json -{ "model_key": "...", "state": "DELETING" } -``` - -语义:从“声明式配置”中删除该模型,reconciler 会在下一轮 tick 触发 `serve.run(...)` 更新 app 配置并最终使其不可见。 - -### 2.6 Admin: Serve cluster status(可选) - -`GET /api/v2/serve/status` - -#### Response (200) - -返回 `serve.status()` 摘要(集群级 + app 级)。 - -> 仅 admin token 可访问(沿用 v3.x admin gate)。 - -## 3. 推理 API(Ray Serve OpenAI ingress) - -> v3.8 不做鉴权:无需 `Authorization`。 - -### 3.1 List models - -`GET http://:8000/v1/models` - -返回可用 model 列表(包含 `alice-qwen-0.5b` 这类带前缀名称)。 - -### 3.2 Chat completions - -`POST http://:8000/v1/chat/completions` - -```json -{ - "model": "alice-202601061235-qwen-0.5b", - "messages": [{"role":"user","content":"Hello"}], - "stream": false -} -``` - -### 3.3 Completions / Embeddings - -按 Ray Serve LLM OpenAI ingress 支持范围提供(v3.8 验收至少覆盖 chat)。 - -## 4. 错误码约定(MVP API server) - -- `400 invalid yaml/spec`:YAML 解析失败、字段缺失、值不合法 -- `403 forbidden`:路径越权(model_source 访问其他用户目录) -- `409 conflict`:model_id_suffix 冲突(同一用户重复创建且不允许覆盖时;若选择 upsert 则不返回该错误) -- `422 unprocessable`:资源参数非法(replica/gpu <=0) -- `500 internal`:reconciler/serve 调用异常(详情记录到 `serve_events`,并写入 `error_summary`) diff --git a/specs/mvp/v3.8/v3.8_design.md b/specs/mvp/v3.8/v3.8_design.md deleted file mode 100644 index a69a99c..0000000 --- a/specs/mvp/v3.8/v3.8_design.md +++ /dev/null @@ -1,371 +0,0 @@ -# MVP v3.8 详细设计方案:Ray Serve(vLLM)模型动态部署与管理 - -> 基线:当前已具备 v3.7 能力(训练平台 + W&B + SFTPGo + WebUI/API + Ray stateless pool,训练侧默认 rollout=vllm)。 -> v3.8 目标:在同一套 Ray 集群上,引入 **Ray Serve LLM(后端 vLLM)** 的模型推理服务能力,并通过 WebUI/API 动态管理模型生命周期。 - -## 0. 需求范围(来自 requirements.md) - -1) 通过 Ray Serve(后端 vLLM)动态拉起 LLM,支持**多模型 application** 部署 -2) 默认一个模型 1 个 replica,用户可配置多个 -3) 用户可删除(下线)模型 -4) 用户可指定模型使用几张 GPU -5) WebUI 可配置、查看模型列表、查看详情 -6) 模型路径可用 common,也可用 user 路径(本地路径) - -## 1. 总体架构 - -### 1.1 组件关系 - -v3.8 在现有“训练平台”之上新增一个 **Serving 子系统**: - -- **API server(现有)** - - 新增 Serving API(模型部署/删除/扩缩容/状态) - - 新增 Serving 后台线程(reconciler):周期性对齐 DB 与 Ray Serve 实际状态 -- **SQLite(现有)** - - 新增 `serve_models`、`serve_events` 等表,保存声明式配置与状态 -- **Ray 集群(现有 stateless pool)** - - 复用现有 head/worker 容器 - - 在集群内启动 Ray Serve(controller + proxy + deployments) -- **Ray Serve LLM(新增)** - - 通过 `ray.serve.llm.build_openai_app` 构建一个 OpenAI-compatible app - - app 内包含多个 `LLMConfig`(每个对应一个模型) - -### 1.2 为什么选择“单个 multi-model application” - -Ray Serve 支持 multi-app,但在 dev/docker 场景下多个 app 的 route_prefix 管理更复杂;同时 requirements 要求“多模型 application 部署”,因此 v3.8 采用: - -- 一个固定的 app:`argus_llm_app`(名字可配置) -- route_prefix 固定为 `/`(对外暴露 `/v1/...` OpenAI 接口) -- 每个模型对应一个 `LLMConfig`,通过 `model_id` 区分(即 OpenAI API 里的 `model` 字段) - -这样对用户而言最直观: - -- base_url 固定:`http://:8000/v1` -- `model=` 选择不同模型(`/v1/models` 自动列出) - -## 2. Ray Serve 部署策略(dev/h1 约束) - -### 2.1 HTTP 入口端口与 docker compose - -Ray Serve 默认 HTTP 端口是 `8000`。v3.8 约定: - -- 在 **head 容器** 映射 `8000:8000` -- API server 仍在 `8080` -- Ray Dashboard 在 `8265` - -原因:在单机多容器 docker 环境里,如果让 proxy “每个节点都起”,会出现多个容器同时想绑定同一个 host 端口的问题(不可行)。因此 v3.8 推荐: - -- Serve proxy 位置设为 **HeadOnly**(只在 head 上提供 HTTP 入口) -- GPU replica 仍运行在 worker 上(proxy 只转发,不跑推理) - -> 需要注意: -> - Serve 的 HTTP 配置(host/port/proxy_location)是 **Ray 集群全局配置**,启动后无法动态修改,因此应当在平台启动时一次性设定并持久化。 -> - proxy Actor 需要 CPU 资源;head 节点的 `num-cpus=0` 策略可能需要在 v3.8 做小幅调整(例如给 head 保留少量 CPU),但仍通过 `entrypoint_resources` 确保训练 driver 不会被调度到 head。 - -#### 2.1.1 compose 预期改动(v3.8 实现时落地) - -- `src/mvp/docker-compose.yaml`(ray_head)新增: - - `ports: - "8000:8000"` - -> worker 容器不暴露 8000(避免 host 端口冲突),由 head proxy 统一对外提供入口。 - -### 2.2 启动/配置方式(Python SDK 优先) - -v3.8 采用 Ray Serve Python SDK: - -- `ray.init(address="auto")` -- `serve.start(proxy_location="HeadOnly", http_options={"host":"0.0.0.0","port":8000})`(一次性全局配置) -- `serve.run(app, name=, route_prefix="/")` -- `serve.delete(name=)`(必要时) -- `serve.status()` 查询集群/应用状态 - -理由: - -- 避免在平台内部引入额外 REST client 依赖(并减少跨版本 REST schema 不稳定风险) -- API server 本身运行在 head 容器内,可直接 `ray.init(address="auto")` 连接现有集群 - -> 另:Ray Dashboard 暴露 Serve REST API(`PUT /api/serve/applications/` 等)可作为备选方案,但 v3.8 先不以它为主通路。 - -### 2.3 依赖与镜像假设 - -v3.8 依赖: - -- `ray[serve]`(Serve Controller/Proxy) -- `ray[llm]`(Ray Serve LLM 的 `ray.serve.llm` 模块) -- vLLM(推理引擎) - -由于 v3.7 已切换到 `verlai/verl:vllm011.latest`,预期镜像内包含 vLLM;但 `ray.serve.llm` 是否开箱即用需要在实现阶段确认。 -若缺失,v3.8 将在 `argus-ray-node` 镜像构建阶段补充 `pip install "ray[serve,llm]"`(或按官方建议的最小依赖)并做版本锁定。 - -### 2.4 Serving 配置(dev.yaml) - -v3.8 新增一段 serving 配置,至少包含: - -```yaml -serving: - serve: - http_port: 8000 # 固定 8000 - proxy_location: HeadOnly # dev/docker 下推荐 - llm: - accelerator_type: H20 # dev 环境填写 H20(对应 ray.serve.llm.LLMConfig.accelerator_type) -``` - -说明: -- `accelerator_type` 是 Ray Serve LLM 的 `LLMConfig.accelerator_type` 字段,用于表达“该模型运行在哪类加速卡上”。在 dev/h1 环境我们固定为 `H20`。 -- v3.8 不把 `accelerator_type` 暴露给普通用户编辑(避免误配);由部署环境配置统一决定。 - -## 3. 模型配置与资源映射 - -### 3.1 关键配置对象:`ray.serve.llm.LLMConfig` - -每个模型部署由一个 `LLMConfig` 描述,关键字段(v3.8 用到的子集): - -- `model_loading_config` - - `model_id`: 对外展示/请求时用的模型名(唯一 key) - - `model_source`: HF repo id / S3 / **local path** -- `accelerator_type` - - 从 `dev.yaml` 的 `serving.llm.accelerator_type` 读取(dev/h1: `H20`) -- `deployment_config` - - `num_replicas` 或 `autoscaling_config`(v3.8 先用固定 `num_replicas`) - - `ray_actor_options`(CPU/资源约束) -- `engine_kwargs` - - vLLM 相关参数(`max_model_len`、`gpu_memory_utilization` 等) -- `placement_group_config` - - 控制 vLLM engine workers 使用的资源 bundle(用于多 GPU / 跨节点) -- `runtime_env` - - 注入 HF cache、离线开关等环境变量 - -### 3.2 GPU 张数(gpus_per_replica)如何落到 LLMConfig - -v3.8 把用户输入的: - -- `gpus_per_replica = N` - -映射为: - -- `engine_kwargs.tensor_parallel_size = N`(单机/跨机张量并行,Ray Serve LLM 官方示例写法) -- `placement_group_config = {"bundles": [{"GPU": 1, "CPU": }] * N, "strategy": "PACK"}` - -并在 `engine_kwargs` 中保留 vLLM 其他参数(`max_model_len`、`gpu_memory_utilization` 等)。 - -> 兼容性说明:Ray Serve LLM/Serve LLM 仍处于快速演进阶段;v3.8 会以我们线上实际 Ray 版本为准做最小适配与回归测试。 - -### 3.2.1 跨节点场景(N > 单机 GPU) - -Ray Serve LLM 默认使用 `PACK` 策略,优先把 GPU worker 放在尽量少的节点上;如果单机放不下,会自动 spill 到其它节点,从而支持跨节点张量并行(TP)部署。 - -### 3.3 replica 数(num_replicas) - -v3.8 默认: - -- `num_replicas = 1` - -允许用户在 UI 中设置为 `>=1`。 -多 replica 会线性消耗 GPU(`num_replicas * gpus_per_replica`),需要做资源预检查。 - -### 3.4 模型路径与宏替换(common / user) - -v3.8 支持两类模型来源: - -1) **common** -- 典型为 `/private/hf/...`(共享 HF cache / snapshot) - -2) **user** -- `/private/users//models/...` -- 以及用户训练输出(例如 `jobs//checkpoints/.../huggingface`) - -为保证 UI 易用,沿用平台已有的宏语义: - -- `$HOME` → `/private/users/` -- `$HOME/common/hf` → `/private/hf` - -并进行路径校验: - -- 允许前缀:`/private/hf`、`/private/users//` -- 拒绝:越权访问其他用户目录、或访问系统敏感路径 - -### 3.5 离线模式(避免 HF mirror 429) - -v3.7 训练侧已验证 `HF_HUB_OFFLINE=1` 的必要性。v3.8 Serving 侧同样默认注入: - -- `HF_HOME=/private/hf` -- `HUGGINGFACE_HUB_CACHE=/private/hf/hub` -- `TRANSFORMERS_CACHE=/private/hf/transformers` -- `HF_HUB_OFFLINE=1` -- `HF_ENDPOINT=https://hf-mirror.com`(可保留,但离线模式下不应触发网络) - -并建议用户在 ServingSpec 中尽量填写 **local path** 作为 `model_source`,而不是直接 repo id。 - -## 4. 平台数据模型(SQLite) - -新增两张主表: - -### 4.1 `serve_models` - -每一行代表一个“声明式模型部署”: - -- `model_key`(平台内部唯一 ID,便于重命名/去重) -- `user_id` -- `model_id`(对外 OpenAI model 名称,要求 per-app 唯一) -- `model_source`(本地路径或 repo id,存 resolved 后的结果) -- `num_replicas` -- `gpus_per_replica` -- `engine_kwargs_json`(可选) -- `state`:`QUEUED | DEPLOYING | RUNNING | FAILED | DELETING | DELETED` -- `serve_app_name`(默认 `argus_llm_app`) -- `created_at / updated_at` -- `error_summary` - -### 4.2 `serve_events` - -记录关键事件与排障信息(类似 task_events): - -- `id` -- `model_key` -- `event_type`(DEPLOY_REQUESTED/DEPLOY_APPLIED/STATUS_SYNC/DELETE_REQUESTED/...) -- `payload_json` -- `created_at` - -## 5. API 设计(新增) - -在现有 `Authorization: Bearer ` 的认证体系下,新增 Serving API(路径仅示意,具体在实现时与现有 `api/v2` 对齐)。 - -### 5.1 用户接口 - -- `POST /api/v2/serve/models` - - body: YAML 或 JSON(v3.8 先用 YAML 与现有 TaskSpec 一致) - - 创建/更新(upsert)一个模型配置,进入 `QUEUED` -- `GET /api/v2/serve/models` - - 列出当前用户的模型列表(含 state、资源、endpoint) -- `GET /api/v2/serve/models/{model_key}` - - 详情:完整 spec + 最近事件 + Serve status 摘要 -- `PATCH /api/v2/serve/models/{model_key}` - - 修改 `num_replicas`、或 engine_kwargs(可选) -- `DELETE /api/v2/serve/models/{model_key}` - - 下线模型(进入 `DELETING`) - -### 5.2 系统接口(admin) - -- `GET /api/v2/serve/status`(admin) - - 返回 `serve.status()` 的摘要(集群级 / app 级) - -### 5.3 对外推理 endpoint - -固定输出到 UI/接口中: - -- `openai_base_url = http://:8000/v1` -- 支持: - - `/v1/chat/completions` - - `/v1/completions` - - `/v1/embeddings` - - `/v1/models` - -> v3.8 不做额外网关与鉴权(保持与现有 dev 环境一致);若后续需要,可在 v3.9+ 引入 token 校验/反向代理。 - -### 5.4 `model_id` 前缀策略(user_id-) - -为避免多用户冲突并保持可读性: - -v3.8 采用“**user_id + 日期小时分钟**”作为稳定前缀,以降低冲突并便于快速定位创建时间: - -- 用户在 UI/API 中仅填写 `model_id_suffix`(或仍用字段名 `model_id`,但语义为 suffix) -- 平台计算实际对外 `model_id`: - - `prefix = f"{user_id}-{YYYYMMDDHHMM}"` - - `model_id = f"{prefix}-{model_id_suffix}"` -- 在列表/详情中同时展示: - - `model_id_suffix`(用户输入) - - `model_id_prefix`(平台生成,例如 `alice-202601061235`) - - `model_id`(对外 OpenAI 名称) - -## 6. 后台执行模型(Serving Reconciler) - -v3.8 参考任务 scheduler 的模式,引入一个轻量的 reconciler: - -- tick 周期(例如 5s) -- 每次 tick: - 1) 拉取 DB 中 `QUEUED/DEPLOYING/RUNNING/DELETING` 的模型 - 2) 调用 `serve.status()` 读取当前 app 及 deployments 状态 - 3) 若存在 `QUEUED` 或需要变更的模型:构建新的 multi-model app(包含全部 `RUNNING/DEPLOYING/QUEUED` 的模型配置)并 `serve.run(...)` - 4) 若存在 `DELETING`:从 app 配置中移除对应模型,并 `serve.run(...)` 应用变更 - 5) 更新每个模型的 state(依据 Serve status) - -重要行为说明(multi-model app 的代价): -- 每次“新增/删除/改 replicas”都会触发对同一个 app 的一次 `serve.run(...)` 更新; -- Ray Serve 会尽量做增量更新,但在某些版本/配置下可能导致 ingress/router 短暂重启; -- v3.8 先接受该代价(满足需求闭环优先);若后续需要“删除某模型不影响其它模型”,可演进为“每模型一个 app + 单独 route_prefix”的方案。 - -资源预检查: -- 在 apply 前使用 `ray.available_resources()` 做粗粒度 GPU 预检查: - - 需要 GPU 总量 = `sum(num_replicas * gpus_per_replica)`(仅对“新增/扩容的差量”更精确) -- 若不足: - - 模型保持 `QUEUED`,记录事件 `PENDING_RESOURCES` - - 用户 UI 显示“资源不足,等待释放” - -> v3.8 不引入更复杂的抢占/优先级。Serving 与 Training 会竞争 GPU;用户需要自行规划资源(或后续版本引入统一调度)。 - -## 7. WebUI 设计(新增 Serving 页面) - -新增侧边栏入口:**Serving** - -### 7.1 Serving 列表页 - -- 展示字段: - - model_id - - user_id(仅 admin 可见) - - replicas / gpus_per_replica / total_gpus - - state(RUNNING/DEPLOYING/QUEUED/FAILED) - - 操作:Scale(修改 replicas)、Delete - -### 7.2 Serving 创建/编辑页 - -两种模式(与 New Task 类似,先做 YAML 模式即可): - -示例 YAML(v3.8): - -```yaml -model_id: qwen-0.5b -model_source: $HOME/common/hf/hub/models--Qwen--Qwen2.5-0.5B-Instruct/snapshots/ -num_replicas: 1 -gpus_per_replica: 1 -# engine_kwargs: -# max_model_len: 8192 -# gpu_memory_utilization: 0.9 -``` - -### 7.3 Serving 详情页 - -- 完整配置(resolved spec) -- Serve status 摘要(deployments 状态、replica 健康) -- OpenAI 调用示例(python openai client) - -## 8. 验收标准(v3.8) - -1) 部署: -- 一键部署一个模型(1 replica、1 GPU)成功,状态变为 RUNNING -- `/v1/models` 可列出该模型 - -2) 扩缩容: -- 修改 `num_replicas` 生效(Serve status 看到副本数变化) - -3) 多模型: -- 同一个 app 内能同时部署 2 个模型(不同 model_id) -- 通过 OpenAI 接口用不同 `model=` 请求可得到响应 - -4) 下线: -- 删除某模型后 `/v1/models` 不再出现 - -5) 模型路径: -- 支持 `/private/hf/...`(common)与 `/private/users//...`(user)两类本地路径 - -6) 资源不足可解释: -- 当 GPU 不足时,模型进入 `QUEUED` 并在 UI/详情中提示“资源不足” - -## 9. 待确认点(请你评审时确认) - -已确认(来自评审): - -1) 推理端口固定使用 `8000`(Ray Serve 默认端口)。 -2) 对外暴露的 OpenAI 接口 **不与现有 token 体系绑定**(v3.8 不做推理侧鉴权)。 -3) `model_id` 命名规则:平台统一加 `user_id + 日期小时分钟` 前缀,用户在 UI 里只填写后缀部分。 - -> 说明:这样可以避免跨用户 model_id 冲突,同时在 OpenAI API 的 `model=` 字段上自然可读。 diff --git a/specs/mvp/v3.8/v3.8_dev_plan.md b/specs/mvp/v3.8/v3.8_dev_plan.md deleted file mode 100644 index 49950f9..0000000 --- a/specs/mvp/v3.8/v3.8_dev_plan.md +++ /dev/null @@ -1,266 +0,0 @@ -# MVP v3.8 开发计划(TDD,细化版) - -> 目标:在 v3.7 基础上引入 Ray Serve(vLLM)模型动态部署与管理(多模型单 app),并提供 WebUI + API 管理闭环。 -> 约束(已确认): -> - 推理端口固定 `8000`(Serve HTTP)。 -> - 推理侧不接入现有 token 鉴权(对外 OpenAI endpoint 无鉴权)。 -> - 对外 `model_id` 统一加前缀:`--`(用户只填 suffix)。 -> - `LLMConfig.accelerator_type` 从 `dev.yaml` 读取(dev/h1: `H20`)。 - -本计划按“测试先行 → 实现 → 回归”的节奏拆分到可验证粒度;每个 milestone 都能单独验收。 - ---- - -## M0 - 基线与依赖探测(不改行为) - -**目的**:确认 v3.7 baseline 稳定,并明确 Ray Serve LLM 依赖是否已具备(否则后续会卡在镜像/依赖)。 - -### M0.1 本地回归 -- [ ] `.venv/bin/python -m pytest` 通过(coverage ≥ 90%) - -### M0.2 远端回归(h1) -- [ ] `src/mvp/scripts/run_all_v30_api.sh` 可跑通(确认训练闭环未回退) - -### M0.3 head 容器内依赖探测(记录结论) -- [ ] `python3 -c "import ray; import ray.serve; print(ray.__version__)"` -- [ ] `python3 -c "from ray.serve.llm import LLMConfig, build_openai_app; print('serve_llm_ok')"` -- [ ] 若失败(例如缺 `gymnasium`):记录缺失项,并在 M6 通过补齐 `ray[llm]` 解决 - -### M0.4 配置探测 -- [ ] `configs/dev.yaml` 中存在: - - `serving.llm.accelerator_type: H20` - - `serving.serve.http_port: 8000` - - `serving.serve.proxy_location: HeadOnly` - -**验收**: -- baseline 无回退;依赖探测结论明确(可用/不可用) - ---- - -## M1 - ServingSpec(解析/校验/宏替换/路径校验)(单测驱动) - -**目的**:先把“输入”这层彻底固化(API/UI 复用),避免后期反复改 schema。 - -### M1.1 新增/扩展数据模型 -- [ ] `ServingSpec`(输入) - - `model_id`(suffix) - - `model_source`(支持 `$HOME` 宏) - - `num_replicas`(default=1) - - `gpus_per_replica`(default=1) - - `engine_kwargs`(可选 dict,先原样存 DB;实现阶段再做白名单/黑名单) -- [ ] `ResolvedServingSpec`(内部) - - `model_id_suffix` - - `model_id_prefix`(由平台生成:`user_id-YYYYMMDDHHMM`) - - `model_id`(对外:`-`) - - `model_source`(resolved path) - -### M1.2 规则(写成纯函数,便于测) -- [ ] `validate_model_id_suffix(suffix)`:长度/字符集限制(建议:`[a-zA-Z0-9][a-zA-Z0-9._-]{0,63}`) -- [ ] `$HOME` 宏替换:`$HOME`、`$HOME/common/hf`、`$HOME/common/datasets` -- [ ] 路径校验(强制本地路径): - - 允许:`/private/hf/...`、`/private/users//...` - - 拒绝:`..`、空、其它用户路径、非 `/private` 路径 -- [ ] `make_model_id_prefix(user_id, now_utc)`:`YYYYMMDDHHMM`(UTC)+ user_id - -### M1.3 单测(先写失败用例,再补实现) -- [ ] `test_serving_spec_validation.py` - - suffix 合法/非法 - - replicas/gpus 边界:0、负数、小数、超大值(按实现决定是否限制上限) -- [ ] `test_serving_spec_paths.py` - - `$HOME` 替换正确 - - 越权路径返回 403/ValueError(按接口层映射) - - `/private/hf` 与 `/private/users/` 均可 -- [ ] `test_serving_model_id_prefix.py` - - 固定时间输入 → prefix 输出一致(避免时区/格式问题) - -**验收**: -- 输入 spec 规则稳定;核心校验/替换均有单测覆盖 - ---- - -## M2 - SQLite 表结构与 Db 接口(单测驱动) - -**目的**:Serving 的声明式状态必须持久化,可审计、可恢复。 - -### M2.1 DB schema -- [ ] `serve_models` - - 主键:`model_key`(平台生成) - - unique:`(user_id, model_id_suffix)`(实现 upsert) - - 存储:resolved spec(包含 prefix/full model_id、resolved model_source) - - 状态:`QUEUED/DEPLOYING/RUNNING/FAILED/DELETING/DELETED` - - `error_summary` -- [ ] `serve_events`(append-only) - -### M2.2 Db 方法 -- [ ] `upsert_serve_model(user_id, spec_yaml, now)` → (model_key, state) -- [ ] `list_serve_models(user_id, include_deleted=False, limit/offset?)` -- [ ] `get_serve_model(model_key)` -- [ ] `set_serve_model_state(model_key, state, error_summary=None)` -- [ ] `append_serve_event(model_key, event_type, payload_json=None)` -- [ ] `pick_next_runnable_serve_change()`(给 reconciler 用) - -### M2.3 单测 -- [ ] `test_db_serving.py` - - upsert 行为(同 suffix 更新不产生新 model_key 或产生新版本——此处需在实现前明确策略) - - state 流转 + 事件记录 - - list 的过滤与排序(按 updated_at) - -**验收**: -- DB 行为可预测;upsert/unique 语义确定并测试覆盖 - ---- - -## M3 - Serving 管理 API(FastAPI)(单测驱动) - -**目的**:先把管理 API 跑通,Ray Serve 先不接真实(reconciler 之后再接)。 - -### M3.1 API 路由(用户) -- [ ] `POST /api/v2/serve/models`(Content-Type: application/yaml) - - 入参:ServingSpec YAML - - 出参:`{model_key,state}`(202) -- [ ] `GET /api/v2/serve/models` - - 返回 items + `openai_base_url=http://:8000/v1` -- [ ] `GET /api/v2/serve/models/{model_key}` - - 返回 model + resolved_spec_yaml + events(分页可后置)+ serve_status(先空/占位) -- [ ] `PATCH /api/v2/serve/models/{model_key}`(JSON) - - 支持 `num_replicas`(最小闭环) -- [ ] `DELETE /api/v2/serve/models/{model_key}` - -### M3.2 API 路由(admin,可选) -- [ ] `GET /api/v2/serve/status`(仅 admin token) - -### M3.3 错误映射(必须测试) -- [ ] YAML 解析失败:400 -- [ ] spec 校验失败:422 -- [ ] 越权路径:403 -- [ ] 不存在 model_key:404 - -### M3.4 单测 -- [ ] `test_app_serving_api.py` - - happy path:create → list → get → patch → delete - - 多用户隔离:用户只能看到自己的 model - - 错误码覆盖:400/403/404/422 - -**验收**: -- API reference (`v3.8_api.md`) 中所有管理接口可返回预期结构(Serve 未接入也能工作) - ---- - -## M4 - ServeClient 抽象 + LLMConfig builder(单测驱动) - -**目的**:将“如何从 ResolvedServingSpec 构造 LLMConfig”固化,并把 Ray Serve 的依赖隔离到 client 里,便于 mock。 - -### M4.1 `ServeClient` 接口(可 mock) -- [ ] `ensure_started(http_port=8000, proxy_location="HeadOnly")` -- [ ] `apply_app(app_name, llm_configs)`(multi-model) -- [ ] `get_status()`(serve.status 摘要) - -### M4.2 `build_llm_config(resolved_spec, accelerator_type, runtime_env_defaults)` 纯函数 -- [ ] 写入 `LLMConfig.accelerator_type`(来自 dev.yaml:H20) -- [ ] `deployment_config.num_replicas` -- [ ] `engine_kwargs.tensor_parallel_size = gpus_per_replica` -- [ ] `placement_group_config` bundles 按 GPU 张数生成 -- [ ] `runtime_env.env_vars` 注入(至少包含 HF cache + `HF_HUB_OFFLINE=1`) - -### M4.3 单测 -- [ ] `test_llm_config_builder.py` - - gpus_per_replica=1/2/4 → tensor_parallel_size 与 bundles 数量正确 - - accelerator_type 注入正确 - - runtime_env 含 HF_HUB_OFFLINE 等关键 env - -**验收**: -- 从平台 spec 到 Ray Serve LLMConfig 的映射规则稳定,有单测锁定 - ---- - -## M5 - Serving Reconciler(状态机 + 资源预检查)(单测驱动) - -**目的**:实现声明式对齐:DB → Serve;同时提供可解释的 QUEUED/FAILED 状态。 - -### M5.1 状态机(最小闭环) -- [ ] `QUEUED`:等待 apply -- [ ] `DEPLOYING`:已触发 apply,等待 Serve running/healthy -- [ ] `RUNNING`:Serve status running -- [ ] `FAILED`:apply 或 status 失败(写 error_summary + event) -- [ ] `DELETING`:等待从 app 中移除 -- [ ] `DELETED`:完成删除(可选保留记录) - -### M5.2 资源预检查 -- [ ] `needed_total_gpus = sum(num_replicas*gpus_per_replica)`(最小可用预检查) -- [ ] `ray.available_resources()["GPU"]`(或更稳健的 per-node 统计)不足时: - - 保持 `QUEUED` - - 记录 `PENDING_RESOURCES` event - -### M5.3 reconcile 策略(multi-model app) -- [ ] tick 读取 active models,构建全量 `llm_configs` -- [ ] 处理 deleting:从 configs 中移除对应 model,再 apply - -### M5.4 单测(mock ServeClient + mock ray resources) -- [ ] `test_serving_reconciler.py` - - 新增模型:apply_app 被调用;state 进入 DEPLOYING - - 删除模型:apply_app configs 不包含该模型 - - GPU 不足:不 apply;state 仍 QUEUED;event 写入 - - apply 抛异常:state FAILED;error_summary 写入 - -**验收**: -- reconciler 行为在纯单测环境可验证;失败可解释 - ---- - -## M6 - 真实集成(h1):Ray Serve 启动 + 推理闭环(E2E) - -**目的**:在 dev/h1 环境真正跑通:部署模型 → `/v1/models` 可见 → `chat/completions` 成功 → 删除后消失。 - -### M6.1 compose/端口 -- [ ] `src/mvp/docker-compose.yaml`:`ray_head` 增加 `8000:8000` - -### M6.2 镜像依赖(若 M0 发现缺失) -- [ ] 在 `argus-ray-node` 镜像中补齐 `ray[serve,llm]`(版本与现有 Ray 对齐,避免升级 Ray 导致不兼容) - - 推荐优先补齐 `ray[llm]`(包含 `ray.serve.llm` 依赖闭包,如 `gymnasium`),再按需补 `ray[serve]` - - 验证点:`python3 -c "from ray.serve.llm import LLMConfig, build_openai_app; print('serve_llm_ok')"` - -### M6.3 E2E 脚本(幂等) -- [ ] 新增 `scripts/run_all_v38_serving.sh`: - - 起 compose(确保 Serve 端口可用) - - 起 API - - 创建 user + token - - `POST /api/v2/serve/models` 创建 1GPU 模型 - - 轮询模型 state 到 RUNNING - - `curl http://127.0.0.1:8000/v1/models` 验证包含 `-` - - `curl http://127.0.0.1:8000/v1/chat/completions` 进行最小推理 - - `DELETE /api/v2/serve/models/{model_key}` 下线 - - 再轮询 `/v1/models` 不包含 - -**验收**: -- E2E 可重复跑通(至少两次连续跑不需要人工清理) - ---- - -## M7 - WebUI(Serving 页面)(单测驱动) - -**目的**:给用户可视化的模型管理页面(最小必要功能)。 - -### M7.1 页面 -- [ ] Sidebar 增加 Serving -- [ ] `/ui/serving`:列表 + 状态 + 操作(delete/scale) -- [ ] `/ui/serving/new`:YAML 输入 + submit -- [ ] `/ui/serving/{model_key}`:详情(resolved spec、events、OpenAI 调用示例) - -### M7.2 单测 -- [ ] `test_ui_serving.py`:路由 200、关键链接存在、包含 openai_base_url=8000 - -**验收**: -- WebUI 覆盖 create/list/detail/scale/delete 的主链路 - ---- - -## M8 - 文档与验收用例(交付) - -**目的**:给用户/运维一套可复用的运行方式与排障路径。 - -- [ ] 更新 `specs/mvp/v3.8/v3.8_progress.md`(按 milestone 记录) -- [ ] 补充 README(可选):端口说明、推理 API 无鉴权警示、模型路径约定 -- [ ] 验收清单(checklist): - - 单测通过 - - h1 E2E 通过 - - UI 主链路可操作 diff --git a/specs/mvp/v3.8/v3.8_per_model_app.md b/specs/mvp/v3.8/v3.8_per_model_app.md deleted file mode 100644 index fec725f..0000000 --- a/specs/mvp/v3.8/v3.8_per_model_app.md +++ /dev/null @@ -1,189 +0,0 @@ -# v3.8 方案补充:每个模型一个 Ray Serve App(隔离增删影响) - -## 背景与问题复现 - -当前 v3.8 的实现采用 **单 application + 多模型** 的方式: - -- 服务层每次 reconcile 都会构造“全量 llm_configs”并调用一次 `serve.run(app, name="argus_llm_app", route_prefix="/")` -- **新增/删除一个模型**会触发对同一个 app 的“整体更新” -- Ray Serve 在 app 更新时会对该 app 内的 deployments/replicas 做滚动更新与重新调度 - -因此你在 Ray Dashboard 中观察到: - -- 添加/删除一个模型时,其他模型的 Serve deployment 也进入更新状态 -- 内存/显存占用重新变化,甚至出现 GPU 卡位变化(replica 重新调度到不同 node/GPU) - -这与“其他未变更 model 不受影响”的期望不一致。 - ---- - -## 目标 - -将 serving 架构调整为: - -- **每个模型一个 Serve App(独立 app name)** -- 每个模型一个独立 `route_prefix` -- 新增/删除/缩放某个模型只更新该模型对应的 app,不影响其他模型 app - -约束保持不变: - -- 推理端口固定 `8000` -- 推理侧不接入现有 token 鉴权(OpenAI endpoint 无鉴权) -- `model_id` 前缀规则:`--` -- `LLMConfig.accelerator_type` 由 `configs/dev.yaml` 配置(dev/h1: `H20`) - ---- - -## 总体设计 - -### 1) 命名与路由 - -为每个 model 生成: - -- `app_name`:建议直接使用 `model_key`(天然唯一且 URL-safe),例如: - - `app_name = "mvp2-alice-serve-20260106-060203-aad8"` -- `route_prefix`:建议使用 model_key,避免 model_id 中的 `.`、`_` 等带来的 URL/编码歧义: - - `route_prefix = f"/serve/{model_key}"` - -于是该模型的 OpenAI base url 为: - -- `openai_base_url = http://:8000/serve//v1` - -说明: - -- 仍然是 **OpenAI-compatible**,只是 base_url 不再是根路径 `/v1`,而是每个模型一个前缀。 -- 这样可以做到“每个模型的 OpenAI endpoint 互不影响”,也更容易做按模型的观测/下线。 - -### 2) 运行方式(Ray Serve) - -单模型 app 的创建/更新: - -- `app = build_openai_app({"llm_configs":[LLMConfig(...)]})` -- `serve.run(app, name=app_name, route_prefix=route_prefix)` - -单模型 app 的删除: - -- `serve.delete(app_name)` - -关键点: - -- **更新/删除只作用于对应 app_name**;其它 app 不会被 serve.run “整体重建”触发滚动更新。 - -### 3) 服务层(Scheduler/Reconciler)改造点(高层) - -现状:`ServingReconciler.tick()` 每次对“全量模型集合” apply 一次 app。 - -目标:改成按 model_key 的“局部 reconcile”: - -- 对于状态 `QUEUED` 的 model: - - 只构建该 model 的 `LLMConfig` - - `serve.run(app, name=model_key, route_prefix="/serve/")` - - 状态:`DEPLOYING` →(probe 成功)→ `RUNNING` -- 对于状态 `DELETING` 的 model: - - `serve.delete(model_key)` - - 状态:`DELETED` - -资源预检查: - -- 只需要预检查“本次变更模型”需要的 GPU(`num_replicas * gpus_per_replica`) -- 不需要把其他模型资源都算入 needed_total_gpus(因为不再重建全量 app) - -### 4) API/UI 返回的 endpoint 结构 - -现状 API 返回: - -- `endpoint.openai_base_url = http://:8000/v1` -- `endpoint.model = ` - -建议改为(字段不变,值变化): - -- `endpoint.openai_base_url = http://:8000/serve//v1` -- `endpoint.model = `(保持) - -UI 的示例 curl 也应使用上面的 base_url。 - ---- - -## 行为变化与兼容性影响 - -### 1) `/v1/models` 聚合能力变化(重要) - -采用“每模型一个 route_prefix”后: - -- `http://:8000/v1/models` **不再是“所有模型的总览”**(除非我们再提供一个聚合层) -- 每个模型的 models list 在它自己的前缀下: - - `http://:8000/serve//v1/models` - -如果仍然希望保留一个统一入口(可选增强,非本方案必做): - -- 额外引入一个“稳定不重建”的 **OpenAI Router**(可以是: - - FastAPI(8080) 侧做反向代理;或 - - 一个单独 Ray Serve app 只负责路由,不随模型变更重建) -- Router 读取 SQLite/内存缓存的 model 映射: - - `model_id -> route_prefix` -- 将 `/v1/chat/completions` 转发到对应 model 的 prefix - -这可以作为 v3.9+ 的增强项;v3.8 的核心目标是“变更隔离”,优先保证稳定性。 - -### 2) 资源与调度稳定性 - -改为 per-app 后: - -- 新增模型 B 不再引起模型 A 的 replica 重新调度 → **A 的 GPU/内存占用更稳定** -- 删除模型 B 也不会触发 A 的滚动更新 - -但仍需注意: - -- 如果 Ray 集群发生节点故障/资源回收,Serve 本身仍可能重启个别 replica(这是系统层行为) - ---- - -## 验证与验收流程(建议) - -### A. 功能验收(API/UI) - -1. 通过 UI/或 API 创建模型 A,等待 RUNNING -2. 记录 A 的: - - `model_key_A` - - `endpoint.openai_base_url_A` -3. 再创建模型 B,等待 RUNNING -4. 确认: - - A 的 endpoint 仍可用(对 A 的 base_url 发 chat completion) - - B 的 endpoint 可用 -5. 删除模型 B,确认: - - B endpoint 404/不可用 - - A endpoint 仍可用 - -### B. “不影响其它模型”的强验证(Ray actor 级别) - -在 Ray 上抓取 A 对应 `LLMServer` replica 的 actor_id/node_id: - -- 创建 B 前:`actor_id_A_before` -- 创建 B 后:`actor_id_A_after` -- 删除 B 后:`actor_id_A_after_delete` - -预期: - -- `actor_id_A_before == actor_id_A_after == actor_id_A_after_delete` - -(允许 `LLMRouter` 变化,但 **LLMServer for A 不应变化**) - ---- - -## 需要修改的代码点(清单级) - -> 这里只列“改哪里”,不展开具体实现(实现时按 TDD 补单测)。 - -- `argus.service.serving_reconciler`: - - 从“全量 apply 单 app”改为“按 model_key 局部 apply/delete 单 app” - - GPU 预检查改为 per-model -- `argus.service.serve_client`: - - 增加 `delete_app(app_name)`(封装 `serve.delete(app_name)`) - - `apply_app` 传入 `app_name/route_prefix`(已存在,但将不再传固定 app_name) -- `argus.service.app`(Serving API 输出): - - `_serve_model_public().endpoint.openai_base_url` 改为 per-model 前缀 - - `/api/v2/serve/models` list/get 的 openai_base_url 语义调整(可返回“该模型的 base_url”,列表里每条都有) -- `argus.service.ui`(Serving 页面): - - “OpenAI /v1/models” 需要调整为“选择某个模型后打开该模型的 /v1/models” - - 详情页 curl 示例使用 per-model base_url - diff --git a/specs/mvp/v3.8/v3.8_per_model_app_dev_plan.md b/specs/mvp/v3.8/v3.8_per_model_app_dev_plan.md deleted file mode 100644 index e61b579..0000000 --- a/specs/mvp/v3.8/v3.8_per_model_app_dev_plan.md +++ /dev/null @@ -1,174 +0,0 @@ -# MVP v3.8(变更)开发计划:Per-Model Serve App(TDD) - -> 目标:按 `specs/mvp/v3.8/v3.8_per_model_app.md` 将 v3.8 从“单 app 多模型(全量重建)”改为“**每个模型一个 Ray Serve app + 独立 route_prefix**”,实现增删/缩放某个模型不触发其它模型重启与重调度。 - -## 约束与结论 - -- 推理端口固定:`8000` -- 推理 endpoint **不做鉴权** -- `model_id` 前缀规则:`--` -- `LLMConfig.accelerator_type` 由 `configs/dev.yaml` 决定(dev/h1: `H20`) -- 路由方案(本迭代固定): - - `app_name = model_key` - - `route_prefix = /serve/` - - `openai_base_url = http://:8000/serve//v1` - -## 非目标(明确不做) - -- 不提供统一 `/v1` 的“跨模型聚合路由”(如要,需要额外 router 层;可在后续迭代做) -- 不改 ServingSpec 语义(输入仍为 `model_id/model_source/num_replicas/gpus_per_replica/engine_kwargs`) - ---- - -## M0 - 基线回归与分支保护 - -**目的**:确保切换架构前训练/现有功能不回退。 - -### 测试 -- [ ] 本地:`.venv/bin/python -m pytest` 全绿(coverage ≥ 90%) - -### 验收 -- [ ] 基线可用;进入 M1 - ---- - -## M1 - API 输出与 endpoint 语义调整(单测驱动) - -**目的**:API/DB/前端都统一 per-model 的 `openai_base_url` 语义;避免 UI/脚本继续使用 `/v1` 根路径。 - -### 变更点 -- `GET /api/v2/serve/models`: - - 保持返回 `items[]`,但每个 item 的 `endpoint.openai_base_url` 必须是 per-model base url - - `openai_base_url`(列表层级字段)处理策略二选一: - - A(推荐):移除该字段(breaking,需同步 UI/脚本) - - B(兼容):保留但改为 `null` 或提示字符串(不再保证可用) -- `GET /api/v2/serve/models/{model_key}`: - - `model.endpoint.openai_base_url` 改为 per-model base url - -### 单测(先写) -- [ ] 更新/新增 `src/mvp/py/tests/test_app_serving_api.py` - - 断言 `endpoint.openai_base_url` 包含 `/serve//v1` - - 断言多条 models 的 base_url 不相同(随 model_key 变化) - -### 实现 -- [ ] 更新 `src/mvp/py/argus/service/app.py`: - - `_serve_model_public()` 的 `endpoint.openai_base_url` 拼接 per-model prefix - - 如选择移除/调整 list 层的 `openai_base_url`,同步实现 - -### 验收 -- [ ] API 单测通过;返回结构可被 UI/脚本消费 - ---- - -## M2 - ServeClient 扩展(delete_app)+ Reconciler 改造成 per-model(单测驱动) - -**目的**:核心行为变更:每次 tick 只部署/删除一个模型对应的 app,不重建全量 app。 - -### 变更点(行为) -- `QUEUED`: - - 对该 `model_key` 执行 `serve.run(app, name=model_key, route_prefix=/serve/)` - - 状态:`DEPLOYING → RUNNING` -- `DELETING`: - - 对该 `model_key` 执行 `serve.delete(model_key)` - - 状态:`DELETED` -- 资源预检查从“全量 needed_total_gpus”改为“本次变更模型所需 GPU” - -### 单测(先写) -- [ ] 更新 `src/mvp/py/tests/test_serving_reconciler.py` - - `create A` 后,reconciler 只 `apply_app(app_name=A.model_key, route_prefix=/serve/A)` - - `create B` 后,reconciler 只 `apply_app(app_name=B.model_key, route_prefix=/serve/B)`(不再对 A 触发 apply) - - `delete B` 后,reconciler 只 `delete_app(B.model_key)`(不触发 A) - - GPU 不足时:保持 `QUEUED` 且 event=SERVE_PENDING_RESOURCES - -### 实现 -- [ ] `src/mvp/py/argus/service/serve_client.py` - - 增加 `delete_app(app_name: str)`(封装 `serve.delete`) -- [ ] `src/mvp/py/argus/service/serving_reconciler.py` - - 移除“全量 app apply”逻辑 - - 每个 model_key 独立部署:`app_name=model_key`、`route_prefix=/serve/` - - 删除路径走 `delete_app` - -### 验收 -- [ ] reconciler 单测全绿;逻辑可解释(events/state 正确) - ---- - -## M3 - WebUI Serving 页面适配 per-model base_url(单测驱动) - -**目的**:用户从 UI 复制的示例命令必须可用;不再指向根 `/v1`。 - -### 变更点 -- `/ui/serving` 列表: - - “OpenAI /v1/models”按钮改为: - - A:移除(因为没有聚合 `/v1/models`) - - B:保留但文案改为“OpenAI base 需进入详情页” -- `/ui/serving/{model_key}` 详情页: - - `curl` 示例使用 per-model `openai_base_url` - - 增加一键打开:`/serve//v1/models` - -### 单测(先写) -- [ ] 更新/新增 `src/mvp/py/tests/test_ui_serving.py` - - 断言页面包含 `/serve/` 前缀 - - 断言详情页示例里包含 `/serve//v1/chat/completions` - -### 实现 -- [ ] `src/mvp/py/argus/service/ui.py` 更新 Serving UI - -### 验收 -- [ ] UI 单测全绿;页面内容与 API 语义一致 - ---- - -## M4 - E2E 脚本更新(v3.8 serving) - -**目的**:在 dev/h1 一键验证 per-model app:A/B 增删不互相影响,且推理可用。 - -### 变更点 -- 更新 `src/mvp/scripts/run_all_v38_serving.sh`: - - `/v1/models` 与 `chat/completions` 均改用 per-model base_url(`/serve//v1`) - - 增加“隔离验证”步骤: - - 部署 A → 记录 A 的 serve replica actor_id/node_id - - 部署 B → 再次记录 A 的 actor_id/node_id,必须一致 - - 删除 B → 再次记录 A 的 actor_id/node_id,必须一致 - - 最后删除 A - -### 验收 -- [ ] E2E 脚本能跑通且输出明确断言(一致/不一致) - ---- - -## M5 - h1 端到端验证与回归 - -**目的**:确认实际 Ray Serve 行为满足“其它模型不滚动更新”的核心目标。 - -### 操作 -- [ ] 同步代码到:`argus@h1:/home2/argus/infra/mvp/src/mvp` -- [ ] 重启 API:`scripts/61_stop_api.sh && scripts/60_start_api.sh` -- [ ] 执行:`MVP_INTERNAL_TOKEN=... scripts/run_all_v38_serving.sh` - -### 验收标准(必须满足) -- [ ] 新增/删除 B 时,A 的 `LLMServer` replica actor_id/node_id 不变 -- [ ] A/B 的 OpenAI endpoint 均可完成 `chat/completions` -- [ ] 删除 B 后 A 仍可推理 - ---- - -## M6 - 文档与迁移说明 - -**目的**:明确“路由语义变化”和“如何使用”。 - -- [ ] 更新 `src/mvp/README.md`: - - 新增 per-model base_url 说明(`/serve//v1`) - - 提示不再提供聚合 `/v1/models` -- [ ] 更新 `specs/mvp/v3.8/v3.8_progress.md`: - - 记录 per-model app 变更与验收结论 - ---- - -## 风险与缓解 - -- **风险:旧 `argus_llm_app` 残留** - - 缓解:在 E2E/迁移步骤里增加一次 best-effort `serve.delete("argus_llm_app")`(可选) -- **风险:用户仍按旧方式访问 `/v1`** - - 缓解:UI/文档/脚本统一切换到 per-model base_url,并在列表页给出明显提示 - diff --git a/specs/mvp/v3.8/v3.8_progress.md b/specs/mvp/v3.8/v3.8_progress.md deleted file mode 100644 index 83eae88..0000000 --- a/specs/mvp/v3.8/v3.8_progress.md +++ /dev/null @@ -1,48 +0,0 @@ -# MVP v3.8 进展记录 - -## 2026-01-06 - -- 完成 v3.8 设计文档:`specs/mvp/v3.8/v3.8_design.md` -- 完成 v3.8 Serving API reference:`specs/mvp/v3.8/v3.8_api.md` -- 完成 v3.8 TDD 开发计划:`specs/mvp/v3.8/v3.8_dev_plan.md` -- 完成 M0:`configs/dev.yaml` 增加 `serving` 配置(http_port=8000, proxy_location=HeadOnly, accelerator_type=H20) -- 完成 M1:ServingSpec 解析/宏替换/路径校验 + 单测(`src/mvp/py/argus/service/serving_spec.py`) -- 完成 M2:SQLite 新增 `serve_models`/`serve_events` + Db API + 单测(`src/mvp/py/argus/service/db.py`) -- 完成 M3:FastAPI Serving 管理 API + 单测(`src/mvp/py/argus/service/app.py`) -- 完成 M4:ServeClient 抽象 + LLMConfig builder(dict 形态)+ 单测(`src/mvp/py/argus/service/serve_client.py`、`src/mvp/py/argus/service/serve_llm_config.py`) -- 完成 M5:Serving reconciler(状态机 + 资源预检查 + mock 单测)(`src/mvp/py/argus/service/serving_reconciler.py`) - -### M6(h1 真实集成) - -- `argus-ray-node` 镜像补齐依赖:`ray[serve,llm]` + `gymnasium` + `dm-tree`(避免 `ray.serve.llm` 导入失败) -- 修复 Ray 2.49.2 兼容性问题: - - `LLMConfig` 不支持 `placement_group_config`,改为使用 `resources_per_bundle`(`src/mvp/py/argus/service/serve_llm_config.py`) -- 远端 E2E: - - `scripts/run_all_v38_serving.sh` 可跑通:create → RUNNING → `/v1/models` → `chat/completions` → delete → DELETED - - 修复脚本中 `/v1/models` 解析的 bash heredoc 引号错误(`src/mvp/scripts/run_all_v38_serving.sh`) - -### M7(WebUI - Serving) - -- WebUI 增加 Serving 页面: - - 列表:`/ui/serving` - - 创建:`/ui/serving/new` - - 详情/事件/缩放/删除:`/ui/serving/{model_key}` -- 单测覆盖: - - `src/mvp/py/tests/test_ui_serving.py` - -### M8(文档/验收) - -- `src/mvp/README.md` 补充 v3.8 serving 端口与 E2E 脚本说明 - -### 环境探测(h1 / head 容器) - -> 目的:确认 Ray Serve LLM 依赖是否开箱即用,避免后续集成阶段才暴雷。 - -- `ray`:可用,版本 `2.49.2` -- `ray.serve`:可 import(Serve 基础可用) -- `ray.serve.llm`:当前不可 import - - 报错:`ModuleNotFoundError: No module named 'gymnasium'` - - 原因:`ray.serve.llm` 的导入链路会触发 `ray.rllib`,而 rllib 依赖 `gymnasium` - -结论: -- v3.8 在实现阶段需要在 `argus-ray-node` 镜像中补齐 `ray[llm]`(推荐)或至少补齐 `gymnasium` 等必要依赖,确保 `from ray.serve.llm import ...` 可用。 diff --git a/specs/mvp/v3.9/ui_refactor_plan.md b/specs/mvp/v3.9/ui_refactor_plan.md deleted file mode 100644 index 2dc3522..0000000 --- a/specs/mvp/v3.9/ui_refactor_plan.md +++ /dev/null @@ -1,108 +0,0 @@ -# v3.9 UI 重构方案(保持功能不变) - -## 背景与问题 - -当前 `src/mvp/py/argus/service/ui.py` 单文件约 1400+ 行,包含: - -- 全局 CSS/JS(长字符串) -- 布局渲染(nav/page 拼接) -- 11 个页面的 HTML + 大段内嵌 JS(包含 TaskSpec 模板与表单逻辑) - -导致:变更难定位、合并冲突多、缺少模块边界、复用困难、测试覆盖薄弱。 - -## 目标(功能不变) - -- **路由与页面行为完全不变**:URL、返回内容、按钮/表单行为、localStorage key(`mvp_token`/`mvp_sftp_password`)、API 调用路径保持不变。 -- **不引入前端构建链/新依赖**(仍然用纯字符串/轻量模板函数)。 -- 将 UI 拆分为可维护的多个文件(放到 `src/mvp/py/argus/ui/`)。 -- 增加最小的单测(确保路由可访问、关键 DOM 标识存在)。 - -## 非目标 - -- 不重做 UI 样式/交互;不引入 React/Vue;不改后端 API。 -- 不新增鉴权逻辑(仍然是浏览器 localStorage + Bearer token)。 - -## 拆分后的目录结构(建议) - -新增包:`src/mvp/py/argus/ui/` - -``` -argus/ui/ - __init__.py # register_ui_routes(app) 统一入口 - assets/ - base_css.py # BASE_CSS 常量 - base_js.py # BASE_JS 常量(apiFetch/apiJson 等通用函数) - layout/ - nav.py # nav(active) + 链接配置 - page.py # page(title, active, body, script, extra_head=...) - pages/ - login.py # /ui/login - tasks.py # /ui/tasks - task_new.py # /ui/tasks/new(模板常量 + 表单 JS) - task_detail.py # /ui/tasks/{task_id} - task_logs.py # /ui/tasks/{task_id}/logs - serving.py # /ui/serving, /ui/serving/new, /ui/serving/{model_key} - data.py # /ui/data - admin.py # /ui/admin - routes.py # 将各 pages.register(app) 聚合注册 -``` - -兼容层(可选但推荐):保留 `src/mvp/py/argus/service/ui.py` 仅做转发: - -```py -from argus.ui import register_ui_routes -``` - -这样可以避免一次性改动 `service/app.py` 的 import 路径,减少风险。 - -## 页面拆分原则 - -每个 page 模块提供两个函数: - -- `render(...) -> HTMLResponse`:只负责拼接 body/script(不直接碰 FastAPI app)。 -- `register(app: FastAPI) -> None`:只负责挂载路由(`@app.get(...)`)。 - -通用能力下沉: - -- `_BASE_CSS`/`_BASE_JS` 移到 `assets/`。 -- `_nav()`、`_page()` 移到 `layout/`。 -- 大块常量(TaskSpec 模板、UI 文案)放在页面模块同文件顶部,避免散落在函数内部。 - -## 资源交付方式(两种可选) - -### 方案 A(最稳):继续内联 CSS/JS,但拆到不同 Python 文件 - -- `page()` 内继续 ``、``。 -- 只改变代码组织,不改变浏览器加载方式,风险最低。 - -### 方案 B(推荐中期):新增静态端点分发资源 - -新增: -- `GET /ui/assets/base.css` -- `GET /ui/assets/base.js` - -页面改为 `` + ``。 -优点:减少 HTML 体积、浏览器缓存更好;缺点:需要确认反向代理/中间件不拦截这些路由。 - -建议 v3.9 先落地方案 A,稳定后再做方案 B。 - -## 迁移步骤(建议分 3 次 PR) - -1) **抽公共层**:引入 `argus/ui/assets/*`、`argus/ui/layout/*`,保持 UI 输出完全一致;`service/ui.py` 仍在但内部改为调用新 layout(或先不动)。 -2) **按页面迁移**:逐个把 routes 迁移到 `argus/ui/pages/*`,每迁一个页面就加一个最小测试用例(200 + 关键文本存在)。 -3) **清理与稳定**:`service/ui.py` 变为兼容转发;可选引入 `/ui/assets/*` 静态端点(方案 B)。 - -## 测试策略(最小但有效) - -新增 `src/mvp/py/tests/test_ui_pages.py`: - -- 创建 FastAPI app(复用现有测试的 app 初始化方式) -- 请求下列页面,断言 `status_code == 200`: - - `/ui/login`, `/ui/tasks`, `/ui/tasks/new`, `/ui/serving`, `/ui/data`, `/ui/admin` -- 断言响应包含稳定锚点文本(例如 `Argus MVP`, `New Task`, `Tasks`),避免脆弱的全量快照。 - -## 验收标准(Definition of Done) - -- 11 个 `/ui/*` 路由行为与输出不变(人工 smoke + 自动化最小测试)。 -- `src/mvp/py/argus/service/ui.py` 不再包含大段 HTML/JS(仅兼容转发或极薄封装)。 -- 新增/修改 UI 页面不需要触碰 1000+ 行单文件;每页的改动范围限定在对应模块。 diff --git a/src/mvp/configs/dev_v30.yaml b/src/mvp/configs/dev_v30.yaml deleted file mode 100644 index 8be5b4e..0000000 --- a/src/mvp/configs/dev_v30.yaml +++ /dev/null @@ -1,64 +0,0 @@ -ray: - # Ray Job server address (head 容器内视角) - address: "http://127.0.0.1:8265" - - # 共享根路径(容器内统一 /private,对齐生产) - shared_root: "/private" - - # 强制 driver 落 worker(head 不跑训练) - entrypoint_num_cpus: 1 - entrypoint_resources: - worker_node: 1 - - # 所有 job 通用 runtime env - runtime_env: - env_vars: - HF_ENDPOINT: "https://hf-mirror.com" - PYTHONUNBUFFERED: "1" - # v3.7: forbid HuggingFace Hub network access from Ray jobs (use cached snapshots). - HF_HUB_OFFLINE: "1" - # Unify cache dirs so `from_pretrained("org/name")` resolves from the same on-disk cache in offline mode. - HF_HOME: "/private/hf" - HUGGINGFACE_HUB_CACHE: "/private/hf/hub" - TRANSFORMERS_CACHE: "/private/hf/hub" - - # v3.0 先不支持 user code 执行 - user_code_path: "/private/user/code" - -service: - api: - host: "0.0.0.0" - port: 8080 - auth: - token_env: "MVP_INTERNAL_TOKEN" - sqlite: - db_path: "/private/common/db/mvp.sqlite3" - scheduler: - tick_s: 5 - retry_interval_s: 60 - max_running_tasks: 1 - -tracking: - wandb: - enabled: true - # For dev compose, recommend docker bridge gateway + host published port for stability. - base_url: "http://172.22.0.1:8090" - api_key_env: "WANDB_API_KEY" - project_suffix: "_project" - -data: - user_root: "/private/users" - sftpgo: - enabled: true - # Returned to users by GET /api/v2/me. For h1 E2E, usually connect to the host IP. - host: "127.0.0.1" - sftp_port: 2022 - # Admin API base should include /api/v2 (SFTPGo OpenAPI server base). - # From head container, access SFTPGo by service name on the compose network. - admin_api_base: "http://argus-sftpgo:8080/api/v2" - admin_user: "admin" - admin_password_env: "SFTPGO_ADMIN_PASSWORD" - retention: - jobs_trash_after_days: 3 - jobs_purge_after_days: 7 - janitor_interval_s: 3600 diff --git a/src/mvp/v1/README.md b/src/mvp/v1/README.md deleted file mode 100644 index fd92b0a..0000000 --- a/src/mvp/v1/README.md +++ /dev/null @@ -1,118 +0,0 @@ -# MVP V1(Ray + VERL PPO)实验脚本 - -本目录用于在“宿主机 + Docker 容器”环境下,**用宿主机脚本(`docker exec`)**协调启动 Ray 集群,并通过 **`ray job submit`(在 head 提交)**跑通一次 `verl` 的 PPO 训练闭环(`total_epochs=1`),且数据/模型/日志/ckpt 都持久化到宿主机目录。 - -## 1. 运行环境与拓扑 - -### 1.1 依赖 - -- 宿主机:Linux -- 必需工具:`docker`、`docker compose`(Compose v2 插件)、`git` -- GPU:至少 8 张可用 GPU(索引 `0-7`),Docker 的 NVIDIA runtime 可用 - -### 1.2 集群拓扑(3 个容器) - -- `mvp-ray-head`(Ray Head) - - **不挂 GPU**(容器内 `nvidia-smi` 不可用) - - `ray start --head --num-cpus=0 --num-gpus=0`:head 只做控制面,不参与计算调度 - - 暴露 dashboard:宿主机端口 `8265` -- `mvp-ray-worker-0`(Ray Worker) - - 4 GPU:`0,1,2,3` - - `ray start ... --resources='{"worker_node": 100}'` -- `mvp-ray-worker-1`(Ray Worker) - - 4 GPU:`4,5,6,7` - - `ray start ... --resources='{"worker_node": 100}'` - -**关键点:driver 不在 head** - -- 作业通过 head 提交:`ray job submit ...` -- 通过 `--entrypoint-resources='{"worker_node": 1}'` 强制 entrypoint/driver 只能调度到 worker(head 没有该资源) - -## 2. 持久化目录(宿主机 <-> 容器) - -在宿主机项目根目录(运行脚本时的 `${PWD}`)下使用 `./shared` 做持久化根目录,并 bind mount 到容器内 `/mnt/shared`: - -- 宿主机:`./shared` -- 容器:`/mnt/shared` - -主要内容: - -- 数据集:`/mnt/shared/datasets/gsm8k/` -- HF 缓存:`/mnt/shared/hf/`(脚本会设置 `HF_HOME`,并尽量幂等跳过重复下载) -- 每个 Ray Job 的输出(按 submission id 分目录): - - `/mnt/shared/jobs//logs/` - - `/mnt/shared/jobs//checkpoints/` - -## 3. 整体流程(代码逻辑) - -脚本都在 `src/mvp/v1/scripts/`,整体顺序如下: - -1) `00_prereq_check.sh` - - 检查 `docker/docker compose/git` -2) `05_ensure_verl_repo.sh` - - 若项目根目录下没有 `./verl`,自动 `git clone https://github.com/volcengine/verl.git` -3) `01_up.sh` - - 创建持久化目录(`./shared/...`) - - `docker compose up -d` 启动 3 个容器 -4) `10_install_verl_editable.sh` - - 在 3 个容器内执行 `pip install -e /workspace/verl`(确保 `python -m verl...` 可用且代码与 `./verl` 同步) -5) `20_start_head.sh` - - 在 `mvp-ray-head` 内启动 Ray head(CPU=0、GPU=0) -6) `21_start_workers.sh` - - 在两个 worker 内启动 Ray worker 加入集群 - - 同时给 worker 打 `worker_node` 自定义资源标签 -7) `30_prepare_data_and_model.sh` - - 数据集:若 `train.parquet/test.parquet` 已存在则跳过,否则生成 - - 模型:使用 HF cache(`HF_HOME=/mnt/shared/hf`),存在则跳过,不存在才下载 -8) `40_submit_ppo_epoch1.sh` - - 在 head 容器里执行 `ray job submit` - - 显式指定 `--submission-id=$SUBMISSION_ID` - - 通过 `--entrypoint-resources='{"worker_node": 1}'` 强制 driver 在 worker - - 训练参数: - - `trainer.total_epochs=1` - - `trainer.total_training_steps=29`(GSM8K 该配置下对应 29 steps) - - `trainer.save_freq=10`(每 10 step 保存一次 checkpoint,避免磁盘爆炸) - - `trainer.default_local_dir=/mnt/shared/jobs/$SUBMISSION_ID/checkpoints` - - `hydra.run.dir=/mnt/shared/jobs/$SUBMISSION_ID/logs/hydra` -9) `50_status.sh` - - 打印 `ray status` / `ray job list` / `ray job status` / `ray job logs | tail` - -## 4. 运行方法 - -### 4.1 一键执行 - -在项目根目录执行: - -- `./src/mvp/v1/scripts/run_all.sh` - -### 4.2 分步执行(推荐) - -按顺序执行: - -- `./src/mvp/v1/scripts/01_up.sh` -- `./src/mvp/v1/scripts/10_install_verl_editable.sh` -- `./src/mvp/v1/scripts/20_start_head.sh` -- `./src/mvp/v1/scripts/21_start_workers.sh` -- `./src/mvp/v1/scripts/30_prepare_data_and_model.sh` -- `SUBMISSION_ID=ppo_h20_8g_$(date +%Y%m%d_%H%M%S) ./src/mvp/v1/scripts/40_submit_ppo_epoch1.sh` -- `./src/mvp/v1/scripts/50_status.sh` - -### 4.3 查看与停止 - -- Dashboard:`http://<宿主机IP>:8265` -- 列出作业(在 head 容器内): - - `docker exec mvp-ray-head bash -lc "ray job list --address=http://127.0.0.1:8265"` -- 停止某个 submission id: - - `docker exec mvp-ray-head bash -lc "ray job stop --address=http://127.0.0.1:8265 "` - -### 4.4 清理 - -- 停止并删除容器:`./src/mvp/v1/scripts/02_down.sh` -- 清理输出(谨慎,数据量可能很大):删除 `./shared/jobs//` - -## 5. 常见坑 - -- **不传 `--submission-id` 会导致“输出目录难以等于 submission id”**:因为 hydra/ckpt 目录需要在提交前确定。当前脚本会显式传 `--submission-id=$SUBMISSION_ID`,并使用同名目录。 -- **checkpoint 太大**:PPO 的 checkpoint 非常占空间。当前脚本默认 `save_freq=10`,如仍过大,可调大 `save_freq` 或减少保存内容/频率。 - -更多分步操作与验收标准见:`specs/mvp/v1_action.md` diff --git a/src/mvp/v1/arch.excalidraw b/src/mvp/v1/arch.excalidraw deleted file mode 100644 index b9e50ce..0000000 --- a/src/mvp/v1/arch.excalidraw +++ /dev/null @@ -1,1877 +0,0 @@ -{ - "type": "excalidraw", - "version": 2, - "source": "https://marketplace.visualstudio.com/items?itemName=pomdtr.excalidraw-editor", - "elements": [ - { - "id": "9Ql3xet2wP4Oy9RJ4s-8H", - "type": "rectangle", - "x": 165.33361053466797, - "y": 124.66671752929688, - "width": 201.66666412353516, - "height": 144.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a0", - "roundness": { - "type": 3 - }, - "seed": 1490759950, - "version": 404, - "versionNonce": 1106431423, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "Yx_fL1nYHbxINMBHYImpi" - }, - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow" - }, - { - "id": "Qzy3gfKzdZyrTwzOpuh86", - "type": "arrow" - }, - { - "id": "zj5n4D3014Kl-BdrNuRZp", - "type": "arrow" - }, - { - "id": "cqQ2Ij98wYdbKqXQcPhxe", - "type": "arrow" - } - ], - "updated": 1766373694946, - "link": null, - "locked": false - }, - { - "id": "Yx_fL1nYHbxINMBHYImpi", - "type": "text", - "x": 232.60698318481445, - "y": 184.5000457763672, - "width": 67.11991882324219, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a1", - "roundness": null, - "seed": 122704078, - "version": 259, - "versionNonce": 104768575, - "isDeleted": false, - "boundElements": [], - "updated": 1766372702157, - "link": null, - "locked": false, - "text": "scripts", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "9Ql3xet2wP4Oy9RJ4s-8H", - "originalText": "scripts", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "1BW7RJyVw0yjg93vAIlWT", - "type": "rectangle", - "x": 813.8334465026855, - "y": 81.00010681152344, - "width": 159.9999771118164, - "height": 88.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a2", - "roundness": { - "type": 3 - }, - "seed": 929976718, - "version": 789, - "versionNonce": 761000657, - "isDeleted": false, - "boundElements": [ - { - "id": "qcyVAzD12V9EAxE15fwAq", - "type": "arrow" - }, - { - "id": "Qzy3gfKzdZyrTwzOpuh86", - "type": "arrow" - } - ], - "updated": 1766373762851, - "link": null, - "locked": false - }, - { - "id": "nIO4qa9Aj4LF_WlHt2BNO", - "type": "rectangle", - "x": 455.8334159851074, - "y": 125.66667175292969, - "width": 201.66666412353516, - "height": 144.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a4", - "roundness": { - "type": 3 - }, - "seed": 2137052434, - "version": 311, - "versionNonce": 1823398289, - "isDeleted": false, - "boundElements": [ - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow" - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow" - }, - { - "id": "qcyVAzD12V9EAxE15fwAq", - "type": "arrow" - } - ], - "updated": 1766373745383, - "link": null, - "locked": false - }, - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow", - "x": 372.0002746582031, - "y": 196.9000457763672, - "width": 252.06685104370115, - "height": 90.56665649414063, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a6", - "roundness": null, - "seed": 1158070290, - "version": 571, - "versionNonce": 231145393, - "isDeleted": false, - "boundElements": [], - "updated": 1766373712586, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 114.08342552185059, - 0 - ], - [ - 114.08342552185059, - -90.56665649414063 - ], - [ - 252.06685104370115, - -90.56665649414063 - ], - [ - 252.06685104370115, - -55.56665649414063 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "9Ql3xet2wP4Oy9RJ4s-8H", - "fixedPoint": [ - 1.0247933887424108, - 0.4993087557117625 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "e58le7CfnSkWVb-LoMmj4", - "fixedPoint": [ - 0.49736842105263096, - -0.13157894736842105 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "aBQ9npStDj077n0B7_JZ3", - "type": "rectangle", - "x": 814.000072479248, - "y": 227.6667022705078, - "width": 159.9999771118164, - "height": 88.66665649414062, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "a7", - "roundness": { - "type": 3 - }, - "seed": 1963206674, - "version": 814, - "versionNonce": 371608031, - "isDeleted": false, - "boundElements": [ - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow" - }, - { - "id": "zj5n4D3014Kl-BdrNuRZp", - "type": "arrow" - } - ], - "updated": 1766373791812, - "link": null, - "locked": false - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow", - "x": 648.1671257019043, - "y": 165.23338928222657, - "width": 145.8328742980957, - "height": 121.4333282470703, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aC", - "roundness": null, - "seed": 990553042, - "version": 371, - "versionNonce": 1356695409, - "isDeleted": false, - "boundElements": [], - "updated": 1766373712586, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 80.41647338867188, - 0 - ], - [ - 80.41647338867188, - 121.4333282470703 - ], - [ - 145.8328742980957, - 121.4333282470703 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "e58le7CfnSkWVb-LoMmj4", - "fixedPoint": [ - 1.131578947368421, - 0.49736842105263174 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "aBQ9npStDj077n0B7_JZ3", - "fixedPoint": [ - -0.12500047087676108, - 0.66541378226761 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "atIqduRWNX97Sp6yKe4hj", - "type": "rectangle", - "x": 431.1368826709601, - "y": 26.199444213977472, - "width": 611.63434968004, - "height": 645.8789403469411, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "dotted", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "aw", - "roundness": { - "type": 3 - }, - "seed": 311282494, - "version": 376, - "versionNonce": 190431967, - "isDeleted": false, - "boundElements": [], - "updated": 1766373009377, - "link": null, - "locked": false - }, - { - "id": "k6SXmpRXbeQSbRrXG_o6a", - "type": "text", - "x": 656.1800675420305, - "y": -12.200757945542989, - "width": 199.19985961914062, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "dotted", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "ax", - "roundness": null, - "seed": 570087970, - "version": 192, - "versionNonce": 158307807, - "isDeleted": false, - "boundElements": [], - "updated": 1766373821110, - "link": null, - "locked": false, - "text": "a single H20 machine", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "a single H20 machine", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "qcyVAzD12V9EAxE15fwAq", - "type": "arrow", - "x": 648.1671257019043, - "y": 165.23338928222657, - "width": 160.66632080078125, - "height": 39.99995422363281, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b03", - "roundness": null, - "seed": 696982833, - "version": 370, - "versionNonce": 1628299665, - "isDeleted": false, - "boundElements": null, - "updated": 1766373712586, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 80.33316040039062, - 0 - ], - [ - 80.33316040039062, - -39.99995422363281 - ], - [ - 160.66632080078125, - -39.99995422363281 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "e58le7CfnSkWVb-LoMmj4", - "fixedPoint": [ - 1.131578947368421, - 0.49736842105263174 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "1BW7RJyVw0yjg93vAIlWT", - "fixedPoint": [ - -0.031250004470349, - 0.4988721803217357 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "Qzy3gfKzdZyrTwzOpuh86", - "type": "arrow", - "x": 371.8835678755345, - "y": 173.74970208077258, - "width": 520.5167182267604, - "height": 132.74959526924914, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b04", - "roundness": null, - "seed": 626515153, - "version": 428, - "versionNonce": 451690431, - "isDeleted": false, - "boundElements": null, - "updated": 1766372702159, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 21.28340523847919, - 0 - ], - [ - 21.28340523847919, - -132.74959526924914 - ], - [ - 520.5167182267604, - -132.74959526924914 - ], - [ - 520.5167182267604, - -111.41628228096789 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "9Ql3xet2wP4Oy9RJ4s-8H", - "fixedPoint": [ - 1.024214677416095, - 0.3392833272086004 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "eeIv7mr_n3Lg6B3DlXJHR", - "fixedPoint": [ - 0.49736842105263096, - -0.13157894736842105 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": [ - { - "index": 2, - "start": [ - 21.28340523847919, - 0 - ], - "end": [ - 21.28340523847919, - -132.74959526924914 - ] - } - ], - "startIsSpecial": false, - "endIsSpecial": false - }, - { - "id": "zj5n4D3014Kl-BdrNuRZp", - "type": "arrow", - "x": 371.87357276423296, - "y": 221.26066759479318, - "width": 525.8600263263431, - "height": 135.07269116985526, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b05", - "roundness": null, - "seed": 2137319889, - "version": 378, - "versionNonce": 1170250751, - "isDeleted": false, - "boundElements": null, - "updated": 1766372702159, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 35.29340034978071, - 0 - ], - [ - 35.29340034978071, - 135.07269116985526 - ], - [ - 525.8600263263431, - 135.07269116985526 - ], - [ - 525.8600263263431, - 116.40612622844901 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "9Ql3xet2wP4Oy9RJ4s-8H", - "fixedPoint": [ - 1.0241651148800903, - 0.6677001626107852 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "c4sciwjA9ZH_GjmspcBan", - "fixedPoint": [ - 0.49736842105262796, - 1.131578947368421 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": [ - { - "index": 2, - "start": [ - 35.29340034978071, - 0 - ], - "end": [ - 35.29340034978071, - 135.07269116985526 - ] - } - ], - "startIsSpecial": false, - "endIsSpecial": false - }, - { - "id": "bzQAQDSv4fPQAKJkqw9an", - "type": "arrow", - "x": 287.8335380554199, - "y": -76.33323669433594, - "width": 70.00006103515625, - "height": 26, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b06", - "roundness": null, - "seed": 301869471, - "version": 103, - "versionNonce": 2132861809, - "isDeleted": false, - "boundElements": null, - "updated": 1766372404307, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 35.000030517578125, - 0 - ], - [ - 35.000030517578125, - -26 - ], - [ - 70.00006103515625, - -26 - ] - ], - "lastCommittedPoint": null, - "startBinding": null, - "endBinding": null, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "JoAr6EMunnvVMp7Uo00g5", - "type": "text", - "x": 379.1668510437012, - "y": -102.99992370605469, - "width": 165.33987426757812, - "height": 25, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b07", - "roundness": null, - "seed": 1372433471, - "version": 19, - "versionNonce": 1494393073, - "isDeleted": false, - "boundElements": null, - "updated": 1766372417246, - "link": null, - "locked": false, - "text": "start ray cluster", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "start ray cluster", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "mWLybQDTFo_Um3eT0cEDa", - "type": "arrow", - "x": 577.8335380554199, - "y": -84.33323669433594, - "width": 59.33331298828125, - "height": 24.66668701171875, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b08", - "roundness": null, - "seed": 2218161, - "version": 62, - "versionNonce": 49511103, - "isDeleted": false, - "boundElements": null, - "updated": 1766372425873, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 29.666656494140625, - 0 - ], - [ - 29.666656494140625, - -24.66668701171875 - ], - [ - 59.33331298828125, - -24.66668701171875 - ] - ], - "lastCommittedPoint": null, - "startBinding": null, - "endBinding": null, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": null, - "startIsSpecial": null, - "endIsSpecial": null - }, - { - "id": "sy0AQFPiKMUpC_fNA1u5Y", - "type": "text", - "x": 653.8335380554199, - "y": -102.99992370605469, - "width": 312.499755859375, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b09", - "roundness": null, - "seed": 516560529, - "version": 57, - "versionNonce": 1162137087, - "isDeleted": false, - "boundElements": null, - "updated": 1766372458567, - "link": null, - "locked": false, - "text": "ray job submit / drivier - worker", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "ray job submit / drivier - worker", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "e58le7CfnSkWVb-LoMmj4", - "type": "ellipse", - "x": 605.1671257019043, - "y": 146.33338928222656, - "width": 38, - "height": 38, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#99e9f2", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0C", - "roundness": { - "type": 2 - }, - "seed": 915719889, - "version": 349, - "versionNonce": 1238458833, - "isDeleted": false, - "boundElements": [ - { - "id": "bAFwE3wo46b9BFt_2Gnm2", - "type": "arrow" - }, - { - "id": "qcyVAzD12V9EAxE15fwAq", - "type": "arrow" - }, - { - "id": "QgI8Gn67BTTI1MdOhOjjn", - "type": "arrow" - }, - { - "id": "cqQ2Ij98wYdbKqXQcPhxe", - "type": "arrow" - } - ], - "updated": 1766373712585, - "link": null, - "locked": false - }, - { - "id": "eeIv7mr_n3Lg6B3DlXJHR", - "type": "ellipse", - "x": 873.5002861022949, - "y": 67.33341979980469, - "width": 38, - "height": 38, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffc9c9", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0D", - "roundness": { - "type": 2 - }, - "seed": 1674226303, - "version": 428, - "versionNonce": 1555106719, - "isDeleted": false, - "boundElements": [ - { - "id": "Qzy3gfKzdZyrTwzOpuh86", - "type": "arrow" - } - ], - "updated": 1766372702159, - "link": null, - "locked": false - }, - { - "id": "c4sciwjA9ZH_GjmspcBan", - "type": "ellipse", - "x": 878.8335990905762, - "y": 294.6667938232422, - "width": 38, - "height": 38, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffc9c9", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0E", - "roundness": { - "type": 2 - }, - "seed": 2058462079, - "version": 476, - "versionNonce": 803991519, - "isDeleted": false, - "boundElements": [ - { - "id": "zj5n4D3014Kl-BdrNuRZp", - "type": "arrow" - } - ], - "updated": 1766372702159, - "link": null, - "locked": false - }, - { - "id": "QQdAB0FVqHTGhVCKstHrm", - "type": "ellipse", - "x": 308.1669120788574, - "y": -185.9999237060547, - "width": 38, - "height": 38, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#99e9f2", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0F", - "roundness": { - "type": 2 - }, - "seed": 156527057, - "version": 305, - "versionNonce": 1422415839, - "isDeleted": false, - "boundElements": [], - "updated": 1766372581044, - "link": null, - "locked": false - }, - { - "id": "37ojV_5RQu-H5_oLEw_CC", - "type": "text", - "x": 375.1668510437012, - "y": -176.9999237060547, - "width": 136.61990356445312, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffc9c9", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0G", - "roundness": null, - "seed": 122498079, - "version": 15, - "versionNonce": 121837457, - "isDeleted": false, - "boundElements": null, - "updated": 1766372589741, - "link": null, - "locked": false, - "text": "ray head node", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "ray head node", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "ZyQitTq4F7KArc1LsSU0L", - "type": "ellipse", - "x": 578.1668510437012, - "y": -185.33323669433594, - "width": 38, - "height": 38, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffc9c9", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0H", - "roundness": { - "type": 2 - }, - "seed": 666768689, - "version": 440, - "versionNonce": 1110150815, - "isDeleted": false, - "boundElements": [], - "updated": 1766372594958, - "link": null, - "locked": false - }, - { - "id": "B_AKAU5jOYUjwmhK54Ddr", - "type": "text", - "x": 657.5235862731934, - "y": -178.16656494140625, - "width": 154.65988159179688, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "#ffc9c9", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0I", - "roundness": null, - "seed": 1500425873, - "version": 72, - "versionNonce": 150248991, - "isDeleted": false, - "boundElements": [], - "updated": 1766372606781, - "link": null, - "locked": false, - "text": "ray worker node", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "ray worker node", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "WPOvDTFRcRTqysrgfilw_", - "type": "rectangle", - "x": 453.1667900085449, - "y": 395.0000762939453, - "width": 572.6666870117189, - "height": 251.3333740234375, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0K", - "roundness": null, - "seed": 62506143, - "version": 121, - "versionNonce": 1380555377, - "isDeleted": false, - "boundElements": null, - "updated": 1766373299556, - "link": null, - "locked": false - }, - { - "id": "icDpH3wy-c2_99TXtmru5", - "type": "rectangle", - "x": 469.1667900085449, - "y": 410.87457554413584, - "width": 83.33331298828125, - "height": 138.7922487966845, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0L", - "roundness": null, - "seed": 292536607, - "version": 130, - "versionNonce": 398901169, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "oYnPwXC5ulNTf8ayVoUHX" - } - ], - "updated": 1766376371670, - "link": null, - "locked": false - }, - { - "id": "oYnPwXC5ulNTf8ayVoUHX", - "type": "text", - "x": 476.93347549438477, - "y": 455.2706999424781, - "width": 67.79994201660156, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0M", - "roundness": null, - "seed": 964724095, - "version": 75, - "versionNonce": 1019940831, - "isDeleted": false, - "boundElements": null, - "updated": 1766376371670, - "link": null, - "locked": false, - "text": "datase\nts", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "icDpH3wy-c2_99TXtmru5", - "originalText": "datasets", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "s3rGKdwzC87Z1v9gN0N-5", - "type": "rectangle", - "x": 582.166820526123, - "y": 410.4639351318977, - "width": 83.33331298828125, - "height": 138.7922487966845, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0N", - "roundness": null, - "seed": 401691633, - "version": 190, - "versionNonce": 700169215, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "D2W7CAX99N7IpvqJQP6eX" - } - ], - "updated": 1766376371670, - "link": null, - "locked": false - }, - { - "id": "D2W7CAX99N7IpvqJQP6eX", - "type": "text", - "x": 613.1934852600098, - "y": 467.36005953023994, - "width": 21.279983520507812, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0O", - "roundness": null, - "seed": 325299665, - "version": 138, - "versionNonce": 770525041, - "isDeleted": false, - "boundElements": [], - "updated": 1766376371670, - "link": null, - "locked": false, - "text": "hf", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "s3rGKdwzC87Z1v9gN0N-5", - "originalText": "hf", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "EGfEHSzmWYNx5ec9bP-9v", - "type": "rectangle", - "x": 701.5001945495605, - "y": 409.6427294956321, - "width": 83.33331298828125, - "height": 138.7922487966845, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0P", - "roundness": null, - "seed": 974114385, - "version": 214, - "versionNonce": 2090152273, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "XIfw_ABOr1dlUCUXEBJqA" - } - ], - "updated": 1766376371670, - "link": null, - "locked": false - }, - { - "id": "XIfw_ABOr1dlUCUXEBJqA", - "type": "text", - "x": 722.9068641662598, - "y": 466.53885389397436, - "width": 40.51997375488281, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0Q", - "roundness": null, - "seed": 881056817, - "version": 164, - "versionNonce": 663619647, - "isDeleted": false, - "boundElements": [], - "updated": 1766376371670, - "link": null, - "locked": false, - "text": "jobs", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "EGfEHSzmWYNx5ec9bP-9v", - "originalText": "jobs", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "Fe9YUb1NNu32IhvievWnr", - "type": "rectangle", - "x": 812.8334465026855, - "y": 408.8214486711559, - "width": 83.33331298828125, - "height": 138.7922487966845, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0R", - "roundness": null, - "seed": 66661759, - "version": 268, - "versionNonce": 1178642527, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "UZhPJS_QBKW_LMYwu1enR" - } - ], - "updated": 1766376371670, - "link": null, - "locked": false - }, - { - "id": "UZhPJS_QBKW_LMYwu1enR", - "type": "text", - "x": 821.1101188659668, - "y": 465.71757306949814, - "width": 66.77996826171875, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0S", - "roundness": null, - "seed": 1284842911, - "version": 227, - "versionNonce": 969134353, - "isDeleted": false, - "boundElements": [], - "updated": 1766376371670, - "link": null, - "locked": false, - "text": "output", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "Fe9YUb1NNu32IhvievWnr", - "originalText": "output", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "r8maqUMI8CEoTqgUHwtnZ", - "type": "rectangle", - "x": 924.8335075378418, - "y": 408.0001678466797, - "width": 83.33331298828125, - "height": 138.7922487966845, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0T", - "roundness": null, - "seed": 1203268831, - "version": 320, - "versionNonce": 204048113, - "isDeleted": false, - "boundElements": [ - { - "type": "text", - "id": "nL0ZOKRltZyanG1aa7hOW" - } - ], - "updated": 1766376371670, - "link": null, - "locked": false - }, - { - "id": "nL0ZOKRltZyanG1aa7hOW", - "type": "text", - "x": 951.7201805114746, - "y": 464.8962922450219, - "width": 29.559967041015625, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0U", - "roundness": null, - "seed": 150305023, - "version": 273, - "versionNonce": 1246452895, - "isDeleted": false, - "boundElements": [], - "updated": 1766376371670, - "link": null, - "locked": false, - "text": "ray", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "middle", - "containerId": "r8maqUMI8CEoTqgUHwtnZ", - "originalText": "ray", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "OmfvpsuW0dhubnI5NH1Ni", - "type": "text", - "x": 675.8334770202637, - "y": 593.0000762939453, - "width": 121.67990112304688, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0V", - "roundness": null, - "seed": 1166095967, - "version": 60, - "versionNonce": 643125617, - "isDeleted": false, - "boundElements": null, - "updated": 1766373325167, - "link": null, - "locked": false, - "text": "/mnt/shared", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "/mnt/shared", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "cqQ2Ij98wYdbKqXQcPhxe", - "type": "arrow", - "x": 371.9714008624129, - "y": 208.42023305299114, - "width": 252.09572483949137, - "height": 50.3333740234375, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0W", - "roundness": null, - "seed": 1948514207, - "version": 127, - "versionNonce": 977608497, - "isDeleted": false, - "boundElements": null, - "updated": 1766373713002, - "link": null, - "locked": false, - "points": [ - [ - 0, - 0 - ], - [ - 96.77889477662518, - 0 - ], - [ - 96.77889477662518, - 31.246530252672926 - ], - [ - 252.09572483949137, - 31.246530252672926 - ], - [ - 252.09572483949137, - -19.086843770764574 - ] - ], - "lastCommittedPoint": null, - "startBinding": { - "elementId": "9Ql3xet2wP4Oy9RJ4s-8H", - "fixedPoint": [ - 1.0246502128937116, - 0.5789413922556957 - ], - "focus": 0, - "gap": 0 - }, - "endBinding": { - "elementId": "e58le7CfnSkWVb-LoMmj4", - "fixedPoint": [ - 0.49736842105263096, - 1.131578947368421 - ], - "focus": 0, - "gap": 0 - }, - "startArrowhead": null, - "endArrowhead": "arrow", - "elbowed": true, - "fixedSegments": [ - { - "index": 3, - "start": [ - 96.77889477662518, - 31.246530252672926 - ], - "end": [ - 252.09572483949137, - 31.246530252672926 - ] - } - ], - "startIsSpecial": false, - "endIsSpecial": false - }, - { - "id": "xn_M6D4MoCOvg2I2eSA3o", - "type": "text", - "x": 491.16682052612305, - "y": 237.66676330566406, - "width": 137.33990478515625, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0X", - "roundness": null, - "seed": 485981873, - "version": 51, - "versionNonce": 224706367, - "isDeleted": false, - "boundElements": null, - "updated": 1766373736215, - "link": null, - "locked": false, - "text": "ray job submit", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "ray job submit", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "n0XX1HzCpzHfeo4hTRson", - "type": "text", - "x": 456.5001640319824, - "y": 281.00013732910156, - "width": 196.61985778808594, - "height": 25, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0Y", - "roundness": null, - "seed": 960522577, - "version": 46, - "versionNonce": 1758456319, - "isDeleted": false, - "boundElements": null, - "updated": 1766373758962, - "link": null, - "locked": false, - "text": "head node container", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "head node container", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "-rnnyMPU-tQs8UVNBCb7C", - "type": "text", - "x": 792.5001945495605, - "y": 176.33338928222656, - "width": 225.5198211669922, - "height": 50, - "angle": 0, - "strokeColor": "#1e1e1e", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0Z", - "roundness": null, - "seed": 501756561, - "version": 78, - "versionNonce": 1893991729, - "isDeleted": false, - "boundElements": null, - "updated": 1766373794871, - "link": null, - "locked": false, - "text": "worker node containers\n 4 x H20", - "fontSize": 20, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "worker node containers\n 4 x H20", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "qWTdVy6o3A4fkZsGRMCKB", - "type": "text", - "x": 483.4334098815918, - "y": 557.5000762939453, - "width": 40.1335388183593, - "height": 16.722307840983046, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0a", - "roundness": null, - "seed": 438165041, - "version": 42, - "versionNonce": 1297545873, - "isDeleted": false, - "boundElements": null, - "updated": 1766376434059, - "link": null, - "locked": false, - "text": "数据集", - "fontSize": 13.377846272786437, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "数据集", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "Zr04JN1SwCMGrPB7Otn5n", - "type": "text", - "x": 599.7667686462403, - "y": 556.6389223734539, - "width": 53.47998046875, - "height": 16.722307840983046, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0b", - "roundness": null, - "seed": 1427393105, - "version": 108, - "versionNonce": 20002801, - "isDeleted": false, - "boundElements": [], - "updated": 1766376447293, - "link": null, - "locked": false, - "text": "基座模型", - "fontSize": 13.377846272786437, - "fontFamily": 5, - "textAlign": "left", - "verticalAlign": "top", - "containerId": null, - "originalText": "基座模型", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "U5mN9zuDxufwaTsXAez1v", - "type": "text", - "x": 683.1001121520997, - "y": 553.9721743265789, - "width": 116.947265625, - "height": 33.44461568196609, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0c", - "roundness": null, - "seed": 1016566161, - "version": 228, - "versionNonce": 460195775, - "isDeleted": false, - "boundElements": [], - "updated": 1766376548390, - "link": null, - "locked": false, - "text": "job级别\nckpt, config, log等", - "fontSize": 13.377846272786437, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "top", - "containerId": null, - "originalText": "job级别\nckpt, config, log等", - "autoResize": true, - "lineHeight": 1.25 - }, - { - "id": "kyEqz0rZKz404SUTYZRai", - "type": "text", - "x": 931.766707611084, - "y": 557.3056093851726, - "width": 74.01625061035156, - "height": 33.44461568196609, - "angle": 0, - "strokeColor": "#e03131", - "backgroundColor": "transparent", - "fillStyle": "solid", - "strokeWidth": 2, - "strokeStyle": "solid", - "roughness": 1, - "opacity": 100, - "groupIds": [], - "frameId": null, - "index": "b0d", - "roundness": null, - "seed": 1742834719, - "version": 152, - "versionNonce": 2136750623, - "isDeleted": false, - "boundElements": [], - "updated": 1766376569303, - "link": null, - "locked": false, - "text": "系统级\nsession日志", - "fontSize": 13.377846272786437, - "fontFamily": 5, - "textAlign": "center", - "verticalAlign": "top", - "containerId": null, - "originalText": "系统级\nsession日志", - "autoResize": true, - "lineHeight": 1.25 - } - ], - "appState": { - "gridSize": 20, - "gridStep": 5, - "gridModeEnabled": false, - "viewBackgroundColor": "#ffffff" - }, - "files": {} -} \ No newline at end of file diff --git a/src/mvp/v1/docker-compose.yaml b/src/mvp/v1/docker-compose.yaml deleted file mode 100644 index 5d31a03..0000000 --- a/src/mvp/v1/docker-compose.yaml +++ /dev/null @@ -1,86 +0,0 @@ -version: "3.8" - -services: - ray_head: - image: verlai/verl:sgl055.latest - container_name: mvp-ray-head - command: sleep infinity - ports: - - "8265:8265" - volumes: - - ./verl:/workspace/verl - - ./shared:/mnt/shared - shm_size: "10g" - ulimits: - nofile: - soft: 65536 - hard: 65536 - cap_add: - - SYS_ADMIN - - SYS_PTRACE - networks: - - mvp-ray-net - environment: - HF_HOME: "/mnt/shared/hf" - HUGGINGFACE_HUB_CACHE: "/mnt/shared/hf/hub" - TRANSFORMERS_CACHE: "/mnt/shared/hf/transformers" - HF_ENDPOINT: "https://hf-mirror.com" - PYTHONUNBUFFERED: "1" - - ray_worker_0: - image: verlai/verl:sgl055.latest - container_name: mvp-ray-worker-0 - command: sleep infinity - volumes: - - ./verl:/workspace/verl - - ./shared:/mnt/shared - shm_size: "10g" - ulimits: - nofile: - soft: 65536 - hard: 65536 - cap_add: - - SYS_ADMIN - - SYS_PTRACE - networks: - - mvp-ray-net - runtime: nvidia - environment: - NVIDIA_VISIBLE_DEVICES: "0,1,2,3" - NVIDIA_DRIVER_CAPABILITIES: "all" - HF_HOME: "/mnt/shared/hf" - HUGGINGFACE_HUB_CACHE: "/mnt/shared/hf/hub" - TRANSFORMERS_CACHE: "/mnt/shared/hf/transformers" - HF_ENDPOINT: "https://hf-mirror.com" - PYTHONUNBUFFERED: "1" - - ray_worker_1: - image: verlai/verl:sgl055.latest - container_name: mvp-ray-worker-1 - command: sleep infinity - volumes: - - ./verl:/workspace/verl - - ./shared:/mnt/shared - shm_size: "10g" - ulimits: - nofile: - soft: 65536 - hard: 65536 - cap_add: - - SYS_ADMIN - - SYS_PTRACE - networks: - - mvp-ray-net - runtime: nvidia - environment: - NVIDIA_VISIBLE_DEVICES: "4,5,6,7" - NVIDIA_DRIVER_CAPABILITIES: "all" - HF_HOME: "/mnt/shared/hf" - HUGGINGFACE_HUB_CACHE: "/mnt/shared/hf/hub" - TRANSFORMERS_CACHE: "/mnt/shared/hf/transformers" - HF_ENDPOINT: "https://hf-mirror.com" - PYTHONUNBUFFERED: "1" - -networks: - mvp-ray-net: - driver: bridge diff --git a/src/mvp/v1/scripts/00_prereq_check.sh b/src/mvp/v1/scripts/00_prereq_check.sh deleted file mode 100755 index db093a9..0000000 --- a/src/mvp/v1/scripts/00_prereq_check.sh +++ /dev/null @@ -1,17 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -require_cmd docker - -require_cmd git - -if ! docker compose version >/dev/null 2>&1; then - echo "docker compose plugin not available; please install docker compose v2" >&2 - exit 1 -fi - -echo "OK: docker + docker compose + git" diff --git a/src/mvp/v1/scripts/01_up.sh b/src/mvp/v1/scripts/01_up.sh deleted file mode 100755 index d835ba2..0000000 --- a/src/mvp/v1/scripts/01_up.sh +++ /dev/null @@ -1,20 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -"${SCRIPT_DIR}/00_prereq_check.sh" -"${SCRIPT_DIR}/05_ensure_verl_repo.sh" - -mkdir -p \ - "${ROOT_DIR}/shared/hf" \ - "${ROOT_DIR}/shared/datasets" \ - "${ROOT_DIR}/shared/jobs" \ - "${ROOT_DIR}/shared/outputs" \ - "${ROOT_DIR}/shared/ray" - -dc up -d -dc ps - diff --git a/src/mvp/v1/scripts/02_down.sh b/src/mvp/v1/scripts/02_down.sh deleted file mode 100755 index 750040e..0000000 --- a/src/mvp/v1/scripts/02_down.sh +++ /dev/null @@ -1,9 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -dc down - diff --git a/src/mvp/v1/scripts/05_ensure_verl_repo.sh b/src/mvp/v1/scripts/05_ensure_verl_repo.sh deleted file mode 100755 index 99eacbd..0000000 --- a/src/mvp/v1/scripts/05_ensure_verl_repo.sh +++ /dev/null @@ -1,19 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -VERL_DIR="${ROOT_DIR}/verl" - -if [[ -d "${VERL_DIR}/.git" ]]; then - echo "OK: verl repo exists: ${VERL_DIR}" - exit 0 -fi - -echo "verl repo not found at ${VERL_DIR}; cloning..." -rm -rf "${VERL_DIR}" -git clone https://github.com/volcengine/verl.git "${VERL_DIR}" -echo "OK: cloned verl -> ${VERL_DIR}" - diff --git a/src/mvp/v1/scripts/10_install_verl_editable.sh b/src/mvp/v1/scripts/10_install_verl_editable.sh deleted file mode 100755 index 549e2b2..0000000 --- a/src/mvp/v1/scripts/10_install_verl_editable.sh +++ /dev/null @@ -1,22 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -install_one() { - local name="$1" - echo "[${name}] ensure verl importable" - if ! dexec "${name}" python3 -c "import verl; print(verl.__file__)" >/dev/null 2>&1; then - echo "[${name}] verl not importable; installing editable from /workspace/verl" - dexec "${name}" bash -lc "pip install -e /workspace/verl" - else - echo "[${name}] verl import OK" - fi -} - -install_one "${HEAD_CONTAINER}" -install_one "${WORKER0_CONTAINER}" -install_one "${WORKER1_CONTAINER}" - diff --git a/src/mvp/v1/scripts/20_start_head.sh b/src/mvp/v1/scripts/20_start_head.sh deleted file mode 100755 index e14da5b..0000000 --- a/src/mvp/v1/scripts/20_start_head.sh +++ /dev/null @@ -1,17 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -echo "[head] ray stop (ignore errors)" -dexec "${HEAD_CONTAINER}" bash -lc "ray stop --force || true" - -echo "[head] ray start (CPU=0, GPU=0 to prevent scheduling on head)" -HEAD_IP="$(container_ip "${HEAD_CONTAINER}")" -echo "[head] container ip: ${HEAD_IP}" -dexec "${HEAD_CONTAINER}" bash -lc "ray start --head --node-ip-address=${HEAD_IP} --dashboard-host=0.0.0.0 --dashboard-port=8265 --port=6379 --num-cpus=0 --num-gpus=0" - -echo "[head] ray status" -dexec "${HEAD_CONTAINER}" bash -lc "ray status || true" diff --git a/src/mvp/v1/scripts/21_start_workers.sh b/src/mvp/v1/scripts/21_start_workers.sh deleted file mode 100755 index 041d709..0000000 --- a/src/mvp/v1/scripts/21_start_workers.sh +++ /dev/null @@ -1,33 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -start_worker() { - local name="$1" - local node_ip - node_ip="$(container_ip "${name}")" - echo "[${name}] ray stop (ignore errors)" - dexec "${name}" bash -lc "ray stop --force || true" - - local head_ip - head_ip="$(container_ip "${HEAD_CONTAINER}")" - echo "[${name}] container ip: ${node_ip}" - echo "[${name}] ray start -> join ${head_ip}:6379 (num_gpus=4, resources worker_node=100)" - dexec "${name}" bash -lc "ray start --node-ip-address=${node_ip} --address=${head_ip}:6379 --num-gpus=4 --resources='{\"worker_node\": 100}'" -} - -start_worker "${WORKER0_CONTAINER}" -start_worker "${WORKER1_CONTAINER}" - -echo "[head] waiting for workers to register" -for _ in $(seq 1 30); do - if dexec "${HEAD_CONTAINER}" bash -lc "ray status" | grep -q "Active:"; then - break - fi - sleep 2 -done - -dexec "${HEAD_CONTAINER}" bash -lc "ray status || true" diff --git a/src/mvp/v1/scripts/30_prepare_data_and_model.sh b/src/mvp/v1/scripts/30_prepare_data_and_model.sh deleted file mode 100755 index bff6da6..0000000 --- a/src/mvp/v1/scripts/30_prepare_data_and_model.sh +++ /dev/null @@ -1,37 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -DATA_DIR="/mnt/shared/datasets/gsm8k" -MODEL_ID="Qwen/Qwen2.5-0.5B-Instruct" - -echo "[head] prepare dataset (idempotent) -> ${DATA_DIR}" -dexec "${HEAD_CONTAINER}" bash -lc "mkdir -p ${DATA_DIR} && if [[ -f ${DATA_DIR}/train.parquet && -f ${DATA_DIR}/test.parquet ]]; then echo 'dataset_exists: skip'; else python3 /workspace/verl/examples/data_preprocess/gsm8k.py --local_save_dir ${DATA_DIR}; fi" - -echo "[head] ensure model cached to persistent HF_HOME (idempotent) -> ${MODEL_ID}" -PY_CODE="$(cat <<'PY' -import os - -model_id = os.environ["MODEL_ID"] - -hf_home = os.environ.get("HF_HOME", "/mnt/shared/hf") -os.environ.setdefault("HF_HOME", hf_home) -os.environ.setdefault("HUGGINGFACE_HUB_CACHE", os.path.join(hf_home, "hub")) -os.environ.setdefault("TRANSFORMERS_CACHE", os.path.join(hf_home, "transformers")) - -from huggingface_hub import snapshot_download - -try: - snapshot_download(repo_id=model_id, local_files_only=True) - print("model_cache_exists: skip", model_id) -except Exception: - print("model_cache_missing: downloading", model_id) - snapshot_download(repo_id=model_id) - print("model_cached_ok:", model_id) -PY -)" - -printf "%s\n" "${PY_CODE}" | dexec "${HEAD_CONTAINER}" bash -lc "MODEL_ID='${MODEL_ID}' python3 -" diff --git a/src/mvp/v1/scripts/40_submit_ppo_epoch1.sh b/src/mvp/v1/scripts/40_submit_ppo_epoch1.sh deleted file mode 100755 index 0b62dce..0000000 --- a/src/mvp/v1/scripts/40_submit_ppo_epoch1.sh +++ /dev/null @@ -1,70 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -SUBMISSION_ID="${SUBMISSION_ID:-mvp_ppo_$(timestamp)_$RANDOM}" -# 为了让“输出目录 = submission id”,默认把 JOB_TAG 也设成 SUBMISSION_ID(可手动覆盖)。 -JOB_TAG="${JOB_TAG:-${SUBMISSION_ID}}" -JOB_DIR="/mnt/shared/jobs/${SUBMISSION_ID}" - -MODEL_ID="Qwen/Qwen2.5-0.5B-Instruct" -TRAIN_FILE="/mnt/shared/datasets/gsm8k/train.parquet" -VAL_FILE="/mnt/shared/datasets/gsm8k/test.parquet" - -echo "[head] create job dir: ${JOB_DIR}" -dexec "${HEAD_CONTAINER}" bash -lc "mkdir -p ${JOB_DIR}/logs ${JOB_DIR}/checkpoints ${JOB_DIR}/config" - -SUBMIT_CMD="python3 -m verl.trainer.main_ppo \ -data.train_files=${TRAIN_FILE} \ -data.val_files=${VAL_FILE} \ -data.train_batch_size=256 \ -data.max_prompt_length=512 \ -data.max_response_length=512 \ -actor_rollout_ref.model.path=${MODEL_ID} \ -actor_rollout_ref.actor.optim.lr=1e-6 \ -actor_rollout_ref.actor.ppo_mini_batch_size=64 \ -actor_rollout_ref.actor.ppo_micro_batch_size_per_gpu=4 \ -actor_rollout_ref.rollout.name=sglang \ -actor_rollout_ref.rollout.log_prob_micro_batch_size_per_gpu=8 \ -actor_rollout_ref.rollout.tensor_model_parallel_size=1 \ -actor_rollout_ref.rollout.gpu_memory_utilization=0.4 \ -actor_rollout_ref.ref.log_prob_micro_batch_size_per_gpu=4 \ -critic.optim.lr=1e-5 \ -critic.model.path=${MODEL_ID} \ -critic.ppo_micro_batch_size_per_gpu=4 \ -algorithm.kl_ctrl.kl_coef=0.001 \ -trainer.logger=console \ -trainer.val_before_train=False \ -trainer.n_gpus_per_node=4 \ -trainer.nnodes=2 \ -trainer.save_freq=10 \ -trainer.test_freq=29 \ -trainer.total_epochs=1 \ -trainer.total_training_steps=29 \ -trainer.resume_mode=disable \ -trainer.default_local_dir=${JOB_DIR}/checkpoints \ -+ray_kwargs.ray_init.address=auto \ -hydra.run.dir=${JOB_DIR}/logs/hydra" - -printf "%s\n" "${SUBMIT_CMD}" | dexec "${HEAD_CONTAINER}" bash -lc "cat > ${JOB_DIR}/config/submit_cmd.txt" - -echo "[head] submit PPO via ray job submit (force driver on worker via entrypoint resources)" - -SUBMIT_OUT="$(dexec "${HEAD_CONTAINER}" bash -lc "export HF_HOME=/mnt/shared/hf HUGGINGFACE_HUB_CACHE=/mnt/shared/hf/hub TRANSFORMERS_CACHE=/mnt/shared/hf/transformers HF_ENDPOINT=https://hf-mirror.com PYTHONUNBUFFERED=1; ray job submit --address=http://127.0.0.1:8265 --submission-id='${SUBMISSION_ID}' --entrypoint-num-cpus=1 --entrypoint-resources='{\"worker_node\": 1}' --runtime-env-json='{\"env_vars\":{\"HF_HOME\":\"/mnt/shared/hf\",\"HUGGINGFACE_HUB_CACHE\":\"/mnt/shared/hf/hub\",\"TRANSFORMERS_CACHE\":\"/mnt/shared/hf/transformers\",\"HF_ENDPOINT\":\"https://hf-mirror.com\",\"PYTHONUNBUFFERED\":\"1\"}}' --no-wait -- ${SUBMIT_CMD}")" - -printf "%s\n" "${SUBMIT_OUT}" -printf "%s\n" "${SUBMIT_OUT}" | dexec "${HEAD_CONTAINER}" bash -lc "cat > ${JOB_DIR}/logs/ray_job_submit.out" - -PARSED_SUBMISSION_ID="$(printf "%s\n" "${SUBMIT_OUT}" | sed -r 's/\x1b\\[[0-9;]*m//g' | grep -Eo "raysubmit_[A-Za-z0-9_-]+" | head -n 1 || true)" -if [[ -n "${PARSED_SUBMISSION_ID}" && "${PARSED_SUBMISSION_ID}" != "${SUBMISSION_ID}" ]]; then - echo "WARN: submission id mismatch: expected=${SUBMISSION_ID} parsed=${PARSED_SUBMISSION_ID}" >&2 -fi - -echo "${SUBMISSION_ID}" | dexec "${HEAD_CONTAINER}" bash -lc "cat > ${JOB_DIR}/config/ray_submission_id.txt" -echo "ray submission id: ${SUBMISSION_ID}" - -echo "submitted. track via Ray dashboard: http://:8265 (driver should be scheduled on a worker due to entrypoint resources)" -echo "job dir: ${JOB_DIR}" diff --git a/src/mvp/v1/scripts/50_status.sh b/src/mvp/v1/scripts/50_status.sh deleted file mode 100755 index 43bd50b..0000000 --- a/src/mvp/v1/scripts/50_status.sh +++ /dev/null @@ -1,26 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -# shellcheck source=lib.sh -source "${SCRIPT_DIR}/lib.sh" - -echo "[head] ray status" -dexec "${HEAD_CONTAINER}" bash -lc "ray status || true" - -echo "[head] ray jobs list (optional)" -dexec "${HEAD_CONTAINER}" bash -lc "ray job list --address=http://127.0.0.1:8265 || true" - -LATEST_JOB_DIR="$(dexec "${HEAD_CONTAINER}" bash -lc "ls -1dt /mnt/shared/jobs/* 2>/dev/null | head -n 1 || true")" -if [[ -n "${LATEST_JOB_DIR}" ]]; then - echo "[host] latest job dir: ${LATEST_JOB_DIR}" - echo "[host] ray submission id (if exists):" - SUB_ID="$(dexec "${HEAD_CONTAINER}" bash -lc "cat ${LATEST_JOB_DIR}/config/ray_submission_id.txt 2>/dev/null || true")" - echo "${SUB_ID}" - if [[ -n "${SUB_ID}" ]]; then - echo "[head] ray job status:" - dexec "${HEAD_CONTAINER}" bash -lc "ray job status --address=http://127.0.0.1:8265 ${SUB_ID} || true" - echo "[head] ray job logs (tail):" - dexec "${HEAD_CONTAINER}" bash -lc "ray job logs --address=http://127.0.0.1:8265 ${SUB_ID} 2>/dev/null | tail -n 60 || true" - fi -fi diff --git a/src/mvp/v1/scripts/lib.sh b/src/mvp/v1/scripts/lib.sh deleted file mode 100755 index 0b34457..0000000 --- a/src/mvp/v1/scripts/lib.sh +++ /dev/null @@ -1,48 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" -ROOT_DIR="$(cd "${SCRIPT_DIR}/../../../../" && pwd)" - -COMPOSE_FILE="${ROOT_DIR}/src/mvp/v1/docker-compose.yaml" - -HEAD_CONTAINER="mvp-ray-head" -WORKER0_CONTAINER="mvp-ray-worker-0" -WORKER1_CONTAINER="mvp-ray-worker-1" - -dc() { - docker compose --project-directory "${ROOT_DIR}" -f "${COMPOSE_FILE}" "$@" -} - -require_cmd() { - local cmd="$1" - command -v "${cmd}" >/dev/null 2>&1 || { - echo "missing required command: ${cmd}" >&2 - exit 1 - } -} - -ensure_container_running() { - local name="$1" - if ! docker ps --format '{{.Names}}' | grep -qx "${name}"; then - echo "container not running: ${name}" >&2 - exit 1 - fi -} - -dexec() { - local name="$1" - shift - ensure_container_running "${name}" - docker exec -i "${name}" "$@" -} - -container_ip() { - local name="$1" - ensure_container_running "${name}" - docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' "${name}" -} - -timestamp() { - date +"%Y%m%d_%H%M%S" -} diff --git a/src/mvp/v1/scripts/run_all.sh b/src/mvp/v1/scripts/run_all.sh deleted file mode 100755 index 9737409..0000000 --- a/src/mvp/v1/scripts/run_all.sh +++ /dev/null @@ -1,13 +0,0 @@ -#!/usr/bin/env bash -set -euo pipefail - -SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" - -"${SCRIPT_DIR}/01_up.sh" -"${SCRIPT_DIR}/10_install_verl_editable.sh" -"${SCRIPT_DIR}/20_start_head.sh" -"${SCRIPT_DIR}/21_start_workers.sh" -"${SCRIPT_DIR}/30_prepare_data_and_model.sh" -"${SCRIPT_DIR}/40_submit_ppo_epoch1.sh" -"${SCRIPT_DIR}/50_status.sh" -