@a9n-shoji/rvw 0.1.1 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +18 -0
- package/README.md +39 -12
- package/dist/cli.mjs +486 -54
- package/dist/cli.mjs.map +4 -4
- package/dist/web/assets/DocumentViewer-CNgHpCuL.js +1560 -0
- package/dist/web/assets/WalkthroughViewer-BVB3ETHG.js +1 -0
- package/dist/web/assets/{abnfDiagram-N423BO3Z-Ck9r3vgI.js → abnfDiagram-N423BO3Z-0v-ndtqQ.js} +1 -1
- package/dist/web/assets/architecture-TIHT7OUA-BjGWtjPU.js +1 -0
- package/dist/web/assets/{architectureDiagram-T3A2C74G-CuKnSDyu.js → architectureDiagram-T3A2C74G-WSNJ-tZE.js} +1 -1
- package/dist/web/assets/{blockDiagram-VBNYF7ZC-BQg6daf-.js → blockDiagram-VBNYF7ZC-lmMbEUwI.js} +1 -1
- package/dist/web/assets/{c4Diagram-5PPSVZJV-DlH9a39M.js → c4Diagram-5PPSVZJV-BrN5YVV8.js} +1 -1
- package/dist/web/assets/channel-DkH22XO0.js +1 -0
- package/dist/web/assets/{chunk-2GRJ4B5K-BVLXBbte.js → chunk-2GRJ4B5K-gt2JPyrH.js} +1 -1
- package/dist/web/assets/{chunk-4I5QYGJK-DiwTdMc_.js → chunk-4I5QYGJK-Cg5GZ_-7.js} +1 -1
- package/dist/web/assets/{chunk-5RXB4S5H-DxlG3rKg.js → chunk-5RXB4S5H-BdhRGvxW.js} +1 -1
- package/dist/web/assets/{chunk-6Q2QTUOP-DOnYF_EB.js → chunk-6Q2QTUOP-B1DYWNVJ.js} +1 -1
- package/dist/web/assets/{chunk-7Z6QIM7H-e6n3pq6e.js → chunk-7Z6QIM7H-D2YImamZ.js} +1 -1
- package/dist/web/assets/{chunk-GF5L2VYU-FUD5NaJd.js → chunk-GF5L2VYU-CWtwL_CM.js} +1 -1
- package/dist/web/assets/{chunk-I66GZJ75-CgtIbVp9.js → chunk-I66GZJ75-DdoGlxMt.js} +1 -1
- package/dist/web/assets/{chunk-JQJVKLGR-m8efG8h-.js → chunk-JQJVKLGR-CVWAp3XP.js} +1 -1
- package/dist/web/assets/{chunk-KBJHAD2P-C0ildSCF.js → chunk-KBJHAD2P-BBacwg3J.js} +1 -1
- package/dist/web/assets/{chunk-NSK5VX7P-DJim9vRL.js → chunk-NSK5VX7P-1AsXiBV3.js} +1 -1
- package/dist/web/assets/{chunk-QR6OTTB3-D3ng5jSq.js → chunk-QR6OTTB3-DL2s5pNp.js} +1 -1
- package/dist/web/assets/{chunk-UBXNYLIW-r4FNgMUm.js → chunk-UBXNYLIW-mu3fkNQI.js} +1 -1
- package/dist/web/assets/{chunk-W5SLKNZC-BxwOtp_h.js → chunk-W5SLKNZC-BAwhMBBb.js} +1 -1
- package/dist/web/assets/{chunk-WRU74C26-DAa9M2Ku.js → chunk-WRU74C26-C7IeXZaP.js} +1 -1
- package/dist/web/assets/classDiagram-JCYQIIEL-C6Z4rmZR.js +1 -0
- package/dist/web/assets/classDiagram-v2-OCEON4UE-C6Z4rmZR.js +1 -0
- package/dist/web/assets/{cynefin-VYW2F7L2-D_MdPIfm.js → cynefin-VYW2F7L2-DNisGvNv.js} +1 -1
- package/dist/web/assets/{cynefinDiagram-MW4NZA55-BQ16VR2b.js → cynefinDiagram-MW4NZA55-BA27gOTz.js} +1 -1
- package/dist/web/assets/{dagre-VZM6K2ZE-BcYktfC7.js → dagre-VZM6K2ZE-vo_1YAuM.js} +1 -1
- package/dist/web/assets/{diagram-7IWD3JNH-BQ-4OKZa.js → diagram-7IWD3JNH-DLLdUj0_.js} +1 -1
- package/dist/web/assets/{diagram-B4RE2ZJO-C24yZ4GQ.js → diagram-B4RE2ZJO-BV0WyNA-.js} +1 -1
- package/dist/web/assets/{diagram-LBJQPF4R-wMs9ij7l.js → diagram-LBJQPF4R-DXxKSx2U.js} +1 -1
- package/dist/web/assets/{diagram-Q27KOJAE-CQR8qV1D.js → diagram-Q27KOJAE-DsQ2GzIK.js} +1 -1
- package/dist/web/assets/{diagram-UB23O5K3-D8Fm2CWy.js → diagram-UB23O5K3-DfjElFP1.js} +1 -1
- package/dist/web/assets/{ebnfDiagram-BXEA7PRR-DctbWdRA.js → ebnfDiagram-BXEA7PRR-cYu0XV1a.js} +1 -1
- package/dist/web/assets/{erDiagram-JOGREHBK-CMXJzItT.js → erDiagram-JOGREHBK-DnsLBHaV.js} +1 -1
- package/dist/web/assets/eventmodeling-45OFAUF4-BUAcQ5NU.js +1 -0
- package/dist/web/assets/flowDiagram-UKHOOZJN-hAe9ojjP.js +1 -0
- package/dist/web/assets/{ganttDiagram-PKOTCBZU-B6UdI6h5.js → ganttDiagram-PKOTCBZU-CVD5gq3E.js} +1 -1
- package/dist/web/assets/{gitGraph-TEB2WS4Q-C7YUJfov.js → gitGraph-TEB2WS4Q-C_j0n-Kw.js} +1 -1
- package/dist/web/assets/{gitGraphDiagram-DS77QQ5N-CKIazrRX.js → gitGraphDiagram-DS77QQ5N-qACevJmW.js} +1 -1
- package/dist/web/assets/index-Coye1BY5.js +384 -0
- package/dist/web/assets/{index-B8_aim9s.css → index-DFdYNMZE.css} +1 -1
- package/dist/web/assets/{info-DKCQHKI2-Dj4QbgxZ.js → info-DKCQHKI2-Cmkbz3Yi.js} +1 -1
- package/dist/web/assets/{infoDiagram-6WML65LV-CkPZHoSH.js → infoDiagram-6WML65LV-CDrAem7M.js} +1 -1
- package/dist/web/assets/{ishikawaDiagram-WSZJBQD7-C1U-aqaM.js → ishikawaDiagram-WSZJBQD7-DXgCnFqW.js} +1 -1
- package/dist/web/assets/{journeyDiagram-NVQOT4AX-BFmnFTx5.js → journeyDiagram-NVQOT4AX-1KW-I7DV.js} +1 -1
- package/dist/web/assets/{kanban-definition-27J2QSJJ-C5KXffho.js → kanban-definition-27J2QSJJ-CCt75OuF.js} +1 -1
- package/dist/web/assets/{line-CPlnGb39.js → line-DQfkDi_r.js} +1 -1
- package/dist/web/assets/markdown-source-map-_dS1q5Dg.js +7 -0
- package/dist/web/assets/{mermaid-parser.core-CQYajAMQ.js → mermaid-parser.core-B7TMMtY0.js} +3 -3
- package/dist/web/assets/{mermaid.core-SFGI5XV8.js → mermaid.core-B93x-7Mk.js} +4 -4
- package/dist/web/assets/{mindmap-definition-FAOFIHXS-Dxek7WcS.js → mindmap-definition-FAOFIHXS-Dyt28V6S.js} +1 -1
- package/dist/web/assets/{packet-7NZHBO7P-CAR0tDyo.js → packet-7NZHBO7P-zQ0u35s3.js} +1 -1
- package/dist/web/assets/{pegDiagram-VL7TDLO6-CN_CBGXn.js → pegDiagram-VL7TDLO6-et0KHGIE.js} +1 -1
- package/dist/web/assets/{pie-RZYD4A2V-CAy1ZkLF.js → pie-RZYD4A2V-uur86LkQ.js} +1 -1
- package/dist/web/assets/{pieDiagram-7S7Q4E2Y-Do--6qr_.js → pieDiagram-7S7Q4E2Y-c027WPTB.js} +1 -1
- package/dist/web/assets/{quadrantDiagram-CIZ2JOQS-_d72nP_y.js → quadrantDiagram-CIZ2JOQS-BtSV4E-0.js} +1 -1
- package/dist/web/assets/{radar-I7S5WNFK-D_NREiMx.js → radar-I7S5WNFK-B_g0VZMF.js} +1 -1
- package/dist/web/assets/{railroad-3IZDKUUU-DU7RDpQt.js → railroad-3IZDKUUU-VFLsM_Em.js} +1 -1
- package/dist/web/assets/railroad-abnf-AHOZXSZD-TVRi9_2L.js +1 -0
- package/dist/web/assets/railroad-ebnf-EBAXGLYW-B5B-JrS4.js +1 -0
- package/dist/web/assets/railroad-peg-LSFZ7HO6-CfIpa6ba.js +1 -0
- package/dist/web/assets/{railroadDiagram-AXF67PYL-DNZ982Bc.js → railroadDiagram-AXF67PYL-uOtnxRbQ.js} +1 -1
- package/dist/web/assets/{requirementDiagram-LRYGKXZP-BNEqDsk3.js → requirementDiagram-LRYGKXZP-DGSZAsj4.js} +1 -1
- package/dist/web/assets/{sankeyDiagram-W5VNT64P-BBdI8stM.js → sankeyDiagram-W5VNT64P-CCDk8Vxt.js} +1 -1
- package/dist/web/assets/{sequenceDiagram-SI44F4Z6-3zzNyCI7.js → sequenceDiagram-SI44F4Z6-Ce-Jzdk5.js} +1 -1
- package/dist/web/assets/{stateDiagram-OKZ733FA-PtqkKvef.js → stateDiagram-OKZ733FA-BYpYzyEa.js} +1 -1
- package/dist/web/assets/stateDiagram-v2-UEYNNEHI-BJFG9cb2.js +1 -0
- package/dist/web/assets/{swimlanes-SLNWSIFB-CPWjF8YR.js → swimlanes-SLNWSIFB-BL-CUc6d.js} +1 -1
- package/dist/web/assets/swimlanesDiagram-ULZ7WXOC-BS8L8fb1.js +8 -0
- package/dist/web/assets/{timeline-definition-Z64GVDOM-Cyh2AdbF.js → timeline-definition-Z64GVDOM-p9pkof_K.js} +1 -1
- package/dist/web/assets/{treeView-QDETBFTQ-zPmED5io.js → treeView-QDETBFTQ-dRhXTU9p.js} +1 -1
- package/dist/web/assets/{treemap-6X3UGDF4-Cd2gjC8X.js → treemap-6X3UGDF4-CZHe3dIh.js} +1 -1
- package/dist/web/assets/{vennDiagram-T6HMQDX7-BaNEKHnw.js → vennDiagram-T6HMQDX7-ipODJegx.js} +1 -1
- package/dist/web/assets/{wardley-OPB4EBWU-B5ry0Fo7.js → wardley-OPB4EBWU-CxHlVjkF.js} +1 -1
- package/dist/web/assets/{wardleyDiagram-T6FBY63Y-BHvM4Wb0.js → wardleyDiagram-T6FBY63Y-YarkIncH.js} +1 -1
- package/dist/web/assets/{xychartDiagram-ELKLHX3M-Qgza2Rjo.js → xychartDiagram-ELKLHX3M-Cw1M-7a4.js} +1 -1
- package/dist/web/index.html +2 -2
- package/migrations/009_comment_watch.sql +30 -0
- package/package.json +1 -1
- package/skills/rvw/SKILL.md +84 -5
- package/skills/rvw/agents/openai.yaml +2 -2
- package/skills/rvw-walkthrough/SKILL.md +17 -8
- package/skills/rvw-walkthrough/references/walkthrough-authoring.md +105 -0
- package/skills/rvw-watch-comments/SKILL.md +175 -0
- package/skills/rvw-watch-comments/agents/openai.yaml +4 -0
- package/skills/rvw-watch-comments/scripts/watch-state.mjs +724 -0
- package/dist/web/assets/DocumentViewer-ERTovlNY.js +0 -1560
- package/dist/web/assets/MarkdownImagePlaceholder-BseUb-vG.js +0 -36
- package/dist/web/assets/WalkthroughViewer-4HaKxbeO.js +0 -2
- package/dist/web/assets/architecture-TIHT7OUA-9PYQORPB.js +0 -1
- package/dist/web/assets/channel-zAJ9N7Xu.js +0 -1
- package/dist/web/assets/classDiagram-JCYQIIEL-DW7PwlYE.js +0 -1
- package/dist/web/assets/classDiagram-v2-OCEON4UE-DW7PwlYE.js +0 -1
- package/dist/web/assets/eventmodeling-45OFAUF4-mByhu-2v.js +0 -1
- package/dist/web/assets/flowDiagram-UKHOOZJN-DTgITdYW.js +0 -1
- package/dist/web/assets/index-DAM-rdgA.js +0 -355
- package/dist/web/assets/railroad-abnf-AHOZXSZD-D0hTyA1H.js +0 -1
- package/dist/web/assets/railroad-ebnf-EBAXGLYW-DzkmoqWU.js +0 -1
- package/dist/web/assets/railroad-peg-LSFZ7HO6-u3hJ9iID.js +0 -1
- package/dist/web/assets/stateDiagram-v2-UEYNNEHI-BY3gjuqo.js +0 -1
- package/dist/web/assets/swimlanesDiagram-ULZ7WXOC-DK-u00Uf.js +0 -8
package/dist/cli.mjs
CHANGED
|
@@ -18512,7 +18512,7 @@ function date4(params) {
|
|
|
18512
18512
|
config(en_default());
|
|
18513
18513
|
|
|
18514
18514
|
// src/infrastructure/db/database.ts
|
|
18515
|
-
import { randomUUID } from "node:crypto";
|
|
18515
|
+
import { createHash, randomUUID } from "node:crypto";
|
|
18516
18516
|
import {
|
|
18517
18517
|
chmodSync,
|
|
18518
18518
|
closeSync,
|
|
@@ -18736,6 +18736,9 @@ function mapPullRequest(row) {
|
|
|
18736
18736
|
repository: stringValue(row, "repository"),
|
|
18737
18737
|
number: numberValue(row, "number"),
|
|
18738
18738
|
url: stringValue(row, "github_url"),
|
|
18739
|
+
latestAuthorLogin: nullableString(row, "latest_author_login"),
|
|
18740
|
+
latestHeadRepositoryOwner: nullableString(row, "latest_head_repository_owner"),
|
|
18741
|
+
latestHeadRepositoryName: nullableString(row, "latest_head_repository_name"),
|
|
18739
18742
|
localRepositoryPath: stringValue(row, "local_repository_path"),
|
|
18740
18743
|
gitCommonDir: stringValue(row, "git_common_dir"),
|
|
18741
18744
|
latestTitle: stringValue(row, "latest_title"),
|
|
@@ -18751,6 +18754,21 @@ function mapPullRequest(row) {
|
|
|
18751
18754
|
updatedAt: stringValue(row, "updated_at")
|
|
18752
18755
|
};
|
|
18753
18756
|
}
|
|
18757
|
+
function mapCommentPost(row) {
|
|
18758
|
+
return {
|
|
18759
|
+
id: stringValue(row, "id"),
|
|
18760
|
+
commentId: stringValue(row, "comment_id"),
|
|
18761
|
+
body: stringValue(row, "body"),
|
|
18762
|
+
relatedCommitOid: nullableString(row, "related_commit_oid"),
|
|
18763
|
+
authorLabel: nullableString(row, "author_label"),
|
|
18764
|
+
isRoot: numberValue(row, "is_root") === 1,
|
|
18765
|
+
createdAt: stringValue(row, "created_at"),
|
|
18766
|
+
updatedAt: stringValue(row, "updated_at")
|
|
18767
|
+
};
|
|
18768
|
+
}
|
|
18769
|
+
function hashIdempotencyKey(value) {
|
|
18770
|
+
return createHash("sha256").update(value, "utf8").digest("hex");
|
|
18771
|
+
}
|
|
18754
18772
|
function findMigrationsDirectory(explicit) {
|
|
18755
18773
|
if (explicit) return explicit;
|
|
18756
18774
|
const moduleDirectory = path4.dirname(fileURLToPath2(import.meta.url));
|
|
@@ -18982,6 +19000,33 @@ var RvwDatabase = class {
|
|
|
18982
19000
|
const row = this.database.prepare("SELECT value FROM app_meta WHERE key = 'change_sequence'").get();
|
|
18983
19001
|
return Number(stringValue(row, "value"));
|
|
18984
19002
|
}
|
|
19003
|
+
getCommentWatchDatabaseId() {
|
|
19004
|
+
const row = this.database.prepare("SELECT value FROM app_meta WHERE key = 'comment_watch_database_id'").get();
|
|
19005
|
+
if (!row) throw new RvwError("DATABASE_ERROR", "comment watch\u306Edatabase ID\u304C\u3042\u308A\u307E\u305B\u3093\u3002");
|
|
19006
|
+
return stringValue(row, "value");
|
|
19007
|
+
}
|
|
19008
|
+
getLatestCommentPostEventSequence() {
|
|
19009
|
+
const row = this.database.prepare("SELECT COALESCE(MAX(sequence), 0) AS sequence FROM comment_post_events").get();
|
|
19010
|
+
return numberValue(row, "sequence");
|
|
19011
|
+
}
|
|
19012
|
+
listCommentPostEvents(afterSequence, limit) {
|
|
19013
|
+
const rows = this.database.prepare(
|
|
19014
|
+
`SELECT e.*, CASE WHEN p.id IS NULL THEN 1 ELSE 0 END AS deleted
|
|
19015
|
+
FROM comment_post_events e
|
|
19016
|
+
LEFT JOIN comment_posts p ON p.id = e.post_id
|
|
19017
|
+
WHERE e.sequence > ?
|
|
19018
|
+
ORDER BY e.sequence ASC
|
|
19019
|
+
LIMIT ?`
|
|
19020
|
+
).all(afterSequence, limit);
|
|
19021
|
+
return rows.map((row) => ({
|
|
19022
|
+
sequence: numberValue(row, "sequence"),
|
|
19023
|
+
createdAt: stringValue(row, "created_at"),
|
|
19024
|
+
postId: stringValue(row, "post_id"),
|
|
19025
|
+
commentRef: stringValue(row, "comment_ref"),
|
|
19026
|
+
pullRequestUrl: stringValue(row, "pull_request_url"),
|
|
19027
|
+
deleted: numberValue(row, "deleted") === 1
|
|
19028
|
+
}));
|
|
19029
|
+
}
|
|
18985
19030
|
getThemePreference() {
|
|
18986
19031
|
const row = this.database.prepare("SELECT value FROM app_meta WHERE key = 'theme_preference'").get();
|
|
18987
19032
|
if (!row) {
|
|
@@ -19037,14 +19082,18 @@ var RvwDatabase = class {
|
|
|
19037
19082
|
`INSERT INTO pull_requests(
|
|
19038
19083
|
id, host, owner, repository, number, github_url,
|
|
19039
19084
|
local_repository_path, git_common_dir,
|
|
19085
|
+
latest_author_login, latest_head_repository_owner, latest_head_repository_name,
|
|
19040
19086
|
latest_title, latest_body, latest_base_ref_name, latest_head_ref_name,
|
|
19041
19087
|
latest_base_oid, latest_head_oid, github_updated_at, fetched_at,
|
|
19042
19088
|
created_at, updated_at, latest_comparison_base_oid
|
|
19043
|
-
) VALUES (?, 'github.com', ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
19089
|
+
) VALUES (?, 'github.com', ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)
|
|
19044
19090
|
ON CONFLICT(host, owner, repository, number) DO UPDATE SET
|
|
19045
19091
|
github_url = excluded.github_url,
|
|
19046
19092
|
local_repository_path = excluded.local_repository_path,
|
|
19047
19093
|
git_common_dir = excluded.git_common_dir,
|
|
19094
|
+
latest_author_login = excluded.latest_author_login,
|
|
19095
|
+
latest_head_repository_owner = excluded.latest_head_repository_owner,
|
|
19096
|
+
latest_head_repository_name = excluded.latest_head_repository_name,
|
|
19048
19097
|
latest_title = excluded.latest_title,
|
|
19049
19098
|
latest_body = excluded.latest_body,
|
|
19050
19099
|
latest_base_ref_name = excluded.latest_base_ref_name,
|
|
@@ -19063,6 +19112,9 @@ var RvwDatabase = class {
|
|
|
19063
19112
|
github.url,
|
|
19064
19113
|
repository.localRepositoryPath,
|
|
19065
19114
|
repository.gitCommonDir,
|
|
19115
|
+
github.authorLogin,
|
|
19116
|
+
github.headRepositoryOwner,
|
|
19117
|
+
github.headRepositoryName,
|
|
19066
19118
|
github.title,
|
|
19067
19119
|
github.body,
|
|
19068
19120
|
github.baseRefName,
|
|
@@ -19303,6 +19355,8 @@ var RvwDatabase = class {
|
|
|
19303
19355
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
19304
19356
|
const id = randomUUID();
|
|
19305
19357
|
const postId = randomUUID();
|
|
19358
|
+
const pullRequest = this.getPullRequest(input.pullRequestId);
|
|
19359
|
+
if (!pullRequest) throw new RvwError("PR_NOT_FOUND", "Pull Request\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002");
|
|
19306
19360
|
this.immediateTransaction(() => {
|
|
19307
19361
|
this.database.prepare(
|
|
19308
19362
|
"INSERT INTO comments(id, pull_request_id, created_head_oid, resolved_at, created_at, updated_at) VALUES (?, ?, ?, NULL, ?, ?)"
|
|
@@ -19311,6 +19365,11 @@ var RvwDatabase = class {
|
|
|
19311
19365
|
this.database.prepare(
|
|
19312
19366
|
"INSERT INTO comment_posts(id, comment_id, body, related_commit_oid, author_label, is_root, created_at, updated_at) VALUES (?, ?, ?, NULL, ?, 1, ?, ?)"
|
|
19313
19367
|
).run(postId, id, input.body, input.authorLabel ?? null, now, now);
|
|
19368
|
+
this.database.prepare(
|
|
19369
|
+
`INSERT INTO comment_post_events(
|
|
19370
|
+
post_id, comment_ref, pull_request_url, created_at
|
|
19371
|
+
) VALUES (?, ?, ?, ?)`
|
|
19372
|
+
).run(postId, formatCommentUri(id), pullRequest.url, now);
|
|
19314
19373
|
this.incrementChangeSequence();
|
|
19315
19374
|
});
|
|
19316
19375
|
const comment = this.getComment(id);
|
|
@@ -19474,56 +19533,94 @@ var RvwDatabase = class {
|
|
|
19474
19533
|
listCommentPosts(commentId) {
|
|
19475
19534
|
return this.database.prepare(
|
|
19476
19535
|
"SELECT * FROM comment_posts WHERE comment_id = ? ORDER BY is_root DESC, created_at ASC, id ASC"
|
|
19477
|
-
).all(commentId).map(
|
|
19478
|
-
id: stringValue(row, "id"),
|
|
19479
|
-
commentId: stringValue(row, "comment_id"),
|
|
19480
|
-
body: stringValue(row, "body"),
|
|
19481
|
-
relatedCommitOid: nullableString(row, "related_commit_oid"),
|
|
19482
|
-
authorLabel: nullableString(row, "author_label"),
|
|
19483
|
-
isRoot: numberValue(row, "is_root") === 1,
|
|
19484
|
-
createdAt: stringValue(row, "created_at"),
|
|
19485
|
-
updatedAt: stringValue(row, "updated_at")
|
|
19486
|
-
}));
|
|
19536
|
+
).all(commentId).map(mapCommentPost);
|
|
19487
19537
|
}
|
|
19488
19538
|
insertReply(commentId, input, incrementSequence = true) {
|
|
19489
|
-
|
|
19490
|
-
throw new RvwError("COMMENT_NOT_FOUND", "\u30B3\u30E1\u30F3\u30C8\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002");
|
|
19491
|
-
const id = randomUUID();
|
|
19492
|
-
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
19539
|
+
let result;
|
|
19493
19540
|
const write = () => {
|
|
19541
|
+
const comment = this.getComment(commentId);
|
|
19542
|
+
if (!comment) {
|
|
19543
|
+
throw new RvwError("COMMENT_NOT_FOUND", "\u30B3\u30E1\u30F3\u30C8\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002");
|
|
19544
|
+
}
|
|
19545
|
+
const pullRequest = this.getPullRequest(comment.pullRequestId);
|
|
19546
|
+
if (!pullRequest) throw new RvwError("PR_NOT_FOUND", "Pull Request\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002");
|
|
19547
|
+
const relatedCommitOid = input.relatedCommitOid ?? null;
|
|
19548
|
+
const authorLabel = input.authorLabel ?? null;
|
|
19549
|
+
const idempotencyKeyHash = input.idempotencyKey === void 0 ? null : hashIdempotencyKey(input.idempotencyKey);
|
|
19550
|
+
const idempotencyRequestHash2 = idempotencyKeyHash === null ? null : input.idempotencyRequestHash ?? hashIdempotencyKey(
|
|
19551
|
+
JSON.stringify({
|
|
19552
|
+
operation: "comment.reply",
|
|
19553
|
+
commentId,
|
|
19554
|
+
body: input.body,
|
|
19555
|
+
relatedCommitOid,
|
|
19556
|
+
authorLabel
|
|
19557
|
+
})
|
|
19558
|
+
);
|
|
19559
|
+
if (idempotencyKeyHash !== null) {
|
|
19560
|
+
const existingRow = this.database.prepare("SELECT * FROM comment_reply_idempotency WHERE key_hash = ?").get(idempotencyKeyHash);
|
|
19561
|
+
if (existingRow) {
|
|
19562
|
+
if (stringValue(existingRow, "request_hash") !== idempotencyRequestHash2) {
|
|
19563
|
+
throw new RvwError(
|
|
19564
|
+
"IDEMPOTENCY_CONFLICT",
|
|
19565
|
+
"\u540C\u3058idempotencyKey\u304C\u5225\u306Ecomment reply\u306B\u4F7F\u7528\u3055\u308C\u3066\u3044\u307E\u3059\u3002"
|
|
19566
|
+
);
|
|
19567
|
+
}
|
|
19568
|
+
const postId = stringValue(existingRow, "post_id");
|
|
19569
|
+
const postRow = this.database.prepare("SELECT * FROM comment_posts WHERE id = ?").get(postId);
|
|
19570
|
+
if (!postRow) {
|
|
19571
|
+
throw new RvwError(
|
|
19572
|
+
"IDEMPOTENCY_RESULT_DELETED",
|
|
19573
|
+
"\u3053\u306EidempotencyKey\u3067\u4F5C\u6210\u3057\u305Fcomment reply\u306F\u65E2\u306B\u524A\u9664\u3055\u308C\u3066\u3044\u307E\u3059\u3002",
|
|
19574
|
+
{ details: { postId } }
|
|
19575
|
+
);
|
|
19576
|
+
}
|
|
19577
|
+
const existing = mapCommentPost(postRow);
|
|
19578
|
+
result = existing;
|
|
19579
|
+
return;
|
|
19580
|
+
}
|
|
19581
|
+
}
|
|
19582
|
+
const id = randomUUID();
|
|
19583
|
+
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
19494
19584
|
this.database.prepare(
|
|
19495
19585
|
"INSERT INTO comment_posts(id, comment_id, body, related_commit_oid, author_label, is_root, created_at, updated_at) VALUES (?, ?, ?, ?, ?, 0, ?, ?)"
|
|
19496
|
-
).run(
|
|
19497
|
-
|
|
19498
|
-
|
|
19499
|
-
|
|
19500
|
-
|
|
19501
|
-
|
|
19502
|
-
|
|
19503
|
-
|
|
19504
|
-
|
|
19586
|
+
).run(id, commentId, input.body, relatedCommitOid, authorLabel, now, now);
|
|
19587
|
+
this.database.prepare(
|
|
19588
|
+
`INSERT INTO comment_post_events(
|
|
19589
|
+
post_id, comment_ref, pull_request_url, created_at
|
|
19590
|
+
) VALUES (?, ?, ?, ?)`
|
|
19591
|
+
).run(id, comment.ref, pullRequest.url, now);
|
|
19592
|
+
if (idempotencyKeyHash !== null && idempotencyRequestHash2 !== null) {
|
|
19593
|
+
this.database.prepare(
|
|
19594
|
+
"INSERT INTO comment_reply_idempotency(key_hash, request_hash, post_id, created_at) VALUES (?, ?, ?, ?)"
|
|
19595
|
+
).run(idempotencyKeyHash, idempotencyRequestHash2, id, now);
|
|
19596
|
+
}
|
|
19505
19597
|
this.database.prepare("UPDATE comments SET updated_at = ? WHERE id = ?").run(now, commentId);
|
|
19506
19598
|
if (incrementSequence) this.incrementChangeSequence();
|
|
19599
|
+
result = {
|
|
19600
|
+
id,
|
|
19601
|
+
commentId,
|
|
19602
|
+
body: input.body,
|
|
19603
|
+
relatedCommitOid,
|
|
19604
|
+
authorLabel,
|
|
19605
|
+
isRoot: false,
|
|
19606
|
+
createdAt: now,
|
|
19607
|
+
updatedAt: now
|
|
19608
|
+
};
|
|
19507
19609
|
};
|
|
19508
19610
|
if (incrementSequence) this.immediateTransaction(write);
|
|
19509
19611
|
else write();
|
|
19510
|
-
|
|
19511
|
-
|
|
19512
|
-
commentId,
|
|
19513
|
-
body: input.body,
|
|
19514
|
-
relatedCommitOid: input.relatedCommitOid ?? null,
|
|
19515
|
-
authorLabel: input.authorLabel ?? null,
|
|
19516
|
-
isRoot: false,
|
|
19517
|
-
createdAt: now,
|
|
19518
|
-
updatedAt: now
|
|
19519
|
-
};
|
|
19612
|
+
if (!result) throw new RvwError("DATABASE_ERROR", "\u8FD4\u4FE1\u7D50\u679C\u3092\u8AAD\u307F\u51FA\u305B\u307E\u305B\u3093\u3002");
|
|
19613
|
+
return result;
|
|
19520
19614
|
}
|
|
19521
|
-
updateCommentPost(commentId, postId, body) {
|
|
19615
|
+
updateCommentPost(commentId, postId, body, relatedCommitOid) {
|
|
19522
19616
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
19523
19617
|
this.immediateTransaction(() => {
|
|
19524
|
-
const result = this.database.prepare(
|
|
19618
|
+
const result = relatedCommitOid === void 0 ? this.database.prepare(
|
|
19525
19619
|
"UPDATE comment_posts SET body = ?, updated_at = ? WHERE id = ? AND comment_id = ?"
|
|
19526
|
-
).run(body, now, postId, commentId)
|
|
19620
|
+
).run(body, now, postId, commentId) : this.database.prepare(
|
|
19621
|
+
`UPDATE comment_posts SET body = ?, related_commit_oid = ?, updated_at = ?
|
|
19622
|
+
WHERE id = ? AND comment_id = ?`
|
|
19623
|
+
).run(body, relatedCommitOid, now, postId, commentId);
|
|
19527
19624
|
if (Number(result.changes) === 0) {
|
|
19528
19625
|
throw new RvwError("COMMENT_POST_NOT_FOUND", "\u30B3\u30E1\u30F3\u30C8\u6295\u7A3F\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002", {
|
|
19529
19626
|
status: 404
|
|
@@ -19599,7 +19696,9 @@ var RvwDatabase = class {
|
|
|
19599
19696
|
{
|
|
19600
19697
|
body: update.reply,
|
|
19601
19698
|
relatedCommitOid,
|
|
19602
|
-
authorLabel: update.authorLabel ?? "Agent"
|
|
19699
|
+
authorLabel: update.authorLabel ?? "Agent",
|
|
19700
|
+
...update.idempotencyKey === void 0 ? {} : { idempotencyKey: update.idempotencyKey },
|
|
19701
|
+
...update.idempotencyRequestHash === void 0 ? {} : { idempotencyRequestHash: update.idempotencyRequestHash }
|
|
19603
19702
|
},
|
|
19604
19703
|
false
|
|
19605
19704
|
);
|
|
@@ -19617,7 +19716,7 @@ import path5 from "node:path";
|
|
|
19617
19716
|
import { TextDecoder as TextDecoder2 } from "node:util";
|
|
19618
19717
|
|
|
19619
19718
|
// src/shared/constants.ts
|
|
19620
|
-
var APP_VERSION = "0.
|
|
19719
|
+
var APP_VERSION = "0.2.0";
|
|
19621
19720
|
var PROTOCOL_VERSION = 2;
|
|
19622
19721
|
var VIEWER_ID_HEADER = "x-rvw-viewer-id";
|
|
19623
19722
|
var GIT_OBJECT_ID_PATTERN = /^[0-9a-f]{40,64}$/i;
|
|
@@ -19625,8 +19724,13 @@ var MAX_TEXT_DOCUMENT_BYTES = 1024 * 1024;
|
|
|
19625
19724
|
var MAX_MARKDOWN_ASSET_BYTES = 5 * 1024 * 1024;
|
|
19626
19725
|
var MAX_COMMENT_BODY_BYTES = 64 * 1024;
|
|
19627
19726
|
var MAX_AUTHOR_LABEL_CHARACTERS = 100;
|
|
19727
|
+
var MAX_IDEMPOTENCY_KEY_CHARACTERS = 200;
|
|
19628
19728
|
var DEFAULT_COMMENT_LIST_LIMIT = 50;
|
|
19629
19729
|
var MAX_COMMENT_LIST_LIMIT = 100;
|
|
19730
|
+
var DEFAULT_COMMENT_WATCH_LIMIT = 100;
|
|
19731
|
+
var MAX_COMMENT_WATCH_LIMIT = 100;
|
|
19732
|
+
var DEFAULT_COMMENT_WATCH_INTERVAL_SECONDS = 10;
|
|
19733
|
+
var MAX_COMMENT_WATCH_INTERVAL_SECONDS = 300;
|
|
19630
19734
|
var MAX_COMMENT_LIST_BODY_PREVIEW_BYTES = 512;
|
|
19631
19735
|
var MAX_WALKTHROUGH_BODY_BYTES = 256 * 1024;
|
|
19632
19736
|
var MAX_WALKTHROUGH_REFERENCES = 200;
|
|
@@ -20269,6 +20373,9 @@ var GitClient = class {
|
|
|
20269
20373
|
|
|
20270
20374
|
// src/infrastructure/github/github-client.ts
|
|
20271
20375
|
var ghPullRequestSchema = external_exports.object({
|
|
20376
|
+
author: external_exports.object({ login: external_exports.string().min(1) }).nullable(),
|
|
20377
|
+
headRepository: external_exports.object({ name: external_exports.string().min(1) }).nullable(),
|
|
20378
|
+
headRepositoryOwner: external_exports.object({ login: external_exports.string().min(1) }).nullable(),
|
|
20272
20379
|
number: external_exports.number().int().positive(),
|
|
20273
20380
|
url: external_exports.url(),
|
|
20274
20381
|
title: external_exports.string(),
|
|
@@ -20309,6 +20416,7 @@ var GitHubClient = class {
|
|
|
20309
20416
|
async getPullRequest(reference, cwd) {
|
|
20310
20417
|
await this.assertAuthenticated();
|
|
20311
20418
|
const fields = [
|
|
20419
|
+
"author",
|
|
20312
20420
|
"number",
|
|
20313
20421
|
"url",
|
|
20314
20422
|
"title",
|
|
@@ -20358,6 +20466,9 @@ var GitHubClient = class {
|
|
|
20358
20466
|
repository: identity.repository,
|
|
20359
20467
|
number: parsed.data.number,
|
|
20360
20468
|
url: parsed.data.url,
|
|
20469
|
+
authorLogin: parsed.data.author?.login ?? null,
|
|
20470
|
+
headRepositoryOwner: parsed.data.headRepositoryOwner?.login ?? null,
|
|
20471
|
+
headRepositoryName: parsed.data.headRepository?.name ?? null,
|
|
20361
20472
|
title: parsed.data.title,
|
|
20362
20473
|
body: parsed.data.body ?? "",
|
|
20363
20474
|
baseRefName: parsed.data.baseRefName,
|
|
@@ -20372,6 +20483,7 @@ var GitHubClient = class {
|
|
|
20372
20483
|
};
|
|
20373
20484
|
|
|
20374
20485
|
// src/application/rvw-service.ts
|
|
20486
|
+
import { createHash as createHash3 } from "node:crypto";
|
|
20375
20487
|
import path6 from "node:path";
|
|
20376
20488
|
|
|
20377
20489
|
// node_modules/.pnpm/mdast-util-to-string@4.0.0/node_modules/mdast-util-to-string/lib/index.js
|
|
@@ -27307,6 +27419,28 @@ function defaultOnError(left, right) {
|
|
|
27307
27419
|
}
|
|
27308
27420
|
}
|
|
27309
27421
|
|
|
27422
|
+
// src/domain/comment-watch-cursor.ts
|
|
27423
|
+
var CURSOR_VERSION = 1;
|
|
27424
|
+
var DATABASE_ID_PATTERN = /^[0-9a-f]{32}$/;
|
|
27425
|
+
function formatCommentWatchCursor(cursor) {
|
|
27426
|
+
return Buffer.from(
|
|
27427
|
+
JSON.stringify({ v: CURSOR_VERSION, d: cursor.databaseId, s: cursor.sequence }),
|
|
27428
|
+
"utf8"
|
|
27429
|
+
).toString("base64url");
|
|
27430
|
+
}
|
|
27431
|
+
function parseCommentWatchCursor(value) {
|
|
27432
|
+
try {
|
|
27433
|
+
if (value.length === 0 || value.length > 512) throw new Error("cursor length");
|
|
27434
|
+
const decoded = JSON.parse(Buffer.from(value, "base64url").toString("utf8"));
|
|
27435
|
+
if (decoded.v !== CURSOR_VERSION || typeof decoded.d !== "string" || !DATABASE_ID_PATTERN.test(decoded.d) || typeof decoded.s !== "number" || !Number.isSafeInteger(decoded.s) || decoded.s < 0) {
|
|
27436
|
+
throw new Error("cursor shape");
|
|
27437
|
+
}
|
|
27438
|
+
return { databaseId: decoded.d, sequence: decoded.s };
|
|
27439
|
+
} catch (error51) {
|
|
27440
|
+
throw new RvwError("INVALID_INPUT", "comment watch cursor\u304C\u4E0D\u6B63\u3067\u3059\u3002", { cause: error51 });
|
|
27441
|
+
}
|
|
27442
|
+
}
|
|
27443
|
+
|
|
27310
27444
|
// node_modules/.pnpm/diff@9.0.0/node_modules/diff/libesm/diff/base.js
|
|
27311
27445
|
var Diff = class {
|
|
27312
27446
|
diff(oldStr, newStr, options = {}) {
|
|
@@ -27527,7 +27661,7 @@ function diffArrays(oldArr, newArr, options) {
|
|
|
27527
27661
|
}
|
|
27528
27662
|
|
|
27529
27663
|
// src/domain/pr-markdown.ts
|
|
27530
|
-
import { createHash } from "node:crypto";
|
|
27664
|
+
import { createHash as createHash2 } from "node:crypto";
|
|
27531
27665
|
function normalizeLf(value) {
|
|
27532
27666
|
return value.replace(/\r\n?/g, "\n");
|
|
27533
27667
|
}
|
|
@@ -27537,7 +27671,7 @@ function buildPullRequestMarkdown(title, body) {
|
|
|
27537
27671
|
${normalizeLf(body)}`;
|
|
27538
27672
|
}
|
|
27539
27673
|
function hashDocument(value) {
|
|
27540
|
-
return
|
|
27674
|
+
return createHash2("sha256").update(normalizeLf(value), "utf8").digest("hex");
|
|
27541
27675
|
}
|
|
27542
27676
|
function selectedLineText(value, startLine, endLine) {
|
|
27543
27677
|
const lines2 = normalizeLf(value).split("\n");
|
|
@@ -27686,6 +27820,18 @@ function assertAuthorLabel(authorLabel) {
|
|
|
27686
27820
|
);
|
|
27687
27821
|
}
|
|
27688
27822
|
}
|
|
27823
|
+
function assertIdempotencyKey(idempotencyKey2) {
|
|
27824
|
+
if (idempotencyKey2 === void 0) return;
|
|
27825
|
+
if (idempotencyKey2.length === 0 || idempotencyKey2.length > MAX_IDEMPOTENCY_KEY_CHARACTERS) {
|
|
27826
|
+
throw new RvwError(
|
|
27827
|
+
"INVALID_INPUT",
|
|
27828
|
+
`idempotencyKey\u306F1\u301C${MAX_IDEMPOTENCY_KEY_CHARACTERS}\u6587\u5B57\u306B\u3057\u3066\u304F\u3060\u3055\u3044\u3002`
|
|
27829
|
+
);
|
|
27830
|
+
}
|
|
27831
|
+
}
|
|
27832
|
+
function idempotencyRequestHash(value) {
|
|
27833
|
+
return createHash3("sha256").update(JSON.stringify(value), "utf8").digest("hex");
|
|
27834
|
+
}
|
|
27689
27835
|
function assertLinePair(startLine, endLine) {
|
|
27690
27836
|
if (startLine === null !== (endLine === null)) {
|
|
27691
27837
|
throw new RvwError("INVALID_INPUT", "\u884C\u7BC4\u56F2\u306F\u958B\u59CB\u884C\u3068\u7D42\u4E86\u884C\u3092\u4E21\u65B9\u6307\u5B9A\u3057\u3066\u304F\u3060\u3055\u3044\u3002");
|
|
@@ -27971,11 +28117,23 @@ var RvwService = class {
|
|
|
27971
28117
|
}
|
|
27972
28118
|
if (update.reply.trim()) assertTextBody(update.reply);
|
|
27973
28119
|
assertAuthorLabel(update.authorLabel);
|
|
28120
|
+
assertIdempotencyKey(update.idempotencyKey);
|
|
28121
|
+
const authorLabel = update.authorLabel ?? "Agent";
|
|
27974
28122
|
return {
|
|
27975
28123
|
commentId,
|
|
27976
28124
|
reply: update.reply,
|
|
27977
28125
|
resolve: update.resolve,
|
|
27978
|
-
...update.authorLabel === void 0 ? {} : { authorLabel: update.authorLabel }
|
|
28126
|
+
...update.authorLabel === void 0 ? {} : { authorLabel: update.authorLabel },
|
|
28127
|
+
...update.idempotencyKey === void 0 ? {} : { idempotencyKey: update.idempotencyKey },
|
|
28128
|
+
...update.idempotencyKey === void 0 ? {} : {
|
|
28129
|
+
idempotencyRequestHash: idempotencyRequestHash({
|
|
28130
|
+
operation: "pr.sync.comment-update",
|
|
28131
|
+
commentId,
|
|
28132
|
+
reply: update.reply,
|
|
28133
|
+
resolve: update.resolve,
|
|
28134
|
+
authorLabel
|
|
28135
|
+
})
|
|
28136
|
+
}
|
|
27979
28137
|
};
|
|
27980
28138
|
});
|
|
27981
28139
|
}
|
|
@@ -28304,6 +28462,15 @@ var RvwService = class {
|
|
|
28304
28462
|
...input.authorLabel === void 0 ? {} : { authorLabel: input.authorLabel }
|
|
28305
28463
|
});
|
|
28306
28464
|
}
|
|
28465
|
+
async createCommentForReference(input) {
|
|
28466
|
+
const pullRequest = this.resolveStoredPullRequest(input.pullRequest);
|
|
28467
|
+
return await this.createComment({
|
|
28468
|
+
pullRequestId: pullRequest.id,
|
|
28469
|
+
target: input.target,
|
|
28470
|
+
body: input.body,
|
|
28471
|
+
...input.authorLabel === void 0 ? {} : { authorLabel: input.authorLabel }
|
|
28472
|
+
});
|
|
28473
|
+
}
|
|
28307
28474
|
getCommentByUri(uri) {
|
|
28308
28475
|
const id = parseCommentUri(uri);
|
|
28309
28476
|
const comment = this.database.getComment(id);
|
|
@@ -28340,7 +28507,7 @@ var RvwService = class {
|
|
|
28340
28507
|
result.pullRequest.url,
|
|
28341
28508
|
result.pullRequest.localRepositoryPath
|
|
28342
28509
|
) : null;
|
|
28343
|
-
const staleAgainstGitHub = live ? live.title !== result.pullRequest.latestTitle || live.body !== result.pullRequest.latestBody || live.baseOid !== result.pullRequest.latestBaseOid || live.headOid !== result.pullRequest.latestHeadOid || live.updatedAt !== result.pullRequest.githubUpdatedAt : null;
|
|
28510
|
+
const staleAgainstGitHub = live ? live.title !== result.pullRequest.latestTitle || live.body !== result.pullRequest.latestBody || live.headRepositoryOwner !== result.pullRequest.latestHeadRepositoryOwner || live.headRepositoryName !== result.pullRequest.latestHeadRepositoryName || live.baseOid !== result.pullRequest.latestBaseOid || live.headOid !== result.pullRequest.latestHeadOid || live.updatedAt !== result.pullRequest.githubUpdatedAt : null;
|
|
28344
28511
|
return {
|
|
28345
28512
|
...result,
|
|
28346
28513
|
latestPlacement,
|
|
@@ -28389,6 +28556,39 @@ var RvwService = class {
|
|
|
28389
28556
|
}
|
|
28390
28557
|
};
|
|
28391
28558
|
}
|
|
28559
|
+
listCommentPostEvents(cursor, limit = DEFAULT_COMMENT_WATCH_LIMIT) {
|
|
28560
|
+
if (!Number.isInteger(limit) || limit < 1 || limit > MAX_COMMENT_WATCH_LIMIT) {
|
|
28561
|
+
throw new RvwError(
|
|
28562
|
+
"INVALID_INPUT",
|
|
28563
|
+
`comment watch\u306Elimit\u306F1\u301C${MAX_COMMENT_WATCH_LIMIT}\u306E\u6574\u6570\u306B\u3057\u3066\u304F\u3060\u3055\u3044\u3002`
|
|
28564
|
+
);
|
|
28565
|
+
}
|
|
28566
|
+
const databaseId = this.database.getCommentWatchDatabaseId();
|
|
28567
|
+
const parsed = cursor === void 0 ? null : parseCommentWatchCursor(cursor);
|
|
28568
|
+
if (parsed !== null && parsed.databaseId !== databaseId) {
|
|
28569
|
+
throw new RvwError("INVALID_INPUT", "comment watch cursor\u306F\u5225\u306Ervw database\u7528\u3067\u3059\u3002");
|
|
28570
|
+
}
|
|
28571
|
+
const latestAtStart = this.database.getLatestCommentPostEventSequence();
|
|
28572
|
+
if (parsed !== null && parsed.sequence > latestAtStart) {
|
|
28573
|
+
throw new RvwError("INVALID_INPUT", "comment watch cursor\u306Fdatabase\u306E\u6700\u65B0event\u3088\u308A\u5148\u3067\u3059\u3002");
|
|
28574
|
+
}
|
|
28575
|
+
const afterSequence = parsed?.sequence ?? latestAtStart;
|
|
28576
|
+
const rawEvents = this.database.listCommentPostEvents(afterSequence, limit);
|
|
28577
|
+
const events = rawEvents.map((event) => ({
|
|
28578
|
+
cursor: formatCommentWatchCursor({ databaseId, sequence: event.sequence }),
|
|
28579
|
+
event
|
|
28580
|
+
}));
|
|
28581
|
+
const lastSequence = rawEvents.at(-1)?.sequence ?? afterSequence;
|
|
28582
|
+
const latestSequence = this.database.getLatestCommentPostEventSequence();
|
|
28583
|
+
return {
|
|
28584
|
+
databaseId,
|
|
28585
|
+
startCursor: formatCommentWatchCursor({ databaseId, sequence: afterSequence }),
|
|
28586
|
+
cursor: formatCommentWatchCursor({ databaseId, sequence: lastSequence }),
|
|
28587
|
+
anchoredAtCurrent: parsed === null,
|
|
28588
|
+
hasMore: lastSequence < latestSequence,
|
|
28589
|
+
events
|
|
28590
|
+
};
|
|
28591
|
+
}
|
|
28392
28592
|
listComments(pullRequestId, resolved) {
|
|
28393
28593
|
this.getPullRequest(pullRequestId);
|
|
28394
28594
|
return this.database.listComments(pullRequestId, resolved);
|
|
@@ -28598,13 +28798,27 @@ var RvwService = class {
|
|
|
28598
28798
|
if (!comment)
|
|
28599
28799
|
throw new RvwError("COMMENT_NOT_FOUND", "\u30B3\u30E1\u30F3\u30C8\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002", { status: 404 });
|
|
28600
28800
|
assertAuthorLabel(input.authorLabel);
|
|
28801
|
+
assertIdempotencyKey(input.idempotencyKey);
|
|
28601
28802
|
if (input.relatedCommitOid) {
|
|
28602
28803
|
await this.assertCommitAvailable(
|
|
28603
28804
|
this.getPullRequest(comment.pullRequestId),
|
|
28604
28805
|
input.relatedCommitOid
|
|
28605
28806
|
);
|
|
28606
28807
|
}
|
|
28607
|
-
|
|
28808
|
+
const body = assertTextBody(input.body);
|
|
28809
|
+
return this.database.insertReply(id, {
|
|
28810
|
+
...input,
|
|
28811
|
+
body,
|
|
28812
|
+
...input.idempotencyKey === void 0 ? {} : {
|
|
28813
|
+
idempotencyRequestHash: idempotencyRequestHash({
|
|
28814
|
+
operation: "comment.reply",
|
|
28815
|
+
commentId: id,
|
|
28816
|
+
body,
|
|
28817
|
+
relatedCommitOid: input.relatedCommitOid ?? null,
|
|
28818
|
+
authorLabel: input.authorLabel ?? null
|
|
28819
|
+
})
|
|
28820
|
+
}
|
|
28821
|
+
});
|
|
28608
28822
|
}
|
|
28609
28823
|
setCommentResolved(uriOrId, resolved) {
|
|
28610
28824
|
const id = uriOrId.startsWith("rvw://") ? parseCommentUri(uriOrId) : uriOrId;
|
|
@@ -28617,6 +28831,25 @@ var RvwService = class {
|
|
|
28617
28831
|
updateCommentPost(commentId, postId, body) {
|
|
28618
28832
|
return this.database.updateCommentPost(commentId, postId, assertTextBody(body));
|
|
28619
28833
|
}
|
|
28834
|
+
async editCommentPost(uriOrId, postId, input) {
|
|
28835
|
+
const commentId = uriOrId.startsWith("rvw://") ? parseCommentUri(uriOrId) : uriOrId;
|
|
28836
|
+
const comment = this.database.getComment(commentId);
|
|
28837
|
+
if (!comment) {
|
|
28838
|
+
throw new RvwError("COMMENT_NOT_FOUND", "\u30B3\u30E1\u30F3\u30C8\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\u3002", { status: 404 });
|
|
28839
|
+
}
|
|
28840
|
+
if (input.relatedCommitOid) {
|
|
28841
|
+
await this.assertCommitAvailable(
|
|
28842
|
+
this.getPullRequest(comment.pullRequestId),
|
|
28843
|
+
input.relatedCommitOid
|
|
28844
|
+
);
|
|
28845
|
+
}
|
|
28846
|
+
return this.database.updateCommentPost(
|
|
28847
|
+
commentId,
|
|
28848
|
+
postId,
|
|
28849
|
+
assertTextBody(input.body),
|
|
28850
|
+
input.relatedCommitOid
|
|
28851
|
+
);
|
|
28852
|
+
}
|
|
28620
28853
|
deleteReply(commentId, postId) {
|
|
28621
28854
|
return this.database.deleteReply(commentId, postId);
|
|
28622
28855
|
}
|
|
@@ -28813,7 +29046,7 @@ function createRuntime(options = {}) {
|
|
|
28813
29046
|
}
|
|
28814
29047
|
|
|
28815
29048
|
// src/infrastructure/skills/skill-installer.ts
|
|
28816
|
-
import { createHash as
|
|
29049
|
+
import { createHash as createHash4, randomUUID as randomUUID3 } from "node:crypto";
|
|
28817
29050
|
import {
|
|
28818
29051
|
cpSync,
|
|
28819
29052
|
existsSync as existsSync2,
|
|
@@ -28829,7 +29062,11 @@ import {
|
|
|
28829
29062
|
import os3 from "node:os";
|
|
28830
29063
|
import path7 from "node:path";
|
|
28831
29064
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
28832
|
-
var skillNames = [
|
|
29065
|
+
var skillNames = [
|
|
29066
|
+
"rvw",
|
|
29067
|
+
"rvw-walkthrough",
|
|
29068
|
+
"rvw-watch-comments"
|
|
29069
|
+
];
|
|
28833
29070
|
var INSTALL_METADATA_FILE = ".rvw-install.json";
|
|
28834
29071
|
var INSTALL_METADATA_SCHEMA_VERSION = 1;
|
|
28835
29072
|
var MAX_DIGEST_ENTRIES = 1e4;
|
|
@@ -28843,7 +29080,7 @@ var adapters = {
|
|
|
28843
29080
|
}
|
|
28844
29081
|
};
|
|
28845
29082
|
function directoryDigest(directory) {
|
|
28846
|
-
const hash2 =
|
|
29083
|
+
const hash2 = createHash4("sha256");
|
|
28847
29084
|
let entriesSeen = 0;
|
|
28848
29085
|
let bytesSeen = 0;
|
|
28849
29086
|
const walk = (current, relative) => {
|
|
@@ -33179,7 +33416,7 @@ async function startServer(service, options = {}) {
|
|
|
33179
33416
|
}
|
|
33180
33417
|
|
|
33181
33418
|
// src/server/agent-socket.ts
|
|
33182
|
-
import { createHash as
|
|
33419
|
+
import { createHash as createHash5, randomUUID as randomUUID4 } from "node:crypto";
|
|
33183
33420
|
import {
|
|
33184
33421
|
chmodSync as chmodSync2,
|
|
33185
33422
|
existsSync as existsSync5,
|
|
@@ -33198,18 +33435,67 @@ import path9 from "node:path";
|
|
|
33198
33435
|
var nonEmptyString = external_exports.string().min(1);
|
|
33199
33436
|
var commentUri = external_exports.string().regex(/^rvw:\/\/comment\//);
|
|
33200
33437
|
var walkthroughUri = external_exports.string().regex(/^rvw:\/\/walkthrough\//);
|
|
33438
|
+
var nullableCommentLine = external_exports.number().int().positive().nullable().optional().default(null);
|
|
33439
|
+
var idempotencyKey = external_exports.string().min(1).max(MAX_IDEMPOTENCY_KEY_CHARACTERS).optional();
|
|
33440
|
+
var commentTargetInputSchema = external_exports.union([
|
|
33441
|
+
external_exports.object({ kind: external_exports.literal("pull-request") }).strict(),
|
|
33442
|
+
external_exports.object({
|
|
33443
|
+
kind: external_exports.literal("walkthrough"),
|
|
33444
|
+
walkthroughId: external_exports.uuid(),
|
|
33445
|
+
startLine: nullableCommentLine,
|
|
33446
|
+
endLine: nullableCommentLine
|
|
33447
|
+
}).strict(),
|
|
33448
|
+
external_exports.object({
|
|
33449
|
+
kind: external_exports.literal("document"),
|
|
33450
|
+
documentKind: external_exports.literal("pull-request-markdown"),
|
|
33451
|
+
startLine: nullableCommentLine,
|
|
33452
|
+
endLine: nullableCommentLine
|
|
33453
|
+
}).strict(),
|
|
33454
|
+
external_exports.object({
|
|
33455
|
+
kind: external_exports.literal("document"),
|
|
33456
|
+
documentKind: external_exports.literal("repository-file"),
|
|
33457
|
+
sourceOid: external_exports.string().regex(GIT_OBJECT_ID_PATTERN),
|
|
33458
|
+
path: nonEmptyString,
|
|
33459
|
+
startLine: nullableCommentLine,
|
|
33460
|
+
endLine: nullableCommentLine
|
|
33461
|
+
}).strict()
|
|
33462
|
+
]).superRefine((target, context) => {
|
|
33463
|
+
if (target.kind === "pull-request") return;
|
|
33464
|
+
if (target.startLine === null !== (target.endLine === null)) {
|
|
33465
|
+
context.addIssue({
|
|
33466
|
+
code: "custom",
|
|
33467
|
+
message: "startLine\u3068endLine\u306F\u4E21\u65B9\u6307\u5B9A\u3059\u308B\u304B\u3001\u4E21\u65B9\u7701\u7565\u3057\u3066\u304F\u3060\u3055\u3044\u3002"
|
|
33468
|
+
});
|
|
33469
|
+
return;
|
|
33470
|
+
}
|
|
33471
|
+
if (target.startLine !== null && target.endLine !== null && target.endLine < target.startLine) {
|
|
33472
|
+
context.addIssue({
|
|
33473
|
+
code: "custom",
|
|
33474
|
+
message: "endLine\u306FstartLine\u4EE5\u4E0A\u306B\u3057\u3066\u304F\u3060\u3055\u3044\u3002"
|
|
33475
|
+
});
|
|
33476
|
+
}
|
|
33477
|
+
});
|
|
33478
|
+
var commentCreateInputSchema = external_exports.object({
|
|
33479
|
+
pullRequest: nonEmptyString,
|
|
33480
|
+
target: commentTargetInputSchema,
|
|
33481
|
+
body: external_exports.string().min(1).refine((value) => value.trim().length > 0).refine((value) => Buffer.byteLength(value, "utf8") <= MAX_COMMENT_BODY_BYTES),
|
|
33482
|
+
authorLabel: external_exports.string().max(MAX_AUTHOR_LABEL_CHARACTERS).nullable().optional()
|
|
33483
|
+
}).strict();
|
|
33201
33484
|
var commentReplyInputSchema = external_exports.object({
|
|
33202
33485
|
body: external_exports.string().min(1).refine((value) => Buffer.byteLength(value, "utf8") <= MAX_COMMENT_BODY_BYTES),
|
|
33203
33486
|
authorLabel: external_exports.string().max(MAX_AUTHOR_LABEL_CHARACTERS).nullable().optional(),
|
|
33204
|
-
relatedCommitOid: external_exports.string().regex(GIT_OBJECT_ID_PATTERN).nullable().optional()
|
|
33487
|
+
relatedCommitOid: external_exports.string().regex(GIT_OBJECT_ID_PATTERN).nullable().optional(),
|
|
33488
|
+
idempotencyKey
|
|
33205
33489
|
}).strict();
|
|
33490
|
+
var commentPostEditInputSchema = commentReplyInputSchema.pick({ body: true, relatedCommitOid: true }).strict();
|
|
33206
33491
|
var pullRequestSyncInputSchema = external_exports.object({
|
|
33207
33492
|
pullRequest: nonEmptyString,
|
|
33208
33493
|
commentUpdates: external_exports.array(
|
|
33209
33494
|
external_exports.object({
|
|
33210
33495
|
commentRef: commentUri,
|
|
33211
33496
|
reply: external_exports.string().refine((value) => Buffer.byteLength(value, "utf8") <= MAX_COMMENT_BODY_BYTES),
|
|
33212
|
-
resolve: external_exports.boolean()
|
|
33497
|
+
resolve: external_exports.boolean(),
|
|
33498
|
+
idempotencyKey
|
|
33213
33499
|
}).strict()
|
|
33214
33500
|
).max(500).optional()
|
|
33215
33501
|
}).strict();
|
|
@@ -33263,8 +33549,14 @@ var agentCommandInputSchemas = {
|
|
|
33263
33549
|
limit: external_exports.number().int().min(1).max(MAX_COMMENT_LIST_LIMIT).default(DEFAULT_COMMENT_LIST_LIMIT),
|
|
33264
33550
|
offset: external_exports.number().int().min(0).default(0)
|
|
33265
33551
|
}).strict(),
|
|
33552
|
+
"comment.watch": external_exports.object({
|
|
33553
|
+
cursor: external_exports.string().min(1).max(512).optional(),
|
|
33554
|
+
limit: external_exports.number().int().min(1).max(MAX_COMMENT_WATCH_LIMIT)
|
|
33555
|
+
}).strict(),
|
|
33556
|
+
"comment.create": commentCreateInputSchema,
|
|
33266
33557
|
"comment.get": external_exports.object({ uri: commentUri, live: external_exports.boolean().default(false) }).strict(),
|
|
33267
33558
|
"comment.reply": external_exports.object({ uri: commentUri, reply: commentReplyInputSchema }).strict(),
|
|
33559
|
+
"comment.edit": external_exports.object({ uri: commentUri, postId: nonEmptyString, edit: commentPostEditInputSchema }).strict(),
|
|
33268
33560
|
"comment.resolve": external_exports.object({ uri: commentUri }).strict(),
|
|
33269
33561
|
"comment.reopen": external_exports.object({ uri: commentUri }).strict(),
|
|
33270
33562
|
"walkthrough.get": external_exports.object({ uri: walkthroughUri }).strict(),
|
|
@@ -33302,7 +33594,7 @@ function agentSocketPath(databaseFilePath) {
|
|
|
33302
33594
|
if (configuredPath) return configuredPath;
|
|
33303
33595
|
const user = process.getuid?.() ?? os4.userInfo().username.replace(/[^A-Za-z0-9_-]/g, "_");
|
|
33304
33596
|
const databasePath = path9.resolve(databaseFilePath ?? databasePathConfiguration().filePath);
|
|
33305
|
-
const databaseKey =
|
|
33597
|
+
const databaseKey = createHash5("sha256").update(databasePath).digest("hex").slice(0, 16);
|
|
33306
33598
|
return path9.join(os4.tmpdir(), `rvw-agent-${user}`, `${databaseKey}.sock`);
|
|
33307
33599
|
}
|
|
33308
33600
|
function ensurePrivateSocketDirectory(socketPath) {
|
|
@@ -33407,6 +33699,16 @@ async function dispatchAgentSocketRequest(service, rawRequest) {
|
|
|
33407
33699
|
offset: input.offset
|
|
33408
33700
|
});
|
|
33409
33701
|
}
|
|
33702
|
+
case "comment.watch": {
|
|
33703
|
+
const input = parseOperationInput("comment.watch", request.input);
|
|
33704
|
+
return service.listCommentPostEvents(input.cursor, input.limit);
|
|
33705
|
+
}
|
|
33706
|
+
case "comment.create": {
|
|
33707
|
+
const input = parseOperationInput("comment.create", request.input);
|
|
33708
|
+
return await service.createCommentForReference(
|
|
33709
|
+
input
|
|
33710
|
+
);
|
|
33711
|
+
}
|
|
33410
33712
|
case "comment.get": {
|
|
33411
33713
|
const input = parseOperationInput("comment.get", request.input);
|
|
33412
33714
|
return await service.getCommentReviewContext(input.uri, { live: input.live });
|
|
@@ -33418,6 +33720,13 @@ async function dispatchAgentSocketRequest(service, rawRequest) {
|
|
|
33418
33720
|
input.reply
|
|
33419
33721
|
);
|
|
33420
33722
|
}
|
|
33723
|
+
case "comment.edit": {
|
|
33724
|
+
const input = parseOperationInput("comment.edit", request.input);
|
|
33725
|
+
return await service.editCommentPost(input.uri, input.postId, {
|
|
33726
|
+
body: input.edit.body,
|
|
33727
|
+
...input.edit.relatedCommitOid === void 0 ? {} : { relatedCommitOid: input.edit.relatedCommitOid }
|
|
33728
|
+
});
|
|
33729
|
+
}
|
|
33421
33730
|
case "comment.resolve": {
|
|
33422
33731
|
const input = parseOperationInput("comment.resolve", request.input);
|
|
33423
33732
|
return service.setCommentResolved(input.uri, true);
|
|
@@ -33972,11 +34281,20 @@ var commentListOptionsSchema = external_exports.object({
|
|
|
33972
34281
|
limit: external_exports.coerce.number().int().min(1).max(MAX_COMMENT_LIST_LIMIT).default(DEFAULT_COMMENT_LIST_LIMIT),
|
|
33973
34282
|
offset: external_exports.coerce.number().int().min(0).default(0)
|
|
33974
34283
|
});
|
|
34284
|
+
var commentWatchOptionsSchema = external_exports.object({
|
|
34285
|
+
after: external_exports.string().min(1).max(512).optional(),
|
|
34286
|
+
interval: external_exports.coerce.number().int().min(1).max(MAX_COMMENT_WATCH_INTERVAL_SECONDS).default(DEFAULT_COMMENT_WATCH_INTERVAL_SECONDS),
|
|
34287
|
+
limit: external_exports.coerce.number().int().min(1).max(MAX_COMMENT_WATCH_LIMIT).default(DEFAULT_COMMENT_WATCH_LIMIT),
|
|
34288
|
+
once: external_exports.boolean().optional().default(false),
|
|
34289
|
+
jsonSeq: external_exports.literal(true)
|
|
34290
|
+
});
|
|
33975
34291
|
var commentPullRequestOutputSchema = external_exports.object({
|
|
33976
34292
|
url: external_exports.string(),
|
|
33977
34293
|
owner: external_exports.string(),
|
|
33978
34294
|
repository: external_exports.string(),
|
|
33979
34295
|
number: external_exports.number().int(),
|
|
34296
|
+
authorLogin: external_exports.string().nullable(),
|
|
34297
|
+
headRepository: external_exports.object({ owner: external_exports.string(), name: external_exports.string(), url: external_exports.string() }).strict().nullable(),
|
|
33980
34298
|
title: external_exports.string(),
|
|
33981
34299
|
body: external_exports.string().optional(),
|
|
33982
34300
|
baseRefName: external_exports.string(),
|
|
@@ -34124,6 +34442,8 @@ var commentGetOutputSchema = external_exports.object({
|
|
|
34124
34442
|
liveCheckedAt: external_exports.string().nullable(),
|
|
34125
34443
|
staleAgainstGitHub: external_exports.boolean().nullable(),
|
|
34126
34444
|
live: external_exports.object({
|
|
34445
|
+
authorLogin: external_exports.string().nullable(),
|
|
34446
|
+
headRepository: external_exports.object({ owner: external_exports.string(), name: external_exports.string(), url: external_exports.string() }).strict().nullable(),
|
|
34127
34447
|
title: external_exports.string(),
|
|
34128
34448
|
body: external_exports.string().optional(),
|
|
34129
34449
|
baseRefName: external_exports.string(),
|
|
@@ -34183,11 +34503,18 @@ function truncateUtf82(value, maxBytes) {
|
|
|
34183
34503
|
return { value: result, truncated: true };
|
|
34184
34504
|
}
|
|
34185
34505
|
function formatPullRequest(pullRequest, options = {}) {
|
|
34506
|
+
const headRepository = pullRequest.latestHeadRepositoryOwner && pullRequest.latestHeadRepositoryName ? {
|
|
34507
|
+
owner: pullRequest.latestHeadRepositoryOwner,
|
|
34508
|
+
name: pullRequest.latestHeadRepositoryName,
|
|
34509
|
+
url: `https://github.com/${pullRequest.latestHeadRepositoryOwner}/${pullRequest.latestHeadRepositoryName}`
|
|
34510
|
+
} : null;
|
|
34186
34511
|
return {
|
|
34187
34512
|
url: pullRequest.url,
|
|
34188
34513
|
owner: pullRequest.owner,
|
|
34189
34514
|
repository: pullRequest.repository,
|
|
34190
34515
|
number: pullRequest.number,
|
|
34516
|
+
authorLogin: pullRequest.latestAuthorLogin,
|
|
34517
|
+
headRepository,
|
|
34191
34518
|
title: pullRequest.latestTitle,
|
|
34192
34519
|
...options.includeBody ? { body: pullRequest.latestBody } : {},
|
|
34193
34520
|
baseRefName: pullRequest.latestBaseRefName,
|
|
@@ -34245,6 +34572,12 @@ function formatCommentGetOutput(result, options = {}) {
|
|
|
34245
34572
|
liveCheckedAt: result.githubState.liveCheckedAt,
|
|
34246
34573
|
staleAgainstGitHub: result.githubState.staleAgainstGitHub,
|
|
34247
34574
|
live: result.githubState.live ? {
|
|
34575
|
+
authorLogin: result.githubState.live.authorLogin,
|
|
34576
|
+
headRepository: result.githubState.live.headRepositoryOwner && result.githubState.live.headRepositoryName ? {
|
|
34577
|
+
owner: result.githubState.live.headRepositoryOwner,
|
|
34578
|
+
name: result.githubState.live.headRepositoryName,
|
|
34579
|
+
url: `https://github.com/${result.githubState.live.headRepositoryOwner}/${result.githubState.live.headRepositoryName}`
|
|
34580
|
+
} : null,
|
|
34248
34581
|
title: result.githubState.live.title,
|
|
34249
34582
|
...options.includePrBody ? { body: result.githubState.live.body } : {},
|
|
34250
34583
|
baseRefName: result.githubState.live.baseRefName,
|
|
@@ -34256,6 +34589,12 @@ function formatCommentGetOutput(result, options = {}) {
|
|
|
34256
34589
|
}
|
|
34257
34590
|
});
|
|
34258
34591
|
}
|
|
34592
|
+
function formatCommentWatchEvent(item) {
|
|
34593
|
+
return {
|
|
34594
|
+
cursor: item.cursor,
|
|
34595
|
+
event: item.event
|
|
34596
|
+
};
|
|
34597
|
+
}
|
|
34259
34598
|
function formatCommentListOutput(result, state) {
|
|
34260
34599
|
return commentListOutputSchema.parse({
|
|
34261
34600
|
ok: true,
|
|
@@ -34295,6 +34634,13 @@ function writeJson(value) {
|
|
|
34295
34634
|
process.stdout.write(`${JSON.stringify(value)}
|
|
34296
34635
|
`);
|
|
34297
34636
|
}
|
|
34637
|
+
function writeJsonSequence(value) {
|
|
34638
|
+
process.stdout.write(`${JSON.stringify(value)}
|
|
34639
|
+
`);
|
|
34640
|
+
}
|
|
34641
|
+
async function waitForCommentWatchInterval(milliseconds) {
|
|
34642
|
+
await new Promise((resolve) => setTimeout(resolve, milliseconds));
|
|
34643
|
+
}
|
|
34298
34644
|
function writeOutput(options, value, human) {
|
|
34299
34645
|
if (options.json) writeJson(value);
|
|
34300
34646
|
else process.stdout.write(`${human}
|
|
@@ -34668,9 +35014,12 @@ function createProgram(runtimeFactory = defaultRuntimeFactory) {
|
|
|
34668
35014
|
appVersion: APP_VERSION,
|
|
34669
35015
|
capabilities: [
|
|
34670
35016
|
"agent.transport",
|
|
35017
|
+
"comment.create",
|
|
34671
35018
|
"comment.list",
|
|
35019
|
+
"comment.watch",
|
|
34672
35020
|
"comment.read",
|
|
34673
35021
|
"comment.reply",
|
|
35022
|
+
"comment.edit",
|
|
34674
35023
|
"comment.resolve",
|
|
34675
35024
|
"comment.reopen",
|
|
34676
35025
|
"pullRequest.sync",
|
|
@@ -34870,6 +35219,73 @@ function createProgram(runtimeFactory = defaultRuntimeFactory) {
|
|
|
34870
35219
|
);
|
|
34871
35220
|
writeJson({ ok: true, deleted });
|
|
34872
35221
|
});
|
|
35222
|
+
comment.command("watch").description("\u5168\u767B\u9332PR\u3067\u8D77\u52D5\u5F8C\u306B\u4F5C\u6210\u3055\u308C\u305Froot comment\u3068reply\u3092\u76E3\u8996").option("--after <cursor>", "\u4EE5\u524D\u306Ewatch cursor\u304B\u3089\u518D\u958B").option(
|
|
35223
|
+
"--interval <seconds>",
|
|
35224
|
+
`poll\u9593\u9694\uFF08\u65E2\u5B9A: ${DEFAULT_COMMENT_WATCH_INTERVAL_SECONDS}\u79D2\uFF09`,
|
|
35225
|
+
String(DEFAULT_COMMENT_WATCH_INTERVAL_SECONDS)
|
|
35226
|
+
).option(
|
|
35227
|
+
"--limit <limit>",
|
|
35228
|
+
`\u4E00\u5EA6\u306B\u53D6\u5F97\u3059\u308B\u6700\u5927event\u6570\uFF08\u65E2\u5B9A: ${DEFAULT_COMMENT_WATCH_LIMIT}\uFF09`,
|
|
35229
|
+
String(DEFAULT_COMMENT_WATCH_LIMIT)
|
|
35230
|
+
).option("--once", "\u73FE\u5728\u53D6\u5F97\u53EF\u80FD\u306Aevent\u3092\u51FA\u529B\u3057\u3066\u7D42\u4E86").requiredOption("--json-seq", "RFC 7464 JSON text sequence\u3067\u51FA\u529B").action(async (rawOptions) => {
|
|
35231
|
+
const options = commentWatchOptionsSchema.parse(rawOptions);
|
|
35232
|
+
let cursor = options.after;
|
|
35233
|
+
let first = true;
|
|
35234
|
+
let stopping = false;
|
|
35235
|
+
const stop = () => {
|
|
35236
|
+
stopping = true;
|
|
35237
|
+
};
|
|
35238
|
+
process.once("SIGINT", stop);
|
|
35239
|
+
process.once("SIGTERM", stop);
|
|
35240
|
+
try {
|
|
35241
|
+
do {
|
|
35242
|
+
const result = await callService(
|
|
35243
|
+
"comment.watch",
|
|
35244
|
+
{
|
|
35245
|
+
...cursor === void 0 ? {} : { cursor },
|
|
35246
|
+
limit: options.limit
|
|
35247
|
+
},
|
|
35248
|
+
() => getRuntime().service.listCommentPostEvents(cursor, options.limit)
|
|
35249
|
+
);
|
|
35250
|
+
if (first) {
|
|
35251
|
+
writeJsonSequence({
|
|
35252
|
+
type: "ready",
|
|
35253
|
+
databaseId: result.databaseId,
|
|
35254
|
+
cursor: result.startCursor,
|
|
35255
|
+
anchoredAtCurrent: result.anchoredAtCurrent
|
|
35256
|
+
});
|
|
35257
|
+
}
|
|
35258
|
+
for (const item of result.events) {
|
|
35259
|
+
writeJsonSequence({ type: "comment-posted", ...formatCommentWatchEvent(item) });
|
|
35260
|
+
}
|
|
35261
|
+
cursor = result.cursor;
|
|
35262
|
+
first = false;
|
|
35263
|
+
if (options.once || stopping) break;
|
|
35264
|
+
if (!result.hasMore) {
|
|
35265
|
+
await waitForCommentWatchInterval(options.interval * 1e3);
|
|
35266
|
+
}
|
|
35267
|
+
} while (!stopping);
|
|
35268
|
+
writeJsonSequence({ type: "stopped", cursor });
|
|
35269
|
+
} finally {
|
|
35270
|
+
process.off("SIGINT", stop);
|
|
35271
|
+
process.off("SIGTERM", stop);
|
|
35272
|
+
}
|
|
35273
|
+
});
|
|
35274
|
+
comment.command("create").requiredOption("--stdin", "stdin\u304B\u3089JSON\u3092\u8AAD\u3080").requiredOption("--json", "JSON\u3067\u51FA\u529B").description("\u767B\u9332\u6E08\u307FPR\u3078\u672A\u89E3\u6C7A\u30B3\u30E1\u30F3\u30C8\u3092\u4E00\u4EF6\u4F5C\u6210").action(async () => {
|
|
35275
|
+
const input = commentCreateInputSchema.parse(await readStdinJson());
|
|
35276
|
+
const request = {
|
|
35277
|
+
pullRequest: input.pullRequest,
|
|
35278
|
+
target: input.target,
|
|
35279
|
+
body: input.body,
|
|
35280
|
+
...input.authorLabel === void 0 ? {} : { authorLabel: input.authorLabel }
|
|
35281
|
+
};
|
|
35282
|
+
const created = await callService(
|
|
35283
|
+
"comment.create",
|
|
35284
|
+
request,
|
|
35285
|
+
async () => await getRuntime().service.createCommentForReference(request)
|
|
35286
|
+
);
|
|
35287
|
+
writeJson({ ok: true, comment: created });
|
|
35288
|
+
});
|
|
34873
35289
|
comment.command("list").argument("<pull-request>", "\u767B\u9332\u6E08\u307FPR URL\u307E\u305F\u306F\u756A\u53F7").option("--state <state>", "unresolved\u3001resolved\u3001all\uFF08\u65E2\u5B9A: unresolved\uFF09", "unresolved").option(
|
|
34874
35290
|
"--limit <limit>",
|
|
34875
35291
|
`1\u30DA\u30FC\u30B8\u306E\u6700\u5927\u4EF6\u6570\uFF08\u65E2\u5B9A: ${DEFAULT_COMMENT_LIST_LIMIT}\uFF09`,
|
|
@@ -34902,7 +35318,8 @@ function createProgram(runtimeFactory = defaultRuntimeFactory) {
|
|
|
34902
35318
|
const reply = {
|
|
34903
35319
|
body: input.body,
|
|
34904
35320
|
...input.authorLabel === void 0 ? {} : { authorLabel: input.authorLabel },
|
|
34905
|
-
...input.relatedCommitOid === void 0 ? {} : { relatedCommitOid: input.relatedCommitOid }
|
|
35321
|
+
...input.relatedCommitOid === void 0 ? {} : { relatedCommitOid: input.relatedCommitOid },
|
|
35322
|
+
...input.idempotencyKey === void 0 ? {} : { idempotencyKey: input.idempotencyKey }
|
|
34906
35323
|
};
|
|
34907
35324
|
const post = await callService(
|
|
34908
35325
|
"comment.reply",
|
|
@@ -34911,6 +35328,19 @@ function createProgram(runtimeFactory = defaultRuntimeFactory) {
|
|
|
34911
35328
|
);
|
|
34912
35329
|
writeJson({ ok: true, post });
|
|
34913
35330
|
});
|
|
35331
|
+
comment.command("edit").argument("<comment-uri>").requiredOption("--post <post-id>", "\u7DE8\u96C6\u3059\u308Bpost ID").requiredOption("--stdin", "stdin\u304B\u3089JSON\u3092\u8AAD\u3080").requiredOption("--json", "JSON\u3067\u51FA\u529B").action(async (uri, options) => {
|
|
35332
|
+
const input = commentPostEditInputSchema.parse(await readStdinJson());
|
|
35333
|
+
const edit = {
|
|
35334
|
+
body: input.body,
|
|
35335
|
+
...input.relatedCommitOid === void 0 ? {} : { relatedCommitOid: input.relatedCommitOid }
|
|
35336
|
+
};
|
|
35337
|
+
const post = await callService(
|
|
35338
|
+
"comment.edit",
|
|
35339
|
+
{ uri, postId: options.post, edit },
|
|
35340
|
+
async () => await getRuntime().service.editCommentPost(uri, options.post, edit)
|
|
35341
|
+
);
|
|
35342
|
+
writeJson({ ok: true, post });
|
|
35343
|
+
});
|
|
34914
35344
|
comment.command("resolve").argument("<comment-uri>").requiredOption("--json", "JSON\u3067\u51FA\u529B").action(async (uri) => {
|
|
34915
35345
|
const comment2 = await callService(
|
|
34916
35346
|
"comment.resolve",
|
|
@@ -34958,13 +35388,15 @@ function createProgram(runtimeFactory = defaultRuntimeFactory) {
|
|
|
34958
35388
|
}
|
|
34959
35389
|
async function runCli(argv = process.argv) {
|
|
34960
35390
|
const json3 = argv.includes("--json");
|
|
35391
|
+
const jsonSequence = argv.includes("--json-seq");
|
|
34961
35392
|
try {
|
|
34962
35393
|
await createProgram().parseAsync(argv);
|
|
34963
35394
|
} catch (error51) {
|
|
34964
35395
|
const rvwError = error51 instanceof external_exports.ZodError ? new RvwError("INVALID_INPUT", "\u5165\u529B\u304CCLI schema\u306B\u9069\u5408\u3057\u307E\u305B\u3093\u3002", {
|
|
34965
35396
|
details: external_exports.treeifyError(error51)
|
|
34966
35397
|
}) : asRvwError(error51);
|
|
34967
|
-
if (
|
|
35398
|
+
if (jsonSequence) writeJsonSequence({ type: "error", error: rvwError.toJSON() });
|
|
35399
|
+
else if (json3) writeJson({ ok: false, error: rvwError.toJSON() });
|
|
34968
35400
|
else process.stderr.write(`rvw: ${rvwError.message}
|
|
34969
35401
|
${rvwError.suggestions.join("\n")}
|
|
34970
35402
|
`);
|