269 lines
8.9 KiB
Batchfile
269 lines
8.9 KiB
Batchfile
@echo off
|
||
setlocal enabledelayedexpansion
|
||
|
||
rem Sync project templates to target project.
|
||
rem - Copies templates/memory-bank/ -> <project-root>/memory-bank/
|
||
rem - Copies templates/prompts/ -> <project-root>/docs/prompts/
|
||
rem - Copies templates/AGENTS.template.md -> <project-root>/AGENTS.md
|
||
rem - Copies templates/AGENT_RULES.template.md -> <project-root>/AGENT_RULES.md
|
||
rem Existing targets are NOT overwritten (skip if exists).
|
||
rem
|
||
rem Usage:
|
||
rem sync_templates.bat # sync to current git root
|
||
rem sync_templates.bat -project-root <path> # sync to specified project
|
||
rem sync_templates.bat -force # overwrite existing files
|
||
rem sync_templates.bat -full # append full framework to existing AGENTS.md
|
||
|
||
set "SCRIPT_DIR=%~dp0"
|
||
for %%I in ("%SCRIPT_DIR%..") do set "SRC=%%~fI"
|
||
|
||
set "FORCE=0"
|
||
set "FULL=0"
|
||
set "PROJECT_ROOT="
|
||
|
||
:parse_args
|
||
if "%~1"=="" goto args_done
|
||
if /I "%~1"=="-force" (
|
||
set "FORCE=1"
|
||
shift
|
||
goto parse_args
|
||
)
|
||
if /I "%~1"=="-full" (
|
||
set "FULL=1"
|
||
shift
|
||
goto parse_args
|
||
)
|
||
if /I "%~1"=="-project-root" (
|
||
if "%~2"=="" (
|
||
echo ERROR: -project-root requires a path.
|
||
exit /b 1
|
||
)
|
||
set "PROJECT_ROOT=%~2"
|
||
shift
|
||
shift
|
||
goto parse_args
|
||
)
|
||
if /I "%~1"=="-h" goto show_help
|
||
if /I "%~1"=="-help" goto show_help
|
||
echo ERROR: positional args are not supported. Use -project-root.
|
||
exit /b 1
|
||
|
||
:show_help
|
||
echo Usage:
|
||
echo sync_templates.bat [options]
|
||
echo sync_templates.bat -project-root ^<path^>
|
||
echo.
|
||
echo Options:
|
||
echo -project-root PATH Target project root ^(default: git root^)
|
||
echo -force Overwrite existing files
|
||
echo -full Append full framework (规则优先级 + 新会话开始时) to existing AGENTS.md
|
||
echo -h, -help Show this help
|
||
exit /b 0
|
||
|
||
:args_done
|
||
|
||
rem Determine project root
|
||
if "%PROJECT_ROOT%"=="" (
|
||
for /f "delims=" %%R in ('git -C "%SCRIPT_DIR%" rev-parse --show-toplevel 2^>nul') do set "PROJECT_ROOT=%%R"
|
||
)
|
||
if "%PROJECT_ROOT%"=="" set "PROJECT_ROOT=%cd%"
|
||
for %%I in ("%PROJECT_ROOT%") do set "PROJECT_ROOT=%%~fI"
|
||
|
||
rem Source directories
|
||
set "TEMPLATES_DIR=%SRC%\templates"
|
||
set "MEMORY_BANK_SRC=%TEMPLATES_DIR%\memory-bank"
|
||
set "PROMPTS_SRC=%TEMPLATES_DIR%\prompts"
|
||
set "AGENTS_SRC=%TEMPLATES_DIR%\AGENTS.template.md"
|
||
set "AGENT_RULES_SRC=%TEMPLATES_DIR%\AGENT_RULES.template.md"
|
||
|
||
rem Check source exists
|
||
if not exist "%TEMPLATES_DIR%" (
|
||
echo ERROR: Templates directory not found: %TEMPLATES_DIR%
|
||
exit /b 1
|
||
)
|
||
|
||
rem Skip if source equals destination
|
||
if /I "%SRC%"=="%PROJECT_ROOT%" (
|
||
echo Skip: playbook root equals project root.
|
||
echo Done.
|
||
exit /b 0
|
||
)
|
||
|
||
for /f "usebackq delims=" %%D in (`powershell -NoProfile -Command "Get-Date -Format 'yyyy-MM-dd'"`) do set "SYNC_DATE=%%D"
|
||
if "%SYNC_DATE%"=="" set "SYNC_DATE=%date%"
|
||
|
||
echo Syncing templates to: %PROJECT_ROOT%
|
||
echo.
|
||
|
||
rem 1. Sync memory-bank/
|
||
set "MEMORY_BANK_DST=%PROJECT_ROOT%\memory-bank"
|
||
if exist "%MEMORY_BANK_SRC%" (
|
||
if exist "%MEMORY_BANK_DST%" (
|
||
if "%FORCE%"=="0" (
|
||
echo memory-bank/ already exists. Skip. Use -force to overwrite.
|
||
goto sync_prompts
|
||
)
|
||
)
|
||
if not exist "%MEMORY_BANK_DST%" mkdir "%MEMORY_BANK_DST%"
|
||
xcopy "%MEMORY_BANK_SRC%\*" "%MEMORY_BANK_DST%\" /e /i /y >nul 2>nul
|
||
|
||
rem Rename .template.md to .md
|
||
for %%F in ("%MEMORY_BANK_DST%\*.template.md") do (
|
||
set "OLDNAME=%%~nxF"
|
||
set "NEWNAME=!OLDNAME:.template.md=.md!"
|
||
ren "%%F" "!NEWNAME!"
|
||
)
|
||
|
||
rem Replace {{DATE}} placeholder
|
||
for %%F in ("%MEMORY_BANK_DST%\*.md") do (
|
||
powershell -NoProfile -Command "$f='%%~fF'; $c=Get-Content -Raw $f; $c=$c.Replace('{{DATE}}','%SYNC_DATE%'); Set-Content -Path $f -Value $c -Encoding UTF8 -NoNewline"
|
||
)
|
||
echo Synced: memory-bank/
|
||
) else (
|
||
echo Skip: memory-bank/ templates not found
|
||
)
|
||
|
||
:sync_prompts
|
||
rem 2. Sync docs/prompts/
|
||
set "PROMPTS_DST=%PROJECT_ROOT%\docs\prompts"
|
||
if exist "%PROMPTS_SRC%" (
|
||
if exist "%PROMPTS_DST%" (
|
||
if "%FORCE%"=="0" (
|
||
echo docs/prompts/ already exists. Skip. Use -force to overwrite.
|
||
goto sync_agents
|
||
)
|
||
)
|
||
if not exist "%PROJECT_ROOT%\docs" mkdir "%PROJECT_ROOT%\docs"
|
||
if not exist "%PROMPTS_DST%" mkdir "%PROMPTS_DST%"
|
||
xcopy "%PROMPTS_SRC%\*" "%PROMPTS_DST%\" /e /i /y >nul 2>nul
|
||
|
||
rem Rename .template.md to .md recursively
|
||
for /r "%PROMPTS_DST%" %%F in (*.template.md) do (
|
||
set "OLDNAME=%%~nxF"
|
||
set "NEWNAME=!OLDNAME:.template.md=.md!"
|
||
ren "%%F" "!NEWNAME!"
|
||
)
|
||
|
||
rem Replace {{DATE}} placeholder
|
||
for /r "%PROMPTS_DST%" %%F in (*.md) do (
|
||
powershell -NoProfile -Command "$f='%%~fF'; $c=Get-Content -Raw $f; $c=$c.Replace('{{DATE}}','%SYNC_DATE%'); Set-Content -Path $f -Value $c -Encoding UTF8 -NoNewline"
|
||
)
|
||
echo Synced: docs/prompts/
|
||
) else (
|
||
echo Skip: prompts/ templates not found
|
||
)
|
||
|
||
:sync_agents
|
||
rem 3. Sync AGENTS.md
|
||
set "AGENTS_DST=%PROJECT_ROOT%\AGENTS.md"
|
||
|
||
rem Choose markers based on -full flag
|
||
if "%FULL%"=="1" (
|
||
set "MARKER_START=<!-- playbook:framework:start -->"
|
||
set "MARKER_END=<!-- playbook:framework:end -->"
|
||
set "SECTION_NAME=framework"
|
||
) else (
|
||
set "MARKER_START=<!-- playbook:templates:start -->"
|
||
set "MARKER_END=<!-- playbook:templates:end -->"
|
||
set "SECTION_NAME=templates"
|
||
)
|
||
|
||
if exist "%AGENTS_SRC%" (
|
||
if not exist "%AGENTS_DST%" (
|
||
rem AGENTS.md doesn't exist: create from full template
|
||
copy /y "%AGENTS_SRC%" "%AGENTS_DST%" >nul
|
||
powershell -NoProfile -Command "$f='%AGENTS_DST%'; $c=Get-Content -Raw $f; $c=$c.Replace('{{DATE}}','%SYNC_DATE%'); Set-Content -Path $f -Value $c -Encoding UTF8 -NoNewline"
|
||
echo Created: AGENTS.md
|
||
) else (
|
||
rem AGENTS.md exists: update or append section (extract from template)
|
||
powershell -NoProfile -Command ^
|
||
"$src='%AGENTS_SRC%'; $dst='%AGENTS_DST%'; $date='%SYNC_DATE%'; " ^
|
||
"$markerStart='!MARKER_START!'; $markerEnd='!MARKER_END!'; $sectionName='!SECTION_NAME!'; " ^
|
||
"$templateContent = Get-Content -Raw $src; " ^
|
||
"$extractPattern = '(?s)(' + [regex]::Escape($markerStart) + '.*?' + [regex]::Escape($markerEnd) + ')'; " ^
|
||
"if ($templateContent -match $extractPattern) { " ^
|
||
" $snippetContent = $Matches[1]; " ^
|
||
" $content = Get-Content -Raw $dst; " ^
|
||
" if ($content -match [regex]::Escape($markerStart)) { " ^
|
||
" $replacePattern = '(?s)' + [regex]::Escape($markerStart) + '.*?' + [regex]::Escape($markerEnd); " ^
|
||
" $newContent = $content -replace $replacePattern, $snippetContent; " ^
|
||
" $newContent = $newContent.Replace('{{DATE}}', $date); " ^
|
||
" Set-Content -Path $dst -Value $newContent -Encoding UTF8 -NoNewline; " ^
|
||
" Write-Host \"Updated: AGENTS.md ($sectionName section)\"; " ^
|
||
" } else { " ^
|
||
" $newContent = $content.TrimEnd() + \"`n`n\" + $snippetContent; " ^
|
||
" $newContent = $newContent.Replace('{{DATE}}', $date); " ^
|
||
" Set-Content -Path $dst -Value $newContent -Encoding UTF8 -NoNewline; " ^
|
||
" Write-Host \"Appended: AGENTS.md ($sectionName section)\"; " ^
|
||
" } " ^
|
||
"} else { " ^
|
||
" Write-Host 'Skip: markers not found in template'; " ^
|
||
"}"
|
||
)
|
||
) else (
|
||
echo Skip: AGENTS.template.md not found
|
||
)
|
||
|
||
:sync_agent_rules
|
||
rem 4. Sync AGENT_RULES.md
|
||
set "AGENT_RULES_DST=%PROJECT_ROOT%\AGENT_RULES.md"
|
||
if exist "%AGENT_RULES_SRC%" (
|
||
if exist "%AGENT_RULES_DST%" (
|
||
if "%FORCE%"=="0" (
|
||
echo AGENT_RULES.md already exists. Skip. Use -force to overwrite.
|
||
goto sync_todo
|
||
)
|
||
)
|
||
copy /y "%AGENT_RULES_SRC%" "%AGENT_RULES_DST%" >nul
|
||
powershell -NoProfile -Command "$f='%AGENT_RULES_DST%'; $c=Get-Content -Raw $f; $c=$c.Replace('{{DATE}}','%SYNC_DATE%'); Set-Content -Path $f -Value $c -Encoding UTF8 -NoNewline"
|
||
echo Synced: AGENT_RULES.md
|
||
) else (
|
||
echo Skip: AGENT_RULES.template.md not found
|
||
)
|
||
|
||
:sync_todo
|
||
rem 5. Create TODO.md if not exist
|
||
set "TODO_DST=%PROJECT_ROOT%\TODO.md"
|
||
if not exist "%TODO_DST%" (
|
||
> "%TODO_DST%" echo # TODO
|
||
>> "%TODO_DST%" echo.
|
||
>> "%TODO_DST%" echo ## Plan 1: [计划名称]
|
||
>> "%TODO_DST%" echo.
|
||
>> "%TODO_DST%" echo - [ ] 任务 1
|
||
>> "%TODO_DST%" echo - [ ] 任务 2
|
||
>> "%TODO_DST%" echo.
|
||
>> "%TODO_DST%" echo ---
|
||
>> "%TODO_DST%" echo.
|
||
>> "%TODO_DST%" echo **最后更新**:%SYNC_DATE%
|
||
echo Created: TODO.md
|
||
)
|
||
|
||
rem 6. Create CONFIRM.md if not exist
|
||
set "CONFIRM_DST=%PROJECT_ROOT%\CONFIRM.md"
|
||
if not exist "%CONFIRM_DST%" (
|
||
> "%CONFIRM_DST%" echo # 待确认事项
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo ## 待确认
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo ^<!-- 记录需要确认的事项 --^>
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo ## 已确认
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo ^<!-- 已确认的事项移到这里 --^>
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo ---
|
||
>> "%CONFIRM_DST%" echo.
|
||
>> "%CONFIRM_DST%" echo **最后更新**:%SYNC_DATE%
|
||
echo Created: CONFIRM.md
|
||
)
|
||
|
||
echo.
|
||
echo Done.
|
||
echo.
|
||
echo Next steps:
|
||
echo 1. Edit memory-bank\*.md to fill in project-specific content
|
||
echo 2. Replace remaining {{PLACEHOLDER}} values
|
||
echo 3. Run sync_standards.bat to sync .agents\ rules
|
||
|
||
endlocal
|