feat!: drop the backend-side elevation windows; password and passkey sessions share capabilities, passkeys guard what nodes verify; the trust page lists added and removed passkeys [CI]

This commit is contained in:
justme committed 2026-10-08 04:57:28 +08:00
1 parent f704c66dd9
commit 4106f831dc
34 files changed
+191 -1364

No files matched your search

@@ -275,7 +275,7 @@ public class BackendFixture : IAsyncLifetime
/// <summary>
/// 管理员的全能力 API key:和线上一样的路径——密码登录的会话没有任何能力,只能注册 passkey;
/// 注册之后用 passkey 登录才有能力,再触碰一次开凭证窗口,才能创建带信任类能力的 key。
/// 注册之后用 passkey 登录(要签操作员集合等节点会验证的事时才需要 passkey)。
/// </summary>
private async Task<string> CreateAdminTokenAsync()
{
@@ -306,15 +306,6 @@ public class BackendFixture : IAsyncLifetime
strong.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", JsonNode.Parse(await signedIn.Content.ReadAsStringAsync())!["session_token"]!.GetValue<string>());
}
using (HttpResponseMessage options = await strong.PostAsync("/api/admin/auth/elevation/options", Json(new JsonObject { ["class"] = "credential" })))
{
options.EnsureSuccessStatusCode();
JsonObject assertion = passkey.Assert(JsonNode.Parse(await options.Content.ReadAsStringAsync())!["challenge"]!.GetValue<string>());
assertion["class"] = "credential";
using HttpResponseMessage elevated = await strong.PostAsync("/api/admin/auth/elevation", Json(assertion));
elevated.EnsureSuccessStatusCode();
}
using HttpResponseMessage created = await strong.PostAsync("/api/admin/api-tokens", Json(new JsonObject { ["name"] = "tests", ["capabilities"] = AllCapabilities() }));
created.EnsureSuccessStatusCode();
return JsonNode.Parse(await created.Content.ReadAsStringAsync())!["plaintext"]!.GetValue<string>();