chore(gitea): 技能依結束碼分流,可併行的步驟改成同時跑
技能以前只寫成功路徑。腳本回非 0 時,模型得自己猜下一步,猜錯就是靜靜 往下走。現在每一支腳本在檔頭宣告自己的結束碼,技能也逐碼寫明要停、要 問、還是要改參數再呼叫一次。兩支技能補上連線變數的解析步驟,讓缺值在 第一步就浮出來,而不是在中途撞出一行英文錯誤。 流程也拉平了。取內容、選範本、問輸出位置這幾件事彼此不相依,改成同一批 送出;存取庫批次同步從逐一處理改成各存取庫同時進行,一個 owner 底下有 上百個存取庫時差距最明顯。 相依的技能組下限寫進外掛設定,版本推進。
This commit is contained in:
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "jsc-gitea",
|
"name": "jsc-gitea",
|
||||||
"version": "0.1.7",
|
"version": "0.1.8",
|
||||||
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
||||||
"skills": "./skills",
|
"skills": "./skills",
|
||||||
"author": {
|
"author": {
|
||||||
@@ -13,5 +13,12 @@
|
|||||||
"gitea",
|
"gitea",
|
||||||
"skills",
|
"skills",
|
||||||
"cross-tool"
|
"cross-tool"
|
||||||
]
|
],
|
||||||
|
"jsc": {
|
||||||
|
"requires": {
|
||||||
|
"jsc-ask": ">=0.0.6",
|
||||||
|
"jsc-git": ">=0.0.9",
|
||||||
|
"jsc-meta": ">=0.2.2"
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,13 @@
|
|||||||
{
|
{
|
||||||
"name": "jsc-gitea",
|
"name": "jsc-gitea",
|
||||||
"version": "0.1.7",
|
"version": "0.1.8",
|
||||||
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
||||||
"skills": "./skills"
|
"skills": "./skills",
|
||||||
|
"jsc": {
|
||||||
|
"requires": {
|
||||||
|
"jsc-ask": ">=0.0.6",
|
||||||
|
"jsc-git": ">=0.0.9",
|
||||||
|
"jsc-meta": ">=0.2.2"
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+9
-2
@@ -1,6 +1,13 @@
|
|||||||
{
|
{
|
||||||
"name": "jsc-gitea",
|
"name": "jsc-gitea",
|
||||||
"version": "0.1.7",
|
"version": "0.1.8",
|
||||||
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
"description": "Gitea API 工具、Wiki 讀寫、議題轉換、HTML 匯出與存取庫批次同步",
|
||||||
"skills": "./skills/"
|
"skills": "./skills/",
|
||||||
|
"jsc": {
|
||||||
|
"requires": {
|
||||||
|
"jsc-ask": ">=0.0.6",
|
||||||
|
"jsc-git": ">=0.0.9",
|
||||||
|
"jsc-meta": ">=0.2.2"
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,17 +9,16 @@ The link is the only input. The output is one file that opens anywhere, with no
|
|||||||
|
|
||||||
## Steps
|
## Steps
|
||||||
|
|
||||||
1. **Link gate.** Run `tools/gitea-link.sh parse {url}`. Exit 3 or no link in the request: **stop and report it**. Never fall back to the working directory's remote or to a page name the user mentioned in passing. Completion condition: `kind` is `wiki` or `issue`, and `repo` plus `page` or `index` are known.
|
1. **Link gate.** Run `tools/gitea-link.sh parse {url}`. Exit 3, or no link in the request: **stop and report it**. Exit 2 is a usage error — fix the arguments and call again. Never fall back to the working directory's remote or to a page name the user mentioned in passing. This gate runs first because it stops the whole skill more often than any other check, and it costs no API call. Completion condition: `kind` is `wiki` or `issue`, and `repo` plus `page` or `index` are known.
|
||||||
2. **Work out the kind key** — it decides which template applies:
|
2. **Host gate.** Confirm `GITEA_HOST` holds a value in the current shell; ask for it per the `jsc-ask:ask` rules when it does not. `GITEA_TOKEN` needs no inventory — `tools/gitea.sh` resolves it, retries once with the tea CLI login token, and exits 7 when neither works. Completion condition: `GITEA_HOST` holds a value.
|
||||||
- wiki page → `WIKI:{prefix}`, where the prefix is the page name up to the first underscore (`ANALYZE_D3F1A2B0` → `WIKI:ANALYZE`; a page with no underscore uses the whole name).
|
3. **Run these three tracks at the same time.** They are independent, so start them in one batch rather than one after another; only the issue branch of track B waits, and only for track A's `labels` line.
|
||||||
- issue → run `tools/issue.sh labels-of {repo} {index}` and try `ISSUE:{label}` for each label in order; the first one `tools/html-style.sh get` answers with source `project` or `global` wins. No label matches: use `ISSUE:DEFAULT`.
|
- **Track A — content.** Wiki page: `jsc-gitea:wiki` `wiki-get {repo} {page}` for the markdown, plus `wiki-url {repo} {page}` for the source URL; route its exit codes by that skill's table (4 = no such page, 7 = the key is invalid, 8 = other API failure), and every one of them stops this skill with the page name in the report. Issue: `tools/issue.sh show {repo} {index}`, which returns title, labels and body from **one** API call — never call `title`, `body` and `labels-of` separately on the same issue. Exit 1 means the issue could not be read: stop and report the issue number; exit 2 is a usage error, so fix the arguments and call again.
|
||||||
|
- **Track B — template.** Wiki page: `tools/html-style.sh key wiki {page}`. Issue: `tools/html-style.sh key issue {repo} {index} --labels {the names from track A's labels line}`, which spends no extra API call; the labels line arrives before the body, so this track starts well before track A finishes. The script owns both derivation rules — the page-name prefix, and trying each label in order until one is configured. It prints `{key}<TAB>{reason}`; keep the reason, it is how the report says which prefix or label produced the key. Exit 1 means the labels could not be read: **report that first**, then continue with `ISSUE:DEFAULT` and say in the report that the template was picked without labels. Exit 2 is a usage error — fix the arguments and call again. Then run `tools/html-style.sh get {key}`, which always prints `layout<TAB>style<TAB>source`. **Read the third column and report it**: `project` or `global` means the user configured this kind; `default` means it fell back to the DEFAULT row; `builtin` means nothing is configured at all and `report`/`minimal` was used. For `default` and `builtin`, tell the user in one line that `jsc-gitea:html-style` can set this kind's own template.
|
||||||
|
- **Track C — destination.** Ask per the `jsc-ask:ask` rules where the file goes, proposing `./.jsc/html/{page-or-issue}.html`. State the impact scope: a path inside a repository gets committed unless it is ignored.
|
||||||
|
|
||||||
Completion condition: exactly one kind key is chosen, and you can say which label or prefix produced it.
|
Completion condition: the markdown and the document title are in hand, exactly one kind key is chosen with the reason that produced it, the layout, style and source are reported, and the user has confirmed one output path.
|
||||||
3. Run `tools/html-style.sh get {key}`. It always prints `layout<TAB>style<TAB>source`. **Read the third column and report it**: `project` or `global` means the user configured this kind; `default` means it fell back to the DEFAULT row; `builtin` means nothing is configured at all and `report`/`minimal` was used. For `default` and `builtin`, tell the user in one line that `jsc-gitea:html-style` can set this kind's own template. Completion condition: layout, style and source are reported before anything is rendered.
|
4. **Prepare the markdown — this step MUST run as a sub agent.** Convert `[[display|page]]` wiki links to absolute URLs from `wiki-url`; the renderer does not resolve them, so they would ship as literal brackets. Strip personal data — an exported file travels further than the page it came from. Leave everything else exactly as written; this step never rewrites the content. Completion condition: no `[[...]]` remains, and the diff against the source is limited to link conversion and personal-data removal.
|
||||||
4. Fetch the content: `jsc-gitea:wiki` `wiki-get` for a page, or `tools/issue.sh title` plus `tools/issue.sh body` for an issue. Exit 4 (page missing) or an API failure stops the skill with the page name or issue number in the report. Completion condition: the markdown and the document title are in hand.
|
5. Render: `tools/html-render.sh --markdown {file} --title {title} --layout {layout} --style {style} --source-url {absolute URL} --out {path}`. Route every exit code: 0 → the path it printed is the finished file; 1 → Gitea's renderer or the write failed, so report it and stop, with no half-rendered file left behind; 2 → a usage error or a missing markdown file, so fix the arguments and call again; 4 → the layout or style template file is gone, so report which pair was asked for and send the user to `jsc-gitea:html-style` rather than editing the configuration by hand. Completion condition: the file exists, and the report names its path, the layout, the style and where that pair came from.
|
||||||
5. **Prepare the markdown — this step MUST run as a sub agent.** Convert `[[display|page]]` wiki links to absolute URLs from `wiki-url`; the renderer does not resolve them, so they would ship as literal brackets. Strip personal data — an exported file travels further than the page it came from. Leave everything else exactly as written; this step never rewrites the content. Completion condition: no `[[...]]` remains, and the diff against the source is limited to link conversion and personal-data removal.
|
|
||||||
6. Ask per `jsc-ask:ask` rules where the file goes, proposing `./.jsc/html/{page-or-issue}.html`. State the impact scope: a path inside a repository gets committed unless it is ignored. Completion condition: the user has confirmed one output path.
|
|
||||||
7. Render: `tools/html-render.sh --markdown {file} --title {title} --layout {layout} --style {style} --source-url {absolute URL} --out {path}`. Exit 1 means Gitea's renderer failed — report it and stop, with no half-rendered file left behind. Completion condition: the file exists, and the report names its path, the layout, the style and where that pair came from.
|
|
||||||
|
|
||||||
## Rules
|
## Rules
|
||||||
|
|
||||||
|
|||||||
@@ -10,10 +10,10 @@ One kind of page, one layout, one style. `jsc-gitea:html-export` reads what this
|
|||||||
## Steps
|
## Steps
|
||||||
|
|
||||||
1. **Settle the kind key.** Show the current configuration with `tools/html-style.sh list` first, then ask per `jsc-ask:ask` rules which kind this run sets. The three shapes are fixed: `WIKI:{page-name prefix}` (`WIKI:PLAN`, `WIKI:ANALYZE`, `WIKI:LOG` …), `ISSUE:{label name}` (`ISSUE:bug`), and `DEFAULT` for everything that matches nothing else. Every option states its impact scope — `DEFAULT` changes every kind that has no row of its own. Completion condition: exactly one key is agreed, and its current value from `tools/html-style.sh get {key}` has been read back with its source column.
|
1. **Settle the kind key.** Show the current configuration with `tools/html-style.sh list` first, then ask per `jsc-ask:ask` rules which kind this run sets. The three shapes are fixed: `WIKI:{page-name prefix}` (`WIKI:PLAN`, `WIKI:ANALYZE`, `WIKI:LOG` …), `ISSUE:{label name}` (`ISSUE:bug`), and `DEFAULT` for everything that matches nothing else. Every option states its impact scope — `DEFAULT` changes every kind that has no row of its own. Completion condition: exactly one key is agreed, and its current value from `tools/html-style.sh get {key}` has been read back with its source column.
|
||||||
2. **Pick the layout — offer all six.** Run `tools/html-style.sh layouts`; it prints each name with its Traditional Chinese description, taken from the template file itself. Present all six as options per `jsc-ask:ask` rules, each with what it does to the content (`report` builds a table of contents beside the text, `slide` turns every `##` into a keyboard-flipped page, `dashboard` turns them into cards, `spec` freezes table headers, `timeline` strings them along a line, `onepager` narrows everything into one printable page). Completion condition: the user has picked one layout name that the script listed.
|
2. **Pick the layout — offer all six.** Run `tools/html-style.sh layouts`; it prints each name with its Traditional Chinese description, taken from the template file itself. `list`, `get`, `layouts` and `styles` exit 2 on a usage error — fix the arguments and call again. An empty listing means the template directory is missing, which stops this skill: report the path rather than offering a name the export cannot use. Present all six as options per `jsc-ask:ask` rules, each with what it does to the content (`report` builds a table of contents beside the text, `slide` turns every `##` into a keyboard-flipped page, `dashboard` turns them into cards, `spec` freezes table headers, `timeline` strings them along a line, `onepager` narrows everything into one printable page). Completion condition: the user has picked one layout name that the script listed.
|
||||||
3. **Pick the style — offer all five.** Run `tools/html-style.sh styles` and present every one it prints (`minimal`, `corporate`, `dark`, `print`, `vivid`) with its description. Never trim the list to a shortlist: the point of this skill is that the user sees the whole set. Completion condition: the user has picked one style name that the script listed.
|
3. **Pick the style — offer all five.** Run `tools/html-style.sh styles` and present every one it prints (`minimal`, `corporate`, `dark`, `print`, `vivid`) with its description. Never trim the list to a shortlist: the point of this skill is that the user sees the whole set. Completion condition: the user has picked one style name that the script listed.
|
||||||
4. **Pick the scope.** Ask per `jsc-ask:ask` rules: `--project` writes `./.jsc/html-styles`, which only applies inside this working directory and is committed with the repository; `--global` writes `$JSC_HOME/html-styles.conf`, which follows the user across every project on this machine. State that the project file wins whenever both hold the same key. Completion condition: the user has picked one scope.
|
4. **Pick the scope.** Ask per `jsc-ask:ask` rules: `--project` writes `./.jsc/html-styles`, which only applies inside this working directory and is committed with the repository; `--global` writes `$JSC_HOME/html-styles.conf`, which follows the user across every project on this machine. State that the project file wins whenever both hold the same key. Completion condition: the user has picked one scope.
|
||||||
5. Write it: `tools/html-style.sh set {key} {layout} {style} [--project|--global]`. Exit 4 means the name is not one of the listed templates — go back to step 2 or 3 rather than editing the file by hand. Completion condition: the script exits 0 and prints the file it wrote.
|
5. Write it: `tools/html-style.sh set {key} {layout} {style} [--project|--global]`. Route every exit code: 0 → the file it printed now holds the pair; 1 → the settings file's directory could not be created, so report the path and stop, since nothing was written; 2 → a usage error, such as a missing name or a scope flag that is neither `--project` nor `--global`, so fix the arguments and call again; 4 → the layout or style name has no template file, so go back to step 2 or step 3 rather than editing the settings file by hand. Completion condition: the script exits 0 and prints the file it wrote.
|
||||||
6. Read it back with `tools/html-style.sh get {key}` and report the resolved layout, style and source. Completion condition: the source column shows `project` or `global`, matching the scope chosen in step 4.
|
6. Read it back with `tools/html-style.sh get {key}` and report the resolved layout, style and source. Completion condition: the source column shows `project` or `global`, matching the scope chosen in step 4.
|
||||||
|
|
||||||
## Rules
|
## Rules
|
||||||
|
|||||||
@@ -7,11 +7,12 @@ description: Batch-sync all readable repos of a chosen Gitea owner into the work
|
|||||||
|
|
||||||
## Steps
|
## Steps
|
||||||
|
|
||||||
1. Before calling `tools/gitea.sh`, resolve `GITEA_HOST` and `GITEA_TOKEN` from the current shell environment (also check `tea login list` for a usable login token when `GITEA_TOKEN` is unset). If `GITEA_HOST` is unresolvable, or `GITEA_TOKEN` is unset and no tea login token exists either, ask the user for the missing value per the `jsc-ask:ask` rules before proceeding to any `tools/gitea.sh` call. Done when `GITEA_HOST` holds a value and either `GITEA_TOKEN` or a tea login token is available.
|
1. Run `tools/gitea.sh owners` to list every `{owner}` the user can read. The script reads `GITEA_HOST` and `GITEA_TOKEN` from the inherited environment and retries once with the tea CLI login token, so take no separate inventory first — a missing value surfaces here, before any work is done. Route on the result: at least one `{owner}` printed → next step; the script stops with `GITEA_HOST is required` or `GITEA_TOKEN is required` → ask the user for that one value per the `jsc-ask:ask` rules and run the command again, guessing no host; exit 7 → report that the key is invalid or lacks permission, and stop; exit 8 → report the HTTP status in the message, and stop; exit 0 with no output → report that this key can read no owner, and stop. Done when at least one `{owner}` is printed, or the run stopped with one of those reasons.
|
||||||
2. Run `tools/gitea.sh owners` to list every `{owner}` the user can read. Done when the command has printed at least one `{owner}`.
|
2. Ask the user which `{owner}` to sync, per the `jsc-ask:ask` rules. Every option states the owner's repo count and impact scope. Done when the user has named exactly one `{owner}` from that list.
|
||||||
3. Ask the user which `{owner}` to sync, per the `jsc-ask:ask` rules. Every option states the owner's repo count and impact scope. Done when the user has named exactly one `{owner}` from that list.
|
3. Run `tools/gitea.sh repos {owner}` to list every readable `{repo}` under that owner. Exit 7 and exit 8 stop the run with the same report as step 1; an empty list means this owner has no readable repo and there is nothing to sync. Done when the command has printed the full `{owner}/{repo}` list for the chosen owner, or the run stopped.
|
||||||
4. Run `tools/gitea.sh repos {owner}` to list every readable `{repo}` under that owner. Done when the command has printed the full `{owner}/{repo}` list for the chosen owner.
|
4. Sync every `{repo}` from step 3 **in parallel — one sub agent per repo, all launched in the same batch**, never one after another. Each repo has its own directory and its own remote, so nothing makes them wait for each other, and a hundred-repo owner otherwise costs a hundred sequential clones. Each sub agent does this:
|
||||||
5. Sync each `{repo}` one by one. This step **MUST run as a sub agent** (one sub agent per repo):
|
1. Run `tools/repo-sync.sh {owner}/{repo}`. The script owns the clone-versus-pull decision and the base-branch precedence, so run no `git clone`, `git checkout` or `git pull` by hand, and derive no branch name yourself. Route on its single line of output: `cloned` or `updated` (exit 0) → this repo is done; `dirty {branch}` (exit 0) → go to substep 2; `failed {reason}` (exit 1) → record that reason and stop this repo. Done when exactly one of those four outcomes is recorded for this repo.
|
||||||
1. Run `tools/repo-sync.sh {owner}/{repo}`. The script owns the clone-versus-pull decision and the base-branch precedence, so run no `git clone`, `git checkout` or `git pull` by hand, and derive no branch name yourself. Route on its single line of output: `cloned` or `updated` → this repo is done; `dirty {branch}` → go to substep 2; `failed {reason}` → record that reason and stop this repo. Done when exactly one of those four outcomes is recorded for this repo.
|
|
||||||
2. `dirty {branch}` → call `jsc-git:pr` with `{branch}` from that same output line as the base, passed through verbatim. It commits, branches, pushes and opens the PR itself, so add none of those steps. Done when `jsc-git:pr` returns the PR URL and reports it with the table format in `jsc-meta/references/pr-report.md`.
|
2. `dirty {branch}` → call `jsc-git:pr` with `{branch}` from that same output line as the base, passed through verbatim. It commits, branches, pushes and opens the PR itself, so add none of those steps. Done when `jsc-git:pr` returns the PR URL and reports it with the table format in `jsc-meta/references/pr-report.md`.
|
||||||
6. Report the sync result for every repo: cloned, updated, PR table row, or the failure reason. Done when every `{repo}` from step 4 carries one of those four results, and all PR rows share one table when more than one PR exists.
|
|
||||||
|
Done when every repo's sub agent has returned one of those outcomes; one repo failing never cancels the others.
|
||||||
|
5. Report the sync result for every repo: cloned, updated, PR table row, or the failure reason. Done when every `{repo}` from step 3 carries one of those four results, and all PR rows share one table when more than one PR exists.
|
||||||
|
|||||||
@@ -9,12 +9,20 @@ The wiki link is the only input. Everything else — repository, page name, host
|
|||||||
|
|
||||||
## Steps
|
## Steps
|
||||||
|
|
||||||
1. **Link gate.** Run `tools/gitea-link.sh parse {url}` on the link the user gave. Exit 3, no link in the request, or `kind=issue` (this skill reads wiki pages, not issues) all mean the same thing: **stop and report which one it was**. Never ask for a repository name instead, and never fall back to the working directory's remote — a page written into the wrong repository's issue tracker is public and hard to take back. Completion condition: `kind=wiki`, and `repo`, `page` and `host` are known.
|
1. **Input gate — the link and the host, checked in the same batch.** Neither depends on the other, so run both before anything else and report every failure found, not just the first.
|
||||||
2. Read the page with `jsc-gitea:wiki` (`wiki-get {repo} {page}`). Exit 4 means the page does not exist — stop and report the page name. Take the page's absolute URL from `wiki-url` in the same pass; it goes into the issue body. Completion condition: the page's markdown and its absolute URL are both in hand.
|
- **The link.** Run `tools/gitea-link.sh parse {url}` on the link the user gave. Exit 3, no link in the request, or `kind=issue` (this skill reads wiki pages, not issues) all mean the same thing: **stop and report which one it was**. Exit 2 is a usage error — fix the arguments and call again. Never ask for a repository name instead, and never fall back to the working directory's remote — a page written into the wrong repository's issue tracker is public and hard to take back.
|
||||||
3. **Draft the issue — this step MUST run as a sub agent.** Title: the page's first heading, or the page name when it has none. Body: the page content in Traditional Chinese, opening with a 「來源:{絕對網址}」 line so the issue points back at the wiki. Convert `[[display|page]]` links to absolute URLs (`wiki-url`), because `[[...]]` resolves only inside a wiki. Drop personal data — an issue is read by more people than a wiki page. Write `issue.sh create` 前先確認,因為建立議題本身也會要求確認。Completion condition: title and body file exist, the body carries the source line, and no `[[...]]` link is left in it.
|
- **The host.** Confirm `GITEA_HOST` holds a value in the current shell; ask for it per the `jsc-ask:ask` rules when it does not. `GITEA_TOKEN` needs no inventory — `tools/gitea.sh` resolves it, retries once with the tea CLI login token, and exits 7 when neither works.
|
||||||
4. **Labels come from what the repository already has.** Run `tools/issue.sh labels {repo}`, propose the fitting ones with a reason each, and confirm per `jsc-ask:ask` rules — every option states its impact scope (a label drives filters and board rules, so a wrong one routes the work to the wrong queue). Turn the confirmed names into ids with `tools/issue.sh label-ids`. An empty label list, or nothing fitting: ask whether to create the issue with no label, and record that answer. **Never invent a label that the repository does not have.** Completion condition: the user has confirmed a label set — possibly empty — and its ids are resolved.
|
|
||||||
5. **Project board.** Run `tools/issue.sh projects {repo}`. Exit 3 means this Gitea has no board API: say so plainly, and hand the user the board URL the script printed so they can drag the issue in themselves. A board list comes back: let the user pick one per `jsc-ask:ask` rules, attach it, and report the failure verbatim if the attach call is refused. Completion condition: the issue is either attached to a board, or the report states in one line that the board link is still outstanding and who has to do it.
|
Completion condition: the parse printed `kind=wiki` with `repo`, `page` and `host` known, **and** `GITEA_HOST` holds a value — both, or the run has stopped with the reason named.
|
||||||
6. Create the issue: `tools/issue.sh create {repo} {title} {body-file} [--labels {ids}]`. Report the `index=` and `url=` it prints. Completion condition: the issue URL is reported to the user, together with the labels applied and the board status from step 5.
|
2. **Run these three tracks at the same time.** The label list and the board list depend on the repository only, not on the page, so they start in the same batch as the read rather than queueing behind the draft.
|
||||||
|
- **Track A — read and draft.** Read the page with `jsc-gitea:wiki` (`wiki-get {repo} {page}`) and take its absolute URL from `wiki-url` in the same pass. Route the exit codes by that skill's table: 4 means the page does not exist, 7 means the key is invalid or lacks permission, 8 is any other API failure — all three stop this skill with the page name in the report. **Drafting MUST run as a sub agent.** Title: the page's first heading, or the page name when it has none. Body: the page content in Traditional Chinese, opening with a 「來源:{絕對網址}」 line so the issue points back at the wiki. Convert `[[display|page]]` links to absolute URLs (`wiki-url`), because `[[...]]` resolves only inside a wiki. Drop personal data — an issue is read by more people than a wiki page.
|
||||||
|
- **Track B — label list.** Run `tools/issue.sh labels {repo}`. Exit 1 means the label list could not be read: stop and report it, because the alternative is inventing labels. Exit 2 is a usage error — fix the arguments and call again.
|
||||||
|
- **Track C — board list.** Run `tools/issue.sh projects {repo}`. Exit 3 means this Gitea has no board API — keep the board URL the script printed for step 4. Exit 1 means the call failed for another reason: report it and treat the board link as outstanding. Exit 2 is a usage error — fix the arguments and call again.
|
||||||
|
|
||||||
|
Completion condition: the title and body file exist with the source line and no `[[...]]` left in the body, the repository's label list is in hand or the run has stopped, and the board list is either in hand or recorded as unavailable.
|
||||||
|
3. **Labels come from what the repository already has.** Propose the fitting ones from track B's list with a reason each, and confirm per `jsc-ask:ask` rules — every option states its impact scope (a label drives filters and board rules, so a wrong one routes the work to the wrong queue). Turn the confirmed names into ids with `tools/issue.sh label-ids {repo} {names}`. Exit 4 means a name is not in the repository: go back to the list and pick again, never create the label to make the command pass. Exit 1 means the call failed — report it and stop. An empty label list, or nothing fitting: ask whether to create the issue with no label, and record that answer. **Never invent a label that the repository does not have.** Completion condition: the user has confirmed a label set — possibly empty — and its ids are resolved.
|
||||||
|
4. **Project board.** Track C returned a board list: let the user pick one per `jsc-ask:ask` rules, attach it, and report the failure verbatim if the attach call is refused. Track C exited 3: say plainly that this Gitea has no board API, and hand the user the board URL the script printed so they can drag the issue in themselves. Completion condition: the issue is either attached to a board, or the report states in one line that the board link is still outstanding and who has to do it.
|
||||||
|
5. Create the issue: `tools/issue.sh create {repo} {title} {body-file} [--labels {ids}]`. The script asks for confirmation before it writes, so expect that prompt and hand the user the title, the labels and the board it is about to apply. Exit 0: report the `index=` and `url=` it prints. Exit 1 means no issue was created — report that plainly, and hand back the path of the drafted body file so the draft is not lost. Exit 2 is a usage error, usually a body file that is not there — fix the arguments and call again. Completion condition: the issue URL is reported to the user together with the labels applied and the board status from step 4, or the report states that no issue was created and where the draft is.
|
||||||
|
|
||||||
## Rules
|
## Rules
|
||||||
|
|
||||||
|
|||||||
@@ -6,6 +6,7 @@
|
|||||||
# 規則:
|
# 規則:
|
||||||
# 先取 SHA-1 前 8 碼大寫。
|
# 先取 SHA-1 前 8 碼大寫。
|
||||||
# 若首碼為 0-9、A、B、C,改成 H 加上原 SHA-1 前 7 碼。
|
# 若首碼為 0-9、A、B、C,改成 H 加上原 SHA-1 前 7 碼。
|
||||||
|
# 結束碼: 0=成功 1=這台機器沒有 sha1sum 也沒有 shasum,算不出雜湊
|
||||||
set -eu
|
set -eu
|
||||||
|
|
||||||
input=''
|
input=''
|
||||||
|
|||||||
+8
-2
@@ -12,8 +12,14 @@
|
|||||||
# 照樣印出來再退出,退出碼仍是 0:留言不會因為 PR 剛好合併就消失。
|
# 照樣印出來再退出,退出碼仍是 0:留言不會因為 PR 剛好合併就消失。
|
||||||
# 輸出: 全部繁中,留言行維持 gitea.sh pr-comments 的原格式
|
# 輸出: 全部繁中,留言行維持 gitea.sh pr-comments 的原格式
|
||||||
# 「{時間}<TAB>{作者}<TAB>{類型}<TAB>{內容}」,呼叫端可直接用 cut -f 取欄位。
|
# 「{時間}<TAB>{作者}<TAB>{類型}<TAB>{內容}」,呼叫端可直接用 cut -f 取欄位。
|
||||||
# 退出碼: 0 = PR 已合併或關閉,印出最終狀態;10 = 有新留言待呼叫端跑決策樹;
|
# 結束碼: 0=PR 已合併或關閉,最終狀態印在 stdout。盯完了,不用再盯一次。
|
||||||
# 2 = 參數錯誤或第一輪就連不上 Gitea;3 = 查不到該 PR。
|
# 2=用法或環境問題:參數個數不對、第一個參數不是 {owner}/{repo}、PR 編號不是數字、
|
||||||
|
# JSC_PR_WATCH_INTERVAL 不是正整數秒、建不出暫存檔,或第一輪就連不上 Gitea。
|
||||||
|
# 照 stderr 的訊息修參數或 GITEA_HOST、GITEA_TOKEN,再重新盯。
|
||||||
|
# 3=查不到該 PR。確認存取庫與 PR 編號再重新盯,不要原樣重試——
|
||||||
|
# 編號打錯會變成永遠輪詢一支不存在的 PR。
|
||||||
|
# 10=有新留言,內容印在 stdout。接手跑決策樹處理完,再重新盯同一支 PR。
|
||||||
|
# 130=收到 INT 或 TERM 訊號而中止。狀態檔留著,重新盯會從上次那則留言接下去。
|
||||||
# 護欄: gitea.sh pr-status 對不存在的 PR 會印「? none none」並且 exit 0。
|
# 護欄: gitea.sh pr-status 對不存在的 PR 會印「? none none」並且 exit 0。
|
||||||
# 所以 state 只認 open 與 closed、merged 只認 true 與 false,對不上就回 3。
|
# 所以 state 只認 open 與 closed、merged 只認 true 與 false,對不上就回 3。
|
||||||
# 少了這道白名單,PR 編號打錯會變成永遠輪詢一支不存在的 PR。
|
# 少了這道白名單,PR 編號打錯會變成永遠輪詢一支不存在的 PR。
|
||||||
|
|||||||
@@ -11,6 +11,9 @@
|
|||||||
# 輸出: 恰好一行,cloned、updated、dirty {分支} 或 failed {原因}。
|
# 輸出: 恰好一行,cloned、updated、dirty {分支} 或 failed {原因}。
|
||||||
# 前三種 exit 0;failed exit 1。
|
# 前三種 exit 0;failed exit 1。
|
||||||
# dirty 會把解析好的基準分支一起帶出來,呼叫端直接拿去當 PR 的 base。
|
# dirty 會把解析好的基準分支一起帶出來,呼叫端直接拿去當 PR 的 base。
|
||||||
|
# 結束碼: 0=同步完成,輸出是 cloned、updated 或 dirty {分支}
|
||||||
|
# 1=失敗,輸出是 failed {原因};參數錯誤、clone-url 取不到、fetch/checkout/pull 失敗、
|
||||||
|
# 以及找不到基準分支都走這一碼。只有 0 與 1 兩種。
|
||||||
set -u
|
set -u
|
||||||
|
|
||||||
script_dir=$(CDPATH= cd -- "$(dirname -- "$0")" && pwd)
|
script_dir=$(CDPATH= cd -- "$(dirname -- "$0")" && pwd)
|
||||||
|
|||||||
Reference in New Issue
Block a user