@seawork/server 1.0.18-rc.1 → 1.0.18-rc.2
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/server/client/daemon-client.d.ts +6 -1
- package/dist/server/client/daemon-client.d.ts.map +1 -1
- package/dist/server/client/daemon-client.js +12 -0
- package/dist/server/client/daemon-client.js.map +1 -1
- package/dist/server/server/bootstrap.d.ts.map +1 -1
- package/dist/server/server/bootstrap.js +10 -0
- package/dist/server/server/bootstrap.js.map +1 -1
- package/dist/server/server/daemon-config-store.js +12 -0
- package/dist/server/server/daemon-config-store.js.map +1 -1
- package/dist/server/server/git-forge/github-client.d.ts +12 -0
- package/dist/server/server/git-forge/github-client.d.ts.map +1 -0
- package/dist/server/server/git-forge/github-client.js +39 -0
- package/dist/server/server/git-forge/github-client.js.map +1 -0
- package/dist/server/server/git-forge/gitlab-client.d.ts +17 -0
- package/dist/server/server/git-forge/gitlab-client.d.ts.map +1 -0
- package/dist/server/server/git-forge/gitlab-client.js +53 -0
- package/dist/server/server/git-forge/gitlab-client.js.map +1 -0
- package/dist/server/server/git-forge/parse-remote.d.ts +23 -0
- package/dist/server/server/git-forge/parse-remote.d.ts.map +1 -0
- package/dist/server/server/git-forge/parse-remote.js +88 -0
- package/dist/server/server/git-forge/parse-remote.js.map +1 -0
- package/dist/server/server/git-forge/service.d.ts +40 -0
- package/dist/server/server/git-forge/service.d.ts.map +1 -0
- package/dist/server/server/git-forge/service.js +106 -0
- package/dist/server/server/git-forge/service.js.map +1 -0
- package/dist/server/server/git-forge/token-mask.d.ts +17 -0
- package/dist/server/server/git-forge/token-mask.d.ts.map +1 -0
- package/dist/server/server/git-forge/token-mask.js +51 -0
- package/dist/server/server/git-forge/token-mask.js.map +1 -0
- package/dist/server/server/persisted-config.d.ts +54 -0
- package/dist/server/server/persisted-config.d.ts.map +1 -1
- package/dist/server/server/persisted-config.js +21 -0
- package/dist/server/server/persisted-config.js.map +1 -1
- package/dist/server/server/session.d.ts.map +1 -1
- package/dist/server/server/session.js +98 -20
- package/dist/server/server/session.js.map +1 -1
- package/dist/server/server/websocket-server.d.ts.map +1 -1
- package/dist/server/server/websocket-server.js +2 -1
- package/dist/server/server/websocket-server.js.map +1 -1
- package/dist/server/server/worktree-session.d.ts.map +1 -1
- package/dist/server/server/worktree-session.js +17 -7
- package/dist/server/server/worktree-session.js.map +1 -1
- package/dist/server/shared/messages.d.ts +5639 -20
- package/dist/server/shared/messages.d.ts.map +1 -1
- package/dist/server/shared/messages.js +71 -0
- package/dist/server/shared/messages.js.map +1 -1
- package/package.json +3 -3
|
@@ -100,6 +100,11 @@ export class DaemonConfigStore {
|
|
|
100
100
|
}
|
|
101
101
|
function mergeMutableConfigIntoPersistedConfig(params) {
|
|
102
102
|
const { persisted, mutable } = params;
|
|
103
|
+
// gitForge tokens round-trip 1:1 between mutable runtime state and the
|
|
104
|
+
// persisted file. Empty array is preserved (means "user explicitly cleared
|
|
105
|
+
// all hosts" rather than "nothing configured yet" — the loadInitial helper
|
|
106
|
+
// distinguishes the two by checking whether the key was present at load).
|
|
107
|
+
const tokens = mutable.integrations?.gitForge?.tokens;
|
|
103
108
|
return {
|
|
104
109
|
...persisted,
|
|
105
110
|
daemon: {
|
|
@@ -109,6 +114,13 @@ function mergeMutableConfigIntoPersistedConfig(params) {
|
|
|
109
114
|
injectIntoAgents: mutable.mcp.injectIntoAgents,
|
|
110
115
|
},
|
|
111
116
|
},
|
|
117
|
+
integrations: {
|
|
118
|
+
...persisted.integrations,
|
|
119
|
+
gitForge: {
|
|
120
|
+
...persisted.integrations?.gitForge,
|
|
121
|
+
tokens: tokens ?? persisted.integrations?.gitForge?.tokens,
|
|
122
|
+
},
|
|
123
|
+
},
|
|
112
124
|
};
|
|
113
125
|
}
|
|
114
126
|
//# sourceMappingURL=daemon-config-store.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"daemon-config-store.js","sourceRoot":"","sources":["../../../src/server/daemon-config-store.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"daemon-config-store.js","sourceRoot":"","sources":["../../../src/server/daemon-config-store.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { GitForgeItem } from "../../shared/messages.js";
|
|
2
|
+
/**
|
|
3
|
+
* GitHub: `/repos/{owner}/{repo}/issues?state=open` returns both issues and
|
|
4
|
+
* PRs. Items with a `pull_request` field are PRs.
|
|
5
|
+
*/
|
|
6
|
+
export declare function fetchGithubIssuesAndPRs(input: {
|
|
7
|
+
host: string;
|
|
8
|
+
owner: string;
|
|
9
|
+
repo: string;
|
|
10
|
+
token: string;
|
|
11
|
+
}): Promise<GitForgeItem[]>;
|
|
12
|
+
//# sourceMappingURL=github-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"github-client.d.ts","sourceRoot":"","sources":["../../../../src/server/git-forge/github-client.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAe7D;;;GAGG;AACH,wBAAsB,uBAAuB,CAAC,KAAK,EAAE;IACnD,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;CACf,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC,CAkC1B"}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitHub: `/repos/{owner}/{repo}/issues?state=open` returns both issues and
|
|
3
|
+
* PRs. Items with a `pull_request` field are PRs.
|
|
4
|
+
*/
|
|
5
|
+
export async function fetchGithubIssuesAndPRs(input) {
|
|
6
|
+
// Only github.com is supported here. GitHub Enterprise would use a
|
|
7
|
+
// different base URL (`https://<host>/api/v3`); not in scope for v1.
|
|
8
|
+
if (input.host !== "github.com") {
|
|
9
|
+
throw new Error(`Unsupported GitHub host: ${input.host}`);
|
|
10
|
+
}
|
|
11
|
+
const url = `https://api.github.com/repos/${encodeURIComponent(input.owner)}/${encodeURIComponent(input.repo)}/issues?state=open&per_page=50&sort=updated&direction=desc`;
|
|
12
|
+
const res = await fetch(url, {
|
|
13
|
+
headers: {
|
|
14
|
+
Accept: "application/vnd.github+json",
|
|
15
|
+
Authorization: `Bearer ${input.token}`,
|
|
16
|
+
"X-GitHub-Api-Version": "2022-11-28",
|
|
17
|
+
},
|
|
18
|
+
});
|
|
19
|
+
if (!res.ok) {
|
|
20
|
+
throw new Error(`GitHub API ${res.status}: ${res.statusText}`);
|
|
21
|
+
}
|
|
22
|
+
const raw = (await res.json());
|
|
23
|
+
return raw.map((item) => {
|
|
24
|
+
const isPr = Boolean(item.pull_request);
|
|
25
|
+
return {
|
|
26
|
+
id: `gh:${input.owner}/${input.repo}#${item.number}`,
|
|
27
|
+
kind: isPr ? "pull_request" : "issue",
|
|
28
|
+
number: item.number,
|
|
29
|
+
title: item.title,
|
|
30
|
+
state: item.state,
|
|
31
|
+
authorLogin: item.user?.login ?? null,
|
|
32
|
+
url: item.html_url,
|
|
33
|
+
updatedAt: item.updated_at,
|
|
34
|
+
labels: item.labels.map((l) => (typeof l === "string" ? l : l.name)),
|
|
35
|
+
...(isPr ? { draft: Boolean(item.pull_request?.draft ?? item.draft) } : {}),
|
|
36
|
+
};
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
//# sourceMappingURL=github-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"github-client.js","sourceRoot":"","sources":["../../../../src/server/git-forge/github-client.ts"],"names":[],"mappings":"AAeA;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAAC,KAK7C;IACC,mEAAmE;IACnE,qEAAqE;IACrE,IAAI,KAAK,CAAC,IAAI,KAAK,YAAY,EAAE,CAAC;QAChC,MAAM,IAAI,KAAK,CAAC,4BAA4B,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC;IAC5D,CAAC;IAED,MAAM,GAAG,GAAG,gCAAgC,kBAAkB,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,kBAAkB,CAAC,KAAK,CAAC,IAAI,CAAC,4DAA4D,CAAC;IAC1K,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE;QAC3B,OAAO,EAAE;YACP,MAAM,EAAE,6BAA6B;YACrC,aAAa,EAAE,UAAU,KAAK,CAAC,KAAK,EAAE;YACtC,sBAAsB,EAAE,YAAY;SACrC;KACF,CAAC,CAAC;IACH,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CAAC,cAAc,GAAG,CAAC,MAAM,KAAK,GAAG,CAAC,UAAU,EAAE,CAAC,CAAC;IACjE,CAAC;IACD,MAAM,GAAG,GAAG,CAAC,MAAM,GAAG,CAAC,IAAI,EAAE,CAAqB,CAAC;IACnD,OAAO,GAAG,CAAC,GAAG,CAAC,CAAC,IAAI,EAAgB,EAAE;QACpC,MAAM,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC;QACxC,OAAO;YACL,EAAE,EAAE,MAAM,KAAK,CAAC,KAAK,IAAI,KAAK,CAAC,IAAI,IAAI,IAAI,CAAC,MAAM,EAAE;YACpD,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,OAAO;YACrC,MAAM,EAAE,IAAI,CAAC,MAAM;YACnB,KAAK,EAAE,IAAI,CAAC,KAAK;YACjB,KAAK,EAAE,IAAI,CAAC,KAAK;YACjB,WAAW,EAAE,IAAI,CAAC,IAAI,EAAE,KAAK,IAAI,IAAI;YACrC,GAAG,EAAE,IAAI,CAAC,QAAQ;YAClB,SAAS,EAAE,IAAI,CAAC,UAAU;YAC1B,MAAM,EAAE,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,OAAO,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC;YACpE,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,CAAC,IAAI,CAAC,YAAY,EAAE,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;SAC5E,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { GitForgeItem } from "../../shared/messages.js";
|
|
2
|
+
/**
|
|
3
|
+
* GitLab (gitlab.com or self-hosted). Two endpoints:
|
|
4
|
+
* - GET /api/v4/projects/{enc(owner/repo)}/issues?state=opened
|
|
5
|
+
* - GET /api/v4/projects/{enc(owner/repo)}/merge_requests?state=opened
|
|
6
|
+
*
|
|
7
|
+
* Tokens are sent as `Authorization: Bearer <token>` (works for both
|
|
8
|
+
* personal access tokens and project access tokens).
|
|
9
|
+
*/
|
|
10
|
+
export declare function fetchGitlabIssuesAndMRs(input: {
|
|
11
|
+
host: string;
|
|
12
|
+
owner: string;
|
|
13
|
+
repo: string;
|
|
14
|
+
token: string;
|
|
15
|
+
scheme: "http" | "https";
|
|
16
|
+
}): Promise<GitForgeItem[]>;
|
|
17
|
+
//# sourceMappingURL=gitlab-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gitlab-client.d.ts","sourceRoot":"","sources":["../../../../src/server/git-forge/gitlab-client.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAkB7D;;;;;;;GAOG;AACH,wBAAsB,uBAAuB,CAAC,KAAK,EAAE;IACnD,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC;CAC1B,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC,CAoD1B"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GitLab (gitlab.com or self-hosted). Two endpoints:
|
|
3
|
+
* - GET /api/v4/projects/{enc(owner/repo)}/issues?state=opened
|
|
4
|
+
* - GET /api/v4/projects/{enc(owner/repo)}/merge_requests?state=opened
|
|
5
|
+
*
|
|
6
|
+
* Tokens are sent as `Authorization: Bearer <token>` (works for both
|
|
7
|
+
* personal access tokens and project access tokens).
|
|
8
|
+
*/
|
|
9
|
+
export async function fetchGitlabIssuesAndMRs(input) {
|
|
10
|
+
const projectPath = encodeURIComponent(`${input.owner}/${input.repo}`);
|
|
11
|
+
const base = `${input.scheme}://${input.host}/api/v4/projects/${projectPath}`;
|
|
12
|
+
const headers = { Authorization: `Bearer ${input.token}` };
|
|
13
|
+
const [issuesRes, mrsRes] = await Promise.all([
|
|
14
|
+
fetch(`${base}/issues?state=opened&per_page=50&order_by=updated_at&sort=desc`, { headers }),
|
|
15
|
+
fetch(`${base}/merge_requests?state=opened&per_page=50&order_by=updated_at&sort=desc`, {
|
|
16
|
+
headers,
|
|
17
|
+
}),
|
|
18
|
+
]);
|
|
19
|
+
if (!issuesRes.ok) {
|
|
20
|
+
throw new Error(`GitLab API (issues) ${issuesRes.status}: ${issuesRes.statusText}`);
|
|
21
|
+
}
|
|
22
|
+
if (!mrsRes.ok) {
|
|
23
|
+
throw new Error(`GitLab API (mrs) ${mrsRes.status}: ${mrsRes.statusText}`);
|
|
24
|
+
}
|
|
25
|
+
const issues = (await issuesRes.json());
|
|
26
|
+
const mrs = (await mrsRes.json());
|
|
27
|
+
const baseId = `gl:${input.host}:${input.owner}/${input.repo}`;
|
|
28
|
+
const issueItems = issues.map((it) => ({
|
|
29
|
+
id: `${baseId}#i${it.iid}`,
|
|
30
|
+
kind: "issue",
|
|
31
|
+
number: it.iid,
|
|
32
|
+
title: it.title,
|
|
33
|
+
state: it.state,
|
|
34
|
+
authorLogin: it.author?.username ?? null,
|
|
35
|
+
url: it.web_url,
|
|
36
|
+
updatedAt: it.updated_at,
|
|
37
|
+
labels: it.labels ?? [],
|
|
38
|
+
}));
|
|
39
|
+
const mrItems = mrs.map((mr) => ({
|
|
40
|
+
id: `${baseId}#mr${mr.iid}`,
|
|
41
|
+
kind: "pull_request",
|
|
42
|
+
number: mr.iid,
|
|
43
|
+
title: mr.title,
|
|
44
|
+
state: mr.state,
|
|
45
|
+
authorLogin: mr.author?.username ?? null,
|
|
46
|
+
url: mr.web_url,
|
|
47
|
+
updatedAt: mr.updated_at,
|
|
48
|
+
labels: mr.labels ?? [],
|
|
49
|
+
draft: Boolean(mr.draft ?? mr.work_in_progress),
|
|
50
|
+
}));
|
|
51
|
+
return [...issueItems, ...mrItems];
|
|
52
|
+
}
|
|
53
|
+
//# sourceMappingURL=gitlab-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"gitlab-client.js","sourceRoot":"","sources":["../../../../src/server/git-forge/gitlab-client.ts"],"names":[],"mappings":"AAkBA;;;;;;;GAOG;AACH,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAAC,KAM7C;IACC,MAAM,WAAW,GAAG,kBAAkB,CAAC,GAAG,KAAK,CAAC,KAAK,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC;IACvE,MAAM,IAAI,GAAG,GAAG,KAAK,CAAC,MAAM,MAAM,KAAK,CAAC,IAAI,oBAAoB,WAAW,EAAE,CAAC;IAC9E,MAAM,OAAO,GAAG,EAAE,aAAa,EAAE,UAAU,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;IAE3D,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;QAC5C,KAAK,CAAC,GAAG,IAAI,gEAAgE,EAAE,EAAE,OAAO,EAAE,CAAC;QAC3F,KAAK,CAAC,GAAG,IAAI,wEAAwE,EAAE;YACrF,OAAO;SACR,CAAC;KACH,CAAC,CAAC;IACH,IAAI,CAAC,SAAS,CAAC,EAAE,EAAE,CAAC;QAClB,MAAM,IAAI,KAAK,CAAC,uBAAuB,SAAS,CAAC,MAAM,KAAK,SAAS,CAAC,UAAU,EAAE,CAAC,CAAC;IACtF,CAAC;IACD,IAAI,CAAC,MAAM,CAAC,EAAE,EAAE,CAAC;QACf,MAAM,IAAI,KAAK,CAAC,oBAAoB,MAAM,CAAC,MAAM,KAAK,MAAM,CAAC,UAAU,EAAE,CAAC,CAAC;IAC7E,CAAC;IACD,MAAM,MAAM,GAAG,CAAC,MAAM,SAAS,CAAC,IAAI,EAAE,CAAqB,CAAC;IAC5D,MAAM,GAAG,GAAG,CAAC,MAAM,MAAM,CAAC,IAAI,EAAE,CAAkB,CAAC;IAEnD,MAAM,MAAM,GAAG,MAAM,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,KAAK,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC;IAE/D,MAAM,UAAU,GAAG,MAAM,CAAC,GAAG,CAC3B,CAAC,EAAE,EAAgB,EAAE,CAAC,CAAC;QACrB,EAAE,EAAE,GAAG,MAAM,KAAK,EAAE,CAAC,GAAG,EAAE;QAC1B,IAAI,EAAE,OAAO;QACb,MAAM,EAAE,EAAE,CAAC,GAAG;QACd,KAAK,EAAE,EAAE,CAAC,KAAK;QACf,KAAK,EAAE,EAAE,CAAC,KAAK;QACf,WAAW,EAAE,EAAE,CAAC,MAAM,EAAE,QAAQ,IAAI,IAAI;QACxC,GAAG,EAAE,EAAE,CAAC,OAAO;QACf,SAAS,EAAE,EAAE,CAAC,UAAU;QACxB,MAAM,EAAE,EAAE,CAAC,MAAM,IAAI,EAAE;KACxB,CAAC,CACH,CAAC;IAEF,MAAM,OAAO,GAAG,GAAG,CAAC,GAAG,CACrB,CAAC,EAAE,EAAgB,EAAE,CAAC,CAAC;QACrB,EAAE,EAAE,GAAG,MAAM,MAAM,EAAE,CAAC,GAAG,EAAE;QAC3B,IAAI,EAAE,cAAc;QACpB,MAAM,EAAE,EAAE,CAAC,GAAG;QACd,KAAK,EAAE,EAAE,CAAC,KAAK;QACf,KAAK,EAAE,EAAE,CAAC,KAAK;QACf,WAAW,EAAE,EAAE,CAAC,MAAM,EAAE,QAAQ,IAAI,IAAI;QACxC,GAAG,EAAE,EAAE,CAAC,OAAO;QACf,SAAS,EAAE,EAAE,CAAC,UAAU;QACxB,MAAM,EAAE,EAAE,CAAC,MAAM,IAAI,EAAE;QACvB,KAAK,EAAE,OAAO,CAAC,EAAE,CAAC,KAAK,IAAI,EAAE,CAAC,gBAAgB,CAAC;KAChD,CAAC,CACH,CAAC;IAEF,OAAO,CAAC,GAAG,UAAU,EAAE,GAAG,OAAO,CAAC,CAAC;AACrC,CAAC"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
export type ParsedRemote = {
|
|
2
|
+
host: string;
|
|
3
|
+
owner: string;
|
|
4
|
+
repo: string;
|
|
5
|
+
scheme: "http" | "https";
|
|
6
|
+
};
|
|
7
|
+
/**
|
|
8
|
+
* Parses a git origin URL into host/owner/repo. Three forms:
|
|
9
|
+
* 1. URL form with scheme (ssh://, https://, http://, git://) — uses URL().
|
|
10
|
+
* For HTTP(S), `host` keeps the port (self-hosted GitLab on :8443 etc.)
|
|
11
|
+
* so the same value can identify the API endpoint AND look up the token.
|
|
12
|
+
* For SSH/git, the port is meaningless to the HTTPS API so we strip it.
|
|
13
|
+
* 2. scp-like form `[user@]host:path` (no scheme, no port) — common for
|
|
14
|
+
* `git@github.com:owner/repo.git`.
|
|
15
|
+
* 3. Anything else → null.
|
|
16
|
+
*
|
|
17
|
+
* `repo` may contain `/` for GitLab subgroups; `owner` is always the top group.
|
|
18
|
+
* Trailing `.git` and trailing slashes are stripped.
|
|
19
|
+
*/
|
|
20
|
+
export declare function parseGitRemoteUrl(url: string): ParsedRemote | null;
|
|
21
|
+
export declare function getOriginRemoteUrl(cwd: string): Promise<string | null>;
|
|
22
|
+
export declare function resolveOriginRemote(cwd: string): Promise<ParsedRemote | null>;
|
|
23
|
+
//# sourceMappingURL=parse-remote.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parse-remote.d.ts","sourceRoot":"","sources":["../../../../src/server/git-forge/parse-remote.ts"],"names":[],"mappings":"AAKA,MAAM,MAAM,YAAY,GAAG;IACzB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IAKb,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC;CAC1B,CAAC;AAEF;;;;;;;;;;;;GAYG;AACH,wBAAgB,iBAAiB,CAAC,GAAG,EAAE,MAAM,GAAG,YAAY,GAAG,IAAI,CAkClE;AAoBD,wBAAsB,kBAAkB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAW5E;AAED,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,GAAG,IAAI,CAAC,CAInF"}
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
import { exec } from "node:child_process";
|
|
2
|
+
import { promisify } from "node:util";
|
|
3
|
+
const execAsync = promisify(exec);
|
|
4
|
+
/**
|
|
5
|
+
* Parses a git origin URL into host/owner/repo. Three forms:
|
|
6
|
+
* 1. URL form with scheme (ssh://, https://, http://, git://) — uses URL().
|
|
7
|
+
* For HTTP(S), `host` keeps the port (self-hosted GitLab on :8443 etc.)
|
|
8
|
+
* so the same value can identify the API endpoint AND look up the token.
|
|
9
|
+
* For SSH/git, the port is meaningless to the HTTPS API so we strip it.
|
|
10
|
+
* 2. scp-like form `[user@]host:path` (no scheme, no port) — common for
|
|
11
|
+
* `git@github.com:owner/repo.git`.
|
|
12
|
+
* 3. Anything else → null.
|
|
13
|
+
*
|
|
14
|
+
* `repo` may contain `/` for GitLab subgroups; `owner` is always the top group.
|
|
15
|
+
* Trailing `.git` and trailing slashes are stripped.
|
|
16
|
+
*/
|
|
17
|
+
export function parseGitRemoteUrl(url) {
|
|
18
|
+
const trimmed = url.trim();
|
|
19
|
+
if (!trimmed)
|
|
20
|
+
return null;
|
|
21
|
+
// URL form: must start with a recognized scheme://
|
|
22
|
+
if (/^[a-z][a-z0-9+.-]*:\/\//i.test(trimmed)) {
|
|
23
|
+
try {
|
|
24
|
+
const parsed = new URL(trimmed);
|
|
25
|
+
const scheme = parsed.protocol.replace(/:$/, "").toLowerCase();
|
|
26
|
+
if (!["ssh", "https", "http", "git"].includes(scheme))
|
|
27
|
+
return null;
|
|
28
|
+
const isHttp = scheme === "http" || scheme === "https";
|
|
29
|
+
// hostname strips port; host keeps it. For HTTP(S) we need the port to
|
|
30
|
+
// reach self-hosted forges on non-standard ports. SSH ports never apply
|
|
31
|
+
// to the HTTPS API so we always drop them.
|
|
32
|
+
const host = isHttp ? parsed.host : parsed.hostname;
|
|
33
|
+
if (!host)
|
|
34
|
+
return null;
|
|
35
|
+
// Plain HTTP only when the remote is *explicitly* HTTP (self-hosted
|
|
36
|
+
// GitLab on internal networks). SSH/git remotes have no protocol info
|
|
37
|
+
// and assume HTTPS for the API.
|
|
38
|
+
const apiScheme = scheme === "http" ? "http" : "https";
|
|
39
|
+
return splitOwnerRepo(host, parsed.pathname, apiScheme);
|
|
40
|
+
}
|
|
41
|
+
catch {
|
|
42
|
+
return null;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
// scp-like form: [user@]host:path. No scheme, port not allowed (would
|
|
46
|
+
// require ssh:// to disambiguate from a path component).
|
|
47
|
+
const scp = trimmed.match(/^(?:[^@\s:]+@)?([^:\s]+):([^\s]+)$/);
|
|
48
|
+
if (scp) {
|
|
49
|
+
return splitOwnerRepo(scp[1], scp[2], "https");
|
|
50
|
+
}
|
|
51
|
+
return null;
|
|
52
|
+
}
|
|
53
|
+
function splitOwnerRepo(host, rawPath, scheme) {
|
|
54
|
+
const path = rawPath
|
|
55
|
+
.replace(/^\/+/, "")
|
|
56
|
+
.replace(/\/+$/, "")
|
|
57
|
+
.replace(/\.git$/, "");
|
|
58
|
+
if (!path)
|
|
59
|
+
return null;
|
|
60
|
+
const segments = path.split("/");
|
|
61
|
+
if (segments.length < 2)
|
|
62
|
+
return null;
|
|
63
|
+
const owner = segments[0];
|
|
64
|
+
const repo = segments.slice(1).join("/");
|
|
65
|
+
if (!owner || !repo)
|
|
66
|
+
return null;
|
|
67
|
+
return { host, owner, repo, scheme };
|
|
68
|
+
}
|
|
69
|
+
export async function getOriginRemoteUrl(cwd) {
|
|
70
|
+
try {
|
|
71
|
+
const { stdout } = await execAsync("git remote get-url origin", {
|
|
72
|
+
cwd,
|
|
73
|
+
timeout: 5000,
|
|
74
|
+
});
|
|
75
|
+
const value = stdout.trim();
|
|
76
|
+
return value.length > 0 ? value : null;
|
|
77
|
+
}
|
|
78
|
+
catch {
|
|
79
|
+
return null;
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
export async function resolveOriginRemote(cwd) {
|
|
83
|
+
const url = await getOriginRemoteUrl(cwd);
|
|
84
|
+
if (!url)
|
|
85
|
+
return null;
|
|
86
|
+
return parseGitRemoteUrl(url);
|
|
87
|
+
}
|
|
88
|
+
//# sourceMappingURL=parse-remote.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parse-remote.js","sourceRoot":"","sources":["../../../../src/server/git-forge/parse-remote.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { GitForgeItem, GitForgeRepoInfo } from "../../shared/messages.js";
|
|
2
|
+
import type { DaemonConfigStore } from "../daemon-config-store.js";
|
|
3
|
+
import type { WorkspaceRegistry } from "../workspace-registry.js";
|
|
4
|
+
type FetchInput = {
|
|
5
|
+
workspaceId?: string;
|
|
6
|
+
cwd?: string;
|
|
7
|
+
};
|
|
8
|
+
export type FetchGitForgeIssuesResult = {
|
|
9
|
+
ok: true;
|
|
10
|
+
repo: GitForgeRepoInfo;
|
|
11
|
+
items: GitForgeItem[];
|
|
12
|
+
fetchedAt: string;
|
|
13
|
+
} | {
|
|
14
|
+
ok: false;
|
|
15
|
+
reason: "no-workspace" | "no-remote" | "no-token" | "unsupported-host" | "api-error";
|
|
16
|
+
host?: string;
|
|
17
|
+
message?: string;
|
|
18
|
+
};
|
|
19
|
+
export interface GitForgeServiceDeps {
|
|
20
|
+
configStore: DaemonConfigStore;
|
|
21
|
+
workspaceRegistry: WorkspaceRegistry;
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Two-pass lookup:
|
|
25
|
+
* 1. Case-insensitive exact match (so `host:port` tokens still target a
|
|
26
|
+
* single port if the user configured one, regardless of casing).
|
|
27
|
+
* 2. Bare-hostname fallback — only against tokens stored *without* a port.
|
|
28
|
+
* This preserves the "port-specific token only matches that port"
|
|
29
|
+
* guarantee: if the user has `gitlab.example.com:8443`, it must NOT
|
|
30
|
+
* leak to a request for `gitlab.example.com:9443` or bare host.
|
|
31
|
+
*
|
|
32
|
+
* Exported for unit testing; production callers use `pickToken`.
|
|
33
|
+
*/
|
|
34
|
+
export declare function findTokenForHost(tokens: ReadonlyArray<{
|
|
35
|
+
host: string;
|
|
36
|
+
token: string;
|
|
37
|
+
}>, host: string): string | null;
|
|
38
|
+
export declare function fetchGitForgeIssues(input: FetchInput, deps: GitForgeServiceDeps): Promise<FetchGitForgeIssuesResult>;
|
|
39
|
+
export {};
|
|
40
|
+
//# sourceMappingURL=service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"service.d.ts","sourceRoot":"","sources":["../../../../src/server/git-forge/service.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC/E,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AACnE,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAKlE,KAAK,UAAU,GAAG;IAAE,WAAW,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC;AAEzD,MAAM,MAAM,yBAAyB,GACjC;IACE,EAAE,EAAE,IAAI,CAAC;IACT,IAAI,EAAE,gBAAgB,CAAC;IACvB,KAAK,EAAE,YAAY,EAAE,CAAC;IACtB,SAAS,EAAE,MAAM,CAAC;CACnB,GACD;IACE,EAAE,EAAE,KAAK,CAAC;IACV,MAAM,EAAE,cAAc,GAAG,WAAW,GAAG,UAAU,GAAG,kBAAkB,GAAG,WAAW,CAAC;IACrF,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB,CAAC;AAEN,MAAM,WAAW,mBAAmB;IAClC,WAAW,EAAE,iBAAiB,CAAC;IAC/B,iBAAiB,EAAE,iBAAiB,CAAC;CACtC;AAqBD;;;;;;;;;;GAUG;AACH,wBAAgB,gBAAgB,CAC9B,MAAM,EAAE,aAAa,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CAAC,EACtD,IAAI,EAAE,MAAM,GACX,MAAM,GAAG,IAAI,CAOf;AAgCD,wBAAsB,mBAAmB,CACvC,KAAK,EAAE,UAAU,EACjB,IAAI,EAAE,mBAAmB,GACxB,OAAO,CAAC,yBAAyB,CAAC,CA4CpC"}
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import { fetchGithubIssuesAndPRs } from "./github-client.js";
|
|
2
|
+
import { fetchGitlabIssuesAndMRs } from "./gitlab-client.js";
|
|
3
|
+
import { resolveOriginRemote } from "./parse-remote.js";
|
|
4
|
+
async function resolveCwd(input, workspaceRegistry) {
|
|
5
|
+
if (input.cwd && input.cwd.trim().length > 0)
|
|
6
|
+
return input.cwd;
|
|
7
|
+
if (!input.workspaceId)
|
|
8
|
+
return null;
|
|
9
|
+
const record = await workspaceRegistry.get(input.workspaceId);
|
|
10
|
+
return record?.cwd ?? null;
|
|
11
|
+
}
|
|
12
|
+
/** Strip port + lowercase. Used for the bare-hostname fallback below. */
|
|
13
|
+
function normalizeHostKey(host) {
|
|
14
|
+
return host.replace(/:\d+$/, "").toLowerCase();
|
|
15
|
+
}
|
|
16
|
+
function hasExplicitPort(host) {
|
|
17
|
+
return /:\d+$/.test(host);
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Two-pass lookup:
|
|
21
|
+
* 1. Case-insensitive exact match (so `host:port` tokens still target a
|
|
22
|
+
* single port if the user configured one, regardless of casing).
|
|
23
|
+
* 2. Bare-hostname fallback — only against tokens stored *without* a port.
|
|
24
|
+
* This preserves the "port-specific token only matches that port"
|
|
25
|
+
* guarantee: if the user has `gitlab.example.com:8443`, it must NOT
|
|
26
|
+
* leak to a request for `gitlab.example.com:9443` or bare host.
|
|
27
|
+
*
|
|
28
|
+
* Exported for unit testing; production callers use `pickToken`.
|
|
29
|
+
*/
|
|
30
|
+
export function findTokenForHost(tokens, host) {
|
|
31
|
+
const lowerHost = host.toLowerCase();
|
|
32
|
+
const exact = tokens.find((t) => t.host.toLowerCase() === lowerHost);
|
|
33
|
+
if (exact)
|
|
34
|
+
return exact.token;
|
|
35
|
+
const bare = normalizeHostKey(host);
|
|
36
|
+
const fuzzy = tokens.find((t) => !hasExplicitPort(t.host) && t.host.toLowerCase() === bare);
|
|
37
|
+
return fuzzy?.token ?? null;
|
|
38
|
+
}
|
|
39
|
+
function pickToken(store, host) {
|
|
40
|
+
const tokens = store.get().integrations?.gitForge?.tokens ?? [];
|
|
41
|
+
return findTokenForHost(tokens, host);
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Public SaaS forges we don't (yet) support. Returning `unsupported-host`
|
|
45
|
+
* early — before asking for a token — avoids the misleading flow where users
|
|
46
|
+
* configure a Bitbucket token and then hit a confusing GitLab API 404.
|
|
47
|
+
*
|
|
48
|
+
* We deliberately match only canonical SaaS hostnames (no prefix patterns):
|
|
49
|
+
* a self-hosted GitLab whose DNS happens to be `bitbucket.example.com` should
|
|
50
|
+
* still fall through to the GitLab path. Users on self-hosted Gitea/Bitbucket
|
|
51
|
+
* will hit a clear API error from the GitLab call rather than be silently
|
|
52
|
+
* blocked here.
|
|
53
|
+
*/
|
|
54
|
+
const UNSUPPORTED_PUBLIC_HOSTS = new Set([
|
|
55
|
+
"bitbucket.org",
|
|
56
|
+
"gitea.com",
|
|
57
|
+
"gitea.io",
|
|
58
|
+
"codeberg.org",
|
|
59
|
+
"git.sr.ht",
|
|
60
|
+
// SourceForge's actual git clone host (sourceforge.net is the web origin).
|
|
61
|
+
"git.code.sf.net",
|
|
62
|
+
]);
|
|
63
|
+
function isExplicitlyUnsupported(host) {
|
|
64
|
+
return UNSUPPORTED_PUBLIC_HOSTS.has(normalizeHostKey(host));
|
|
65
|
+
}
|
|
66
|
+
export async function fetchGitForgeIssues(input, deps) {
|
|
67
|
+
const cwd = await resolveCwd(input, deps.workspaceRegistry);
|
|
68
|
+
if (!cwd)
|
|
69
|
+
return { ok: false, reason: "no-workspace" };
|
|
70
|
+
const remote = await resolveOriginRemote(cwd);
|
|
71
|
+
if (!remote)
|
|
72
|
+
return { ok: false, reason: "no-remote" };
|
|
73
|
+
if (isExplicitlyUnsupported(remote.host)) {
|
|
74
|
+
return { ok: false, reason: "unsupported-host", host: remote.host };
|
|
75
|
+
}
|
|
76
|
+
const token = pickToken(deps.configStore, remote.host);
|
|
77
|
+
if (!token)
|
|
78
|
+
return { ok: false, reason: "no-token", host: remote.host };
|
|
79
|
+
const provider = remote.host === "github.com" ? "github" : "gitlab";
|
|
80
|
+
try {
|
|
81
|
+
const items = provider === "github"
|
|
82
|
+
? await fetchGithubIssuesAndPRs({ ...remote, token })
|
|
83
|
+
: await fetchGitlabIssuesAndMRs({ ...remote, token });
|
|
84
|
+
// GitHub is SaaS-only (always https). For GitLab the web URL must match
|
|
85
|
+
// the actual scheme — self-hosted on plain http would otherwise emit
|
|
86
|
+
// dead https links the user can't open.
|
|
87
|
+
const webUrl = provider === "github"
|
|
88
|
+
? `https://github.com/${remote.owner}/${remote.repo}`
|
|
89
|
+
: `${remote.scheme}://${remote.host}/${remote.owner}/${remote.repo}`;
|
|
90
|
+
return {
|
|
91
|
+
ok: true,
|
|
92
|
+
repo: { host: remote.host, owner: remote.owner, repo: remote.repo, webUrl },
|
|
93
|
+
items,
|
|
94
|
+
fetchedAt: new Date().toISOString(),
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
catch (err) {
|
|
98
|
+
return {
|
|
99
|
+
ok: false,
|
|
100
|
+
reason: "api-error",
|
|
101
|
+
host: remote.host,
|
|
102
|
+
message: err instanceof Error ? err.message : String(err),
|
|
103
|
+
};
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
//# sourceMappingURL=service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"service.js","sourceRoot":"","sources":["../../../../src/server/git-forge/service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { type MutableDaemonConfig, type MutableDaemonConfigPatch } from "../../shared/messages.js";
|
|
2
|
+
/**
|
|
3
|
+
* Returns a copy of the daemon config with all gitForge tokens replaced by a
|
|
4
|
+
* sentinel string before broadcasting to clients. Plain tokens never leave
|
|
5
|
+
* the daemon over WebSocket.
|
|
6
|
+
*/
|
|
7
|
+
export declare function redactGitForgeTokens(config: MutableDaemonConfig): MutableDaemonConfig;
|
|
8
|
+
/**
|
|
9
|
+
* When applying a patch from a client, entries whose token equals the
|
|
10
|
+
* sentinel are kept as-is on the server (the client is round-tripping a
|
|
11
|
+
* masked entry). Other entries replace existing values.
|
|
12
|
+
*/
|
|
13
|
+
export declare function rehydratePatchTokens(input: {
|
|
14
|
+
patch: MutableDaemonConfigPatch;
|
|
15
|
+
current: MutableDaemonConfig;
|
|
16
|
+
}): MutableDaemonConfigPatch;
|
|
17
|
+
//# sourceMappingURL=token-mask.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"token-mask.d.ts","sourceRoot":"","sources":["../../../../src/server/git-forge/token-mask.ts"],"names":[],"mappings":"AAAA,OAAO,EAGL,KAAK,mBAAmB,EACxB,KAAK,wBAAwB,EAC9B,MAAM,0BAA0B,CAAC;AAElC;;;;GAIG;AACH,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,mBAAmB,GAAG,mBAAmB,CAarF;AAED;;;;GAIG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,EAAE;IAC1C,KAAK,EAAE,wBAAwB,CAAC;IAChC,OAAO,EAAE,mBAAmB,CAAC;CAC9B,GAAG,wBAAwB,CAyB3B"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { GIT_FORGE_TOKEN_REDACTED, } from "../../shared/messages.js";
|
|
2
|
+
/**
|
|
3
|
+
* Returns a copy of the daemon config with all gitForge tokens replaced by a
|
|
4
|
+
* sentinel string before broadcasting to clients. Plain tokens never leave
|
|
5
|
+
* the daemon over WebSocket.
|
|
6
|
+
*/
|
|
7
|
+
export function redactGitForgeTokens(config) {
|
|
8
|
+
const tokens = config.integrations?.gitForge?.tokens;
|
|
9
|
+
if (!tokens || tokens.length === 0)
|
|
10
|
+
return config;
|
|
11
|
+
return {
|
|
12
|
+
...config,
|
|
13
|
+
integrations: {
|
|
14
|
+
...config.integrations,
|
|
15
|
+
gitForge: {
|
|
16
|
+
...config.integrations?.gitForge,
|
|
17
|
+
tokens: tokens.map((t) => ({ host: t.host, token: GIT_FORGE_TOKEN_REDACTED })),
|
|
18
|
+
},
|
|
19
|
+
},
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* When applying a patch from a client, entries whose token equals the
|
|
24
|
+
* sentinel are kept as-is on the server (the client is round-tripping a
|
|
25
|
+
* masked entry). Other entries replace existing values.
|
|
26
|
+
*/
|
|
27
|
+
export function rehydratePatchTokens(input) {
|
|
28
|
+
const incoming = input.patch.integrations?.gitForge?.tokens;
|
|
29
|
+
if (!incoming)
|
|
30
|
+
return input.patch;
|
|
31
|
+
const existing = input.current.integrations?.gitForge?.tokens ?? [];
|
|
32
|
+
const existingByHost = new Map(existing.map((t) => [t.host, t.token]));
|
|
33
|
+
const rehydrated = incoming.map((entry) => {
|
|
34
|
+
if (entry.token === GIT_FORGE_TOKEN_REDACTED) {
|
|
35
|
+
const real = existingByHost.get(entry.host);
|
|
36
|
+
return { host: entry.host, token: real ?? "" };
|
|
37
|
+
}
|
|
38
|
+
return entry;
|
|
39
|
+
});
|
|
40
|
+
return {
|
|
41
|
+
...input.patch,
|
|
42
|
+
integrations: {
|
|
43
|
+
...input.patch.integrations,
|
|
44
|
+
gitForge: {
|
|
45
|
+
...input.patch.integrations?.gitForge,
|
|
46
|
+
tokens: rehydrated,
|
|
47
|
+
},
|
|
48
|
+
},
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=token-mask.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"token-mask.js","sourceRoot":"","sources":["../../../../src/server/git-forge/token-mask.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,wBAAwB,GAIzB,MAAM,0BAA0B,CAAC;AAElC;;;;GAIG;AACH,MAAM,UAAU,oBAAoB,CAAC,MAA2B;IAC9D,MAAM,MAAM,GAAG,MAAM,CAAC,YAAY,EAAE,QAAQ,EAAE,MAAM,CAAC;IACrD,IAAI,CAAC,MAAM,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,MAAM,CAAC;IAClD,OAAO;QACL,GAAG,MAAM;QACT,YAAY,EAAE;YACZ,GAAG,MAAM,CAAC,YAAY;YACtB,QAAQ,EAAE;gBACR,GAAG,MAAM,CAAC,YAAY,EAAE,QAAQ;gBAChC,MAAM,EAAE,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,wBAAwB,EAAE,CAAC,CAAC;aAC/E;SACF;KACF,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,oBAAoB,CAAC,KAGpC;IACC,MAAM,QAAQ,GAAG,KAAK,CAAC,KAAK,CAAC,YAAY,EAAE,QAAQ,EAAE,MAAM,CAAC;IAC5D,IAAI,CAAC,QAAQ;QAAE,OAAO,KAAK,CAAC,KAAK,CAAC;IAElC,MAAM,QAAQ,GAAyB,KAAK,CAAC,OAAO,CAAC,YAAY,EAAE,QAAQ,EAAE,MAAM,IAAI,EAAE,CAAC;IAC1F,MAAM,cAAc,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;IAEvE,MAAM,UAAU,GAAyB,QAAQ,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE;QAC9D,IAAI,KAAK,CAAC,KAAK,KAAK,wBAAwB,EAAE,CAAC;YAC7C,MAAM,IAAI,GAAG,cAAc,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;YAC5C,OAAO,EAAE,IAAI,EAAE,KAAK,CAAC,IAAI,EAAE,KAAK,EAAE,IAAI,IAAI,EAAE,EAAE,CAAC;QACjD,CAAC;QACD,OAAO,KAAK,CAAC;IACf,CAAC,CAAC,CAAC;IAEH,OAAO;QACL,GAAG,KAAK,CAAC,KAAK;QACd,YAAY,EAAE;YACZ,GAAG,KAAK,CAAC,KAAK,CAAC,YAAY;YAC3B,QAAQ,EAAE;gBACR,GAAG,KAAK,CAAC,KAAK,CAAC,YAAY,EAAE,QAAQ;gBACrC,MAAM,EAAE,UAAU;aACnB;SACF;KACF,CAAC;AACJ,CAAC"}
|
|
@@ -513,6 +513,44 @@ export declare const PersistedConfigSchema: z.ZodObject<{
|
|
|
513
513
|
level?: "error" | "info" | "fatal" | "warn" | "debug" | "trace" | undefined;
|
|
514
514
|
} | undefined;
|
|
515
515
|
}>>;
|
|
516
|
+
integrations: z.ZodOptional<z.ZodObject<{
|
|
517
|
+
gitForge: z.ZodOptional<z.ZodObject<{
|
|
518
|
+
tokens: z.ZodOptional<z.ZodArray<z.ZodObject<{
|
|
519
|
+
host: z.ZodString;
|
|
520
|
+
token: z.ZodString;
|
|
521
|
+
}, "strip", z.ZodTypeAny, {
|
|
522
|
+
host: string;
|
|
523
|
+
token: string;
|
|
524
|
+
}, {
|
|
525
|
+
host: string;
|
|
526
|
+
token: string;
|
|
527
|
+
}>, "many">>;
|
|
528
|
+
}, "strict", z.ZodTypeAny, {
|
|
529
|
+
tokens?: {
|
|
530
|
+
host: string;
|
|
531
|
+
token: string;
|
|
532
|
+
}[] | undefined;
|
|
533
|
+
}, {
|
|
534
|
+
tokens?: {
|
|
535
|
+
host: string;
|
|
536
|
+
token: string;
|
|
537
|
+
}[] | undefined;
|
|
538
|
+
}>>;
|
|
539
|
+
}, "strict", z.ZodTypeAny, {
|
|
540
|
+
gitForge?: {
|
|
541
|
+
tokens?: {
|
|
542
|
+
host: string;
|
|
543
|
+
token: string;
|
|
544
|
+
}[] | undefined;
|
|
545
|
+
} | undefined;
|
|
546
|
+
}, {
|
|
547
|
+
gitForge?: {
|
|
548
|
+
tokens?: {
|
|
549
|
+
host: string;
|
|
550
|
+
token: string;
|
|
551
|
+
}[] | undefined;
|
|
552
|
+
} | undefined;
|
|
553
|
+
}>>;
|
|
516
554
|
}, "strict", z.ZodTypeAny, {
|
|
517
555
|
features?: {
|
|
518
556
|
dictation?: {
|
|
@@ -550,6 +588,14 @@ export declare const PersistedConfigSchema: z.ZodObject<{
|
|
|
550
588
|
} | undefined;
|
|
551
589
|
} | undefined;
|
|
552
590
|
} | undefined;
|
|
591
|
+
integrations?: {
|
|
592
|
+
gitForge?: {
|
|
593
|
+
tokens?: {
|
|
594
|
+
host: string;
|
|
595
|
+
token: string;
|
|
596
|
+
}[] | undefined;
|
|
597
|
+
} | undefined;
|
|
598
|
+
} | undefined;
|
|
553
599
|
agents?: {
|
|
554
600
|
models?: unknown;
|
|
555
601
|
providers?: Record<string, {
|
|
@@ -648,6 +694,14 @@ export declare const PersistedConfigSchema: z.ZodObject<{
|
|
|
648
694
|
} | undefined;
|
|
649
695
|
} | undefined;
|
|
650
696
|
} | undefined;
|
|
697
|
+
integrations?: {
|
|
698
|
+
gitForge?: {
|
|
699
|
+
tokens?: {
|
|
700
|
+
host: string;
|
|
701
|
+
token: string;
|
|
702
|
+
}[] | undefined;
|
|
703
|
+
} | undefined;
|
|
704
|
+
} | undefined;
|
|
651
705
|
agents?: {
|
|
652
706
|
models?: unknown;
|
|
653
707
|
providers?: Record<string, {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"persisted-config.d.ts","sourceRoot":"","sources":["../../../src/server/persisted-config.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAKxB,QAAA,MAAM,qBAAqB;;;;;;;;;;;;;;;EAOhB,CAAC;AAEZ,MAAM,MAAM,eAAe,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,qBAAqB,CAAC,CAAC;AAEpE,eAAO,MAAM,sBAAsB;;;;;;;;;;;;;;;YAAgE,CAAC;AAEpG,MAAM,MAAM,sBAAsB,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,sBAAsB,CAAC,CAAC;AA+H5E,eAAO,MAAM,qBAAqB
|
|
1
|
+
{"version":3,"file":"persisted-config.d.ts","sourceRoot":"","sources":["../../../src/server/persisted-config.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAKxB,QAAA,MAAM,qBAAqB;;;;;;;;;;;;;;;EAOhB,CAAC;AAEZ,MAAM,MAAM,eAAe,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,qBAAqB,CAAC,CAAC;AAEpE,eAAO,MAAM,sBAAsB;;;;;;;;;;;;;;;YAAgE,CAAC;AAEpG,MAAM,MAAM,sBAAsB,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,sBAAsB,CAAC,CAAC;AA+H5E,eAAO,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAqFvB,CAAC;AAEZ,KAAK,kBAAkB,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,qBAAqB,CAAC,CAAC;AAOhE,MAAM,MAAM,eAAe,GAAG,IAAI,CAAC,kBAAkB,EAAE,QAAQ,CAAC,GAAG;IACjE,MAAM,CAAC,EAAE;QACP,SAAS,CAAC,EAAE,WAAW,CAAC,kBAAkB,CAAC,QAAQ,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC;QACnE,MAAM,CAAC,EAAE,sBAAsB,CAAC;KACjC,CAAC;CACH,CAAC;AAiCF,KAAK,UAAU,GAAG;IAChB,KAAK,CAAC,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,UAAU,CAAC;IACrD,IAAI,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;IAC3B,IAAI,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;CAC5B,CAAC;AAuNF,wBAAgB,mBAAmB,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,UAAU,GAAG,eAAe,CAsB7F;AAED;;;;;;;;GAQG;AACH,wBAAgB,sBAAsB,CAAC,WAAW,EAAE,MAAM,GAAG,eAAe,GAAG,IAAI,CAMlF;AAED,wBAAgB,mBAAmB,CACjC,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,eAAe,EACvB,MAAM,CAAC,EAAE,UAAU,GAClB,IAAI,CA6CN"}
|