@getpaseo/server 0.1.101 → 0.1.102-beta.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/scripts/supervisor.js +26 -8
- package/dist/server/server/agent/activity-curator.d.ts +17 -0
- package/dist/server/server/agent/activity-curator.js +101 -24
- package/dist/server/server/agent/agent-manager.js +5 -1
- package/dist/server/server/agent/agent-sdk-types.d.ts +7 -2
- package/dist/server/server/agent/provider-snapshot-manager.d.ts +8 -1
- package/dist/server/server/agent/provider-snapshot-manager.js +78 -33
- package/dist/server/server/agent/providers/acp-agent.d.ts +7 -0
- package/dist/server/server/agent/providers/acp-agent.js +8 -1
- package/dist/server/server/agent/providers/claude/agent.js +51 -14
- package/dist/server/server/agent/providers/claude/query.d.ts +3 -0
- package/dist/server/server/agent/providers/claude/query.js +4 -2
- package/dist/server/server/agent/providers/mock-load-test-agent.js +8 -0
- package/dist/server/server/agent/providers/opencode/paths.d.ts +2 -0
- package/dist/server/server/agent/providers/opencode/paths.js +7 -0
- package/dist/server/server/agent/providers/opencode/server-manager.d.ts +2 -0
- package/dist/server/server/agent/providers/opencode/server-manager.js +34 -5
- package/dist/server/server/agent/providers/opencode-agent.d.ts +4 -0
- package/dist/server/server/agent/providers/opencode-agent.js +14 -2
- package/dist/server/server/agent/providers/pi/agent.d.ts +3 -0
- package/dist/server/server/agent/providers/pi/agent.js +9 -3
- package/dist/server/server/agent/providers/provider-image-output.js +11 -6
- package/dist/server/server/agent/tools/paseo-tools.d.ts +1 -1
- package/dist/server/server/agent/tools/paseo-tools.js +0 -2
- package/dist/server/server/bootstrap.d.ts +7 -1
- package/dist/server/server/bootstrap.js +18 -0
- package/dist/server/server/config.d.ts +2 -0
- package/dist/server/server/config.js +57 -1
- package/dist/server/server/daemon-worker.js +19 -7
- package/dist/server/server/lifecycle-reasons.d.ts +4 -0
- package/dist/server/server/lifecycle-reasons.js +6 -0
- package/dist/server/server/persisted-config.d.ts +7 -0
- package/dist/server/server/persisted-config.js +8 -0
- package/dist/server/server/process-diagnostics.d.ts +17 -0
- package/dist/server/server/process-diagnostics.js +22 -0
- package/dist/server/server/relay-transport.js +1 -0
- package/dist/server/server/resolve-worktree-creation-intent.js +3 -1
- package/dist/server/server/session/daemon/daemon-self-update-session-controller.d.ts +32 -0
- package/dist/server/server/session/daemon/daemon-self-update-session-controller.js +88 -0
- package/dist/server/server/session/daemon/daemon-self-updater.d.ts +32 -0
- package/dist/server/server/session/daemon/daemon-self-updater.js +56 -0
- package/dist/server/server/session/daemon/daemon-session.d.ts +12 -0
- package/dist/server/server/session/daemon/daemon-session.js +12 -0
- package/dist/server/server/session/daemon/diagnostics.js +10 -0
- package/dist/server/server/session/daemon/install-origin.d.ts +7 -0
- package/dist/server/server/session/daemon/install-origin.js +64 -0
- package/dist/server/server/session/daemon/npm-global-cli.d.ts +29 -0
- package/dist/server/server/session/daemon/npm-global-cli.js +98 -0
- package/dist/server/server/session/provider/provider-catalog-session.js +8 -4
- package/dist/server/server/session.d.ts +5 -3
- package/dist/server/server/session.js +74 -32
- package/dist/server/server/web-ui.d.ts +10 -0
- package/dist/server/server/web-ui.js +205 -0
- package/dist/server/server/websocket/runtime-metrics.d.ts +3 -0
- package/dist/server/server/websocket-server.d.ts +3 -0
- package/dist/server/server/websocket-server.js +190 -32
- package/dist/server/services/quota-fetcher/manifest.js +5 -0
- package/dist/server/services/quota-fetcher/providers/minimax.d.ts +29 -0
- package/dist/server/services/quota-fetcher/providers/minimax.js +227 -0
- package/dist/server/terminal/agent-hooks/agent-hook-installer.js +2 -2
- package/dist/server/utils/checkout-git.js +156 -3
- package/dist/server/utils/directory-suggestions.js +1 -4
- package/dist/server/utils/path.d.ts +2 -0
- package/dist/server/utils/path.js +13 -0
- package/dist/server/utils/worktree.d.ts +1 -0
- package/dist/server/utils/worktree.js +92 -11
- package/dist/server/web-ui/_expo/static/css/xterm-3bb1704bf6cb0876640973dc0244b4cb.css +1 -0
- package/dist/server/web-ui/_expo/static/css/xterm-3bb1704bf6cb0876640973dc0244b4cb.css.br +0 -0
- package/dist/server/web-ui/_expo/static/css/xterm-3bb1704bf6cb0876640973dc0244b4cb.css.gz +0 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-bridge-b01555c9b42665a03988c0a0032ef528.js +1 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-bridge-b01555c9b42665a03988c0a0032ef528.js.br +0 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-bridge-b01555c9b42665a03988c0a0032ef528.js.gz +0 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-store-648388eca5c510b496e1eddf523f70ff.js +1 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-store-648388eca5c510b496e1eddf523f70ff.js.br +0 -0
- package/dist/server/web-ui/_expo/static/js/web/desktop-attachment-store-648388eca5c510b496e1eddf523f70ff.js.gz +0 -0
- package/dist/server/web-ui/_expo/static/js/web/index-0ebbea2cd337f0c0680fdb3f8d4d5af3.js +16157 -0
- package/dist/server/web-ui/_expo/static/js/web/index-0ebbea2cd337f0c0680fdb3f8d4d5af3.js.br +0 -0
- package/dist/server/web-ui/_expo/static/js/web/index-0ebbea2cd337f0c0680fdb3f8d4d5af3.js.gz +0 -0
- package/dist/server/web-ui/_expo/static/js/web/indexeddb-attachment-store-c64fa2416284927857a39087fd8d1332.js +1 -0
- package/dist/server/web-ui/_expo/static/js/web/indexeddb-attachment-store-c64fa2416284927857a39087fd8d1332.js.br +0 -0
- package/dist/server/web-ui/_expo/static/js/web/indexeddb-attachment-store-c64fa2416284927857a39087fd8d1332.js.gz +0 -0
- package/dist/server/web-ui/_expo/static/js/web/native-file-attachment-store-a9784226715772edf87ef36c596599c2.js +3 -0
- package/dist/server/web-ui/_expo/static/js/web/native-file-attachment-store-a9784226715772edf87ef36c596599c2.js.br +0 -0
- package/dist/server/web-ui/_expo/static/js/web/native-file-attachment-store-a9784226715772edf87ef36c596599c2.js.gz +0 -0
- package/dist/server/web-ui/apple-touch-icon.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/back-icon-mask.0a328cd9c1afd0afe8e3b1ec5165b1b4.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/back-icon.35ba0eaec5a4f5ed12ca16fabeae451d.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/clear-icon.c94f6478e7ae0cdd9f15de1fcb9e5e55.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/clear-icon.c94f6478e7ae0cdd9f15de1fcb9e5e55@2x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/clear-icon.c94f6478e7ae0cdd9f15de1fcb9e5e55@3x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/clear-icon.c94f6478e7ae0cdd9f15de1fcb9e5e55@4x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/close-icon.808e1b1b9b53114ec2838071a7e6daa7.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/close-icon.808e1b1b9b53114ec2838071a7e6daa7@2x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/close-icon.808e1b1b9b53114ec2838071a7e6daa7@3x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/close-icon.808e1b1b9b53114ec2838071a7e6daa7@4x.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/@react-navigation/elements/lib/module/assets/search-icon.286d67d3f74808a60a78d3ebf1a5fb57.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/arrow_down.017bc6ba3fc25503e5eb5e53826d48a8.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/error.d1ea1496f9057eb392d5bbf3732a61b7.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/file.19eeb73b9593a38f8e9f418337fc7d10.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/forward.d8b800c443b8972542883e0b9de2bdc6.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/pkg.ab19f4cbc543357183a20571f68380a3.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/sitemap.412dd9275b6b48ad28f5e3d81bb1f626.png +0 -0
- package/dist/server/web-ui/assets/__node_modules/expo-router/assets/unmatched.20e71bdf79e3a97bf55fd9e164041578.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/antigravity.6e91a685c33435e0b466a56db86cf141.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/cursor.c31d6bce4fe9aadc3fe59962f4c4fcf3.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/file-explorer.3e15e8f72c825c85ce336bcb0cdef776.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/finder.7f68fc2c475621a672e1be09309d5567.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/vscode.832bdb4c685d930f1c864c793703600b.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/webstorm.aa5dc2cd8c20cc0a155c4c5c5ab3c5f5.png +0 -0
- package/dist/server/web-ui/assets/assets/images/editor-apps/zed.f3a670b7f9aa226da4fe53fb86f1abbd.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-dark-attention.882b3a27dcb2073e9e31b334f9ed9728.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-dark-running.8112342ff0d39e047a7f8d4fad9402f3.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-dark.8005ed36ac07a5a7c60de25780897bd4.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-light-attention.882b3a27dcb2073e9e31b334f9ed9728.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-light-running.8112342ff0d39e047a7f8d4fad9402f3.png +0 -0
- package/dist/server/web-ui/assets/assets/images/favicon-light.8005ed36ac07a5a7c60de25780897bd4.png +0 -0
- package/dist/server/web-ui/assets/assets/images/notification-icon.3bf81d33ddbf380606bdd248ba83e158.png +0 -0
- package/dist/server/web-ui/favicon.ico +0 -0
- package/dist/server/web-ui/index.html +90 -0
- package/dist/server/web-ui/index.html.br +0 -0
- package/dist/server/web-ui/index.html.gz +0 -0
- package/dist/server/web-ui/manifest.json +27 -0
- package/dist/server/web-ui/manifest.json.br +0 -0
- package/dist/server/web-ui/manifest.json.gz +0 -0
- package/dist/server/web-ui/metadata.json +1 -0
- package/dist/server/web-ui/metadata.json.br +1 -0
- package/dist/server/web-ui/metadata.json.gz +0 -0
- package/dist/server/web-ui/pwa-icon-192.png +0 -0
- package/dist/server/web-ui/pwa-icon-512.png +0 -0
- package/dist/server/web-ui/robots.txt +2 -0
- package/dist/src/server/persisted-config.js +8 -0
- package/package.json +7 -7
|
@@ -0,0 +1,227 @@
|
|
|
1
|
+
import { existsSync, promises as fs } from "node:fs";
|
|
2
|
+
import { homedir } from "node:os";
|
|
3
|
+
import { join } from "node:path";
|
|
4
|
+
import { z } from "zod";
|
|
5
|
+
import { ApiNumberSchema, ApiOptionalStringSchema, fetchProviderApi, unavailableUsage, windowFromUsedPct, } from "../usage.js";
|
|
6
|
+
const MINIMAX_GLOBAL_BASE_URL = "https://api.minimax.io";
|
|
7
|
+
const MINIMAX_CN_BASE_URL = "https://api.minimaxi.com";
|
|
8
|
+
const MINIMAX_CREDENTIALS_PATH = join(homedir(), ".mmx", "credentials.json");
|
|
9
|
+
const MINIMAX_CONFIG_PATH = join(homedir(), ".mmx", "config.json");
|
|
10
|
+
const MiniMaxModelRemainSchema = z.object({
|
|
11
|
+
model_name: ApiOptionalStringSchema,
|
|
12
|
+
start_time: ApiNumberSchema.optional(),
|
|
13
|
+
end_time: ApiNumberSchema.optional(),
|
|
14
|
+
remains_time: ApiNumberSchema.optional(),
|
|
15
|
+
current_interval_total_count: ApiNumberSchema.optional(),
|
|
16
|
+
current_interval_usage_count: ApiNumberSchema.optional(),
|
|
17
|
+
current_interval_remaining_percent: ApiNumberSchema.optional(),
|
|
18
|
+
current_weekly_total_count: ApiNumberSchema.optional(),
|
|
19
|
+
current_weekly_usage_count: ApiNumberSchema.optional(),
|
|
20
|
+
current_weekly_remaining_percent: ApiNumberSchema.optional(),
|
|
21
|
+
current_interval_status: ApiNumberSchema.optional(),
|
|
22
|
+
current_weekly_status: ApiNumberSchema.optional(),
|
|
23
|
+
weekly_start_time: ApiNumberSchema.optional(),
|
|
24
|
+
weekly_end_time: ApiNumberSchema.optional(),
|
|
25
|
+
weekly_remains_time: ApiNumberSchema.optional(),
|
|
26
|
+
weekly_boost_permille: ApiNumberSchema.optional(),
|
|
27
|
+
});
|
|
28
|
+
const MiniMaxQuotaResponseSchema = z.object({
|
|
29
|
+
model_remains: z.array(MiniMaxModelRemainSchema).optional(),
|
|
30
|
+
});
|
|
31
|
+
const MiniMaxCredentialsSchema = z.object({
|
|
32
|
+
access_token: z.string().optional(),
|
|
33
|
+
refresh_token: z.string().optional(),
|
|
34
|
+
expires_at: ApiOptionalStringSchema,
|
|
35
|
+
resource_url: ApiOptionalStringSchema,
|
|
36
|
+
});
|
|
37
|
+
const MiniMaxConfigSchema = z.object({
|
|
38
|
+
api_key: z.string().optional(),
|
|
39
|
+
region: z.string().optional(),
|
|
40
|
+
base_url: ApiOptionalStringSchema,
|
|
41
|
+
oauth: MiniMaxCredentialsSchema.optional(),
|
|
42
|
+
});
|
|
43
|
+
function resolveBaseUrl(input) {
|
|
44
|
+
const explicit = input.baseUrl;
|
|
45
|
+
if (explicit && explicit.startsWith("http"))
|
|
46
|
+
return explicit;
|
|
47
|
+
if (input.region === "cn")
|
|
48
|
+
return MINIMAX_CN_BASE_URL;
|
|
49
|
+
return MINIMAX_GLOBAL_BASE_URL;
|
|
50
|
+
}
|
|
51
|
+
function computeUsedPct(remaining, total) {
|
|
52
|
+
if (typeof remaining !== "number" || typeof total !== "number")
|
|
53
|
+
return null;
|
|
54
|
+
if (!Number.isFinite(total) || total <= 0)
|
|
55
|
+
return null;
|
|
56
|
+
if (!Number.isFinite(remaining))
|
|
57
|
+
return null;
|
|
58
|
+
const used = total - remaining;
|
|
59
|
+
return Math.max(0, Math.min(100, (used / total) * 100));
|
|
60
|
+
}
|
|
61
|
+
function epochMsToIso(value) {
|
|
62
|
+
if (typeof value !== "number" || !Number.isFinite(value) || value <= 0)
|
|
63
|
+
return null;
|
|
64
|
+
return new Date(value).toISOString();
|
|
65
|
+
}
|
|
66
|
+
function toneForStatus(status) {
|
|
67
|
+
if (status === 2)
|
|
68
|
+
return "danger";
|
|
69
|
+
if (status === 3)
|
|
70
|
+
return "default";
|
|
71
|
+
return "ok";
|
|
72
|
+
}
|
|
73
|
+
function toIntervalWindow(modelName, model) {
|
|
74
|
+
const total = model.current_interval_total_count ?? null;
|
|
75
|
+
const used = model.current_interval_usage_count ?? null;
|
|
76
|
+
const remainingPercent = model.current_interval_remaining_percent ?? null;
|
|
77
|
+
const usedPct = typeof remainingPercent === "number" && Number.isFinite(remainingPercent)
|
|
78
|
+
? Math.max(0, Math.min(100, 100 - remainingPercent))
|
|
79
|
+
: computeUsedPct(typeof total === "number" && typeof used === "number" ? total - used : null, total);
|
|
80
|
+
if (usedPct === null)
|
|
81
|
+
return null;
|
|
82
|
+
return windowFromUsedPct({
|
|
83
|
+
id: `interval_${modelName}`,
|
|
84
|
+
label: `${modelName} · Interval`,
|
|
85
|
+
utilizationPct: usedPct,
|
|
86
|
+
resetsAt: epochMsToIso(model.end_time),
|
|
87
|
+
tone: toneForStatus(model.current_interval_status),
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
function toWeeklyWindow(modelName, model) {
|
|
91
|
+
const total = model.current_weekly_total_count ?? null;
|
|
92
|
+
const used = model.current_weekly_usage_count ?? null;
|
|
93
|
+
const remainingPercent = model.current_weekly_remaining_percent ?? null;
|
|
94
|
+
let usedPct = null;
|
|
95
|
+
if (typeof remainingPercent === "number" && Number.isFinite(remainingPercent)) {
|
|
96
|
+
usedPct = Math.max(0, Math.min(100, 100 - remainingPercent));
|
|
97
|
+
}
|
|
98
|
+
else if (typeof total === "number" && typeof used === "number") {
|
|
99
|
+
usedPct = computeUsedPct(total - used, total);
|
|
100
|
+
}
|
|
101
|
+
if (usedPct === null)
|
|
102
|
+
return null;
|
|
103
|
+
return windowFromUsedPct({
|
|
104
|
+
id: `weekly_${modelName}`,
|
|
105
|
+
label: `${modelName} · Weekly`,
|
|
106
|
+
utilizationPct: usedPct,
|
|
107
|
+
resetsAt: epochMsToIso(model.weekly_end_time),
|
|
108
|
+
tone: toneForStatus(model.current_weekly_status),
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
export class MiniMaxQuotaProvider {
|
|
112
|
+
constructor(options) {
|
|
113
|
+
this.providerId = "minimax";
|
|
114
|
+
this.displayName = "MiniMax";
|
|
115
|
+
this.logger = options.logger;
|
|
116
|
+
this.fetchApi = options.fetch ?? fetch;
|
|
117
|
+
this.configPath = options.configPath ?? MINIMAX_CONFIG_PATH;
|
|
118
|
+
this.credentialsPath = options.credentialsPath ?? MINIMAX_CREDENTIALS_PATH;
|
|
119
|
+
this.env = options.env ?? process.env;
|
|
120
|
+
this.now = options.now ?? Date.now;
|
|
121
|
+
}
|
|
122
|
+
async fetchUsage() {
|
|
123
|
+
const auth = await this.resolveAuth();
|
|
124
|
+
if (!auth)
|
|
125
|
+
return unavailableUsage(this);
|
|
126
|
+
const res = await fetchProviderApi(this.fetchApi, `${auth.baseUrl}/v1/token_plan/remains`, {
|
|
127
|
+
headers: {
|
|
128
|
+
Authorization: `Bearer ${auth.token}`,
|
|
129
|
+
Accept: "application/json",
|
|
130
|
+
},
|
|
131
|
+
});
|
|
132
|
+
if (!res.ok) {
|
|
133
|
+
this.logger.debug({ status: res.status }, "MiniMax usage fetch failed");
|
|
134
|
+
return unavailableUsage(this);
|
|
135
|
+
}
|
|
136
|
+
const resp = MiniMaxQuotaResponseSchema.parse(await res.json());
|
|
137
|
+
const models = resp.model_remains ?? [];
|
|
138
|
+
const windows = [];
|
|
139
|
+
for (const model of models) {
|
|
140
|
+
const name = model.model_name ?? "token-plan";
|
|
141
|
+
const intervalWindow = toIntervalWindow(name, model);
|
|
142
|
+
if (intervalWindow)
|
|
143
|
+
windows.push(intervalWindow);
|
|
144
|
+
const weeklyWindow = toWeeklyWindow(name, model);
|
|
145
|
+
if (weeklyWindow)
|
|
146
|
+
windows.push(weeklyWindow);
|
|
147
|
+
}
|
|
148
|
+
return {
|
|
149
|
+
providerId: this.providerId,
|
|
150
|
+
displayName: this.displayName,
|
|
151
|
+
status: windows.length > 0 ? "available" : "unavailable",
|
|
152
|
+
planLabel: null,
|
|
153
|
+
windows,
|
|
154
|
+
balances: [],
|
|
155
|
+
details: [],
|
|
156
|
+
error: null,
|
|
157
|
+
};
|
|
158
|
+
}
|
|
159
|
+
async resolveAuth() {
|
|
160
|
+
const envToken = this.env["MINIMAX_API_KEY"];
|
|
161
|
+
if (envToken) {
|
|
162
|
+
const envBase = this.env["MINIMAX_BASE_URL"];
|
|
163
|
+
return {
|
|
164
|
+
token: envToken,
|
|
165
|
+
baseUrl: resolveBaseUrl({ baseUrl: envBase }),
|
|
166
|
+
};
|
|
167
|
+
}
|
|
168
|
+
const credentials = await this.readCredentials();
|
|
169
|
+
if (credentials?.access_token && !this.isExpired(credentials.expires_at)) {
|
|
170
|
+
return {
|
|
171
|
+
token: credentials.access_token,
|
|
172
|
+
baseUrl: resolveBaseUrl({ baseUrl: credentials.resource_url }),
|
|
173
|
+
};
|
|
174
|
+
}
|
|
175
|
+
const config = await this.readConfig();
|
|
176
|
+
if (config?.api_key) {
|
|
177
|
+
return {
|
|
178
|
+
token: config.api_key,
|
|
179
|
+
baseUrl: resolveBaseUrl({
|
|
180
|
+
baseUrl: config.base_url,
|
|
181
|
+
region: config.region,
|
|
182
|
+
}),
|
|
183
|
+
};
|
|
184
|
+
}
|
|
185
|
+
if (config?.oauth?.access_token && !this.isExpired(config.oauth.expires_at)) {
|
|
186
|
+
return {
|
|
187
|
+
token: config.oauth.access_token,
|
|
188
|
+
baseUrl: resolveBaseUrl({
|
|
189
|
+
baseUrl: config.oauth.resource_url ?? config.base_url,
|
|
190
|
+
region: config.region,
|
|
191
|
+
}),
|
|
192
|
+
};
|
|
193
|
+
}
|
|
194
|
+
return null;
|
|
195
|
+
}
|
|
196
|
+
isExpired(expiresAt) {
|
|
197
|
+
if (!expiresAt)
|
|
198
|
+
return false;
|
|
199
|
+
const parsed = Date.parse(expiresAt);
|
|
200
|
+
if (!Number.isFinite(parsed))
|
|
201
|
+
return false;
|
|
202
|
+
return parsed <= this.now();
|
|
203
|
+
}
|
|
204
|
+
async readCredentials() {
|
|
205
|
+
if (!existsSync(this.credentialsPath))
|
|
206
|
+
return null;
|
|
207
|
+
try {
|
|
208
|
+
const raw = JSON.parse(await fs.readFile(this.credentialsPath, "utf8"));
|
|
209
|
+
return MiniMaxCredentialsSchema.parse(raw);
|
|
210
|
+
}
|
|
211
|
+
catch {
|
|
212
|
+
return null;
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
async readConfig() {
|
|
216
|
+
if (!existsSync(this.configPath))
|
|
217
|
+
return null;
|
|
218
|
+
try {
|
|
219
|
+
const raw = JSON.parse(await fs.readFile(this.configPath, "utf8"));
|
|
220
|
+
return MiniMaxConfigSchema.parse(raw);
|
|
221
|
+
}
|
|
222
|
+
catch {
|
|
223
|
+
return null;
|
|
224
|
+
}
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
//# sourceMappingURL=minimax.js.map
|
|
@@ -42,11 +42,11 @@ function resolveAgentHookInstallPath(install, options) {
|
|
|
42
42
|
}
|
|
43
43
|
export function buildAgentHookShellCommand(provider, event) {
|
|
44
44
|
const hookCommand = `"\${PASEO_HOOK_CLI:-paseo}" hooks ${shellToken(provider.id)} ${shellToken(event.event)}`;
|
|
45
|
-
return `[ -n "$PASEO_TERMINAL_ID" ]
|
|
45
|
+
return `if [ -n "$PASEO_TERMINAL_ID" ]; then ${hookCommand}; fi`;
|
|
46
46
|
}
|
|
47
47
|
export function buildAgentHookWindowsCommand(provider, event) {
|
|
48
48
|
const hookArgs = `hooks ${windowsToken(provider.id)} ${windowsToken(event.event)}`;
|
|
49
|
-
return `if defined PASEO_TERMINAL_ID (if defined PASEO_HOOK_CLI ("%PASEO_HOOK_CLI%" ${hookArgs}) else (paseo ${hookArgs}))`;
|
|
49
|
+
return `if defined PASEO_TERMINAL_ID (if defined PASEO_HOOK_CLI ("%PASEO_HOOK_CLI%" ${hookArgs}) else (paseo ${hookArgs})) else (exit /b 0)`;
|
|
50
50
|
}
|
|
51
51
|
function installAgentHookPluginFile(install, options) {
|
|
52
52
|
const configPath = resolveAgentHookInstallPath(install, options);
|
|
@@ -723,6 +723,20 @@ async function getGitConfigValue(cwd, key, context) {
|
|
|
723
723
|
return null;
|
|
724
724
|
}
|
|
725
725
|
}
|
|
726
|
+
async function getGitRemotePushUrl(cwd, remoteName, context) {
|
|
727
|
+
try {
|
|
728
|
+
const { stdout } = await runGitCommand(["remote", "get-url", "--push", remoteName], {
|
|
729
|
+
cwd,
|
|
730
|
+
envOverlay: READ_ONLY_GIT_ENV,
|
|
731
|
+
logger: context?.logger,
|
|
732
|
+
});
|
|
733
|
+
const value = stdout.trim();
|
|
734
|
+
return value.length > 0 ? value : null;
|
|
735
|
+
}
|
|
736
|
+
catch {
|
|
737
|
+
return null;
|
|
738
|
+
}
|
|
739
|
+
}
|
|
726
740
|
function parseBranchMergeHeadRef(mergeRef) {
|
|
727
741
|
const prefix = "refs/heads/";
|
|
728
742
|
if (!mergeRef?.startsWith(prefix)) {
|
|
@@ -749,14 +763,15 @@ async function resolvePullRequestStatusLookupTarget(cwd, currentBranch, context)
|
|
|
749
763
|
resolvedBaseRef: null,
|
|
750
764
|
});
|
|
751
765
|
if (localBranchTarget.headRef === currentBranch) {
|
|
752
|
-
|
|
766
|
+
const pushTarget = await resolvePullRequestLookupTargetFromPushConfig(cwd, currentBranch, null, null, context);
|
|
767
|
+
return pushTarget ?? localBranchTarget;
|
|
753
768
|
}
|
|
754
769
|
const [branchRemoteUrl, originRemoteUrl, resolvedBaseRef] = await Promise.all([
|
|
755
770
|
branchRemoteName ? getGitConfigValue(cwd, `remote.${branchRemoteName}.url`, context) : null,
|
|
756
771
|
getGitConfigValue(cwd, "remote.origin.url", context),
|
|
757
772
|
getResolvedBaseRefForCwd(cwd, context),
|
|
758
773
|
]);
|
|
759
|
-
|
|
774
|
+
const branchTarget = buildPullRequestLookupTargetFromBranchConfig({
|
|
760
775
|
currentBranch,
|
|
761
776
|
branchRemoteName,
|
|
762
777
|
branchMergeRef,
|
|
@@ -764,6 +779,11 @@ async function resolvePullRequestStatusLookupTarget(cwd, currentBranch, context)
|
|
|
764
779
|
originRemoteUrl,
|
|
765
780
|
resolvedBaseRef,
|
|
766
781
|
});
|
|
782
|
+
if (branchTarget.headRef !== currentBranch || branchTarget.headRepositoryOwner) {
|
|
783
|
+
return branchTarget;
|
|
784
|
+
}
|
|
785
|
+
const pushTarget = await resolvePullRequestLookupTargetFromPushConfig(cwd, currentBranch, originRemoteUrl, resolvedBaseRef, context);
|
|
786
|
+
return pushTarget ?? branchTarget;
|
|
767
787
|
}
|
|
768
788
|
export async function resolveAbsoluteGitDir(cwd) {
|
|
769
789
|
try {
|
|
@@ -1054,6 +1074,48 @@ function buildPullRequestLookupTargetFromBranchConfig(input) {
|
|
|
1054
1074
|
...(headRepositoryOwner ? { headRepositoryOwner } : {}),
|
|
1055
1075
|
};
|
|
1056
1076
|
}
|
|
1077
|
+
function buildPullRequestLookupTargetFromPushConfig(input) {
|
|
1078
|
+
const pushedHeadRef = parseHeadPushRefspec(input.pushRefspec);
|
|
1079
|
+
if (!input.pushRemoteName || !pushedHeadRef || pushedHeadRef === input.currentBranch) {
|
|
1080
|
+
return null;
|
|
1081
|
+
}
|
|
1082
|
+
const remoteRepo = input.pushRemoteUrl ? parseGitHubRepoFromRemote(input.pushRemoteUrl) : null;
|
|
1083
|
+
const originRepo = input.originRemoteUrl
|
|
1084
|
+
? parseGitHubRepoFromRemote(input.originRemoteUrl)
|
|
1085
|
+
: null;
|
|
1086
|
+
const isSameRepo = Boolean(remoteRepo && originRepo && remoteRepo === originRepo);
|
|
1087
|
+
const headRepositoryOwner = remoteRepo && !isSameRepo ? remoteRepo.split("/")[0] : null;
|
|
1088
|
+
const normalizedBaseRef = input.resolvedBaseRef
|
|
1089
|
+
? normalizeLocalBranchRefName(input.resolvedBaseRef)
|
|
1090
|
+
: null;
|
|
1091
|
+
if (pushedHeadRef === normalizedBaseRef && !headRepositoryOwner) {
|
|
1092
|
+
return null;
|
|
1093
|
+
}
|
|
1094
|
+
return {
|
|
1095
|
+
headRef: pushedHeadRef,
|
|
1096
|
+
...(headRepositoryOwner ? { headRepositoryOwner } : {}),
|
|
1097
|
+
};
|
|
1098
|
+
}
|
|
1099
|
+
async function resolvePullRequestLookupTargetFromPushConfig(cwd, currentBranch, knownOriginRemoteUrl, knownResolvedBaseRef, context) {
|
|
1100
|
+
const pushRemoteName = await getGitConfigValue(cwd, `branch.${currentBranch}.pushRemote`, context);
|
|
1101
|
+
if (!pushRemoteName) {
|
|
1102
|
+
return null;
|
|
1103
|
+
}
|
|
1104
|
+
const [pushRefspec, pushRemoteUrl, originRemoteUrl, resolvedBaseRef] = await Promise.all([
|
|
1105
|
+
getGitConfigValue(cwd, `remote.${pushRemoteName}.push`, context),
|
|
1106
|
+
getGitConfigValue(cwd, `remote.${pushRemoteName}.url`, context),
|
|
1107
|
+
knownOriginRemoteUrl === null ? getGitConfigValue(cwd, "remote.origin.url", context) : null,
|
|
1108
|
+
knownResolvedBaseRef === null ? getResolvedBaseRefForCwd(cwd, context) : null,
|
|
1109
|
+
]);
|
|
1110
|
+
return buildPullRequestLookupTargetFromPushConfig({
|
|
1111
|
+
currentBranch,
|
|
1112
|
+
pushRemoteName,
|
|
1113
|
+
pushRefspec,
|
|
1114
|
+
pushRemoteUrl,
|
|
1115
|
+
originRemoteUrl: knownOriginRemoteUrl ?? originRemoteUrl,
|
|
1116
|
+
resolvedBaseRef: knownResolvedBaseRef ?? resolvedBaseRef,
|
|
1117
|
+
});
|
|
1118
|
+
}
|
|
1057
1119
|
export async function getCheckoutSnapshotFacts(cwd, context) {
|
|
1058
1120
|
if (context?.facts) {
|
|
1059
1121
|
return context.facts;
|
|
@@ -1085,7 +1147,7 @@ export async function getCheckoutSnapshotFacts(cwd, context) {
|
|
|
1085
1147
|
]);
|
|
1086
1148
|
}
|
|
1087
1149
|
}
|
|
1088
|
-
|
|
1150
|
+
let pullRequestLookupTarget = inspected.currentBranch
|
|
1089
1151
|
? buildPullRequestLookupTargetFromBranchConfig({
|
|
1090
1152
|
currentBranch: inspected.currentBranch,
|
|
1091
1153
|
branchRemoteName,
|
|
@@ -1095,6 +1157,12 @@ export async function getCheckoutSnapshotFacts(cwd, context) {
|
|
|
1095
1157
|
resolvedBaseRef,
|
|
1096
1158
|
})
|
|
1097
1159
|
: null;
|
|
1160
|
+
if (inspected.currentBranch &&
|
|
1161
|
+
pullRequestLookupTarget?.headRef === inspected.currentBranch &&
|
|
1162
|
+
!pullRequestLookupTarget.headRepositoryOwner) {
|
|
1163
|
+
pullRequestLookupTarget =
|
|
1164
|
+
(await resolvePullRequestLookupTargetFromPushConfig(cwd, inspected.currentBranch, inspected.remoteUrl, resolvedBaseRef, context)) ?? pullRequestLookupTarget;
|
|
1165
|
+
}
|
|
1098
1166
|
return {
|
|
1099
1167
|
isGit: true,
|
|
1100
1168
|
worktreeRoot: inspected.worktreeRoot,
|
|
@@ -1960,6 +2028,19 @@ export async function pushCurrentBranch(cwd, github) {
|
|
|
1960
2028
|
if (!currentBranch || currentBranch === "HEAD") {
|
|
1961
2029
|
throw new Error("Unable to determine current branch for push");
|
|
1962
2030
|
}
|
|
2031
|
+
const configuredPushTarget = await getCurrentBranchConfiguredPushTarget(cwd, currentBranch);
|
|
2032
|
+
if (configuredPushTarget) {
|
|
2033
|
+
await runGitCommand(["push", configuredPushTarget.remoteName, `HEAD:refs/heads/${configuredPushTarget.headRef}`], { cwd, timeout: 120000 });
|
|
2034
|
+
await refreshCurrentBranchTrackedRefAfterPush(cwd, currentBranch, configuredPushTarget);
|
|
2035
|
+
github?.invalidate({ cwd });
|
|
2036
|
+
return;
|
|
2037
|
+
}
|
|
2038
|
+
const upstreamTarget = await getCurrentBranchUpstreamPushTarget(cwd, currentBranch);
|
|
2039
|
+
if (upstreamTarget) {
|
|
2040
|
+
await runGitCommand(["push", "-u", upstreamTarget.remoteName, `HEAD:refs/heads/${upstreamTarget.headRef}`], { cwd, timeout: 120000 });
|
|
2041
|
+
github?.invalidate({ cwd });
|
|
2042
|
+
return;
|
|
2043
|
+
}
|
|
1963
2044
|
const hasRemote = await hasOriginRemote(cwd);
|
|
1964
2045
|
if (!hasRemote) {
|
|
1965
2046
|
throw new Error("Remote 'origin' is not configured.");
|
|
@@ -1967,6 +2048,78 @@ export async function pushCurrentBranch(cwd, github) {
|
|
|
1967
2048
|
await runGitCommand(["push", "-u", "origin", currentBranch], { cwd, timeout: 120000 });
|
|
1968
2049
|
github?.invalidate({ cwd });
|
|
1969
2050
|
}
|
|
2051
|
+
async function getCurrentBranchConfiguredPushTarget(cwd, currentBranch) {
|
|
2052
|
+
const remoteName = await getGitConfigValue(cwd, `branch.${currentBranch}.pushRemote`);
|
|
2053
|
+
const pushRefspec = remoteName ? await getGitConfigValue(cwd, `remote.${remoteName}.push`) : null;
|
|
2054
|
+
const headRef = parseHeadPushRefspec(pushRefspec);
|
|
2055
|
+
if (!remoteName || !headRef) {
|
|
2056
|
+
return null;
|
|
2057
|
+
}
|
|
2058
|
+
const remoteUrl = await getGitConfigValue(cwd, `remote.${remoteName}.url`);
|
|
2059
|
+
return remoteUrl ? { remoteName, headRef } : null;
|
|
2060
|
+
}
|
|
2061
|
+
async function refreshCurrentBranchTrackedRefAfterPush(cwd, currentBranch, pushedTarget) {
|
|
2062
|
+
const trackingRemoteName = await getGitConfigValue(cwd, `branch.${currentBranch}.remote`);
|
|
2063
|
+
const trackingMergeRef = await getGitConfigValue(cwd, `branch.${currentBranch}.merge`);
|
|
2064
|
+
const trackingHeadRef = parseBranchMergeHeadRef(trackingMergeRef);
|
|
2065
|
+
if (!trackingRemoteName && !trackingMergeRef) {
|
|
2066
|
+
const updated = await updateRemoteTrackingRef(cwd, pushedTarget.remoteName, pushedTarget.headRef);
|
|
2067
|
+
if (!updated) {
|
|
2068
|
+
return;
|
|
2069
|
+
}
|
|
2070
|
+
await runGitCommand(["config", `branch.${currentBranch}.remote`, pushedTarget.remoteName], {
|
|
2071
|
+
cwd,
|
|
2072
|
+
});
|
|
2073
|
+
await runGitCommand(["config", `branch.${currentBranch}.merge`, `refs/heads/${pushedTarget.headRef}`], {
|
|
2074
|
+
cwd,
|
|
2075
|
+
});
|
|
2076
|
+
return;
|
|
2077
|
+
}
|
|
2078
|
+
if (!trackingRemoteName || trackingHeadRef !== pushedTarget.headRef) {
|
|
2079
|
+
return;
|
|
2080
|
+
}
|
|
2081
|
+
const [trackingRemotePushUrl, pushedRemotePushUrl] = await Promise.all([
|
|
2082
|
+
getGitRemotePushUrl(cwd, trackingRemoteName),
|
|
2083
|
+
getGitRemotePushUrl(cwd, pushedTarget.remoteName),
|
|
2084
|
+
]);
|
|
2085
|
+
if (!trackingRemotePushUrl || trackingRemotePushUrl !== pushedRemotePushUrl) {
|
|
2086
|
+
return;
|
|
2087
|
+
}
|
|
2088
|
+
await updateRemoteTrackingRef(cwd, trackingRemoteName, trackingHeadRef);
|
|
2089
|
+
}
|
|
2090
|
+
async function updateRemoteTrackingRef(cwd, remoteName, headRef) {
|
|
2091
|
+
const trackingRef = `refs/remotes/${remoteName}/${headRef}`;
|
|
2092
|
+
const checkRef = await runGitCommand(["check-ref-format", trackingRef], {
|
|
2093
|
+
cwd,
|
|
2094
|
+
acceptExitCodes: [0, 1],
|
|
2095
|
+
});
|
|
2096
|
+
if (checkRef.exitCode !== 0) {
|
|
2097
|
+
return false;
|
|
2098
|
+
}
|
|
2099
|
+
await runGitCommand(["update-ref", trackingRef, "HEAD"], { cwd, timeout: 120000 });
|
|
2100
|
+
return true;
|
|
2101
|
+
}
|
|
2102
|
+
async function getCurrentBranchUpstreamPushTarget(cwd, currentBranch) {
|
|
2103
|
+
const remoteName = await getGitConfigValue(cwd, `branch.${currentBranch}.remote`);
|
|
2104
|
+
const mergeRef = remoteName
|
|
2105
|
+
? await getGitConfigValue(cwd, `branch.${currentBranch}.merge`)
|
|
2106
|
+
: null;
|
|
2107
|
+
const headRef = parseBranchMergeHeadRef(mergeRef);
|
|
2108
|
+
if (!remoteName || !headRef) {
|
|
2109
|
+
return null;
|
|
2110
|
+
}
|
|
2111
|
+
const remoteUrl = await getGitConfigValue(cwd, `remote.${remoteName}.url`);
|
|
2112
|
+
return remoteUrl ? { remoteName, headRef } : null;
|
|
2113
|
+
}
|
|
2114
|
+
function parseHeadPushRefspec(refspec) {
|
|
2115
|
+
const prefix = "HEAD:refs/heads/";
|
|
2116
|
+
const normalized = refspec?.trim().replace(/^\+/, "");
|
|
2117
|
+
if (!normalized?.startsWith(prefix)) {
|
|
2118
|
+
return null;
|
|
2119
|
+
}
|
|
2120
|
+
const headRef = normalized.slice(prefix.length).trim();
|
|
2121
|
+
return headRef.length > 0 ? headRef : null;
|
|
2122
|
+
}
|
|
1970
2123
|
export async function createPullRequest(cwd, options, github = createGitHubService(), context) {
|
|
1971
2124
|
await requireGitRepo(cwd);
|
|
1972
2125
|
const repo = await resolveGitHubRepo(cwd);
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { readdir, realpath, stat } from "node:fs/promises";
|
|
2
2
|
import path from "node:path";
|
|
3
|
+
import { isPathInsideRoot } from "./path.js";
|
|
3
4
|
const DEFAULT_LIMIT = 30;
|
|
4
5
|
const MAX_LIMIT = 100;
|
|
5
6
|
const DEFAULT_MAX_DEPTH = 12;
|
|
@@ -558,10 +559,6 @@ function normalizeRelativePath(homeRoot, absolutePath) {
|
|
|
558
559
|
}
|
|
559
560
|
return relative.split(path.sep).join("/");
|
|
560
561
|
}
|
|
561
|
-
function isPathInsideRoot(root, target) {
|
|
562
|
-
const relative = path.relative(root, target);
|
|
563
|
-
return relative === "" || (!relative.startsWith("..") && !path.isAbsolute(relative));
|
|
564
|
-
}
|
|
565
562
|
function normalizeQueryParts(query, homeRoot) {
|
|
566
563
|
const typedQuery = query.trim().replace(/\\/g, "/");
|
|
567
564
|
let normalized = typedQuery;
|
|
@@ -13,4 +13,6 @@ export declare function expandTilde(path: string): string;
|
|
|
13
13
|
export declare function areEquivalentPaths(left: string, right: string): boolean;
|
|
14
14
|
export declare function createPathEquivalenceMatcher(target: string): (candidate: string) => boolean;
|
|
15
15
|
export declare function createRealpathAwarePathMatcher(target: string): (candidate: string) => boolean;
|
|
16
|
+
export declare function isPathInsideRoot(root: string, candidate: string): boolean;
|
|
17
|
+
export declare function isRealpathInsideRoot(root: string, candidate: string): boolean;
|
|
16
18
|
//# sourceMappingURL=path.d.ts.map
|
|
@@ -46,6 +46,19 @@ export function createRealpathAwarePathMatcher(target) {
|
|
|
46
46
|
return candidateVariants.some((variant) => targetMatchers.some((matches) => matches(variant)));
|
|
47
47
|
};
|
|
48
48
|
}
|
|
49
|
+
export function isPathInsideRoot(root, candidate) {
|
|
50
|
+
const compareAsWindows = shouldCompareAsWindows(root, candidate);
|
|
51
|
+
const platformPath = compareAsWindows ? nodePath.win32 : nodePath.posix;
|
|
52
|
+
const normalizedRoot = normalizePathForComparison(root, compareAsWindows);
|
|
53
|
+
const normalizedCandidate = normalizePathForComparison(candidate, compareAsWindows);
|
|
54
|
+
const relative = platformPath.relative(normalizedRoot, normalizedCandidate);
|
|
55
|
+
return relative === "" || (!relative.startsWith("..") && !platformPath.isAbsolute(relative));
|
|
56
|
+
}
|
|
57
|
+
export function isRealpathInsideRoot(root, candidate) {
|
|
58
|
+
const rootVariants = collectPathVariants(root);
|
|
59
|
+
const candidateVariants = collectPathVariants(candidate);
|
|
60
|
+
return rootVariants.some((rootVariant) => candidateVariants.some((candidateVariant) => isPathInsideRoot(rootVariant, candidateVariant)));
|
|
61
|
+
}
|
|
49
62
|
function collectPathVariants(value) {
|
|
50
63
|
const variants = new Set([value]);
|
|
51
64
|
for (const realpath of resolveRealpathVariants(value)) {
|
|
@@ -860,6 +860,13 @@ export const createWorktree = async ({ cwd, source, worktreeSlug, runSetup, pase
|
|
|
860
860
|
remote: sourcePlan.pushRemote,
|
|
861
861
|
});
|
|
862
862
|
}
|
|
863
|
+
if (sourcePlan.trackingRemote) {
|
|
864
|
+
await configureWorktreeTrackingRemote({
|
|
865
|
+
cwd,
|
|
866
|
+
branchName: sourcePlan.branchName,
|
|
867
|
+
remote: sourcePlan.trackingRemote,
|
|
868
|
+
});
|
|
869
|
+
}
|
|
863
870
|
writePaseoWorktreeMetadata(worktreePath, { baseRefName: sourcePlan.metadataBaseRefName });
|
|
864
871
|
// If paseo.json exists in the main repo but wasn't checked into the worktree
|
|
865
872
|
// (e.g. uncommitted on first-time setup), seed the worktree with it so setup
|
|
@@ -940,19 +947,42 @@ async function resolveWorktreeSourcePlan({ cwd, source, desiredSlug, }) {
|
|
|
940
947
|
cwd,
|
|
941
948
|
timeout: 120000,
|
|
942
949
|
});
|
|
950
|
+
const trackingRemote = source.trackOriginHead
|
|
951
|
+
? await tryFetchWorktreeTrackingRemote({
|
|
952
|
+
cwd,
|
|
953
|
+
remoteName: "origin",
|
|
954
|
+
headRef: source.headRef,
|
|
955
|
+
})
|
|
956
|
+
: undefined;
|
|
957
|
+
const remotePlan = {};
|
|
958
|
+
if (source.pushRemoteUrl) {
|
|
959
|
+
const remoteName = `paseo-pr-${source.githubPrNumber}`;
|
|
960
|
+
remotePlan.pushRemote = {
|
|
961
|
+
name: remoteName,
|
|
962
|
+
url: source.pushRemoteUrl,
|
|
963
|
+
headRef: source.headRef,
|
|
964
|
+
track: true,
|
|
965
|
+
};
|
|
966
|
+
}
|
|
967
|
+
else if (source.trackOriginHead && localBranchName !== source.headRef) {
|
|
968
|
+
const originUrl = await getWorktreeRemotePushUrl(cwd, "origin");
|
|
969
|
+
if (originUrl) {
|
|
970
|
+
remotePlan.pushRemote = {
|
|
971
|
+
name: `paseo-pr-${source.githubPrNumber}`,
|
|
972
|
+
url: originUrl,
|
|
973
|
+
headRef: source.headRef,
|
|
974
|
+
track: false,
|
|
975
|
+
};
|
|
976
|
+
}
|
|
977
|
+
}
|
|
978
|
+
if (trackingRemote) {
|
|
979
|
+
remotePlan.trackingRemote = trackingRemote;
|
|
980
|
+
}
|
|
943
981
|
return {
|
|
944
982
|
branchName: localBranchName,
|
|
945
983
|
metadataBaseRefName: normalizedBaseRefName,
|
|
946
984
|
addArguments: [localBranchName],
|
|
947
|
-
...
|
|
948
|
-
? {
|
|
949
|
-
pushRemote: {
|
|
950
|
-
name: `paseo-pr-${source.githubPrNumber}`,
|
|
951
|
-
url: source.pushRemoteUrl,
|
|
952
|
-
headRef: source.headRef,
|
|
953
|
-
},
|
|
954
|
-
}
|
|
955
|
-
: {}),
|
|
985
|
+
...remotePlan,
|
|
956
986
|
};
|
|
957
987
|
}
|
|
958
988
|
}
|
|
@@ -962,10 +992,61 @@ async function configureWorktreePushRemote(options) {
|
|
|
962
992
|
cwd: options.cwd,
|
|
963
993
|
});
|
|
964
994
|
await runGitCommand(["config", `remote.${options.remote.name}.push`, `HEAD:refs/heads/${options.remote.headRef}`], { cwd: options.cwd });
|
|
965
|
-
await runGitCommand(["config", `branch.${options.branchName}.
|
|
995
|
+
await runGitCommand(["config", `branch.${options.branchName}.pushRemote`, options.remote.name], {
|
|
966
996
|
cwd: options.cwd,
|
|
967
997
|
});
|
|
968
|
-
|
|
998
|
+
if (!options.remote.track) {
|
|
999
|
+
return;
|
|
1000
|
+
}
|
|
1001
|
+
await runGitCommand([
|
|
1002
|
+
"config",
|
|
1003
|
+
`remote.${options.remote.name}.fetch`,
|
|
1004
|
+
`+refs/heads/${options.remote.headRef}:refs/remotes/${options.remote.name}/${options.remote.headRef}`,
|
|
1005
|
+
], { cwd: options.cwd });
|
|
1006
|
+
const trackingRemote = await tryFetchWorktreeTrackingRemote({
|
|
1007
|
+
cwd: options.cwd,
|
|
1008
|
+
remoteName: options.remote.name,
|
|
1009
|
+
headRef: options.remote.headRef,
|
|
1010
|
+
});
|
|
1011
|
+
if (trackingRemote) {
|
|
1012
|
+
await configureWorktreeTrackingRemote({
|
|
1013
|
+
cwd: options.cwd,
|
|
1014
|
+
branchName: options.branchName,
|
|
1015
|
+
remote: trackingRemote,
|
|
1016
|
+
});
|
|
1017
|
+
}
|
|
1018
|
+
}
|
|
1019
|
+
async function tryFetchWorktreeTrackingRemote(options) {
|
|
1020
|
+
const result = await runGitCommand([
|
|
1021
|
+
"fetch",
|
|
1022
|
+
options.remoteName,
|
|
1023
|
+
`+refs/heads/${options.headRef}:refs/remotes/${options.remoteName}/${options.headRef}`,
|
|
1024
|
+
], {
|
|
1025
|
+
cwd: options.cwd,
|
|
1026
|
+
timeout: 120000,
|
|
1027
|
+
acceptExitCodes: [0, 1, 128],
|
|
1028
|
+
});
|
|
1029
|
+
return result.exitCode === 0 ? { name: options.remoteName, headRef: options.headRef } : undefined;
|
|
1030
|
+
}
|
|
1031
|
+
async function getWorktreeRemotePushUrl(cwd, remoteName) {
|
|
1032
|
+
try {
|
|
1033
|
+
const { stdout } = await runGitCommand(["remote", "get-url", "--push", remoteName], {
|
|
1034
|
+
cwd,
|
|
1035
|
+
});
|
|
1036
|
+
const url = stdout.trim();
|
|
1037
|
+
return url.length > 0 ? url : undefined;
|
|
1038
|
+
}
|
|
1039
|
+
catch {
|
|
1040
|
+
return undefined;
|
|
1041
|
+
}
|
|
1042
|
+
}
|
|
1043
|
+
async function configureWorktreeTrackingRemote(options) {
|
|
1044
|
+
await runGitCommand([
|
|
1045
|
+
"branch",
|
|
1046
|
+
"--set-upstream-to",
|
|
1047
|
+
`${options.remote.name}/${options.remote.headRef}`,
|
|
1048
|
+
options.branchName,
|
|
1049
|
+
], { cwd: options.cwd });
|
|
969
1050
|
}
|
|
970
1051
|
function validateWorktreeBranchName(branchName) {
|
|
971
1052
|
const validation = validateBranchSlug(branchName);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
.xterm{cursor:text;user-select:none;position:relative}.xterm.focus,.xterm:focus{outline:none}.xterm .xterm-helpers{z-index:5;position:absolute;top:0}.xterm .xterm-helper-textarea{opacity:0;z-index:-5;white-space:nowrap;resize:none;border:0;width:0;height:0;margin:0;padding:0;position:absolute;top:0;left:-9999em;overflow:hidden}.xterm .composition-view{color:#fff;white-space:nowrap;z-index:1;background:#000;display:none;position:absolute}.xterm .composition-view.active{display:block}.xterm .xterm-viewport{cursor:default;position:absolute;inset:0;overflow-y:scroll}.xterm:not(.allow-transparency) .xterm-viewport{background-color:#000}.xterm .xterm-screen{position:relative}.xterm .xterm-screen canvas{position:absolute;top:0;left:0}.xterm.enable-mouse-events{cursor:default}.xterm.xterm-cursor-pointer,.xterm .xterm-cursor-pointer{cursor:pointer}.xterm.column-select.focus{cursor:crosshair}.xterm .xterm-accessibility:not(.debug),.xterm .xterm-message{z-index:10;color:#0000;pointer-events:none;position:absolute;inset:0}.xterm .xterm-accessibility-tree:not(.debug) ::selection{color:#0000}.xterm .xterm-accessibility-tree{user-select:text;white-space:pre;font-family:monospace}.xterm .xterm-accessibility-tree>div{transform-origin:0;width:fit-content}.xterm .live-region{width:1px;height:1px;position:absolute;left:-9999px;overflow:hidden}.xterm-dim{opacity:1!important}.xterm-underline-1{text-decoration:underline}.xterm-underline-2{text-decoration:underline double}.xterm-underline-3{text-decoration:underline wavy}.xterm-underline-4{text-decoration:underline dotted}.xterm-underline-5{text-decoration:underline dashed}.xterm-overline{text-decoration:overline}.xterm-overline.xterm-underline-1{text-decoration:underline overline}.xterm-overline.xterm-underline-2{text-decoration:overline double underline}.xterm-overline.xterm-underline-3{text-decoration:overline wavy underline}.xterm-overline.xterm-underline-4{text-decoration:overline dotted underline}.xterm-overline.xterm-underline-5{text-decoration:overline dashed underline}.xterm-strikethrough{text-decoration:line-through}.xterm-screen .xterm-decoration-container .xterm-decoration{z-index:6;position:absolute}.xterm-screen .xterm-decoration-container .xterm-decoration.xterm-decoration-top-layer{z-index:7}.xterm-decoration-overview-ruler{z-index:8;pointer-events:none;position:absolute;top:0;right:0}.xterm-decoration-top{z-index:2;position:relative}.xterm .xterm-scrollable-element>.xterm-scrollbar{cursor:default}.xterm .xterm-scrollable-element>.xterm-scrollbar>.xterm-scra{cursor:pointer;background-color:var(--vscode-scrollbarSliderBackground,#64646466);-webkit-mask-image:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 11 11'><path d='M2.5 8.5 L5.5 2.5 L8.5 8.5 Z' fill='black'/></svg>");mask-image:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 11 11'><path d='M2.5 8.5 L5.5 2.5 L8.5 8.5 Z' fill='black'/></svg>");-webkit-mask-position:50%;mask-position:50%;-webkit-mask-size:100% 100%;mask-size:100% 100%;-webkit-mask-repeat:no-repeat;mask-repeat:no-repeat}.xterm .xterm-scrollable-element>.xterm-scrollbar>.xterm-scra.xterm-arrow-down{transform:rotate(180deg)}.xterm .xterm-scrollable-element>.xterm-visible{opacity:1;z-index:11;background:0 0;transition:opacity .1s linear}.xterm .xterm-scrollable-element>.xterm-invisible{opacity:0;pointer-events:none}.xterm .xterm-scrollable-element>.xterm-invisible.xterm-fade{transition:opacity .8s linear}.xterm .xterm-scrollable-element>.xterm-shadow{display:none;position:absolute}.xterm .xterm-scrollable-element>.xterm-shadow.xterm-shadow-top{width:100%;height:3px;box-shadow:var(--vscode-scrollbar-shadow,#000)0 6px 6px -6px inset;display:block;top:0;left:3px}.xterm .xterm-scrollable-element>.xterm-shadow.xterm-shadow-left{width:3px;height:100%;box-shadow:var(--vscode-scrollbar-shadow,#000)6px 0 6px -6px inset;display:block;top:3px;left:0}.xterm .xterm-scrollable-element>.xterm-shadow.xterm-shadow-top-left-corner{width:3px;height:3px;display:block;top:0;left:0}.xterm .xterm-scrollable-element>.xterm-shadow.xterm-shadow-top.xterm-shadow-left{box-shadow:var(--vscode-scrollbar-shadow,#000)6px 0 6px -6px inset}
|
|
Binary file
|
|
Binary file
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__d(function(g,r,i,a,m,e,d){"use strict";Object.defineProperty(e,'__esModule',{value:!0}),e.createDesktopAttachmentBridge=function(){const l=(0,s.createDesktopPreviewUrlResolver)({reader:(0,s.createDesktopFileReader)(),objectUrls:(0,s.createBrowserObjectUrlMinter)()});return{copyFile:t.copyDesktopAttachmentFile,writeBase64:t.writeDesktopAttachmentBase64,writeBytes:t.writeDesktopAttachmentBytes,deleteFile:t.deleteDesktopAttachmentFile,garbageCollect:t.garbageCollectDesktopAttachmentFiles,readFileBase64:s.readDesktopFileBase64,resolvePreviewUrl:t=>l.resolve(t),releasePreviewUrl:t=>l.release(t)}};var t=r(d[0]),s=r(d[1])},4397,[3924,3925]);
|
|
Binary file
|