feat(web): Add api key components

This commit is contained in:
maooyer
2026-04-22 21:51:21 +08:00
committed by shuaiplus
parent 31ffd98166
commit 1147c1e013
6 changed files with 165 additions and 0 deletions
+28
View File
@@ -594,3 +594,31 @@ export async function deleteAllAuthorizedDevices(authedFetch: AuthedFetch): Prom
const resp = await authedFetch('/api/devices', { method: 'DELETE' });
if (!resp.ok) throw new Error(t('txt_remove_all_devices_failed'));
}
export async function getApiKey(authedFetch: AuthedFetch, masterPasswordHash: string): Promise<string> {
const resp = await authedFetch('/api/accounts/api_key', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ masterPasswordHash }),
});
if (!resp.ok) {
const body = await parseJson<TokenError>(resp);
throw new Error(body?.error_description || body?.error || 'Failed to get API key');
}
const body = (await parseJson<{ apiKey?: string }>(resp)) || {};
return String(body.apiKey || '');
}
export async function rotateApiKey(authedFetch: AuthedFetch, masterPasswordHash: string): Promise<string> {
const resp = await authedFetch('/api/accounts/rotate_api_key', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ masterPasswordHash }),
});
if (!resp.ok) {
const body = await parseJson<TokenError>(resp);
throw new Error(body?.error_description || body?.error || 'Failed to rotate API key');
}
const body = (await parseJson<{ apiKey?: string }>(resp)) || {};
return String(body.apiKey || '');
}
+22
View File
@@ -601,6 +601,17 @@ const messages: Record<Locale, Record<string, string>> = {
txt_recovery_code_copied: "Recovery code copied",
txt_recovery_code_is_empty: "Recovery code is empty",
txt_recovery_code_loaded: "Recovery code loaded",
txt_api_key: "API Key",
txt_view_api_key: "View API Key",
txt_rotate_api_key: "Rotate API Key",
txt_api_key_copied: "API key copied",
txt_api_key_loaded: "API key loaded",
txt_api_key_rotated: "API key rotated",
txt_rotate_api_key_confirm: "Rotate API key? The current key will stop working immediately.",
txt_api_key_is_empty: "API key is empty",
txt_client_id: "client_id",
txt_client_secret: "client_secret",
txt_scope: "scope",
txt_refresh: "Refresh",
txt_refresh_in_seconds_s: "Refresh in {seconds}s",
txt_regenerate: "Regenerate",
@@ -1363,6 +1374,17 @@ const zhCNOverrides: Record<string, string> = {
txt_recovery_code_copied: '恢复代码已复制',
txt_recovery_code_is_empty: '恢复代码为空',
txt_recovery_code_loaded: '恢复代码已加载',
txt_api_key: 'API 密钥',
txt_view_api_key: '查看 API 密钥',
txt_rotate_api_key: '轮换 API 密钥',
txt_api_key_copied: 'API 密钥已复制',
txt_api_key_loaded: 'API 密钥已加载',
txt_api_key_rotated: 'API 密钥已轮换',
txt_rotate_api_key_confirm: '轮换 API 密钥?当前密钥将立即失效。',
txt_api_key_is_empty: 'API 密钥为空',
txt_client_id: 'client_id',
txt_client_secret: 'client_secret',
txt_scope: 'scope',
txt_refresh_in_seconds_s: '{seconds} 秒后刷新',
txt_registration_succeeded_please_sign_in: '注册成功,请登录',
txt_remove_device: '移除设备',