@opentag/github 0.2.0 → 0.3.1
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/dist/index.js +212 -82
- package/dist/index.js.map +1 -1
- package/dist/ingress.d.ts +8 -0
- package/dist/ingress.d.ts.map +1 -1
- package/dist/normalize.d.ts +4 -0
- package/dist/normalize.d.ts.map +1 -1
- package/dist/render.d.ts +7 -2
- package/dist/render.d.ts.map +1 -1
- package/package.json +3 -3
package/dist/index.js
CHANGED
|
@@ -534,7 +534,12 @@ async function applyGitHubIssueMutationIntents(input) {
|
|
|
534
534
|
import { createHmac, randomUUID, timingSafeEqual } from "crypto";
|
|
535
535
|
import { serve } from "@hono/node-server";
|
|
536
536
|
import { createOpenTagClient } from "@opentag/client";
|
|
537
|
-
import {
|
|
537
|
+
import {
|
|
538
|
+
DEFAULT_MAX_REQUEST_BODY_BYTES,
|
|
539
|
+
RequestBodyTooLargeError,
|
|
540
|
+
parseThreadActionCommand,
|
|
541
|
+
readRequestTextWithLimit
|
|
542
|
+
} from "@opentag/core";
|
|
538
543
|
import { Hono } from "hono";
|
|
539
544
|
|
|
540
545
|
// src/normalize.ts
|
|
@@ -689,6 +694,8 @@ function normalizeGitHubIssueComment(input) {
|
|
|
689
694
|
repo: input.repo,
|
|
690
695
|
issueNumber: input.issueNumber,
|
|
691
696
|
...commandMetadata(command),
|
|
697
|
+
...input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {},
|
|
698
|
+
...typeof input.signatureVerified === "boolean" ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? "verified" : "unverified" } : {},
|
|
692
699
|
...typeof input.installationId === "number" ? { installationId: input.installationId } : {}
|
|
693
700
|
}
|
|
694
701
|
};
|
|
@@ -752,6 +759,8 @@ function normalizeGitHubPullRequestReviewComment(input) {
|
|
|
752
759
|
repo: input.repo,
|
|
753
760
|
pullRequestNumber: input.pullRequestNumber,
|
|
754
761
|
...commandMetadata(command),
|
|
762
|
+
...input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {},
|
|
763
|
+
...typeof input.signatureVerified === "boolean" ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? "verified" : "unverified" } : {},
|
|
755
764
|
...typeof input.installationId === "number" ? { installationId: input.installationId } : {}
|
|
756
765
|
}
|
|
757
766
|
};
|
|
@@ -768,6 +777,42 @@ function verifyGitHubSignature(input) {
|
|
|
768
777
|
const actualBuffer = Buffer.from(input.signature);
|
|
769
778
|
return expectedBuffer.length === actualBuffer.length && timingSafeEqual(expectedBuffer, actualBuffer);
|
|
770
779
|
}
|
|
780
|
+
async function recordGitHubSignatureFailure(input) {
|
|
781
|
+
try {
|
|
782
|
+
await input.recordControlPlaneEvent?.({
|
|
783
|
+
type: "security.signature_failed",
|
|
784
|
+
severity: "warn",
|
|
785
|
+
subject: `github:POST ${input.webhookPath}`,
|
|
786
|
+
payload: {
|
|
787
|
+
provider: "github",
|
|
788
|
+
endpoint: `POST ${input.webhookPath}`,
|
|
789
|
+
reason: input.reason,
|
|
790
|
+
...input.deliveryId ? { deliveryId: input.deliveryId } : {},
|
|
791
|
+
hasSignature: input.hasSignature
|
|
792
|
+
}
|
|
793
|
+
});
|
|
794
|
+
} catch {
|
|
795
|
+
}
|
|
796
|
+
}
|
|
797
|
+
async function recordGitHubRequestBodyRejected(input) {
|
|
798
|
+
try {
|
|
799
|
+
await input.recordControlPlaneEvent?.({
|
|
800
|
+
type: "security.request_body_rejected",
|
|
801
|
+
severity: "warn",
|
|
802
|
+
subject: `github:POST ${input.webhookPath}`,
|
|
803
|
+
payload: {
|
|
804
|
+
provider: "github",
|
|
805
|
+
endpoint: `POST ${input.webhookPath}`,
|
|
806
|
+
reason: input.reason,
|
|
807
|
+
...input.maxBytes !== void 0 ? { maxBytes: input.maxBytes } : {},
|
|
808
|
+
contentLength: input.contentLength,
|
|
809
|
+
...input.deliveryId ? { deliveryId: input.deliveryId } : {},
|
|
810
|
+
...input.eventName ? { githubEvent: input.eventName } : {}
|
|
811
|
+
}
|
|
812
|
+
});
|
|
813
|
+
} catch {
|
|
814
|
+
}
|
|
815
|
+
}
|
|
771
816
|
function parseJsonPayload(rawBody) {
|
|
772
817
|
try {
|
|
773
818
|
return JSON.parse(rawBody);
|
|
@@ -775,6 +820,24 @@ function parseJsonPayload(rawBody) {
|
|
|
775
820
|
return null;
|
|
776
821
|
}
|
|
777
822
|
}
|
|
823
|
+
function isRecord(value) {
|
|
824
|
+
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
825
|
+
}
|
|
826
|
+
function hasGitHubActor(value) {
|
|
827
|
+
return isRecord(value) && typeof value.id === "number" && typeof value.login === "string";
|
|
828
|
+
}
|
|
829
|
+
function hasGitHubRepository(value) {
|
|
830
|
+
return isRecord(value) && typeof value.name === "string" && typeof value.private === "boolean" && isRecord(value.owner) && typeof value.owner.login === "string";
|
|
831
|
+
}
|
|
832
|
+
function hasGitHubInstallation(value) {
|
|
833
|
+
return isRecord(value) && typeof value.id === "number";
|
|
834
|
+
}
|
|
835
|
+
function isGitHubIssueCommentPayload(value) {
|
|
836
|
+
return isRecord(value) && (value.action === void 0 || typeof value.action === "string") && isRecord(value.comment) && typeof value.comment.id === "number" && typeof value.comment.body === "string" && typeof value.comment.html_url === "string" && isRecord(value.issue) && typeof value.issue.html_url === "string" && typeof value.issue.comments_url === "string" && typeof value.issue.number === "number" && hasGitHubRepository(value.repository) && hasGitHubActor(value.sender) && (value.installation === void 0 || hasGitHubInstallation(value.installation));
|
|
837
|
+
}
|
|
838
|
+
function isGitHubPullRequestReviewCommentPayload(value) {
|
|
839
|
+
return isRecord(value) && (value.action === void 0 || typeof value.action === "string") && isRecord(value.comment) && typeof value.comment.id === "number" && typeof value.comment.body === "string" && typeof value.comment.html_url === "string" && isRecord(value.pull_request) && typeof value.pull_request.html_url === "string" && typeof value.pull_request.number === "number" && hasGitHubRepository(value.repository) && hasGitHubActor(value.sender) && (value.installation === void 0 || hasGitHubInstallation(value.installation));
|
|
840
|
+
}
|
|
778
841
|
async function handleIssueCommentCreated(input) {
|
|
779
842
|
if (input.payload.action && input.payload.action !== "created") return;
|
|
780
843
|
if (parseThreadActionCommand(input.payload.comment.body) && input.submitThreadAction) {
|
|
@@ -796,7 +859,9 @@ async function handleIssueCommentCreated(input) {
|
|
|
796
859
|
owner: input.payload.repository.owner.login,
|
|
797
860
|
repo: input.payload.repository.name,
|
|
798
861
|
issueNumber: input.payload.issue.number,
|
|
799
|
-
commentUrl: input.payload.comment.html_url
|
|
862
|
+
commentUrl: input.payload.comment.html_url,
|
|
863
|
+
...input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {},
|
|
864
|
+
...typeof input.signatureVerified === "boolean" ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? "verified" : "unverified" } : {}
|
|
800
865
|
}
|
|
801
866
|
});
|
|
802
867
|
return;
|
|
@@ -814,6 +879,8 @@ async function handleIssueCommentCreated(input) {
|
|
|
814
879
|
actorLogin: input.payload.sender.login,
|
|
815
880
|
private: input.payload.repository.private,
|
|
816
881
|
receivedAt: input.now(),
|
|
882
|
+
...input.deliveryId ? { deliveryId: input.deliveryId } : {},
|
|
883
|
+
...typeof input.signatureVerified === "boolean" ? { signatureVerified: input.signatureVerified } : {},
|
|
817
884
|
...input.payload.installation ? { installationId: input.payload.installation.id } : {}
|
|
818
885
|
});
|
|
819
886
|
if (event) {
|
|
@@ -843,7 +910,9 @@ async function handlePullRequestReviewCommentCreated(input) {
|
|
|
843
910
|
owner,
|
|
844
911
|
repo,
|
|
845
912
|
pullRequestNumber: input.payload.pull_request.number,
|
|
846
|
-
commentUrl: input.payload.comment.html_url
|
|
913
|
+
commentUrl: input.payload.comment.html_url,
|
|
914
|
+
...input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {},
|
|
915
|
+
...typeof input.signatureVerified === "boolean" ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? "verified" : "unverified" } : {}
|
|
847
916
|
}
|
|
848
917
|
});
|
|
849
918
|
return;
|
|
@@ -861,6 +930,8 @@ async function handlePullRequestReviewCommentCreated(input) {
|
|
|
861
930
|
actorLogin: input.payload.sender.login,
|
|
862
931
|
private: input.payload.repository.private,
|
|
863
932
|
receivedAt: input.now(),
|
|
933
|
+
...input.deliveryId ? { deliveryId: input.deliveryId } : {},
|
|
934
|
+
...typeof input.signatureVerified === "boolean" ? { signatureVerified: input.signatureVerified } : {},
|
|
864
935
|
...input.payload.installation ? { installationId: input.payload.installation.id } : {}
|
|
865
936
|
});
|
|
866
937
|
if (event) {
|
|
@@ -870,41 +941,108 @@ async function handlePullRequestReviewCommentCreated(input) {
|
|
|
870
941
|
function createGitHubWebhookApp(input) {
|
|
871
942
|
const app = new Hono();
|
|
872
943
|
const webhookPath = input.webhookPath ?? "/github/webhooks";
|
|
944
|
+
const maxRequestBodyBytes = input.maxRequestBodyBytes ?? DEFAULT_MAX_REQUEST_BODY_BYTES;
|
|
873
945
|
if (!webhookPath.startsWith("/")) {
|
|
874
946
|
throw new Error("GitHub webhook path must start with /.");
|
|
875
947
|
}
|
|
876
948
|
app.post(webhookPath, async (c) => {
|
|
877
949
|
const signature = c.req.header("x-hub-signature-256");
|
|
878
950
|
if (!signature) {
|
|
951
|
+
await recordGitHubSignatureFailure({
|
|
952
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
953
|
+
webhookPath,
|
|
954
|
+
reason: "missing_signature_header",
|
|
955
|
+
...c.req.header("x-github-delivery") ? { deliveryId: c.req.header("x-github-delivery") } : {},
|
|
956
|
+
hasSignature: false
|
|
957
|
+
});
|
|
879
958
|
return c.json({ error: "missing_signature_header" }, 401);
|
|
880
959
|
}
|
|
881
|
-
|
|
960
|
+
let rawBody;
|
|
961
|
+
try {
|
|
962
|
+
rawBody = await readRequestTextWithLimit(c.req.raw, { maxBytes: maxRequestBodyBytes });
|
|
963
|
+
} catch (error) {
|
|
964
|
+
if (error instanceof RequestBodyTooLargeError) {
|
|
965
|
+
await recordGitHubRequestBodyRejected({
|
|
966
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
967
|
+
webhookPath,
|
|
968
|
+
reason: "request_body_too_large",
|
|
969
|
+
maxBytes: error.maxBytes,
|
|
970
|
+
contentLength: c.req.raw.headers.get("content-length"),
|
|
971
|
+
...c.req.header("x-github-delivery") ? { deliveryId: c.req.header("x-github-delivery") } : {},
|
|
972
|
+
...c.req.header("x-github-event") ? { eventName: c.req.header("x-github-event") } : {}
|
|
973
|
+
});
|
|
974
|
+
return c.json({ error: "request_body_too_large", maxBytes: error.maxBytes }, 413);
|
|
975
|
+
}
|
|
976
|
+
throw error;
|
|
977
|
+
}
|
|
882
978
|
if (!verifyGitHubSignature({ webhookSecret: input.webhookSecret, rawBody, signature })) {
|
|
979
|
+
await recordGitHubSignatureFailure({
|
|
980
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
981
|
+
webhookPath,
|
|
982
|
+
reason: "invalid_signature",
|
|
983
|
+
...c.req.header("x-github-delivery") ? { deliveryId: c.req.header("x-github-delivery") } : {},
|
|
984
|
+
hasSignature: true
|
|
985
|
+
});
|
|
883
986
|
return c.json({ error: "invalid_signature" }, 401);
|
|
884
987
|
}
|
|
988
|
+
const deliveryId = c.req.header("x-github-delivery");
|
|
885
989
|
const eventName = c.req.header("x-github-event");
|
|
886
990
|
const payload = parseJsonPayload(rawBody);
|
|
887
991
|
if (!payload || typeof payload !== "object") {
|
|
992
|
+
await recordGitHubRequestBodyRejected({
|
|
993
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
994
|
+
webhookPath,
|
|
995
|
+
reason: "invalid_json_body",
|
|
996
|
+
contentLength: c.req.raw.headers.get("content-length"),
|
|
997
|
+
...deliveryId ? { deliveryId } : {},
|
|
998
|
+
...eventName ? { eventName } : {}
|
|
999
|
+
});
|
|
888
1000
|
return c.json({ error: "invalid_json" }, 400);
|
|
889
1001
|
}
|
|
890
1002
|
if (eventName === "ping") {
|
|
891
1003
|
return c.json({ ok: true });
|
|
892
1004
|
}
|
|
893
1005
|
if (eventName === "issue_comment") {
|
|
1006
|
+
if (!isGitHubIssueCommentPayload(payload)) {
|
|
1007
|
+
await recordGitHubRequestBodyRejected({
|
|
1008
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
1009
|
+
webhookPath,
|
|
1010
|
+
reason: "invalid_request_body",
|
|
1011
|
+
contentLength: c.req.raw.headers.get("content-length"),
|
|
1012
|
+
...deliveryId ? { deliveryId } : {},
|
|
1013
|
+
eventName
|
|
1014
|
+
});
|
|
1015
|
+
return c.json({ error: "invalid_request_body" }, 400);
|
|
1016
|
+
}
|
|
894
1017
|
await handleIssueCommentCreated({
|
|
895
1018
|
payload,
|
|
896
1019
|
createRun: input.createRun,
|
|
897
1020
|
...input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {},
|
|
898
|
-
now: input.now
|
|
1021
|
+
now: input.now,
|
|
1022
|
+
...deliveryId ? { deliveryId } : {},
|
|
1023
|
+
signatureVerified: true
|
|
899
1024
|
});
|
|
900
1025
|
return c.json({ ok: true });
|
|
901
1026
|
}
|
|
902
1027
|
if (eventName === "pull_request_review_comment") {
|
|
1028
|
+
if (!isGitHubPullRequestReviewCommentPayload(payload)) {
|
|
1029
|
+
await recordGitHubRequestBodyRejected({
|
|
1030
|
+
recordControlPlaneEvent: input.recordControlPlaneEvent,
|
|
1031
|
+
webhookPath,
|
|
1032
|
+
reason: "invalid_request_body",
|
|
1033
|
+
contentLength: c.req.raw.headers.get("content-length"),
|
|
1034
|
+
...deliveryId ? { deliveryId } : {},
|
|
1035
|
+
eventName
|
|
1036
|
+
});
|
|
1037
|
+
return c.json({ error: "invalid_request_body" }, 400);
|
|
1038
|
+
}
|
|
903
1039
|
await handlePullRequestReviewCommentCreated({
|
|
904
1040
|
payload,
|
|
905
1041
|
createRun: input.createRun,
|
|
906
1042
|
...input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {},
|
|
907
|
-
now: input.now
|
|
1043
|
+
now: input.now,
|
|
1044
|
+
...deliveryId ? { deliveryId } : {},
|
|
1045
|
+
signatureVerified: true
|
|
908
1046
|
});
|
|
909
1047
|
return c.json({ ok: true });
|
|
910
1048
|
}
|
|
@@ -924,6 +1062,7 @@ function startGitHubIngress(config) {
|
|
|
924
1062
|
fetch: createGitHubWebhookApp({
|
|
925
1063
|
webhookSecret: config.webhookSecret,
|
|
926
1064
|
webhookPath,
|
|
1065
|
+
...config.maxRequestBodyBytes ? { maxRequestBodyBytes: config.maxRequestBodyBytes } : {},
|
|
927
1066
|
async createRun(event) {
|
|
928
1067
|
const runId = `run_${randomUUID()}`;
|
|
929
1068
|
const created = await dispatcherClient.createRun({ runId, event });
|
|
@@ -932,6 +1071,9 @@ function startGitHubIngress(config) {
|
|
|
932
1071
|
async submitThreadAction(action) {
|
|
933
1072
|
await dispatcherClient.submitThreadAction(action);
|
|
934
1073
|
},
|
|
1074
|
+
async recordControlPlaneEvent(event) {
|
|
1075
|
+
await dispatcherClient.recordControlPlaneEvent(event);
|
|
1076
|
+
},
|
|
935
1077
|
now: () => (/* @__PURE__ */ new Date()).toISOString()
|
|
936
1078
|
}).fetch,
|
|
937
1079
|
port,
|
|
@@ -956,83 +1098,63 @@ function startGitHubIngress(config) {
|
|
|
956
1098
|
}
|
|
957
1099
|
|
|
958
1100
|
// src/render.ts
|
|
959
|
-
import {
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
return
|
|
1101
|
+
import {
|
|
1102
|
+
createFinalSummaryPresentation
|
|
1103
|
+
} from "@opentag/core";
|
|
1104
|
+
function tableValue(value) {
|
|
1105
|
+
return value.replace(/\|/g, "\\|").replace(/\n/g, "<br>");
|
|
964
1106
|
}
|
|
965
|
-
function
|
|
966
|
-
|
|
967
|
-
|
|
1107
|
+
function decisionLabel(decision) {
|
|
1108
|
+
if (decision === "apply") return "Apply now";
|
|
1109
|
+
if (decision === "approve") return "Approve only";
|
|
1110
|
+
if (decision === "continue") return "Continue";
|
|
1111
|
+
return "Reject";
|
|
968
1112
|
}
|
|
969
|
-
function
|
|
970
|
-
|
|
971
|
-
if (
|
|
972
|
-
|
|
1113
|
+
function decisionEffect(decision) {
|
|
1114
|
+
if (decision === "apply") return "Approves and applies this action to the system of record.";
|
|
1115
|
+
if (decision === "approve") return "Records approval without applying yet.";
|
|
1116
|
+
if (decision === "continue") return "Starts a follow-up run from this approved action.";
|
|
1117
|
+
return "Rejects this action.";
|
|
973
1118
|
}
|
|
974
|
-
function
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
979
|
-
const command = item["command"];
|
|
980
|
-
const outcome = item["outcome"];
|
|
981
|
-
return typeof command === "string" && typeof outcome === "string" ? ` - \`${command}\`: ${outcome}` : void 0;
|
|
982
|
-
}).filter((line) => Boolean(line));
|
|
1119
|
+
function actionDetailRows(action) {
|
|
1120
|
+
if (action.detailRows?.length) return action.detailRows.map((row) => [row.label, row.value]);
|
|
1121
|
+
const rows = [["Target", action.targetLabel]];
|
|
1122
|
+
if (action.setupReason) rows.push(["Status", action.setupReason]);
|
|
1123
|
+
return rows;
|
|
983
1124
|
}
|
|
984
|
-
function
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
const
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
if (head || base) lines.push(` Branch: \`${head ?? "unknown"}\` -> \`${base ?? "main"}\``);
|
|
995
|
-
if (changedFiles.length > 0) lines.push(` Changed files: ${changedFiles.map((file) => `\`${file}\``).join(", ")}`);
|
|
996
|
-
if (risks.length > 0) {
|
|
997
|
-
lines.push(" Risks:");
|
|
998
|
-
for (const risk of risks) {
|
|
999
|
-
lines.push(` - ${risk}`);
|
|
1000
|
-
}
|
|
1001
|
-
}
|
|
1002
|
-
if (verification.length > 0) {
|
|
1003
|
-
lines.push(" Verification:");
|
|
1004
|
-
lines.push(...verification);
|
|
1125
|
+
function renderSuggestedActions(presentation) {
|
|
1126
|
+
const actions = presentation.actions ?? [];
|
|
1127
|
+
if (actions.length === 0 || !presentation.actionReceiptTitle) return [];
|
|
1128
|
+
const lines = [
|
|
1129
|
+
`### ${presentation.actionReceiptTitle}`,
|
|
1130
|
+
"",
|
|
1131
|
+
"OpenTag prepared a source-thread action receipt. Choose one command in this GitHub thread; full protocol lineage stays in the audit log."
|
|
1132
|
+
];
|
|
1133
|
+
if (presentation.auditRunId) {
|
|
1134
|
+
lines.push("", `Audit: run \`opentag status --run ${presentation.auditRunId}\` locally.`);
|
|
1005
1135
|
}
|
|
1006
|
-
|
|
1007
|
-
}
|
|
1008
|
-
function renderSuggestedActions(result) {
|
|
1009
|
-
const candidates = suggestedActionCandidatesFromResult(result);
|
|
1010
|
-
if (candidates.length === 0) return [];
|
|
1011
|
-
const lines = ["Suggested actions:"];
|
|
1012
|
-
for (const candidate of candidates) {
|
|
1136
|
+
for (const action of actions) {
|
|
1013
1137
|
lines.push(
|
|
1014
1138
|
"",
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1139
|
+
`#### ${action.index}. ${action.title}`,
|
|
1140
|
+
"",
|
|
1141
|
+
"| Field | Value |",
|
|
1142
|
+
"| --- | --- |"
|
|
1019
1143
|
);
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1144
|
+
for (const [label, value] of actionDetailRows(action)) {
|
|
1145
|
+
lines.push(`| ${label} | ${tableValue(value)} |`);
|
|
1146
|
+
}
|
|
1147
|
+
lines.push(
|
|
1148
|
+
"",
|
|
1149
|
+
"**Choose in this thread**",
|
|
1150
|
+
"",
|
|
1151
|
+
`| Decision | Comment command | Effect |`,
|
|
1152
|
+
`| --- | --- | --- |`
|
|
1153
|
+
);
|
|
1154
|
+
for (const decision of action.visibleDecisions) {
|
|
1155
|
+
lines.push(`| ${decisionLabel(decision)} | \`${decision} ${action.index}\` | ${decisionEffect(decision)} |`);
|
|
1026
1156
|
}
|
|
1027
1157
|
}
|
|
1028
|
-
lines.push(
|
|
1029
|
-
"",
|
|
1030
|
-
"Reply with:",
|
|
1031
|
-
"- `approve 1` to record approval without applying yet",
|
|
1032
|
-
"- `apply 1` or `apply all` to apply supported actions",
|
|
1033
|
-
"- `continue 1` to continue with a follow-up run",
|
|
1034
|
-
"- `reject 1` to reject an action"
|
|
1035
|
-
);
|
|
1036
1158
|
return lines;
|
|
1037
1159
|
}
|
|
1038
1160
|
function renderAcknowledgement(runId) {
|
|
@@ -1041,21 +1163,28 @@ function renderAcknowledgement(runId) {
|
|
|
1041
1163
|
function renderProgress(input) {
|
|
1042
1164
|
return `OpenTag progress for \`${input.runId}\`: ${input.message}`;
|
|
1043
1165
|
}
|
|
1044
|
-
function renderFinalResult(result) {
|
|
1045
|
-
|
|
1046
|
-
|
|
1166
|
+
function renderFinalResult(result, options = {}) {
|
|
1167
|
+
return renderFinalSummaryPresentation(
|
|
1168
|
+
createFinalSummaryPresentation({
|
|
1169
|
+
result,
|
|
1170
|
+
...options.receiptContext ? { receiptContext: options.receiptContext } : {},
|
|
1171
|
+
...options.auditRunId ? { auditRunId: options.auditRunId } : {}
|
|
1172
|
+
})
|
|
1173
|
+
);
|
|
1174
|
+
}
|
|
1175
|
+
function renderFinalSummaryPresentation(presentation) {
|
|
1176
|
+
const lines = [`OpenTag finished with **${presentation.outcome}**.`, "", presentation.summary];
|
|
1177
|
+
if (presentation.verification?.length) {
|
|
1047
1178
|
lines.push("", "Verification:");
|
|
1048
|
-
for (const check of
|
|
1179
|
+
for (const check of presentation.verification) {
|
|
1049
1180
|
lines.push(`- \`${check.command}\`: ${check.outcome}`);
|
|
1050
1181
|
}
|
|
1051
1182
|
}
|
|
1052
|
-
const
|
|
1053
|
-
if (nextAction) {
|
|
1054
|
-
lines.push("", `Next action: ${nextAction}`);
|
|
1055
|
-
}
|
|
1056
|
-
const suggestedActions = renderSuggestedActions(result);
|
|
1183
|
+
const suggestedActions = renderSuggestedActions(presentation);
|
|
1057
1184
|
if (suggestedActions.length > 0) {
|
|
1058
1185
|
lines.push("", ...suggestedActions);
|
|
1186
|
+
} else if (presentation.nextActions?.length) {
|
|
1187
|
+
lines.push("", `Next action: ${presentation.nextActions[0]}`);
|
|
1059
1188
|
}
|
|
1060
1189
|
return lines.join("\n");
|
|
1061
1190
|
}
|
|
@@ -1074,6 +1203,7 @@ export {
|
|
|
1074
1203
|
normalizeGitHubPullRequestReviewComment,
|
|
1075
1204
|
renderAcknowledgement,
|
|
1076
1205
|
renderFinalResult,
|
|
1206
|
+
renderFinalSummaryPresentation,
|
|
1077
1207
|
renderProgress,
|
|
1078
1208
|
startGitHubIngress,
|
|
1079
1209
|
verifyGitHubSignature
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/pull-request.ts","../src/apply.ts","../src/ingress.ts","../src/normalize.ts","../src/render.ts"],"sourcesContent":["import type { OpenTagRunResult } from \"@opentag/core\";\n\nexport type CreatePullRequestInput = {\n token: string;\n owner: string;\n repo: string;\n title: string;\n body: string;\n head: string;\n base: string;\n};\n\nexport type FetchLike = typeof fetch;\n\nexport function buildPullRequestBody(result: OpenTagRunResult): string {\n const lines = [\"## Summary\", \"\", result.summary];\n\n if (result.changedFiles?.length) {\n lines.push(\"\", \"## Changed Files\");\n for (const file of result.changedFiles) {\n lines.push(`- \\`${file}\\``);\n }\n }\n\n if (result.verification?.length) {\n lines.push(\"\", \"## Verification\");\n for (const check of result.verification) {\n lines.push(`- \\`${check.command}\\`: ${check.outcome}`);\n }\n }\n\n return lines.join(\"\\n\");\n}\n\nexport async function createPullRequestViaFetch(input: CreatePullRequestInput, fetchImpl: FetchLike = fetch): Promise<string> {\n const response = await fetchImpl(`https://api.github.com/repos/${input.owner}/${input.repo}/pulls`, {\n method: \"POST\",\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n },\n body: JSON.stringify({\n title: input.title,\n body: input.body,\n head: input.head,\n base: input.base\n })\n });\n\n if (!response.ok) {\n throw new Error(`create pull request failed: ${response.status} ${await response.text()}`);\n }\n\n const body = (await response.json()) as { html_url?: string };\n if (!body.html_url) {\n throw new Error(\"create pull request response did not include html_url\");\n }\n return body.html_url;\n}\n","import type { AdapterMutationCompiler, AdapterMutationMapping, ApplyIntentOutcome, MutationIntent } from \"@opentag/core\";\nimport { createPullRequestViaFetch, type FetchLike } from \"./pull-request.js\";\n\nexport type GitHubIssueMutationTarget = {\n token: string;\n owner: string;\n repo: string;\n issueNumber?: number;\n pullRequestNumber?: number;\n};\n\nexport type GitHubIssueMutationOperation =\n | {\n kind: \"add_label\";\n intentId: string;\n label: string;\n }\n | {\n kind: \"remove_label\";\n intentId: string;\n label: string;\n }\n | {\n kind: \"replace_mapped_label\";\n intentId: string;\n label: string;\n removeLabels: string[];\n }\n | {\n kind: \"set_labels\";\n intentId: string;\n labels: string[];\n }\n | {\n kind: \"set_assignees\";\n intentId: string;\n assignees: string[];\n }\n | {\n kind: \"add_assignee\";\n intentId: string;\n assignee: string;\n }\n | {\n kind: \"remove_assignee\";\n intentId: string;\n assignee: string;\n }\n | {\n kind: \"request_review\";\n intentId: string;\n reviewers: string[];\n teamReviewers?: string[];\n }\n | {\n kind: \"create_pull_request\";\n intentId: string;\n title: string;\n body: string;\n head: string;\n base: string;\n };\n\nexport type GitHubIssueMutationCompilation =\n | {\n ok: true;\n intentId: string;\n operation: GitHubIssueMutationOperation;\n }\n | {\n ok: false;\n outcome: ApplyIntentOutcome;\n };\n\nfunction labelFromIntent(intent: MutationIntent): string | undefined {\n const value = intent.params?.[\"label\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction labelsFromIntent(intent: MutationIntent): string[] | undefined {\n const value = intent.params?.[\"labels\"];\n if (!Array.isArray(value)) return undefined;\n const labels = value.filter((label): label is string => typeof label === \"string\" && label.length > 0);\n return labels.length > 0 ? labels : undefined;\n}\n\nfunction assigneeFromIntent(intent: MutationIntent): string | undefined {\n const value = intent.params?.[\"assignee\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction assigneesFromIntent(intent: MutationIntent): string[] | undefined {\n const value = intent.params?.[\"assignees\"];\n if (!Array.isArray(value)) return undefined;\n const assignees = value.filter((assignee): assignee is string => typeof assignee === \"string\" && assignee.length > 0);\n return assignees.length > 0 ? assignees : undefined;\n}\n\nfunction reviewersFromIntent(intent: MutationIntent): string[] | undefined {\n const reviewer = intent.params?.[\"reviewer\"];\n const reviewers = intent.params?.[\"reviewers\"];\n const values = [\n ...(typeof reviewer === \"string\" ? [reviewer] : []),\n ...(Array.isArray(reviewers) ? reviewers : [])\n ].filter((value): value is string => typeof value === \"string\" && value.length > 0);\n return values.length > 0 ? [...new Set(values)] : undefined;\n}\n\nfunction teamReviewersFromIntent(intent: MutationIntent): string[] | undefined {\n const reviewer = intent.params?.[\"teamReviewer\"];\n const reviewers = intent.params?.[\"teamReviewers\"] ?? intent.params?.[\"team_reviewers\"];\n const values = [\n ...(typeof reviewer === \"string\" ? [reviewer] : []),\n ...(Array.isArray(reviewers) ? reviewers : [])\n ].filter((value): value is string => typeof value === \"string\" && value.length > 0);\n return values.length > 0 ? [...new Set(values)] : undefined;\n}\n\nfunction stringParam(intent: MutationIntent, ...keys: string[]): string | undefined {\n for (const key of keys) {\n const value = intent.params?.[key];\n if (typeof value === \"string\" && value.length > 0) return value;\n }\n return undefined;\n}\n\nfunction stringArrayParam(intent: MutationIntent, key: string): string[] {\n const value = intent.params?.[key];\n if (!Array.isArray(value)) return [];\n return value.filter((item): item is string => typeof item === \"string\" && item.length > 0);\n}\n\nfunction verificationLinesFromIntent(intent: MutationIntent): string[] {\n const value = intent.params?.[\"verification\"];\n if (!Array.isArray(value)) return [];\n return value\n .map((item) => {\n if (!item || typeof item !== \"object\" || Array.isArray(item)) return undefined;\n const command = (item as Record<string, unknown>)[\"command\"];\n const outcome = (item as Record<string, unknown>)[\"outcome\"];\n return typeof command === \"string\" && typeof outcome === \"string\" ? `- \\`${command}\\`: ${outcome}` : undefined;\n })\n .filter((line): line is string => Boolean(line));\n}\n\nfunction pullRequestBodyFromIntent(intent: MutationIntent): string {\n const explicitBody = stringParam(intent, \"body\");\n const changedFiles = stringArrayParam(intent, \"changedFiles\");\n const risks = stringArrayParam(intent, \"risks\");\n const verification = verificationLinesFromIntent(intent);\n const executorConditions = stringArrayParam(intent, \"executorConditions\");\n const lines = explicitBody ? [explicitBody] : [\"## Summary\", \"\", intent.summary];\n if (changedFiles.length > 0) {\n lines.push(\"\", \"## Changed Files\", ...changedFiles.map((file) => `- \\`${file}\\``));\n }\n if (risks.length > 0) {\n lines.push(\"\", \"## Risks\", ...risks.map((risk) => `- ${risk}`));\n }\n if (verification.length > 0) {\n lines.push(\"\", \"## Verification\", ...verification);\n }\n if (executorConditions.length > 0) {\n lines.push(\"\", \"## Executor Conditions\", ...executorConditions.map((condition) => `- ${condition}`));\n }\n return lines.join(\"\\n\");\n}\n\nfunction mappedValueFromIntent(intent: MutationIntent): string | undefined {\n const key = intent.domain === \"status\" ? \"status\" : \"priority\";\n const value = intent.params?.[key] ?? intent.params?.[\"value\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction labelMappingForIntent(input: { intent: MutationIntent; mappings: AdapterMutationMapping[] }): { label: string; removeLabels: string[] } | undefined {\n const semanticValue = mappedValueFromIntent(input.intent);\n if (!semanticValue) return undefined;\n const mapping = input.mappings.find(\n (candidate) => candidate.adapter === \"github\" && candidate.domain === input.intent.domain && candidate.strategy === \"label\"\n );\n const label = mapping?.values[semanticValue];\n if (!label || !mapping) return undefined;\n return {\n label,\n removeLabels: Object.values(mapping.values).filter((mappedLabel) => mappedLabel !== label)\n };\n}\n\nasync function githubJson(input: {\n target: GitHubIssueMutationTarget;\n fetchImpl: FetchLike;\n method: \"GET\" | \"POST\" | \"PUT\" | \"PATCH\" | \"DELETE\";\n path: string;\n body?: unknown;\n okStatuses?: number[];\n}): Promise<string | undefined> {\n const response = await input.fetchImpl(`https://api.github.com/repos/${input.target.owner}/${input.target.repo}${input.path}`, {\n method: input.method,\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.target.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n },\n ...(input.body ? { body: JSON.stringify(input.body) } : {})\n });\n\n if (!response.ok && !(input.okStatuses ?? []).includes(response.status)) {\n throw new Error(`${input.method} ${input.path} failed: ${response.status} ${await response.text()}`);\n }\n return `https://github.com/${input.target.owner}/${input.target.repo}/issues/${input.target.issueNumber}`;\n}\n\nasync function githubJsonBody<T>(input: {\n target: GitHubIssueMutationTarget;\n fetchImpl: FetchLike;\n method: \"GET\";\n path: string;\n okStatuses?: number[];\n}): Promise<T> {\n const response = await input.fetchImpl(`https://api.github.com/repos/${input.target.owner}/${input.target.repo}${input.path}`, {\n method: input.method,\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.target.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n }\n });\n\n if (!response.ok && !(input.okStatuses ?? []).includes(response.status)) {\n throw new Error(`${input.method} ${input.path} failed: ${response.status} ${await response.text()}`);\n }\n return await response.json() as T;\n}\n\ntype RequestedReviewersResponse = {\n users?: Array<{ login?: unknown }>;\n teams?: Array<{ slug?: unknown; name?: unknown }>;\n};\n\nfunction requestedReviewerLogins(response: RequestedReviewersResponse): Set<string> {\n return new Set((response.users ?? []).map((user) => user.login).filter((login): login is string => typeof login === \"string\"));\n}\n\nfunction requestedTeamReviewerNames(response: RequestedReviewersResponse): Set<string> {\n return new Set(\n (response.teams ?? [])\n .flatMap((team) => [team.slug, team.name])\n .filter((value): value is string => typeof value === \"string\" && value.length > 0)\n );\n}\n\nexport function compileGitHubIssueMutationIntent(\n intent: MutationIntent,\n options: { mappings?: AdapterMutationMapping[]; targetKind?: \"issue\" | \"pull_request\" } = {}\n): GitHubIssueMutationCompilation {\n if (intent.action === \"create_pull_request\") {\n const head = stringParam(intent, \"head\", \"branch\");\n if (!head) {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"failed\",\n message: \"create_pull_request requires params.head or params.branch.\"\n }\n };\n }\n return {\n ok: true,\n intentId: intent.intentId,\n operation: {\n kind: \"create_pull_request\",\n intentId: intent.intentId,\n title: stringParam(intent, \"title\") ?? intent.summary,\n body: pullRequestBodyFromIntent(intent),\n head,\n base: stringParam(intent, \"base\", \"baseBranch\") ?? \"main\"\n }\n };\n }\n\n if (intent.action === \"request_review\" || intent.domain === \"review\") {\n if (options.targetKind !== \"pull_request\") {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub review requests require a pull request target.\"\n }\n };\n }\n const reviewers = reviewersFromIntent(intent);\n const teamReviewers = teamReviewersFromIntent(intent);\n if (!reviewers?.length && !teamReviewers?.length) {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"failed\",\n message: \"request_review requires params.reviewer, params.reviewers, or params.teamReviewers.\"\n }\n };\n }\n return {\n ok: true,\n intentId: intent.intentId,\n operation: {\n kind: \"request_review\",\n intentId: intent.intentId,\n reviewers: reviewers ?? [],\n ...(teamReviewers?.length ? { teamReviewers } : {})\n }\n };\n }\n\n if (intent.domain === \"status\") {\n const mapped = labelMappingForIntent({ intent, mappings: options.mappings ?? [] });\n if (mapped) {\n return { ok: true, intentId: intent.intentId, operation: { kind: \"replace_mapped_label\", intentId: intent.intentId, ...mapped } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub status writes require an explicit Project field or label mapping policy.\"\n }\n };\n }\n if (intent.domain === \"priority\") {\n const mapped = labelMappingForIntent({ intent, mappings: options.mappings ?? [] });\n if (mapped) {\n return { ok: true, intentId: intent.intentId, operation: { kind: \"replace_mapped_label\", intentId: intent.intentId, ...mapped } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub priority writes require an explicit label or Project field mapping policy.\"\n }\n };\n }\n if (intent.domain !== \"labels\" && intent.domain !== \"assignee\") {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply supports labels and assignee only, not ${intent.domain}.`\n }\n };\n }\n\n if (intent.domain === \"assignee\") {\n if (intent.action === \"set_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_assignees\", intentId: intent.intentId, assignees: [assignee] } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_assignee requires params.assignee.\" } };\n }\n if (intent.action === \"set_assignees\") {\n const assignees = assigneesFromIntent(intent);\n return assignees\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_assignees\", intentId: intent.intentId, assignees } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_assignees requires params.assignees.\" } };\n }\n if (intent.action === \"add_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"add_assignee\", intentId: intent.intentId, assignee } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"add_assignee requires params.assignee.\" } };\n }\n if (intent.action === \"remove_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"remove_assignee\", intentId: intent.intentId, assignee } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"remove_assignee requires params.assignee.\" } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply does not support assignee action ${intent.action}.`\n }\n };\n }\n\n if (intent.action === \"add_label\") {\n const label = labelFromIntent(intent);\n return label\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"add_label\", intentId: intent.intentId, label } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"add_label requires params.label.\" } };\n }\n if (intent.action === \"remove_label\") {\n const label = labelFromIntent(intent);\n return label\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"remove_label\", intentId: intent.intentId, label } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"remove_label requires params.label.\" } };\n }\n if (intent.action === \"set_labels\") {\n const labels = labelsFromIntent(intent);\n return labels\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_labels\", intentId: intent.intentId, labels } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_labels requires params.labels.\" } };\n }\n\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply does not support labels action ${intent.action}.`\n }\n };\n}\n\nexport function compileGitHubIssueMutationIntents(\n intents: MutationIntent[],\n options: { mappings?: AdapterMutationMapping[]; targetKind?: \"issue\" | \"pull_request\" } = {}\n): GitHubIssueMutationCompilation[] {\n return intents.map((intent) => compileGitHubIssueMutationIntent(intent, options));\n}\n\nexport function createGitHubIssueMutationCompiler(options: {\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n} = {}): AdapterMutationCompiler<GitHubIssueMutationOperation> {\n return {\n adapter: \"github\",\n compile(intent) {\n const compilation = compileGitHubIssueMutationIntent(intent, options);\n if (!compilation.ok) {\n return {\n ok: false,\n adapter: \"github\",\n outcome: compilation.outcome\n };\n }\n return {\n ok: true,\n adapter: \"github\",\n intentId: compilation.intentId,\n operation: compilation.operation\n };\n }\n };\n}\n\nexport async function applyGitHubIssueMutationOperation(input: {\n target: GitHubIssueMutationTarget;\n operation: GitHubIssueMutationOperation;\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome> {\n const fetchImpl = input.fetchImpl ?? fetch;\n try {\n if (input.operation.kind === \"create_pull_request\") {\n const externalUri = await createPullRequestViaFetch(\n {\n token: input.target.token,\n owner: input.target.owner,\n repo: input.target.repo,\n title: input.operation.title,\n body: input.operation.body,\n head: input.operation.head,\n base: input.operation.base\n },\n fetchImpl\n );\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"request_review\") {\n const pullRequestNumber = input.target.pullRequestNumber;\n if (typeof pullRequestNumber !== \"number\") {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n message: \"request_review requires target.pullRequestNumber.\"\n };\n }\n const requested = await githubJsonBody<RequestedReviewersResponse>({\n target: input.target,\n fetchImpl,\n method: \"GET\",\n path: `/pulls/${pullRequestNumber}/requested_reviewers`\n });\n const existingReviewers = requestedReviewerLogins(requested);\n const existingTeamReviewers = requestedTeamReviewerNames(requested);\n const reviewers = input.operation.reviewers.filter((reviewer) => !existingReviewers.has(reviewer));\n const teamReviewers = input.operation.teamReviewers?.filter((reviewer) => !existingTeamReviewers.has(reviewer));\n if (reviewers.length === 0 && (!teamReviewers || teamReviewers.length === 0)) {\n return {\n intentId: input.operation.intentId,\n outcome: \"applied\",\n externalUri: `https://github.com/${input.target.owner}/${input.target.repo}/pull/${pullRequestNumber}`,\n message: \"Requested reviewers were already present; skipped GitHub notification retry.\"\n };\n }\n await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/pulls/${pullRequestNumber}/requested_reviewers`,\n body: {\n ...(reviewers.length ? { reviewers } : {}),\n ...(teamReviewers?.length ? { team_reviewers: teamReviewers } : {})\n }\n });\n return {\n intentId: input.operation.intentId,\n outcome: \"applied\",\n externalUri: `https://github.com/${input.target.owner}/${input.target.repo}/pull/${pullRequestNumber}`\n };\n }\n\n const issueNumber = input.target.issueNumber;\n if (typeof issueNumber !== \"number\") {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n message: \"GitHub issue mutation requires target.issueNumber.\"\n };\n }\n\n if (input.operation.kind === \"set_assignees\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"PATCH\",\n path: `/issues/${issueNumber}`,\n body: { assignees: input.operation.assignees }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"add_assignee\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/assignees`,\n body: { assignees: [input.operation.assignee] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"remove_assignee\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/assignees`,\n body: { assignees: [input.operation.assignee] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"replace_mapped_label\") {\n for (const label of input.operation.removeLabels) {\n await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/labels/${encodeURIComponent(label)}`,\n okStatuses: [200, 404]\n });\n }\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: [input.operation.label] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"add_label\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: [input.operation.label] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"remove_label\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/labels/${encodeURIComponent(input.operation.label)}`\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"PUT\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: input.operation.labels }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n } catch (error) {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n error: error instanceof Error ? error.message : String(error)\n };\n }\n}\n\nexport async function applyGitHubIssueMutationIntent(input: {\n target: GitHubIssueMutationTarget;\n intent: MutationIntent;\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome> {\n const compiled = compileGitHubIssueMutationIntent(input.intent, {\n ...(input.mappings ? { mappings: input.mappings } : {}),\n ...(input.targetKind ? { targetKind: input.targetKind } : {})\n });\n if (!compiled.ok) return compiled.outcome;\n return applyGitHubIssueMutationOperation({\n target: input.target,\n operation: compiled.operation,\n ...(input.fetchImpl ? { fetchImpl: input.fetchImpl } : {})\n });\n}\n\nexport async function applyGitHubIssueMutationIntents(input: {\n target: GitHubIssueMutationTarget;\n intents: MutationIntent[];\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome[]> {\n const outcomes: ApplyIntentOutcome[] = [];\n for (const intent of input.intents) {\n outcomes.push(\n await applyGitHubIssueMutationIntent({\n target: input.target,\n intent,\n ...(input.mappings ? { mappings: input.mappings } : {}),\n ...(input.targetKind ? { targetKind: input.targetKind } : {}),\n ...(input.fetchImpl ? { fetchImpl: input.fetchImpl } : {})\n })\n );\n }\n return outcomes;\n}\n","import { createHmac, randomUUID, timingSafeEqual } from \"node:crypto\";\nimport { serve } from \"@hono/node-server\";\nimport { createOpenTagClient } from \"@opentag/client\";\nimport { parseThreadActionCommand, type OpenTagEvent } from \"@opentag/core\";\nimport { Hono } from \"hono\";\nimport { normalizeGitHubIssueComment, normalizeGitHubPullRequestReviewComment } from \"./normalize.js\";\n\ntype GitHubActor = {\n id: number;\n login: string;\n};\n\ntype GitHubRepository = {\n name: string;\n private: boolean;\n owner: { login: string };\n};\n\nexport type GitHubIssueCommentPayload = {\n action?: string;\n comment: { id: number; body: string; html_url: string };\n issue: { html_url: string; comments_url: string; number: number };\n repository: GitHubRepository;\n sender: GitHubActor;\n installation?: { id: number };\n};\n\nexport type GitHubPullRequestReviewCommentPayload = {\n action?: string;\n comment: { id: number; body: string; html_url: string };\n pull_request: { html_url: string; number: number };\n repository: GitHubRepository;\n sender: GitHubActor;\n installation?: { id: number };\n};\n\nexport type GitHubThreadActionInput = {\n id: string;\n rawText: string;\n actor: {\n provider: \"github\";\n providerUserId: string;\n handle: string;\n };\n callback: {\n provider: \"github\";\n uri: string;\n threadKey: string;\n };\n metadata: Record<string, unknown>;\n};\n\nexport type GitHubWebhookAppInput = {\n webhookSecret: string;\n webhookPath?: string;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n now(): string;\n};\n\nexport type GitHubIngressConfig = {\n webhookSecret: string;\n dispatcherUrl: string;\n dispatcherToken?: string;\n port?: number;\n hostname?: string;\n webhookPath?: string;\n};\n\nexport type GitHubIngressHandle = {\n url: string;\n webhookPath: string;\n server: ReturnType<typeof serve>;\n close(): Promise<void>;\n};\n\nexport function computeGitHubSignature(input: { webhookSecret: string; rawBody: string }): string {\n const digest = createHmac(\"sha256\", input.webhookSecret).update(input.rawBody).digest(\"hex\");\n return `sha256=${digest}`;\n}\n\nexport function verifyGitHubSignature(input: {\n webhookSecret: string;\n rawBody: string;\n signature: string;\n}): boolean {\n const expected = computeGitHubSignature(input);\n const expectedBuffer = Buffer.from(expected);\n const actualBuffer = Buffer.from(input.signature);\n return expectedBuffer.length === actualBuffer.length && timingSafeEqual(expectedBuffer, actualBuffer);\n}\n\nfunction parseJsonPayload(rawBody: string): unknown {\n try {\n return JSON.parse(rawBody);\n } catch {\n return null;\n }\n}\n\nasync function handleIssueCommentCreated(input: {\n payload: GitHubIssueCommentPayload;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n now(): string;\n}): Promise<void> {\n if (input.payload.action && input.payload.action !== \"created\") return;\n if (parseThreadActionCommand(input.payload.comment.body) && input.submitThreadAction) {\n await input.submitThreadAction({\n id: `approval_github_comment_${input.payload.comment.id}`,\n rawText: input.payload.comment.body,\n actor: {\n provider: \"github\",\n providerUserId: String(input.payload.sender.id),\n handle: input.payload.sender.login\n },\n callback: {\n provider: \"github\",\n uri: input.payload.issue.comments_url,\n threadKey: `${input.payload.repository.owner.login}/${input.payload.repository.name}#${input.payload.issue.number}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.payload.repository.owner.login,\n repo: input.payload.repository.name,\n issueNumber: input.payload.issue.number,\n commentUrl: input.payload.comment.html_url\n }\n });\n return;\n }\n\n const event = normalizeGitHubIssueComment({\n id: String(input.payload.comment.id),\n commentBody: input.payload.comment.body,\n commentUrl: input.payload.comment.html_url,\n apiCommentsUrl: input.payload.issue.comments_url,\n issueUrl: input.payload.issue.html_url,\n issueNumber: input.payload.issue.number,\n owner: input.payload.repository.owner.login,\n repo: input.payload.repository.name,\n actorId: input.payload.sender.id,\n actorLogin: input.payload.sender.login,\n private: input.payload.repository.private,\n receivedAt: input.now(),\n ...(input.payload.installation ? { installationId: input.payload.installation.id } : {})\n });\n\n if (event) {\n await input.createRun(event);\n }\n}\n\nasync function handlePullRequestReviewCommentCreated(input: {\n payload: GitHubPullRequestReviewCommentPayload;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n now(): string;\n}): Promise<void> {\n if (input.payload.action && input.payload.action !== \"created\") return;\n const owner = input.payload.repository.owner.login;\n const repo = input.payload.repository.name;\n if (parseThreadActionCommand(input.payload.comment.body) && input.submitThreadAction) {\n await input.submitThreadAction({\n id: `approval_github_pr_review_comment_${input.payload.comment.id}`,\n rawText: input.payload.comment.body,\n actor: {\n provider: \"github\",\n providerUserId: String(input.payload.sender.id),\n handle: input.payload.sender.login\n },\n callback: {\n provider: \"github\",\n uri: `https://api.github.com/repos/${owner}/${repo}/issues/${input.payload.pull_request.number}/comments`,\n threadKey: `${owner}/${repo}#${input.payload.pull_request.number}`\n },\n metadata: {\n repoProvider: \"github\",\n owner,\n repo,\n pullRequestNumber: input.payload.pull_request.number,\n commentUrl: input.payload.comment.html_url\n }\n });\n return;\n }\n\n const event = normalizeGitHubPullRequestReviewComment({\n id: String(input.payload.comment.id),\n commentBody: input.payload.comment.body,\n commentUrl: input.payload.comment.html_url,\n pullRequestUrl: input.payload.pull_request.html_url,\n apiCommentsUrl: `https://api.github.com/repos/${owner}/${repo}/issues/${input.payload.pull_request.number}/comments`,\n owner,\n repo,\n pullRequestNumber: input.payload.pull_request.number,\n actorId: input.payload.sender.id,\n actorLogin: input.payload.sender.login,\n private: input.payload.repository.private,\n receivedAt: input.now(),\n ...(input.payload.installation ? { installationId: input.payload.installation.id } : {})\n });\n\n if (event) {\n await input.createRun(event);\n }\n}\n\nexport function createGitHubWebhookApp(input: GitHubWebhookAppInput) {\n const app = new Hono();\n const webhookPath = input.webhookPath ?? \"/github/webhooks\";\n if (!webhookPath.startsWith(\"/\")) {\n throw new Error(\"GitHub webhook path must start with /.\");\n }\n\n app.post(webhookPath, async (c) => {\n const signature = c.req.header(\"x-hub-signature-256\");\n if (!signature) {\n return c.json({ error: \"missing_signature_header\" }, 401);\n }\n const rawBody = await c.req.text();\n if (!verifyGitHubSignature({ webhookSecret: input.webhookSecret, rawBody, signature })) {\n return c.json({ error: \"invalid_signature\" }, 401);\n }\n\n const eventName = c.req.header(\"x-github-event\");\n const payload = parseJsonPayload(rawBody);\n if (!payload || typeof payload !== \"object\") {\n return c.json({ error: \"invalid_json\" }, 400);\n }\n\n if (eventName === \"ping\") {\n return c.json({ ok: true });\n }\n if (eventName === \"issue_comment\") {\n await handleIssueCommentCreated({\n payload: payload as GitHubIssueCommentPayload,\n createRun: input.createRun,\n ...(input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {}),\n now: input.now\n });\n return c.json({ ok: true });\n }\n if (eventName === \"pull_request_review_comment\") {\n await handlePullRequestReviewCommentCreated({\n payload: payload as GitHubPullRequestReviewCommentPayload,\n createRun: input.createRun,\n ...(input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {}),\n now: input.now\n });\n return c.json({ ok: true });\n }\n\n return c.json({ ok: true, ignored: \"unsupported_event\" });\n });\n\n return app;\n}\n\nexport function startGitHubIngress(config: GitHubIngressConfig): GitHubIngressHandle {\n const dispatcherClient = createOpenTagClient({\n dispatcherUrl: config.dispatcherUrl,\n ...(config.dispatcherToken ? { pairingToken: config.dispatcherToken } : {})\n });\n const port = config.port ?? 3000;\n const hostname = config.hostname ?? \"127.0.0.1\";\n const webhookPath = config.webhookPath ?? \"/github/webhooks\";\n const server = serve({\n fetch: createGitHubWebhookApp({\n webhookSecret: config.webhookSecret,\n webhookPath,\n async createRun(event) {\n const runId = `run_${randomUUID()}`;\n const created = await dispatcherClient.createRun({ runId, event });\n return created.outcome === \"run_created\" ? { runId: created.run.id } : {};\n },\n async submitThreadAction(action) {\n await dispatcherClient.submitThreadAction(action);\n },\n now: () => new Date().toISOString()\n }).fetch,\n port,\n hostname\n });\n\n return {\n url: `http://${hostname}:${port}`,\n webhookPath,\n server,\n close() {\n return new Promise((resolve, reject) => {\n server.close((error?: Error) => {\n if (error) {\n reject(error);\n return;\n }\n resolve();\n });\n });\n }\n };\n}\n","import { parseOpenTagMention, type OpenTagEvent } from \"@opentag/core\";\nimport type { ContextPointer, OpenTagCommand, PermissionGrant, WorkItemReference } from \"@opentag/core\";\n\nexport type GitHubIssueCommentInput = {\n id: string;\n commentBody: string;\n commentUrl: string;\n apiCommentsUrl: string;\n issueUrl: string;\n issueNumber: number;\n owner: string;\n repo: string;\n actorId: number;\n actorLogin: string;\n private: boolean;\n receivedAt: string;\n installationId?: number;\n};\n\nexport type GitHubPullRequestReviewCommentInput = {\n id: string;\n commentBody: string;\n commentUrl: string;\n pullRequestUrl: string;\n apiCommentsUrl: string;\n owner: string;\n repo: string;\n pullRequestNumber: number;\n actorId: number;\n actorLogin: string;\n private: boolean;\n receivedAt: string;\n installationId?: number;\n};\n\nfunction permissionsForIntent(intent: OpenTagCommand[\"intent\"]): PermissionGrant[] {\n const permissions: PermissionGrant[] = [\n {\n scope: \"issue:comment\",\n reason: \"reply to the source GitHub thread\"\n },\n {\n scope: \"runner:local\",\n reason: \"execute the run on a paired local daemon\"\n }\n ];\n if (intent === \"fix\" || intent === \"run\") {\n permissions.push(\n {\n scope: \"repo:read\",\n reason: \"inspect the repository in the paired local checkout\"\n },\n {\n scope: \"repo:write\",\n reason: \"commit code changes on an isolated run branch\"\n },\n {\n scope: \"pr:create\",\n reason: \"open a pull request for completed code changes\"\n }\n );\n }\n return permissions;\n}\n\nfunction permissionsForPullRequestReviewCommentIntent(intent: OpenTagCommand[\"intent\"]): PermissionGrant[] {\n const permissions = permissionsForIntent(intent);\n if (intent === \"review\") {\n permissions.push({\n scope: \"pr:update\",\n reason: \"request reviewers on the source pull request after explicit approval\"\n });\n }\n return permissions;\n}\n\nfunction contextPointersForCommand(command: OpenTagCommand, privateRepo: boolean): ContextPointer[] {\n const visibility = privateRepo ? \"private\" : \"public\";\n const context: ContextPointer[] = [];\n\n for (const reference of command.parsed?.references ?? []) {\n if (reference.kind === \"url\") {\n context.push({\n kind: \"url\",\n uri: reference.uri,\n visibility,\n title: reference.title ?? \"Command URL reference\"\n });\n continue;\n }\n\n if (reference.kind === \"file\" || reference.kind === \"path\" || reference.kind === \"line\" || reference.kind === \"range\") {\n context.push({\n kind: \"file\",\n uri: reference.uri,\n ...(reference.line ? { line: reference.line } : {}),\n ...(reference.startLine ? { startLine: reference.startLine } : {}),\n ...(reference.endLine ? { endLine: reference.endLine } : {}),\n visibility,\n title: referenceTitle(reference)\n });\n }\n }\n\n return context;\n}\n\nfunction referenceTitle(reference: NonNullable<OpenTagCommand[\"parsed\"]>[\"references\"][number]): string {\n return reference.title ?? \"Command file reference\";\n}\n\nfunction githubWorkItem(input: {\n owner: string;\n repo: string;\n kind: \"issue\" | \"pull_request\";\n number: number;\n uri: string;\n}): WorkItemReference {\n return {\n provider: \"github\",\n kind: input.kind,\n externalId: `${input.owner}/${input.repo}#${input.number}`,\n uri: input.uri,\n ownerContainer: {\n provider: \"github\",\n id: `${input.owner}/${input.repo}`,\n uri: `https://github.com/${input.owner}/${input.repo}`\n }\n };\n}\n\nfunction commandMetadata(command: OpenTagCommand): Record<string, unknown> {\n if (!command.parsed) return {};\n return {\n commandParser: command.parsed.version,\n commandDiagnostics: command.parsed.diagnostics,\n ...(command.parsed.approval ? { approval: command.parsed.approval } : {}),\n ...(command.parsed.network ? { network: command.parsed.network } : {})\n };\n}\n\nexport function normalizeGitHubIssueComment(input: GitHubIssueCommentInput): OpenTagEvent | null {\n const mention = parseOpenTagMention(input.commentBody);\n if (!mention.matched) return null;\n\n const command = {\n rawText: mention.rawText,\n intent: mention.intent,\n args: mention.args,\n ...(mention.parsed ? { parsed: mention.parsed } : {})\n };\n\n return {\n id: `evt_github_comment_${input.id}`,\n source: \"github\",\n sourceEventId: input.id,\n receivedAt: input.receivedAt,\n actor: {\n provider: \"github\",\n providerUserId: String(input.actorId),\n handle: input.actorLogin\n },\n target: {\n mention: \"@opentag\",\n agentId: \"opentag\",\n ...(mention.parsed?.executorHint ? { executorHint: mention.parsed.executorHint } : {})\n },\n command,\n context: [\n {\n provider: \"github\",\n kind: \"issue\",\n uri: input.issueUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n {\n provider: \"github\",\n kind: \"comment\",\n uri: input.commentUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n ...contextPointersForCommand(command, input.private)\n ],\n workItem: githubWorkItem({\n owner: input.owner,\n repo: input.repo,\n kind: \"issue\",\n number: input.issueNumber,\n uri: input.issueUrl\n }),\n permissions: permissionsForIntent(mention.intent),\n callback: {\n provider: \"github\",\n uri: input.apiCommentsUrl,\n threadKey: `${input.owner}/${input.repo}#${input.issueNumber}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.owner,\n repo: input.repo,\n issueNumber: input.issueNumber,\n ...commandMetadata(command),\n ...(typeof input.installationId === \"number\" ? { installationId: input.installationId } : {})\n }\n };\n}\n\nexport function normalizeGitHubPullRequestReviewComment(input: GitHubPullRequestReviewCommentInput): OpenTagEvent | null {\n const mention = parseOpenTagMention(input.commentBody);\n if (!mention.matched) return null;\n\n const command = {\n rawText: mention.rawText,\n intent: mention.intent,\n args: mention.args,\n ...(mention.parsed ? { parsed: mention.parsed } : {})\n };\n\n return {\n id: `evt_github_pr_review_comment_${input.id}`,\n source: \"github\",\n sourceEventId: input.id,\n receivedAt: input.receivedAt,\n actor: {\n provider: \"github\",\n providerUserId: String(input.actorId),\n handle: input.actorLogin\n },\n target: {\n mention: \"@opentag\",\n agentId: \"opentag\",\n ...(mention.parsed?.executorHint ? { executorHint: mention.parsed.executorHint } : {})\n },\n command,\n context: [\n {\n provider: \"github\",\n kind: \"pull_request\",\n uri: input.pullRequestUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n {\n provider: \"github\",\n kind: \"comment\",\n uri: input.commentUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n ...contextPointersForCommand(command, input.private)\n ],\n workItem: githubWorkItem({\n owner: input.owner,\n repo: input.repo,\n kind: \"pull_request\",\n number: input.pullRequestNumber,\n uri: input.pullRequestUrl\n }),\n permissions: permissionsForPullRequestReviewCommentIntent(mention.intent),\n callback: {\n provider: \"github\",\n uri: input.apiCommentsUrl,\n threadKey: `${input.owner}/${input.repo}#${input.pullRequestNumber}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.owner,\n repo: input.repo,\n pullRequestNumber: input.pullRequestNumber,\n ...commandMetadata(command),\n ...(typeof input.installationId === \"number\" ? { installationId: input.installationId } : {})\n }\n };\n}\n","import { suggestedActionCandidatesFromResult, type OpenTagRunResult } from \"@opentag/core\";\n\nfunction nextActionSummary(result: OpenTagRunResult): string | undefined {\n if (!result.nextAction) return undefined;\n if (typeof result.nextAction === \"string\") return result.nextAction;\n return result.nextAction.summary;\n}\n\nfunction stringParam(params: Record<string, unknown> | undefined, key: string): string | undefined {\n const value = params?.[key];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction stringArrayParam(params: Record<string, unknown> | undefined, key: string): string[] {\n const value = params?.[key];\n if (!Array.isArray(value)) return [];\n return value.filter((item): item is string => typeof item === \"string\" && item.length > 0);\n}\n\nfunction renderVerificationParams(params: Record<string, unknown> | undefined): string[] {\n const value = params?.[\"verification\"];\n if (!Array.isArray(value)) return [];\n return value\n .map((item) => {\n if (!item || typeof item !== \"object\" || Array.isArray(item)) return undefined;\n const command = (item as Record<string, unknown>)[\"command\"];\n const outcome = (item as Record<string, unknown>)[\"outcome\"];\n return typeof command === \"string\" && typeof outcome === \"string\" ? ` - \\`${command}\\`: ${outcome}` : undefined;\n })\n .filter((line): line is string => Boolean(line));\n}\n\nfunction renderSuggestedActionDetails(params: Record<string, unknown> | undefined, action: string): string[] {\n if (action !== \"create_pull_request\") return [];\n const lines: string[] = [];\n const title = stringParam(params, \"title\");\n const head = stringParam(params, \"head\") ?? stringParam(params, \"branch\");\n const base = stringParam(params, \"base\") ?? stringParam(params, \"baseBranch\");\n const changedFiles = stringArrayParam(params, \"changedFiles\");\n const risks = stringArrayParam(params, \"risks\");\n const verification = renderVerificationParams(params);\n if (title) lines.push(` Title: ${title}`);\n if (head || base) lines.push(` Branch: \\`${head ?? \"unknown\"}\\` -> \\`${base ?? \"main\"}\\``);\n if (changedFiles.length > 0) lines.push(` Changed files: ${changedFiles.map((file) => `\\`${file}\\``).join(\", \")}`);\n if (risks.length > 0) {\n lines.push(\" Risks:\");\n for (const risk of risks) {\n lines.push(` - ${risk}`);\n }\n }\n if (verification.length > 0) {\n lines.push(\" Verification:\");\n lines.push(...verification);\n }\n return lines;\n}\n\nfunction renderSuggestedActions(result: OpenTagRunResult): string[] {\n const candidates = suggestedActionCandidatesFromResult(result);\n if (candidates.length === 0) return [];\n\n const lines = [\"Suggested actions:\"];\n for (const candidate of candidates) {\n lines.push(\n \"\",\n `${candidate.index}. **${candidate.intent.summary}**`,\n ` Intent: \\`${candidate.intent.action}\\` (\\`${candidate.intent.domain}\\`)`,\n ` Proposal: \\`${candidate.proposalId}\\``,\n ` Intent ID: \\`${candidate.intent.intentId}\\``\n );\n lines.push(...renderSuggestedActionDetails(candidate.intent.params, candidate.intent.action));\n if (candidate.proposalPreconditions?.length) {\n lines.push(\" Preconditions:\");\n for (const precondition of candidate.proposalPreconditions) {\n lines.push(` - ${precondition}`);\n }\n }\n }\n\n lines.push(\n \"\",\n \"Reply with:\",\n \"- `approve 1` to record approval without applying yet\",\n \"- `apply 1` or `apply all` to apply supported actions\",\n \"- `continue 1` to continue with a follow-up run\",\n \"- `reject 1` to reject an action\"\n );\n return lines;\n}\n\nexport function renderAcknowledgement(runId: string): string {\n return `OpenTag picked this up. Run: \\`${runId}\\``;\n}\n\nexport function renderProgress(input: { runId: string; message: string }): string {\n return `OpenTag progress for \\`${input.runId}\\`: ${input.message}`;\n}\n\nexport function renderFinalResult(result: OpenTagRunResult): string {\n const lines = [`OpenTag finished with **${result.conclusion}**.`, \"\", result.summary];\n\n if (result.verification?.length) {\n lines.push(\"\", \"Verification:\");\n for (const check of result.verification) {\n lines.push(`- \\`${check.command}\\`: ${check.outcome}`);\n }\n }\n\n const nextAction = nextActionSummary(result);\n if (nextAction) {\n lines.push(\"\", `Next action: ${nextAction}`);\n }\n\n const suggestedActions = renderSuggestedActions(result);\n if (suggestedActions.length > 0) {\n lines.push(\"\", ...suggestedActions);\n }\n\n return lines.join(\"\\n\");\n}\n"],"mappings":"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","names":["externalUri","stringParam","stringArrayParam"]}
|
|
1
|
+
{"version":3,"sources":["../src/pull-request.ts","../src/apply.ts","../src/ingress.ts","../src/normalize.ts","../src/render.ts"],"sourcesContent":["import type { OpenTagRunResult } from \"@opentag/core\";\n\nexport type CreatePullRequestInput = {\n token: string;\n owner: string;\n repo: string;\n title: string;\n body: string;\n head: string;\n base: string;\n};\n\nexport type FetchLike = typeof fetch;\n\nexport function buildPullRequestBody(result: OpenTagRunResult): string {\n const lines = [\"## Summary\", \"\", result.summary];\n\n if (result.changedFiles?.length) {\n lines.push(\"\", \"## Changed Files\");\n for (const file of result.changedFiles) {\n lines.push(`- \\`${file}\\``);\n }\n }\n\n if (result.verification?.length) {\n lines.push(\"\", \"## Verification\");\n for (const check of result.verification) {\n lines.push(`- \\`${check.command}\\`: ${check.outcome}`);\n }\n }\n\n return lines.join(\"\\n\");\n}\n\nexport async function createPullRequestViaFetch(input: CreatePullRequestInput, fetchImpl: FetchLike = fetch): Promise<string> {\n const response = await fetchImpl(`https://api.github.com/repos/${input.owner}/${input.repo}/pulls`, {\n method: \"POST\",\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n },\n body: JSON.stringify({\n title: input.title,\n body: input.body,\n head: input.head,\n base: input.base\n })\n });\n\n if (!response.ok) {\n throw new Error(`create pull request failed: ${response.status} ${await response.text()}`);\n }\n\n const body = (await response.json()) as { html_url?: string };\n if (!body.html_url) {\n throw new Error(\"create pull request response did not include html_url\");\n }\n return body.html_url;\n}\n","import type { AdapterMutationCompiler, AdapterMutationMapping, ApplyIntentOutcome, MutationIntent } from \"@opentag/core\";\nimport { createPullRequestViaFetch, type FetchLike } from \"./pull-request.js\";\n\nexport type GitHubIssueMutationTarget = {\n token: string;\n owner: string;\n repo: string;\n issueNumber?: number;\n pullRequestNumber?: number;\n};\n\nexport type GitHubIssueMutationOperation =\n | {\n kind: \"add_label\";\n intentId: string;\n label: string;\n }\n | {\n kind: \"remove_label\";\n intentId: string;\n label: string;\n }\n | {\n kind: \"replace_mapped_label\";\n intentId: string;\n label: string;\n removeLabels: string[];\n }\n | {\n kind: \"set_labels\";\n intentId: string;\n labels: string[];\n }\n | {\n kind: \"set_assignees\";\n intentId: string;\n assignees: string[];\n }\n | {\n kind: \"add_assignee\";\n intentId: string;\n assignee: string;\n }\n | {\n kind: \"remove_assignee\";\n intentId: string;\n assignee: string;\n }\n | {\n kind: \"request_review\";\n intentId: string;\n reviewers: string[];\n teamReviewers?: string[];\n }\n | {\n kind: \"create_pull_request\";\n intentId: string;\n title: string;\n body: string;\n head: string;\n base: string;\n };\n\nexport type GitHubIssueMutationCompilation =\n | {\n ok: true;\n intentId: string;\n operation: GitHubIssueMutationOperation;\n }\n | {\n ok: false;\n outcome: ApplyIntentOutcome;\n };\n\nfunction labelFromIntent(intent: MutationIntent): string | undefined {\n const value = intent.params?.[\"label\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction labelsFromIntent(intent: MutationIntent): string[] | undefined {\n const value = intent.params?.[\"labels\"];\n if (!Array.isArray(value)) return undefined;\n const labels = value.filter((label): label is string => typeof label === \"string\" && label.length > 0);\n return labels.length > 0 ? labels : undefined;\n}\n\nfunction assigneeFromIntent(intent: MutationIntent): string | undefined {\n const value = intent.params?.[\"assignee\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction assigneesFromIntent(intent: MutationIntent): string[] | undefined {\n const value = intent.params?.[\"assignees\"];\n if (!Array.isArray(value)) return undefined;\n const assignees = value.filter((assignee): assignee is string => typeof assignee === \"string\" && assignee.length > 0);\n return assignees.length > 0 ? assignees : undefined;\n}\n\nfunction reviewersFromIntent(intent: MutationIntent): string[] | undefined {\n const reviewer = intent.params?.[\"reviewer\"];\n const reviewers = intent.params?.[\"reviewers\"];\n const values = [\n ...(typeof reviewer === \"string\" ? [reviewer] : []),\n ...(Array.isArray(reviewers) ? reviewers : [])\n ].filter((value): value is string => typeof value === \"string\" && value.length > 0);\n return values.length > 0 ? [...new Set(values)] : undefined;\n}\n\nfunction teamReviewersFromIntent(intent: MutationIntent): string[] | undefined {\n const reviewer = intent.params?.[\"teamReviewer\"];\n const reviewers = intent.params?.[\"teamReviewers\"] ?? intent.params?.[\"team_reviewers\"];\n const values = [\n ...(typeof reviewer === \"string\" ? [reviewer] : []),\n ...(Array.isArray(reviewers) ? reviewers : [])\n ].filter((value): value is string => typeof value === \"string\" && value.length > 0);\n return values.length > 0 ? [...new Set(values)] : undefined;\n}\n\nfunction stringParam(intent: MutationIntent, ...keys: string[]): string | undefined {\n for (const key of keys) {\n const value = intent.params?.[key];\n if (typeof value === \"string\" && value.length > 0) return value;\n }\n return undefined;\n}\n\nfunction stringArrayParam(intent: MutationIntent, key: string): string[] {\n const value = intent.params?.[key];\n if (!Array.isArray(value)) return [];\n return value.filter((item): item is string => typeof item === \"string\" && item.length > 0);\n}\n\nfunction verificationLinesFromIntent(intent: MutationIntent): string[] {\n const value = intent.params?.[\"verification\"];\n if (!Array.isArray(value)) return [];\n return value\n .map((item) => {\n if (!item || typeof item !== \"object\" || Array.isArray(item)) return undefined;\n const command = (item as Record<string, unknown>)[\"command\"];\n const outcome = (item as Record<string, unknown>)[\"outcome\"];\n return typeof command === \"string\" && typeof outcome === \"string\" ? `- \\`${command}\\`: ${outcome}` : undefined;\n })\n .filter((line): line is string => Boolean(line));\n}\n\nfunction pullRequestBodyFromIntent(intent: MutationIntent): string {\n const explicitBody = stringParam(intent, \"body\");\n const changedFiles = stringArrayParam(intent, \"changedFiles\");\n const risks = stringArrayParam(intent, \"risks\");\n const verification = verificationLinesFromIntent(intent);\n const executorConditions = stringArrayParam(intent, \"executorConditions\");\n const lines = explicitBody ? [explicitBody] : [\"## Summary\", \"\", intent.summary];\n if (changedFiles.length > 0) {\n lines.push(\"\", \"## Changed Files\", ...changedFiles.map((file) => `- \\`${file}\\``));\n }\n if (risks.length > 0) {\n lines.push(\"\", \"## Risks\", ...risks.map((risk) => `- ${risk}`));\n }\n if (verification.length > 0) {\n lines.push(\"\", \"## Verification\", ...verification);\n }\n if (executorConditions.length > 0) {\n lines.push(\"\", \"## Executor Conditions\", ...executorConditions.map((condition) => `- ${condition}`));\n }\n return lines.join(\"\\n\");\n}\n\nfunction mappedValueFromIntent(intent: MutationIntent): string | undefined {\n const key = intent.domain === \"status\" ? \"status\" : \"priority\";\n const value = intent.params?.[key] ?? intent.params?.[\"value\"];\n return typeof value === \"string\" && value.length > 0 ? value : undefined;\n}\n\nfunction labelMappingForIntent(input: { intent: MutationIntent; mappings: AdapterMutationMapping[] }): { label: string; removeLabels: string[] } | undefined {\n const semanticValue = mappedValueFromIntent(input.intent);\n if (!semanticValue) return undefined;\n const mapping = input.mappings.find(\n (candidate) => candidate.adapter === \"github\" && candidate.domain === input.intent.domain && candidate.strategy === \"label\"\n );\n const label = mapping?.values[semanticValue];\n if (!label || !mapping) return undefined;\n return {\n label,\n removeLabels: Object.values(mapping.values).filter((mappedLabel) => mappedLabel !== label)\n };\n}\n\nasync function githubJson(input: {\n target: GitHubIssueMutationTarget;\n fetchImpl: FetchLike;\n method: \"GET\" | \"POST\" | \"PUT\" | \"PATCH\" | \"DELETE\";\n path: string;\n body?: unknown;\n okStatuses?: number[];\n}): Promise<string | undefined> {\n const response = await input.fetchImpl(`https://api.github.com/repos/${input.target.owner}/${input.target.repo}${input.path}`, {\n method: input.method,\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.target.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n },\n ...(input.body ? { body: JSON.stringify(input.body) } : {})\n });\n\n if (!response.ok && !(input.okStatuses ?? []).includes(response.status)) {\n throw new Error(`${input.method} ${input.path} failed: ${response.status} ${await response.text()}`);\n }\n return `https://github.com/${input.target.owner}/${input.target.repo}/issues/${input.target.issueNumber}`;\n}\n\nasync function githubJsonBody<T>(input: {\n target: GitHubIssueMutationTarget;\n fetchImpl: FetchLike;\n method: \"GET\";\n path: string;\n okStatuses?: number[];\n}): Promise<T> {\n const response = await input.fetchImpl(`https://api.github.com/repos/${input.target.owner}/${input.target.repo}${input.path}`, {\n method: input.method,\n headers: {\n accept: \"application/vnd.github+json\",\n authorization: `Bearer ${input.target.token}`,\n \"content-type\": \"application/json\",\n \"x-github-api-version\": \"2022-11-28\"\n }\n });\n\n if (!response.ok && !(input.okStatuses ?? []).includes(response.status)) {\n throw new Error(`${input.method} ${input.path} failed: ${response.status} ${await response.text()}`);\n }\n return await response.json() as T;\n}\n\ntype RequestedReviewersResponse = {\n users?: Array<{ login?: unknown }>;\n teams?: Array<{ slug?: unknown; name?: unknown }>;\n};\n\nfunction requestedReviewerLogins(response: RequestedReviewersResponse): Set<string> {\n return new Set((response.users ?? []).map((user) => user.login).filter((login): login is string => typeof login === \"string\"));\n}\n\nfunction requestedTeamReviewerNames(response: RequestedReviewersResponse): Set<string> {\n return new Set(\n (response.teams ?? [])\n .flatMap((team) => [team.slug, team.name])\n .filter((value): value is string => typeof value === \"string\" && value.length > 0)\n );\n}\n\nexport function compileGitHubIssueMutationIntent(\n intent: MutationIntent,\n options: { mappings?: AdapterMutationMapping[]; targetKind?: \"issue\" | \"pull_request\" } = {}\n): GitHubIssueMutationCompilation {\n if (intent.action === \"create_pull_request\") {\n const head = stringParam(intent, \"head\", \"branch\");\n if (!head) {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"failed\",\n message: \"create_pull_request requires params.head or params.branch.\"\n }\n };\n }\n return {\n ok: true,\n intentId: intent.intentId,\n operation: {\n kind: \"create_pull_request\",\n intentId: intent.intentId,\n title: stringParam(intent, \"title\") ?? intent.summary,\n body: pullRequestBodyFromIntent(intent),\n head,\n base: stringParam(intent, \"base\", \"baseBranch\") ?? \"main\"\n }\n };\n }\n\n if (intent.action === \"request_review\" || intent.domain === \"review\") {\n if (options.targetKind !== \"pull_request\") {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub review requests require a pull request target.\"\n }\n };\n }\n const reviewers = reviewersFromIntent(intent);\n const teamReviewers = teamReviewersFromIntent(intent);\n if (!reviewers?.length && !teamReviewers?.length) {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"failed\",\n message: \"request_review requires params.reviewer, params.reviewers, or params.teamReviewers.\"\n }\n };\n }\n return {\n ok: true,\n intentId: intent.intentId,\n operation: {\n kind: \"request_review\",\n intentId: intent.intentId,\n reviewers: reviewers ?? [],\n ...(teamReviewers?.length ? { teamReviewers } : {})\n }\n };\n }\n\n if (intent.domain === \"status\") {\n const mapped = labelMappingForIntent({ intent, mappings: options.mappings ?? [] });\n if (mapped) {\n return { ok: true, intentId: intent.intentId, operation: { kind: \"replace_mapped_label\", intentId: intent.intentId, ...mapped } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub status writes require an explicit Project field or label mapping policy.\"\n }\n };\n }\n if (intent.domain === \"priority\") {\n const mapped = labelMappingForIntent({ intent, mappings: options.mappings ?? [] });\n if (mapped) {\n return { ok: true, intentId: intent.intentId, operation: { kind: \"replace_mapped_label\", intentId: intent.intentId, ...mapped } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: \"GitHub priority writes require an explicit label or Project field mapping policy.\"\n }\n };\n }\n if (intent.domain !== \"labels\" && intent.domain !== \"assignee\") {\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply supports labels and assignee only, not ${intent.domain}.`\n }\n };\n }\n\n if (intent.domain === \"assignee\") {\n if (intent.action === \"set_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_assignees\", intentId: intent.intentId, assignees: [assignee] } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_assignee requires params.assignee.\" } };\n }\n if (intent.action === \"set_assignees\") {\n const assignees = assigneesFromIntent(intent);\n return assignees\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_assignees\", intentId: intent.intentId, assignees } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_assignees requires params.assignees.\" } };\n }\n if (intent.action === \"add_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"add_assignee\", intentId: intent.intentId, assignee } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"add_assignee requires params.assignee.\" } };\n }\n if (intent.action === \"remove_assignee\") {\n const assignee = assigneeFromIntent(intent);\n return assignee\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"remove_assignee\", intentId: intent.intentId, assignee } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"remove_assignee requires params.assignee.\" } };\n }\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply does not support assignee action ${intent.action}.`\n }\n };\n }\n\n if (intent.action === \"add_label\") {\n const label = labelFromIntent(intent);\n return label\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"add_label\", intentId: intent.intentId, label } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"add_label requires params.label.\" } };\n }\n if (intent.action === \"remove_label\") {\n const label = labelFromIntent(intent);\n return label\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"remove_label\", intentId: intent.intentId, label } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"remove_label requires params.label.\" } };\n }\n if (intent.action === \"set_labels\") {\n const labels = labelsFromIntent(intent);\n return labels\n ? { ok: true, intentId: intent.intentId, operation: { kind: \"set_labels\", intentId: intent.intentId, labels } }\n : { ok: false, outcome: { intentId: intent.intentId, outcome: \"failed\", message: \"set_labels requires params.labels.\" } };\n }\n\n return {\n ok: false,\n outcome: {\n intentId: intent.intentId,\n outcome: \"unsupported\",\n message: `GitHub apply does not support labels action ${intent.action}.`\n }\n };\n}\n\nexport function compileGitHubIssueMutationIntents(\n intents: MutationIntent[],\n options: { mappings?: AdapterMutationMapping[]; targetKind?: \"issue\" | \"pull_request\" } = {}\n): GitHubIssueMutationCompilation[] {\n return intents.map((intent) => compileGitHubIssueMutationIntent(intent, options));\n}\n\nexport function createGitHubIssueMutationCompiler(options: {\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n} = {}): AdapterMutationCompiler<GitHubIssueMutationOperation> {\n return {\n adapter: \"github\",\n compile(intent) {\n const compilation = compileGitHubIssueMutationIntent(intent, options);\n if (!compilation.ok) {\n return {\n ok: false,\n adapter: \"github\",\n outcome: compilation.outcome\n };\n }\n return {\n ok: true,\n adapter: \"github\",\n intentId: compilation.intentId,\n operation: compilation.operation\n };\n }\n };\n}\n\nexport async function applyGitHubIssueMutationOperation(input: {\n target: GitHubIssueMutationTarget;\n operation: GitHubIssueMutationOperation;\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome> {\n const fetchImpl = input.fetchImpl ?? fetch;\n try {\n if (input.operation.kind === \"create_pull_request\") {\n const externalUri = await createPullRequestViaFetch(\n {\n token: input.target.token,\n owner: input.target.owner,\n repo: input.target.repo,\n title: input.operation.title,\n body: input.operation.body,\n head: input.operation.head,\n base: input.operation.base\n },\n fetchImpl\n );\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"request_review\") {\n const pullRequestNumber = input.target.pullRequestNumber;\n if (typeof pullRequestNumber !== \"number\") {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n message: \"request_review requires target.pullRequestNumber.\"\n };\n }\n const requested = await githubJsonBody<RequestedReviewersResponse>({\n target: input.target,\n fetchImpl,\n method: \"GET\",\n path: `/pulls/${pullRequestNumber}/requested_reviewers`\n });\n const existingReviewers = requestedReviewerLogins(requested);\n const existingTeamReviewers = requestedTeamReviewerNames(requested);\n const reviewers = input.operation.reviewers.filter((reviewer) => !existingReviewers.has(reviewer));\n const teamReviewers = input.operation.teamReviewers?.filter((reviewer) => !existingTeamReviewers.has(reviewer));\n if (reviewers.length === 0 && (!teamReviewers || teamReviewers.length === 0)) {\n return {\n intentId: input.operation.intentId,\n outcome: \"applied\",\n externalUri: `https://github.com/${input.target.owner}/${input.target.repo}/pull/${pullRequestNumber}`,\n message: \"Requested reviewers were already present; skipped GitHub notification retry.\"\n };\n }\n await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/pulls/${pullRequestNumber}/requested_reviewers`,\n body: {\n ...(reviewers.length ? { reviewers } : {}),\n ...(teamReviewers?.length ? { team_reviewers: teamReviewers } : {})\n }\n });\n return {\n intentId: input.operation.intentId,\n outcome: \"applied\",\n externalUri: `https://github.com/${input.target.owner}/${input.target.repo}/pull/${pullRequestNumber}`\n };\n }\n\n const issueNumber = input.target.issueNumber;\n if (typeof issueNumber !== \"number\") {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n message: \"GitHub issue mutation requires target.issueNumber.\"\n };\n }\n\n if (input.operation.kind === \"set_assignees\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"PATCH\",\n path: `/issues/${issueNumber}`,\n body: { assignees: input.operation.assignees }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"add_assignee\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/assignees`,\n body: { assignees: [input.operation.assignee] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"remove_assignee\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/assignees`,\n body: { assignees: [input.operation.assignee] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"replace_mapped_label\") {\n for (const label of input.operation.removeLabels) {\n await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/labels/${encodeURIComponent(label)}`,\n okStatuses: [200, 404]\n });\n }\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: [input.operation.label] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"add_label\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"POST\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: [input.operation.label] }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n if (input.operation.kind === \"remove_label\") {\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"DELETE\",\n path: `/issues/${issueNumber}/labels/${encodeURIComponent(input.operation.label)}`\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n }\n\n const externalUri = await githubJson({\n target: input.target,\n fetchImpl,\n method: \"PUT\",\n path: `/issues/${issueNumber}/labels`,\n body: { labels: input.operation.labels }\n });\n return { intentId: input.operation.intentId, outcome: \"applied\", externalUri };\n } catch (error) {\n return {\n intentId: input.operation.intentId,\n outcome: \"failed\",\n error: error instanceof Error ? error.message : String(error)\n };\n }\n}\n\nexport async function applyGitHubIssueMutationIntent(input: {\n target: GitHubIssueMutationTarget;\n intent: MutationIntent;\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome> {\n const compiled = compileGitHubIssueMutationIntent(input.intent, {\n ...(input.mappings ? { mappings: input.mappings } : {}),\n ...(input.targetKind ? { targetKind: input.targetKind } : {})\n });\n if (!compiled.ok) return compiled.outcome;\n return applyGitHubIssueMutationOperation({\n target: input.target,\n operation: compiled.operation,\n ...(input.fetchImpl ? { fetchImpl: input.fetchImpl } : {})\n });\n}\n\nexport async function applyGitHubIssueMutationIntents(input: {\n target: GitHubIssueMutationTarget;\n intents: MutationIntent[];\n mappings?: AdapterMutationMapping[];\n targetKind?: \"issue\" | \"pull_request\";\n fetchImpl?: FetchLike;\n}): Promise<ApplyIntentOutcome[]> {\n const outcomes: ApplyIntentOutcome[] = [];\n for (const intent of input.intents) {\n outcomes.push(\n await applyGitHubIssueMutationIntent({\n target: input.target,\n intent,\n ...(input.mappings ? { mappings: input.mappings } : {}),\n ...(input.targetKind ? { targetKind: input.targetKind } : {}),\n ...(input.fetchImpl ? { fetchImpl: input.fetchImpl } : {})\n })\n );\n }\n return outcomes;\n}\n","import { createHmac, randomUUID, timingSafeEqual } from \"node:crypto\";\nimport { serve } from \"@hono/node-server\";\nimport { createOpenTagClient } from \"@opentag/client\";\nimport {\n DEFAULT_MAX_REQUEST_BODY_BYTES,\n RequestBodyTooLargeError,\n parseThreadActionCommand,\n readRequestTextWithLimit,\n type OpenTagEvent\n} from \"@opentag/core\";\nimport { Hono } from \"hono\";\nimport { normalizeGitHubIssueComment, normalizeGitHubPullRequestReviewComment } from \"./normalize.js\";\n\ntype GitHubActor = {\n id: number;\n login: string;\n};\n\ntype GitHubRepository = {\n name: string;\n private: boolean;\n owner: { login: string };\n};\n\nexport type GitHubIssueCommentPayload = {\n action?: string;\n comment: { id: number; body: string; html_url: string };\n issue: { html_url: string; comments_url: string; number: number };\n repository: GitHubRepository;\n sender: GitHubActor;\n installation?: { id: number };\n};\n\nexport type GitHubPullRequestReviewCommentPayload = {\n action?: string;\n comment: { id: number; body: string; html_url: string };\n pull_request: { html_url: string; number: number };\n repository: GitHubRepository;\n sender: GitHubActor;\n installation?: { id: number };\n};\n\nexport type GitHubThreadActionInput = {\n id: string;\n rawText: string;\n actor: {\n provider: \"github\";\n providerUserId: string;\n handle: string;\n };\n callback: {\n provider: \"github\";\n uri: string;\n threadKey: string;\n };\n metadata: Record<string, unknown>;\n};\n\nexport type GitHubWebhookAppInput = {\n webhookSecret: string;\n webhookPath?: string;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n recordControlPlaneEvent?(event: {\n type: string;\n severity?: \"info\" | \"warn\" | \"error\";\n subject?: string;\n payload?: Record<string, unknown>;\n }): Promise<void>;\n maxRequestBodyBytes?: number;\n now(): string;\n};\n\nexport type GitHubIngressConfig = {\n webhookSecret: string;\n dispatcherUrl: string;\n dispatcherToken?: string;\n port?: number;\n hostname?: string;\n webhookPath?: string;\n maxRequestBodyBytes?: number;\n};\n\nexport type GitHubIngressHandle = {\n url: string;\n webhookPath: string;\n server: ReturnType<typeof serve>;\n close(): Promise<void>;\n};\n\nexport function computeGitHubSignature(input: { webhookSecret: string; rawBody: string }): string {\n const digest = createHmac(\"sha256\", input.webhookSecret).update(input.rawBody).digest(\"hex\");\n return `sha256=${digest}`;\n}\n\nexport function verifyGitHubSignature(input: {\n webhookSecret: string;\n rawBody: string;\n signature: string;\n}): boolean {\n const expected = computeGitHubSignature(input);\n const expectedBuffer = Buffer.from(expected);\n const actualBuffer = Buffer.from(input.signature);\n return expectedBuffer.length === actualBuffer.length && timingSafeEqual(expectedBuffer, actualBuffer);\n}\n\nasync function recordGitHubSignatureFailure(input: {\n recordControlPlaneEvent?: GitHubWebhookAppInput[\"recordControlPlaneEvent\"];\n webhookPath: string;\n reason: \"missing_signature_header\" | \"invalid_signature\";\n deliveryId?: string;\n hasSignature: boolean;\n}): Promise<void> {\n try {\n await input.recordControlPlaneEvent?.({\n type: \"security.signature_failed\",\n severity: \"warn\",\n subject: `github:POST ${input.webhookPath}`,\n payload: {\n provider: \"github\",\n endpoint: `POST ${input.webhookPath}`,\n reason: input.reason,\n ...(input.deliveryId ? { deliveryId: input.deliveryId } : {}),\n hasSignature: input.hasSignature\n }\n });\n } catch {\n // Signature rejection should not turn into a 5xx if audit reporting is unavailable.\n }\n}\n\nasync function recordGitHubRequestBodyRejected(input: {\n recordControlPlaneEvent?: GitHubWebhookAppInput[\"recordControlPlaneEvent\"];\n webhookPath: string;\n reason: \"request_body_too_large\" | \"invalid_json_body\" | \"invalid_request_body\";\n maxBytes?: number;\n contentLength: string | null;\n deliveryId?: string;\n eventName?: string;\n}): Promise<void> {\n try {\n await input.recordControlPlaneEvent?.({\n type: \"security.request_body_rejected\",\n severity: \"warn\",\n subject: `github:POST ${input.webhookPath}`,\n payload: {\n provider: \"github\",\n endpoint: `POST ${input.webhookPath}`,\n reason: input.reason,\n ...(input.maxBytes !== undefined ? { maxBytes: input.maxBytes } : {}),\n contentLength: input.contentLength,\n ...(input.deliveryId ? { deliveryId: input.deliveryId } : {}),\n ...(input.eventName ? { githubEvent: input.eventName } : {})\n }\n });\n } catch {\n // Oversized-payload rejection should still fail closed if audit reporting is unavailable.\n }\n}\n\nfunction parseJsonPayload(rawBody: string): unknown {\n try {\n return JSON.parse(rawBody);\n } catch {\n return null;\n }\n}\n\nfunction isRecord(value: unknown): value is Record<string, unknown> {\n return Boolean(value) && typeof value === \"object\" && !Array.isArray(value);\n}\n\nfunction hasGitHubActor(value: unknown): value is GitHubActor {\n return isRecord(value) && typeof value.id === \"number\" && typeof value.login === \"string\";\n}\n\nfunction hasGitHubRepository(value: unknown): value is GitHubRepository {\n return (\n isRecord(value) &&\n typeof value.name === \"string\" &&\n typeof value.private === \"boolean\" &&\n isRecord(value.owner) &&\n typeof value.owner.login === \"string\"\n );\n}\n\nfunction hasGitHubInstallation(value: unknown): value is { id: number } {\n return isRecord(value) && typeof value.id === \"number\";\n}\n\nfunction isGitHubIssueCommentPayload(value: unknown): value is GitHubIssueCommentPayload {\n return (\n isRecord(value) &&\n (value.action === undefined || typeof value.action === \"string\") &&\n isRecord(value.comment) &&\n typeof value.comment.id === \"number\" &&\n typeof value.comment.body === \"string\" &&\n typeof value.comment.html_url === \"string\" &&\n isRecord(value.issue) &&\n typeof value.issue.html_url === \"string\" &&\n typeof value.issue.comments_url === \"string\" &&\n typeof value.issue.number === \"number\" &&\n hasGitHubRepository(value.repository) &&\n hasGitHubActor(value.sender) &&\n (value.installation === undefined || hasGitHubInstallation(value.installation))\n );\n}\n\nfunction isGitHubPullRequestReviewCommentPayload(value: unknown): value is GitHubPullRequestReviewCommentPayload {\n return (\n isRecord(value) &&\n (value.action === undefined || typeof value.action === \"string\") &&\n isRecord(value.comment) &&\n typeof value.comment.id === \"number\" &&\n typeof value.comment.body === \"string\" &&\n typeof value.comment.html_url === \"string\" &&\n isRecord(value.pull_request) &&\n typeof value.pull_request.html_url === \"string\" &&\n typeof value.pull_request.number === \"number\" &&\n hasGitHubRepository(value.repository) &&\n hasGitHubActor(value.sender) &&\n (value.installation === undefined || hasGitHubInstallation(value.installation))\n );\n}\n\nasync function handleIssueCommentCreated(input: {\n payload: GitHubIssueCommentPayload;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n now(): string;\n deliveryId?: string;\n signatureVerified?: boolean;\n}): Promise<void> {\n if (input.payload.action && input.payload.action !== \"created\") return;\n if (parseThreadActionCommand(input.payload.comment.body) && input.submitThreadAction) {\n await input.submitThreadAction({\n id: `approval_github_comment_${input.payload.comment.id}`,\n rawText: input.payload.comment.body,\n actor: {\n provider: \"github\",\n providerUserId: String(input.payload.sender.id),\n handle: input.payload.sender.login\n },\n callback: {\n provider: \"github\",\n uri: input.payload.issue.comments_url,\n threadKey: `${input.payload.repository.owner.login}/${input.payload.repository.name}#${input.payload.issue.number}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.payload.repository.owner.login,\n repo: input.payload.repository.name,\n issueNumber: input.payload.issue.number,\n commentUrl: input.payload.comment.html_url,\n ...(input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\"\n ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? \"verified\" : \"unverified\" }\n : {})\n }\n });\n return;\n }\n\n const event = normalizeGitHubIssueComment({\n id: String(input.payload.comment.id),\n commentBody: input.payload.comment.body,\n commentUrl: input.payload.comment.html_url,\n apiCommentsUrl: input.payload.issue.comments_url,\n issueUrl: input.payload.issue.html_url,\n issueNumber: input.payload.issue.number,\n owner: input.payload.repository.owner.login,\n repo: input.payload.repository.name,\n actorId: input.payload.sender.id,\n actorLogin: input.payload.sender.login,\n private: input.payload.repository.private,\n receivedAt: input.now(),\n ...(input.deliveryId ? { deliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\" ? { signatureVerified: input.signatureVerified } : {}),\n ...(input.payload.installation ? { installationId: input.payload.installation.id } : {})\n });\n\n if (event) {\n await input.createRun(event);\n }\n}\n\nasync function handlePullRequestReviewCommentCreated(input: {\n payload: GitHubPullRequestReviewCommentPayload;\n createRun(event: OpenTagEvent): Promise<{ runId?: string }>;\n submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;\n now(): string;\n deliveryId?: string;\n signatureVerified?: boolean;\n}): Promise<void> {\n if (input.payload.action && input.payload.action !== \"created\") return;\n const owner = input.payload.repository.owner.login;\n const repo = input.payload.repository.name;\n if (parseThreadActionCommand(input.payload.comment.body) && input.submitThreadAction) {\n await input.submitThreadAction({\n id: `approval_github_pr_review_comment_${input.payload.comment.id}`,\n rawText: input.payload.comment.body,\n actor: {\n provider: \"github\",\n providerUserId: String(input.payload.sender.id),\n handle: input.payload.sender.login\n },\n callback: {\n provider: \"github\",\n uri: `https://api.github.com/repos/${owner}/${repo}/issues/${input.payload.pull_request.number}/comments`,\n threadKey: `${owner}/${repo}#${input.payload.pull_request.number}`\n },\n metadata: {\n repoProvider: \"github\",\n owner,\n repo,\n pullRequestNumber: input.payload.pull_request.number,\n commentUrl: input.payload.comment.html_url,\n ...(input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\"\n ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? \"verified\" : \"unverified\" }\n : {})\n }\n });\n return;\n }\n\n const event = normalizeGitHubPullRequestReviewComment({\n id: String(input.payload.comment.id),\n commentBody: input.payload.comment.body,\n commentUrl: input.payload.comment.html_url,\n pullRequestUrl: input.payload.pull_request.html_url,\n apiCommentsUrl: `https://api.github.com/repos/${owner}/${repo}/issues/${input.payload.pull_request.number}/comments`,\n owner,\n repo,\n pullRequestNumber: input.payload.pull_request.number,\n actorId: input.payload.sender.id,\n actorLogin: input.payload.sender.login,\n private: input.payload.repository.private,\n receivedAt: input.now(),\n ...(input.deliveryId ? { deliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\" ? { signatureVerified: input.signatureVerified } : {}),\n ...(input.payload.installation ? { installationId: input.payload.installation.id } : {})\n });\n\n if (event) {\n await input.createRun(event);\n }\n}\n\nexport function createGitHubWebhookApp(input: GitHubWebhookAppInput) {\n const app = new Hono();\n const webhookPath = input.webhookPath ?? \"/github/webhooks\";\n const maxRequestBodyBytes = input.maxRequestBodyBytes ?? DEFAULT_MAX_REQUEST_BODY_BYTES;\n if (!webhookPath.startsWith(\"/\")) {\n throw new Error(\"GitHub webhook path must start with /.\");\n }\n\n app.post(webhookPath, async (c) => {\n const signature = c.req.header(\"x-hub-signature-256\");\n if (!signature) {\n await recordGitHubSignatureFailure({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"missing_signature_header\",\n ...(c.req.header(\"x-github-delivery\") ? { deliveryId: c.req.header(\"x-github-delivery\")! } : {}),\n hasSignature: false\n });\n return c.json({ error: \"missing_signature_header\" }, 401);\n }\n let rawBody: string;\n try {\n rawBody = await readRequestTextWithLimit(c.req.raw, { maxBytes: maxRequestBodyBytes });\n } catch (error) {\n if (error instanceof RequestBodyTooLargeError) {\n await recordGitHubRequestBodyRejected({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"request_body_too_large\",\n maxBytes: error.maxBytes,\n contentLength: c.req.raw.headers.get(\"content-length\"),\n ...(c.req.header(\"x-github-delivery\") ? { deliveryId: c.req.header(\"x-github-delivery\")! } : {}),\n ...(c.req.header(\"x-github-event\") ? { eventName: c.req.header(\"x-github-event\")! } : {})\n });\n return c.json({ error: \"request_body_too_large\", maxBytes: error.maxBytes }, 413);\n }\n throw error;\n }\n if (!verifyGitHubSignature({ webhookSecret: input.webhookSecret, rawBody, signature })) {\n await recordGitHubSignatureFailure({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"invalid_signature\",\n ...(c.req.header(\"x-github-delivery\") ? { deliveryId: c.req.header(\"x-github-delivery\")! } : {}),\n hasSignature: true\n });\n return c.json({ error: \"invalid_signature\" }, 401);\n }\n\n const deliveryId = c.req.header(\"x-github-delivery\");\n const eventName = c.req.header(\"x-github-event\");\n const payload = parseJsonPayload(rawBody);\n if (!payload || typeof payload !== \"object\") {\n await recordGitHubRequestBodyRejected({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"invalid_json_body\",\n contentLength: c.req.raw.headers.get(\"content-length\"),\n ...(deliveryId ? { deliveryId } : {}),\n ...(eventName ? { eventName } : {})\n });\n return c.json({ error: \"invalid_json\" }, 400);\n }\n\n if (eventName === \"ping\") {\n return c.json({ ok: true });\n }\n if (eventName === \"issue_comment\") {\n if (!isGitHubIssueCommentPayload(payload)) {\n await recordGitHubRequestBodyRejected({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"invalid_request_body\",\n contentLength: c.req.raw.headers.get(\"content-length\"),\n ...(deliveryId ? { deliveryId } : {}),\n eventName\n });\n return c.json({ error: \"invalid_request_body\" }, 400);\n }\n await handleIssueCommentCreated({\n payload,\n createRun: input.createRun,\n ...(input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {}),\n now: input.now,\n ...(deliveryId ? { deliveryId } : {}),\n signatureVerified: true\n });\n return c.json({ ok: true });\n }\n if (eventName === \"pull_request_review_comment\") {\n if (!isGitHubPullRequestReviewCommentPayload(payload)) {\n await recordGitHubRequestBodyRejected({\n recordControlPlaneEvent: input.recordControlPlaneEvent,\n webhookPath,\n reason: \"invalid_request_body\",\n contentLength: c.req.raw.headers.get(\"content-length\"),\n ...(deliveryId ? { deliveryId } : {}),\n eventName\n });\n return c.json({ error: \"invalid_request_body\" }, 400);\n }\n await handlePullRequestReviewCommentCreated({\n payload,\n createRun: input.createRun,\n ...(input.submitThreadAction ? { submitThreadAction: input.submitThreadAction } : {}),\n now: input.now,\n ...(deliveryId ? { deliveryId } : {}),\n signatureVerified: true\n });\n return c.json({ ok: true });\n }\n\n return c.json({ ok: true, ignored: \"unsupported_event\" });\n });\n\n return app;\n}\n\nexport function startGitHubIngress(config: GitHubIngressConfig): GitHubIngressHandle {\n const dispatcherClient = createOpenTagClient({\n dispatcherUrl: config.dispatcherUrl,\n ...(config.dispatcherToken ? { pairingToken: config.dispatcherToken } : {})\n });\n const port = config.port ?? 3000;\n const hostname = config.hostname ?? \"127.0.0.1\";\n const webhookPath = config.webhookPath ?? \"/github/webhooks\";\n const server = serve({\n fetch: createGitHubWebhookApp({\n webhookSecret: config.webhookSecret,\n webhookPath,\n ...(config.maxRequestBodyBytes ? { maxRequestBodyBytes: config.maxRequestBodyBytes } : {}),\n async createRun(event) {\n const runId = `run_${randomUUID()}`;\n const created = await dispatcherClient.createRun({ runId, event });\n return created.outcome === \"run_created\" ? { runId: created.run.id } : {};\n },\n async submitThreadAction(action) {\n await dispatcherClient.submitThreadAction(action);\n },\n async recordControlPlaneEvent(event) {\n await dispatcherClient.recordControlPlaneEvent(event);\n },\n now: () => new Date().toISOString()\n }).fetch,\n port,\n hostname\n });\n\n return {\n url: `http://${hostname}:${port}`,\n webhookPath,\n server,\n close() {\n return new Promise((resolve, reject) => {\n server.close((error?: Error) => {\n if (error) {\n reject(error);\n return;\n }\n resolve();\n });\n });\n }\n };\n}\n","import { parseOpenTagMention, type OpenTagEvent } from \"@opentag/core\";\nimport type { ContextPointer, OpenTagCommand, PermissionGrant, WorkItemReference } from \"@opentag/core\";\n\nexport type GitHubIssueCommentInput = {\n id: string;\n commentBody: string;\n commentUrl: string;\n apiCommentsUrl: string;\n issueUrl: string;\n issueNumber: number;\n owner: string;\n repo: string;\n actorId: number;\n actorLogin: string;\n private: boolean;\n receivedAt: string;\n installationId?: number;\n deliveryId?: string;\n signatureVerified?: boolean;\n};\n\nexport type GitHubPullRequestReviewCommentInput = {\n id: string;\n commentBody: string;\n commentUrl: string;\n pullRequestUrl: string;\n apiCommentsUrl: string;\n owner: string;\n repo: string;\n pullRequestNumber: number;\n actorId: number;\n actorLogin: string;\n private: boolean;\n receivedAt: string;\n installationId?: number;\n deliveryId?: string;\n signatureVerified?: boolean;\n};\n\nfunction permissionsForIntent(intent: OpenTagCommand[\"intent\"]): PermissionGrant[] {\n const permissions: PermissionGrant[] = [\n {\n scope: \"issue:comment\",\n reason: \"reply to the source GitHub thread\"\n },\n {\n scope: \"runner:local\",\n reason: \"execute the run on a paired local daemon\"\n }\n ];\n if (intent === \"fix\" || intent === \"run\") {\n permissions.push(\n {\n scope: \"repo:read\",\n reason: \"inspect the repository in the paired local checkout\"\n },\n {\n scope: \"repo:write\",\n reason: \"commit code changes on an isolated run branch\"\n },\n {\n scope: \"pr:create\",\n reason: \"open a pull request for completed code changes\"\n }\n );\n }\n return permissions;\n}\n\nfunction permissionsForPullRequestReviewCommentIntent(intent: OpenTagCommand[\"intent\"]): PermissionGrant[] {\n const permissions = permissionsForIntent(intent);\n if (intent === \"review\") {\n permissions.push({\n scope: \"pr:update\",\n reason: \"request reviewers on the source pull request after explicit approval\"\n });\n }\n return permissions;\n}\n\nfunction contextPointersForCommand(command: OpenTagCommand, privateRepo: boolean): ContextPointer[] {\n const visibility = privateRepo ? \"private\" : \"public\";\n const context: ContextPointer[] = [];\n\n for (const reference of command.parsed?.references ?? []) {\n if (reference.kind === \"url\") {\n context.push({\n kind: \"url\",\n uri: reference.uri,\n visibility,\n title: reference.title ?? \"Command URL reference\"\n });\n continue;\n }\n\n if (reference.kind === \"file\" || reference.kind === \"path\" || reference.kind === \"line\" || reference.kind === \"range\") {\n context.push({\n kind: \"file\",\n uri: reference.uri,\n ...(reference.line ? { line: reference.line } : {}),\n ...(reference.startLine ? { startLine: reference.startLine } : {}),\n ...(reference.endLine ? { endLine: reference.endLine } : {}),\n visibility,\n title: referenceTitle(reference)\n });\n }\n }\n\n return context;\n}\n\nfunction referenceTitle(reference: NonNullable<OpenTagCommand[\"parsed\"]>[\"references\"][number]): string {\n return reference.title ?? \"Command file reference\";\n}\n\nfunction githubWorkItem(input: {\n owner: string;\n repo: string;\n kind: \"issue\" | \"pull_request\";\n number: number;\n uri: string;\n}): WorkItemReference {\n return {\n provider: \"github\",\n kind: input.kind,\n externalId: `${input.owner}/${input.repo}#${input.number}`,\n uri: input.uri,\n ownerContainer: {\n provider: \"github\",\n id: `${input.owner}/${input.repo}`,\n uri: `https://github.com/${input.owner}/${input.repo}`\n }\n };\n}\n\nfunction commandMetadata(command: OpenTagCommand): Record<string, unknown> {\n if (!command.parsed) return {};\n return {\n commandParser: command.parsed.version,\n commandDiagnostics: command.parsed.diagnostics,\n ...(command.parsed.approval ? { approval: command.parsed.approval } : {}),\n ...(command.parsed.network ? { network: command.parsed.network } : {})\n };\n}\n\nexport function normalizeGitHubIssueComment(input: GitHubIssueCommentInput): OpenTagEvent | null {\n const mention = parseOpenTagMention(input.commentBody);\n if (!mention.matched) return null;\n\n const command = {\n rawText: mention.rawText,\n intent: mention.intent,\n args: mention.args,\n ...(mention.parsed ? { parsed: mention.parsed } : {})\n };\n\n return {\n id: `evt_github_comment_${input.id}`,\n source: \"github\",\n sourceEventId: input.id,\n receivedAt: input.receivedAt,\n actor: {\n provider: \"github\",\n providerUserId: String(input.actorId),\n handle: input.actorLogin\n },\n target: {\n mention: \"@opentag\",\n agentId: \"opentag\",\n ...(mention.parsed?.executorHint ? { executorHint: mention.parsed.executorHint } : {})\n },\n command,\n context: [\n {\n provider: \"github\",\n kind: \"issue\",\n uri: input.issueUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n {\n provider: \"github\",\n kind: \"comment\",\n uri: input.commentUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n ...contextPointersForCommand(command, input.private)\n ],\n workItem: githubWorkItem({\n owner: input.owner,\n repo: input.repo,\n kind: \"issue\",\n number: input.issueNumber,\n uri: input.issueUrl\n }),\n permissions: permissionsForIntent(mention.intent),\n callback: {\n provider: \"github\",\n uri: input.apiCommentsUrl,\n threadKey: `${input.owner}/${input.repo}#${input.issueNumber}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.owner,\n repo: input.repo,\n issueNumber: input.issueNumber,\n ...commandMetadata(command),\n ...(input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\"\n ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? \"verified\" : \"unverified\" }\n : {}),\n ...(typeof input.installationId === \"number\" ? { installationId: input.installationId } : {})\n }\n };\n}\n\nexport function normalizeGitHubPullRequestReviewComment(input: GitHubPullRequestReviewCommentInput): OpenTagEvent | null {\n const mention = parseOpenTagMention(input.commentBody);\n if (!mention.matched) return null;\n\n const command = {\n rawText: mention.rawText,\n intent: mention.intent,\n args: mention.args,\n ...(mention.parsed ? { parsed: mention.parsed } : {})\n };\n\n return {\n id: `evt_github_pr_review_comment_${input.id}`,\n source: \"github\",\n sourceEventId: input.id,\n receivedAt: input.receivedAt,\n actor: {\n provider: \"github\",\n providerUserId: String(input.actorId),\n handle: input.actorLogin\n },\n target: {\n mention: \"@opentag\",\n agentId: \"opentag\",\n ...(mention.parsed?.executorHint ? { executorHint: mention.parsed.executorHint } : {})\n },\n command,\n context: [\n {\n provider: \"github\",\n kind: \"pull_request\",\n uri: input.pullRequestUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n {\n provider: \"github\",\n kind: \"comment\",\n uri: input.commentUrl,\n visibility: input.private ? \"private\" : \"public\"\n },\n ...contextPointersForCommand(command, input.private)\n ],\n workItem: githubWorkItem({\n owner: input.owner,\n repo: input.repo,\n kind: \"pull_request\",\n number: input.pullRequestNumber,\n uri: input.pullRequestUrl\n }),\n permissions: permissionsForPullRequestReviewCommentIntent(mention.intent),\n callback: {\n provider: \"github\",\n uri: input.apiCommentsUrl,\n threadKey: `${input.owner}/${input.repo}#${input.pullRequestNumber}`\n },\n metadata: {\n repoProvider: \"github\",\n owner: input.owner,\n repo: input.repo,\n pullRequestNumber: input.pullRequestNumber,\n ...commandMetadata(command),\n ...(input.deliveryId ? { sourceDeliveryId: input.deliveryId, webhookDeliveryId: input.deliveryId } : {}),\n ...(typeof input.signatureVerified === \"boolean\"\n ? { webhookSignatureVerified: input.signatureVerified, signatureState: input.signatureVerified ? \"verified\" : \"unverified\" }\n : {}),\n ...(typeof input.installationId === \"number\" ? { installationId: input.installationId } : {})\n }\n };\n}\n","import {\n createFinalSummaryPresentation,\n type ActionReceiptContext,\n type ActionReceiptDecision,\n type OpenTagFinalSummaryPresentation,\n type OpenTagPresentationAction,\n type OpenTagRunResult\n} from \"@opentag/core\";\n\nexport type GitHubRenderOptions = {\n receiptContext?: ActionReceiptContext;\n auditRunId?: string;\n};\n\nfunction tableValue(value: string): string {\n return value.replace(/\\|/g, \"\\\\|\").replace(/\\n/g, \"<br>\");\n}\n\nfunction decisionLabel(decision: ActionReceiptDecision): string {\n if (decision === \"apply\") return \"Apply now\";\n if (decision === \"approve\") return \"Approve only\";\n if (decision === \"continue\") return \"Continue\";\n return \"Reject\";\n}\n\nfunction decisionEffect(decision: ActionReceiptDecision): string {\n if (decision === \"apply\") return \"Approves and applies this action to the system of record.\";\n if (decision === \"approve\") return \"Records approval without applying yet.\";\n if (decision === \"continue\") return \"Starts a follow-up run from this approved action.\";\n return \"Rejects this action.\";\n}\n\nfunction actionDetailRows(action: OpenTagPresentationAction): Array<[string, string]> {\n if (action.detailRows?.length) return action.detailRows.map((row) => [row.label, row.value]);\n const rows: Array<[string, string]> = [[\"Target\", action.targetLabel]];\n if (action.setupReason) rows.push([\"Status\", action.setupReason]);\n return rows;\n}\n\nfunction renderSuggestedActions(presentation: OpenTagFinalSummaryPresentation): string[] {\n const actions = presentation.actions ?? [];\n if (actions.length === 0 || !presentation.actionReceiptTitle) return [];\n\n const lines = [\n `### ${presentation.actionReceiptTitle}`,\n \"\",\n \"OpenTag prepared a source-thread action receipt. Choose one command in this GitHub thread; full protocol lineage stays in the audit log.\"\n ];\n if (presentation.auditRunId) {\n lines.push(\"\", `Audit: run \\`opentag status --run ${presentation.auditRunId}\\` locally.`);\n }\n for (const action of actions) {\n lines.push(\n \"\",\n `#### ${action.index}. ${action.title}`,\n \"\",\n \"| Field | Value |\",\n \"| --- | --- |\"\n );\n for (const [label, value] of actionDetailRows(action)) {\n lines.push(`| ${label} | ${tableValue(value)} |`);\n }\n lines.push(\n \"\",\n \"**Choose in this thread**\",\n \"\",\n `| Decision | Comment command | Effect |`,\n `| --- | --- | --- |`\n );\n for (const decision of action.visibleDecisions) {\n lines.push(`| ${decisionLabel(decision)} | \\`${decision} ${action.index}\\` | ${decisionEffect(decision)} |`);\n }\n }\n\n return lines;\n}\n\nexport function renderAcknowledgement(runId: string): string {\n return `OpenTag picked this up. Run: \\`${runId}\\``;\n}\n\nexport function renderProgress(input: { runId: string; message: string }): string {\n return `OpenTag progress for \\`${input.runId}\\`: ${input.message}`;\n}\n\nexport function renderFinalResult(result: OpenTagRunResult, options: GitHubRenderOptions = {}): string {\n return renderFinalSummaryPresentation(\n createFinalSummaryPresentation({\n result,\n ...(options.receiptContext ? { receiptContext: options.receiptContext } : {}),\n ...(options.auditRunId ? { auditRunId: options.auditRunId } : {})\n })\n );\n}\n\nexport function renderFinalSummaryPresentation(presentation: OpenTagFinalSummaryPresentation): string {\n const lines = [`OpenTag finished with **${presentation.outcome}**.`, \"\", presentation.summary];\n\n if (presentation.verification?.length) {\n lines.push(\"\", \"Verification:\");\n for (const check of presentation.verification) {\n lines.push(`- \\`${check.command}\\`: ${check.outcome}`);\n }\n }\n\n const suggestedActions = renderSuggestedActions(presentation);\n if (suggestedActions.length > 0) {\n lines.push(\"\", ...suggestedActions);\n } else if (presentation.nextActions?.length) {\n lines.push(\"\", `Next action: ${presentation.nextActions[0]}`);\n }\n\n return lines.join(\"\\n\");\n}\n"],"mappings":"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","names":["externalUri"]}
|
package/dist/ingress.d.ts
CHANGED
|
@@ -69,6 +69,13 @@ export type GitHubWebhookAppInput = {
|
|
|
69
69
|
runId?: string;
|
|
70
70
|
}>;
|
|
71
71
|
submitThreadAction?(action: GitHubThreadActionInput): Promise<unknown>;
|
|
72
|
+
recordControlPlaneEvent?(event: {
|
|
73
|
+
type: string;
|
|
74
|
+
severity?: "info" | "warn" | "error";
|
|
75
|
+
subject?: string;
|
|
76
|
+
payload?: Record<string, unknown>;
|
|
77
|
+
}): Promise<void>;
|
|
78
|
+
maxRequestBodyBytes?: number;
|
|
72
79
|
now(): string;
|
|
73
80
|
};
|
|
74
81
|
export type GitHubIngressConfig = {
|
|
@@ -78,6 +85,7 @@ export type GitHubIngressConfig = {
|
|
|
78
85
|
port?: number;
|
|
79
86
|
hostname?: string;
|
|
80
87
|
webhookPath?: string;
|
|
88
|
+
maxRequestBodyBytes?: number;
|
|
81
89
|
};
|
|
82
90
|
export type GitHubIngressHandle = {
|
|
83
91
|
url: string;
|
package/dist/ingress.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ingress.d.ts","sourceRoot":"","sources":["../src/ingress.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAE1C,OAAO,
|
|
1
|
+
{"version":3,"file":"ingress.d.ts","sourceRoot":"","sources":["../src/ingress.ts"],"names":[],"mappings":"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"}
|
package/dist/normalize.d.ts
CHANGED
|
@@ -13,6 +13,8 @@ export type GitHubIssueCommentInput = {
|
|
|
13
13
|
private: boolean;
|
|
14
14
|
receivedAt: string;
|
|
15
15
|
installationId?: number;
|
|
16
|
+
deliveryId?: string;
|
|
17
|
+
signatureVerified?: boolean;
|
|
16
18
|
};
|
|
17
19
|
export type GitHubPullRequestReviewCommentInput = {
|
|
18
20
|
id: string;
|
|
@@ -28,6 +30,8 @@ export type GitHubPullRequestReviewCommentInput = {
|
|
|
28
30
|
private: boolean;
|
|
29
31
|
receivedAt: string;
|
|
30
32
|
installationId?: number;
|
|
33
|
+
deliveryId?: string;
|
|
34
|
+
signatureVerified?: boolean;
|
|
31
35
|
};
|
|
32
36
|
export declare function normalizeGitHubIssueComment(input: GitHubIssueCommentInput): OpenTagEvent | null;
|
|
33
37
|
export declare function normalizeGitHubPullRequestReviewComment(input: GitHubPullRequestReviewCommentInput): OpenTagEvent | null;
|
package/dist/normalize.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"normalize.d.ts","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuB,KAAK,YAAY,EAAE,MAAM,eAAe,CAAC;AAGvE,MAAM,MAAM,uBAAuB,GAAG;IACpC,EAAE,EAAE,MAAM,CAAC;IACX,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;IACvB,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"normalize.d.ts","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuB,KAAK,YAAY,EAAE,MAAM,eAAe,CAAC;AAGvE,MAAM,MAAM,uBAAuB,GAAG;IACpC,EAAE,EAAE,MAAM,CAAC;IACX,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;IACvB,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,iBAAiB,CAAC,EAAE,OAAO,CAAC;CAC7B,CAAC;AAEF,MAAM,MAAM,mCAAmC,GAAG;IAChD,EAAE,EAAE,MAAM,CAAC;IACX,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,EAAE,MAAM,CAAC;IACvB,cAAc,EAAE,MAAM,CAAC;IACvB,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,iBAAiB,EAAE,MAAM,CAAC;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,iBAAiB,CAAC,EAAE,OAAO,CAAC;CAC7B,CAAC;AA4GF,wBAAgB,2BAA2B,CAAC,KAAK,EAAE,uBAAuB,GAAG,YAAY,GAAG,IAAI,CAoE/F;AAED,wBAAgB,uCAAuC,CAAC,KAAK,EAAE,mCAAmC,GAAG,YAAY,GAAG,IAAI,CAoEvH"}
|
package/dist/render.d.ts
CHANGED
|
@@ -1,8 +1,13 @@
|
|
|
1
|
-
import { type OpenTagRunResult } from "@opentag/core";
|
|
1
|
+
import { type ActionReceiptContext, type OpenTagFinalSummaryPresentation, type OpenTagRunResult } from "@opentag/core";
|
|
2
|
+
export type GitHubRenderOptions = {
|
|
3
|
+
receiptContext?: ActionReceiptContext;
|
|
4
|
+
auditRunId?: string;
|
|
5
|
+
};
|
|
2
6
|
export declare function renderAcknowledgement(runId: string): string;
|
|
3
7
|
export declare function renderProgress(input: {
|
|
4
8
|
runId: string;
|
|
5
9
|
message: string;
|
|
6
10
|
}): string;
|
|
7
|
-
export declare function renderFinalResult(result: OpenTagRunResult): string;
|
|
11
|
+
export declare function renderFinalResult(result: OpenTagRunResult, options?: GitHubRenderOptions): string;
|
|
12
|
+
export declare function renderFinalSummaryPresentation(presentation: OpenTagFinalSummaryPresentation): string;
|
|
8
13
|
//# sourceMappingURL=render.d.ts.map
|
package/dist/render.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"render.d.ts","sourceRoot":"","sources":["../src/render.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"render.d.ts","sourceRoot":"","sources":["../src/render.ts"],"names":[],"mappings":"AAAA,OAAO,EAEL,KAAK,oBAAoB,EAEzB,KAAK,+BAA+B,EAEpC,KAAK,gBAAgB,EACtB,MAAM,eAAe,CAAC;AAEvB,MAAM,MAAM,mBAAmB,GAAG;IAChC,cAAc,CAAC,EAAE,oBAAoB,CAAC;IACtC,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,CAAC;AAiEF,wBAAgB,qBAAqB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAE3D;AAED,wBAAgB,cAAc,CAAC,KAAK,EAAE;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,GAAG,MAAM,CAEhF;AAED,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,gBAAgB,EAAE,OAAO,GAAE,mBAAwB,GAAG,MAAM,CAQrG;AAED,wBAAgB,8BAA8B,CAAC,YAAY,EAAE,+BAA+B,GAAG,MAAM,CAkBpG"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@opentag/github",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.1",
|
|
4
4
|
"description": "GitHub event normalization and callback rendering for OpenTag.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"engines": {
|
|
@@ -33,8 +33,8 @@
|
|
|
33
33
|
"dependencies": {
|
|
34
34
|
"@hono/node-server": "^1.13.7",
|
|
35
35
|
"hono": "^4.6.15",
|
|
36
|
-
"@opentag/client": "0.
|
|
37
|
-
"@opentag/core": "0.
|
|
36
|
+
"@opentag/client": "0.3.1",
|
|
37
|
+
"@opentag/core": "0.3.1"
|
|
38
38
|
},
|
|
39
39
|
"devDependencies": {
|
|
40
40
|
"tsup": "^8.3.5",
|