opencode-codebuddy-external-auth 1.0.1 → 1.0.3
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/plugin.js +34 -16
- package/package.json +1 -1
package/dist/plugin.js
CHANGED
|
@@ -20,9 +20,6 @@ const CONFIG = {
|
|
|
20
20
|
function sleep(ms) {
|
|
21
21
|
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
22
22
|
}
|
|
23
|
-
function generateState() {
|
|
24
|
-
return crypto.randomUUID();
|
|
25
|
-
}
|
|
26
23
|
/**
|
|
27
24
|
* Creates an authenticated fetch function with CodeBuddy headers
|
|
28
25
|
*/
|
|
@@ -46,15 +43,37 @@ function createAuthenticatedFetch(accessToken, userId) {
|
|
|
46
43
|
// OAuth Flow Implementation (IOA Login)
|
|
47
44
|
// ============================================================================
|
|
48
45
|
/**
|
|
49
|
-
*
|
|
46
|
+
* Request auth state from server - the state is generated by server, not client!
|
|
47
|
+
* This matches the behavior of `codebuddy /login` command
|
|
50
48
|
*/
|
|
51
|
-
function
|
|
49
|
+
async function requestAuthState() {
|
|
50
|
+
// 构造与 codebuddy CLI 相同的请求
|
|
51
|
+
// codebuddy 输出的 URL: https://copilot.tencent.com/login?platform=CLI&state=xxx&ioa=1
|
|
52
52
|
const params = new URLSearchParams({
|
|
53
53
|
platform: CONFIG.platform,
|
|
54
|
-
|
|
55
|
-
|
|
54
|
+
ioa: "1",
|
|
55
|
+
});
|
|
56
|
+
const response = await fetch(`${CONFIG.serverUrl}/plugin/auth/state?${params.toString()}`, {
|
|
57
|
+
method: "GET",
|
|
58
|
+
headers: {
|
|
59
|
+
Accept: "application/json",
|
|
60
|
+
},
|
|
56
61
|
});
|
|
57
|
-
|
|
62
|
+
if (!response.ok) {
|
|
63
|
+
const text = await response.text();
|
|
64
|
+
throw new Error(`Auth state request failed: ${response.status} - ${text}`);
|
|
65
|
+
}
|
|
66
|
+
const data = await response.json();
|
|
67
|
+
if (!data.data?.state) {
|
|
68
|
+
throw new Error(`Invalid auth state response: ${JSON.stringify(data)}`);
|
|
69
|
+
}
|
|
70
|
+
// 构造登录 URL(与 codebuddy CLI 输出的格式一致)
|
|
71
|
+
const loginUrl = data.data.url ||
|
|
72
|
+
`${CONFIG.serverUrl}/login?platform=${CONFIG.platform}&state=${data.data.state}&ioa=1`;
|
|
73
|
+
return {
|
|
74
|
+
state: data.data.state,
|
|
75
|
+
url: loginUrl,
|
|
76
|
+
};
|
|
58
77
|
}
|
|
59
78
|
/**
|
|
60
79
|
* Poll for token after user completes browser authentication
|
|
@@ -70,8 +89,7 @@ async function pollForToken(state, expiresAt, signal) {
|
|
|
70
89
|
const response = await fetch(`${CONFIG.serverUrl}/plugin/auth/token?state=${state}`, {
|
|
71
90
|
method: "GET",
|
|
72
91
|
headers: {
|
|
73
|
-
|
|
74
|
-
"Accept": "application/json",
|
|
92
|
+
Accept: "application/json",
|
|
75
93
|
},
|
|
76
94
|
signal,
|
|
77
95
|
});
|
|
@@ -155,17 +173,17 @@ const CodeBuddyExternalAuthPlugin = async (_input) => {
|
|
|
155
173
|
label: "IOA 登录 (浏览器)",
|
|
156
174
|
type: "oauth",
|
|
157
175
|
async authorize() {
|
|
158
|
-
//
|
|
159
|
-
|
|
160
|
-
const
|
|
176
|
+
// 关键修改:从服务端获取 state,而不是客户端生成
|
|
177
|
+
// 这与 codebuddy CLI 的 /login 命令行为一致
|
|
178
|
+
const authState = await requestAuthState();
|
|
161
179
|
const expiresAt = Date.now() + 10 * 60 * 1000; // 10 minutes
|
|
162
180
|
return {
|
|
163
|
-
url:
|
|
181
|
+
url: authState.url,
|
|
164
182
|
instructions: `请在浏览器中完成 IOA 登录`,
|
|
165
183
|
method: "auto",
|
|
166
184
|
async callback() {
|
|
167
|
-
//
|
|
168
|
-
const tokenData = await pollForToken(state, expiresAt);
|
|
185
|
+
// 使用服务端返回的 state 轮询 token
|
|
186
|
+
const tokenData = await pollForToken(authState.state, expiresAt);
|
|
169
187
|
if (!tokenData) {
|
|
170
188
|
return { type: "failed" };
|
|
171
189
|
}
|