ai_co_discuss 0.3.77 → 0.3.79

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ai_co_discuss",
3
- "version": "0.3.77",
3
+ "version": "0.3.79",
4
4
  "bin": {
5
5
  "codiscuss": "runner/codiscuss.mjs"
6
6
  },
package/web/app.js CHANGED
@@ -2330,6 +2330,8 @@ async function pair_this_device(code) {
2330
2330
  // WebAuthn must run on the user's tap, so everything above is ready before the dialog asks for it.
2331
2331
  return passkey_prompt({ title: "配对这台设备", description: "用这台设备的面容、指纹或设备密码确认,完成与电脑的配对。之后打开网页即可使用,无需账号和密码。", confirm_label: "继续",
2332
2332
  run: async () => {
2333
+ // A refused passkey still asks the computer, which accepts it only when this code was made to allow no passkey.
2334
+ let refused = null;
2333
2335
  const created = await (typeof navigator.credentials?.create === "function" ? navigator.credentials.create({ publicKey: { challenge, rp: { id: location.hostname, name: "AI CoDiscuss" },
2334
2336
  user: { id: crypto.getRandomValues(new Uint8Array(16)), name: `codiscuss · ${device_label()}`, displayName: `AI CoDiscuss · ${device_label()}` },
2335
2337
  pubKeyCredParams: [{ type: "public-key", alg: -7 }, { type: "public-key", alg: -257 }],
@@ -2338,11 +2340,14 @@ async function pair_this_device(code) {
2338
2340
  .catch(error => {
2339
2341
  // A browser without a working credential manager (e.g. Android without Google Play services) pairs by its device key alone.
2340
2342
  if (PASSKEY_UNAVAILABLE.has(error?.name)) return null;
2341
- throw passkey_error(error);
2343
+ if (error?.name !== "NotAllowedError") throw passkey_error(error);
2344
+ refused = error;
2345
+ return null;
2342
2346
  });
2343
2347
  const passkey = created && { id: bytes_to_b64url(created.rawId), client_data_json: bytes_to_b64url(created.response.clientDataJSON),
2344
2348
  attestation_object: bytes_to_b64url(created.response.attestationObject) };
2345
2349
  const answer = await pair_exchange(machine, { public_key: device.public_jwk, label: device_label(), proof, passkey });
2350
+ if (answer.status >= 400 && refused && answer.body?.need === "passkey") throw passkey_error(refused);
2346
2351
  if (answer.status >= 400) throw new Error(answer.body?.error || "配对失败");
2347
2352
  localStorage.setItem(PAIRED_KEY, JSON.stringify({ machine_id: machine.id, fingerprint }));
2348
2353
  Object.assign(state.device, { needs: "", pairing_code: "", pairing_fp: "" });