this repo has no description
1import { err, ok, type Result } from "./types/result.ts"; 2import type { 3 AccessToken, 4 Did, 5 EmailAddress, 6 Handle, 7 Nsid, 8 RefreshToken, 9 Rkey, 10} from "./types/branded.ts"; 11import { 12 unsafeAsAccessToken, 13 unsafeAsDid, 14 unsafeAsEmail, 15 unsafeAsHandle, 16 unsafeAsISODate, 17 unsafeAsRefreshToken, 18} from "./types/branded.ts"; 19import type { 20 AccountInfo, 21 ApiErrorCode, 22 AppPassword, 23 CompletePasskeySetupResponse, 24 ConfirmSignupResult, 25 CreateAccountParams, 26 CreateAccountResult, 27 CreateBackupResponse, 28 CreatedAppPassword, 29 CreateRecordResponse, 30 DidDocument, 31 DidType, 32 EmailUpdateResponse, 33 EnableTotpResponse, 34 FinishPasskeyRegistrationResponse, 35 GetInviteCodesResponse, 36 InviteCodeInfo, 37 LegacyLoginPreference, 38 ListBackupsResponse, 39 ListPasskeysResponse, 40 ListRecordsResponse, 41 ListReposResponse, 42 ListSessionsResponse, 43 ListTrustedDevicesResponse, 44 NotificationHistoryResponse, 45 NotificationPrefs, 46 PasskeyAccountCreateResponse, 47 PasswordStatus, 48 ReauthPasskeyStartResponse, 49 ReauthResponse, 50 ReauthStatus, 51 RecommendedDidCredentials, 52 RecordResponse, 53 RegenerateBackupCodesResponse, 54 RepoDescription, 55 ResendMigrationVerificationResponse, 56 ReserveSigningKeyResponse, 57 SearchAccountsResponse, 58 ServerConfig, 59 ServerDescription, 60 ServerStats, 61 Session, 62 SetBackupEnabledResponse, 63 StartPasskeyRegistrationResponse, 64 SuccessResponse, 65 TotpSecret, 66 TotpStatus, 67 UpdateLegacyLoginResponse, 68 UpdateLocaleResponse, 69 UploadBlobResponse, 70 VerificationChannel, 71 VerifyMigrationEmailResponse, 72 VerifyTokenResponse, 73} from "./types/api.ts"; 74 75const API_BASE = "/xrpc"; 76 77export class ApiError extends Error { 78 public did?: Did; 79 public reauthMethods?: string[]; 80 constructor( 81 public status: number, 82 public error: ApiErrorCode, 83 message: string, 84 did?: string, 85 reauthMethods?: string[], 86 ) { 87 super(message); 88 this.name = "ApiError"; 89 this.did = did ? unsafeAsDid(did) : undefined; 90 this.reauthMethods = reauthMethods; 91 } 92} 93 94let tokenRefreshCallback: (() => Promise<string | null>) | null = null; 95 96export function setTokenRefreshCallback( 97 callback: () => Promise<string | null>, 98) { 99 tokenRefreshCallback = callback; 100} 101 102interface XrpcOptions { 103 method?: "GET" | "POST"; 104 params?: Record<string, string>; 105 body?: unknown; 106 token?: string; 107 skipRetry?: boolean; 108} 109 110async function xrpc<T>(method: string, options?: XrpcOptions): Promise<T> { 111 const { method: httpMethod = "GET", params, body, token, skipRetry } = 112 options ?? {}; 113 let url = `${API_BASE}/${method}`; 114 if (params) { 115 const searchParams = new URLSearchParams(params); 116 url += `?${searchParams}`; 117 } 118 const headers: Record<string, string> = {}; 119 if (token) { 120 headers["Authorization"] = `Bearer ${token}`; 121 } 122 if (body) { 123 headers["Content-Type"] = "application/json"; 124 } 125 const res = await fetch(url, { 126 method: httpMethod, 127 headers, 128 body: body ? JSON.stringify(body) : undefined, 129 }); 130 if (!res.ok) { 131 const errData = await res.json().catch(() => ({ 132 error: "Unknown", 133 message: res.statusText, 134 })); 135 if ( 136 res.status === 401 && 137 (errData.error === "AuthenticationFailed" || 138 errData.error === "ExpiredToken") && 139 token && tokenRefreshCallback && !skipRetry 140 ) { 141 const newToken = await tokenRefreshCallback(); 142 if (newToken && newToken !== token) { 143 return xrpc(method, { ...options, token: newToken, skipRetry: true }); 144 } 145 } 146 throw new ApiError( 147 res.status, 148 errData.error as ApiErrorCode, 149 errData.message, 150 errData.did, 151 errData.reauthMethods, 152 ); 153 } 154 return res.json(); 155} 156 157async function xrpcResult<T>( 158 method: string, 159 options?: XrpcOptions, 160): Promise<Result<T, ApiError>> { 161 try { 162 const value = await xrpc<T>(method, options); 163 return ok(value); 164 } catch (e) { 165 if (e instanceof ApiError) { 166 return err(e); 167 } 168 return err( 169 new ApiError(0, "Unknown", e instanceof Error ? e.message : String(e)), 170 ); 171 } 172} 173 174export interface VerificationMethod { 175 id: string; 176 type: string; 177 publicKeyMultibase: string; 178} 179 180export type { AppPassword, DidDocument, InviteCodeInfo as InviteCode, Session }; 181export type { 182 ConfirmSignupResult, 183 CreateAccountParams, 184 CreateAccountResult, 185 DidType, 186 VerificationChannel, 187}; 188 189function castSession(raw: unknown): Session { 190 const s = raw as Record<string, unknown>; 191 return { 192 did: unsafeAsDid(s.did as string), 193 handle: unsafeAsHandle(s.handle as string), 194 email: s.email ? unsafeAsEmail(s.email as string) : undefined, 195 emailConfirmed: s.emailConfirmed as boolean | undefined, 196 preferredChannel: s.preferredChannel as VerificationChannel | undefined, 197 preferredChannelVerified: s.preferredChannelVerified as boolean | undefined, 198 isAdmin: s.isAdmin as boolean | undefined, 199 active: s.active as boolean | undefined, 200 status: s.status as Session["status"], 201 migratedToPds: s.migratedToPds as string | undefined, 202 migratedAt: s.migratedAt 203 ? unsafeAsISODate(s.migratedAt as string) 204 : undefined, 205 accessJwt: unsafeAsAccessToken(s.accessJwt as string), 206 refreshJwt: unsafeAsRefreshToken(s.refreshJwt as string), 207 }; 208} 209 210export const api = { 211 async createAccount( 212 params: CreateAccountParams, 213 byodToken?: string, 214 ): Promise<CreateAccountResult> { 215 const url = `${API_BASE}/com.atproto.server.createAccount`; 216 const headers: Record<string, string> = { 217 "Content-Type": "application/json", 218 }; 219 if (byodToken) { 220 headers["Authorization"] = `Bearer ${byodToken}`; 221 } 222 const response = await fetch(url, { 223 method: "POST", 224 headers, 225 body: JSON.stringify({ 226 handle: params.handle, 227 email: params.email, 228 password: params.password, 229 inviteCode: params.inviteCode, 230 didType: params.didType, 231 did: params.did, 232 signingKey: params.signingKey, 233 verificationChannel: params.verificationChannel, 234 discordId: params.discordId, 235 telegramUsername: params.telegramUsername, 236 signalNumber: params.signalNumber, 237 }), 238 }); 239 const data = await response.json(); 240 if (!response.ok) { 241 throw new ApiError(response.status, data.error, data.message); 242 } 243 return data; 244 }, 245 246 async createAccountWithServiceAuth( 247 serviceAuthToken: string, 248 params: { 249 did: Did; 250 handle: Handle; 251 email: EmailAddress; 252 password: string; 253 inviteCode?: string; 254 }, 255 ): Promise<Session> { 256 const url = `${API_BASE}/com.atproto.server.createAccount`; 257 const response = await fetch(url, { 258 method: "POST", 259 headers: { 260 "Content-Type": "application/json", 261 "Authorization": `Bearer ${serviceAuthToken}`, 262 }, 263 body: JSON.stringify({ 264 did: params.did, 265 handle: params.handle, 266 email: params.email, 267 password: params.password, 268 inviteCode: params.inviteCode, 269 }), 270 }); 271 const data = await response.json(); 272 if (!response.ok) { 273 throw new ApiError(response.status, data.error, data.message); 274 } 275 return castSession(data); 276 }, 277 278 confirmSignup( 279 did: Did, 280 verificationCode: string, 281 ): Promise<ConfirmSignupResult> { 282 return xrpc("com.atproto.server.confirmSignup", { 283 method: "POST", 284 body: { did, verificationCode }, 285 }); 286 }, 287 288 resendVerification(did: Did): Promise<{ success: boolean }> { 289 return xrpc("com.atproto.server.resendVerification", { 290 method: "POST", 291 body: { did }, 292 }); 293 }, 294 295 async createSession(identifier: string, password: string): Promise<Session> { 296 const raw = await xrpc<unknown>("com.atproto.server.createSession", { 297 method: "POST", 298 body: { identifier, password }, 299 }); 300 return castSession(raw); 301 }, 302 303 checkEmailVerified(identifier: string): Promise<{ verified: boolean }> { 304 return xrpc("_checkEmailVerified", { 305 method: "POST", 306 body: { identifier }, 307 }); 308 }, 309 310 async getSession(token: AccessToken): Promise<Session> { 311 const raw = await xrpc<unknown>("com.atproto.server.getSession", { token }); 312 return castSession(raw); 313 }, 314 315 async refreshSession(refreshJwt: RefreshToken): Promise<Session> { 316 const raw = await xrpc<unknown>("com.atproto.server.refreshSession", { 317 method: "POST", 318 token: refreshJwt, 319 }); 320 return castSession(raw); 321 }, 322 323 async deleteSession(token: AccessToken): Promise<void> { 324 await xrpc("com.atproto.server.deleteSession", { 325 method: "POST", 326 token, 327 }); 328 }, 329 330 listAppPasswords(token: AccessToken): Promise<{ passwords: AppPassword[] }> { 331 return xrpc("com.atproto.server.listAppPasswords", { token }); 332 }, 333 334 createAppPassword( 335 token: AccessToken, 336 name: string, 337 scopes?: string, 338 ): Promise<CreatedAppPassword> { 339 return xrpc("com.atproto.server.createAppPassword", { 340 method: "POST", 341 token, 342 body: { name, scopes }, 343 }); 344 }, 345 346 async revokeAppPassword(token: AccessToken, name: string): Promise<void> { 347 await xrpc("com.atproto.server.revokeAppPassword", { 348 method: "POST", 349 token, 350 body: { name }, 351 }); 352 }, 353 354 getAccountInviteCodes( 355 token: AccessToken, 356 ): Promise<{ codes: InviteCodeInfo[] }> { 357 return xrpc("com.atproto.server.getAccountInviteCodes", { token }); 358 }, 359 360 createInviteCode( 361 token: AccessToken, 362 useCount: number = 1, 363 ): Promise<{ code: string }> { 364 return xrpc("com.atproto.server.createInviteCode", { 365 method: "POST", 366 token, 367 body: { useCount }, 368 }); 369 }, 370 371 async requestPasswordReset(email: EmailAddress): Promise<void> { 372 await xrpc("com.atproto.server.requestPasswordReset", { 373 method: "POST", 374 body: { email }, 375 }); 376 }, 377 378 async resetPassword(token: string, password: string): Promise<void> { 379 await xrpc("com.atproto.server.resetPassword", { 380 method: "POST", 381 body: { token, password }, 382 }); 383 }, 384 385 requestEmailUpdate(token: AccessToken): Promise<EmailUpdateResponse> { 386 return xrpc("com.atproto.server.requestEmailUpdate", { 387 method: "POST", 388 token, 389 }); 390 }, 391 392 async updateEmail( 393 token: AccessToken, 394 email: string, 395 emailToken?: string, 396 ): Promise<void> { 397 await xrpc("com.atproto.server.updateEmail", { 398 method: "POST", 399 token, 400 body: { email, token: emailToken }, 401 }); 402 }, 403 404 async updateHandle(token: AccessToken, handle: Handle): Promise<void> { 405 await xrpc("com.atproto.identity.updateHandle", { 406 method: "POST", 407 token, 408 body: { handle }, 409 }); 410 }, 411 412 async requestAccountDelete(token: AccessToken): Promise<void> { 413 await xrpc("com.atproto.server.requestAccountDelete", { 414 method: "POST", 415 token, 416 }); 417 }, 418 419 async deleteAccount( 420 did: Did, 421 password: string, 422 deleteToken: string, 423 ): Promise<void> { 424 await xrpc("com.atproto.server.deleteAccount", { 425 method: "POST", 426 body: { did, password, token: deleteToken }, 427 }); 428 }, 429 430 describeServer(): Promise<ServerDescription> { 431 return xrpc("com.atproto.server.describeServer"); 432 }, 433 434 listRepos(limit?: number): Promise<ListReposResponse> { 435 const params: Record<string, string> = {}; 436 if (limit) params.limit = String(limit); 437 return xrpc("com.atproto.sync.listRepos", { params }); 438 }, 439 440 getNotificationPrefs(token: AccessToken): Promise<NotificationPrefs> { 441 return xrpc("_account.getNotificationPrefs", { token }); 442 }, 443 444 updateNotificationPrefs(token: AccessToken, prefs: { 445 preferredChannel?: string; 446 discordId?: string; 447 telegramUsername?: string; 448 signalNumber?: string; 449 }): Promise<SuccessResponse> { 450 return xrpc("_account.updateNotificationPrefs", { 451 method: "POST", 452 token, 453 body: prefs, 454 }); 455 }, 456 457 confirmChannelVerification( 458 token: AccessToken, 459 channel: string, 460 identifier: string, 461 code: string, 462 ): Promise<SuccessResponse> { 463 return xrpc("_account.confirmChannelVerification", { 464 method: "POST", 465 token, 466 body: { channel, identifier, code }, 467 }); 468 }, 469 470 getNotificationHistory( 471 token: AccessToken, 472 ): Promise<NotificationHistoryResponse> { 473 return xrpc("_account.getNotificationHistory", { token }); 474 }, 475 476 getServerStats(token: AccessToken): Promise<ServerStats> { 477 return xrpc("_admin.getServerStats", { token }); 478 }, 479 480 getServerConfig(): Promise<ServerConfig> { 481 return xrpc("_server.getConfig"); 482 }, 483 484 updateServerConfig( 485 token: AccessToken, 486 config: { 487 serverName?: string; 488 primaryColor?: string; 489 primaryColorDark?: string; 490 secondaryColor?: string; 491 secondaryColorDark?: string; 492 logoCid?: string; 493 }, 494 ): Promise<SuccessResponse> { 495 return xrpc("_admin.updateServerConfig", { 496 method: "POST", 497 token, 498 body: config, 499 }); 500 }, 501 502 async uploadBlob( 503 token: AccessToken, 504 file: File, 505 ): Promise<UploadBlobResponse> { 506 const res = await fetch("/xrpc/com.atproto.repo.uploadBlob", { 507 method: "POST", 508 headers: { 509 "Authorization": `Bearer ${token}`, 510 "Content-Type": file.type, 511 }, 512 body: file, 513 }); 514 if (!res.ok) { 515 const errData = await res.json().catch(() => ({ 516 error: "Unknown", 517 message: res.statusText, 518 })); 519 throw new ApiError(res.status, errData.error, errData.message); 520 } 521 return res.json(); 522 }, 523 524 async changePassword( 525 token: AccessToken, 526 currentPassword: string, 527 newPassword: string, 528 ): Promise<void> { 529 await xrpc("_account.changePassword", { 530 method: "POST", 531 token, 532 body: { currentPassword, newPassword }, 533 }); 534 }, 535 536 removePassword(token: AccessToken): Promise<SuccessResponse> { 537 return xrpc("_account.removePassword", { 538 method: "POST", 539 token, 540 }); 541 }, 542 543 setPassword(token: AccessToken, newPassword: string): Promise<SuccessResponse> { 544 return xrpc("_account.setPassword", { 545 method: "POST", 546 token, 547 body: { newPassword }, 548 }); 549 }, 550 551 getPasswordStatus(token: AccessToken): Promise<PasswordStatus> { 552 return xrpc("_account.getPasswordStatus", { token }); 553 }, 554 555 getLegacyLoginPreference(token: AccessToken): Promise<LegacyLoginPreference> { 556 return xrpc("_account.getLegacyLoginPreference", { token }); 557 }, 558 559 updateLegacyLoginPreference( 560 token: AccessToken, 561 allowLegacyLogin: boolean, 562 ): Promise<UpdateLegacyLoginResponse> { 563 return xrpc("_account.updateLegacyLoginPreference", { 564 method: "POST", 565 token, 566 body: { allowLegacyLogin }, 567 }); 568 }, 569 570 updateLocale( 571 token: AccessToken, 572 preferredLocale: string, 573 ): Promise<UpdateLocaleResponse> { 574 return xrpc("_account.updateLocale", { 575 method: "POST", 576 token, 577 body: { preferredLocale }, 578 }); 579 }, 580 581 listSessions(token: AccessToken): Promise<ListSessionsResponse> { 582 return xrpc("_account.listSessions", { token }); 583 }, 584 585 async revokeSession(token: AccessToken, sessionId: string): Promise<void> { 586 await xrpc("_account.revokeSession", { 587 method: "POST", 588 token, 589 body: { sessionId }, 590 }); 591 }, 592 593 revokeAllSessions(token: AccessToken): Promise<{ revokedCount: number }> { 594 return xrpc("_account.revokeAllSessions", { 595 method: "POST", 596 token, 597 }); 598 }, 599 600 searchAccounts(token: AccessToken, options?: { 601 handle?: string; 602 cursor?: string; 603 limit?: number; 604 }): Promise<SearchAccountsResponse> { 605 const params: Record<string, string> = {}; 606 if (options?.handle) params.handle = options.handle; 607 if (options?.cursor) params.cursor = options.cursor; 608 if (options?.limit) params.limit = String(options.limit); 609 return xrpc("com.atproto.admin.searchAccounts", { token, params }); 610 }, 611 612 getInviteCodes(token: AccessToken, options?: { 613 sort?: "recent" | "usage"; 614 cursor?: string; 615 limit?: number; 616 }): Promise<GetInviteCodesResponse> { 617 const params: Record<string, string> = {}; 618 if (options?.sort) params.sort = options.sort; 619 if (options?.cursor) params.cursor = options.cursor; 620 if (options?.limit) params.limit = String(options.limit); 621 return xrpc("com.atproto.admin.getInviteCodes", { token, params }); 622 }, 623 624 async disableInviteCodes( 625 token: AccessToken, 626 codes?: string[], 627 accounts?: string[], 628 ): Promise<void> { 629 await xrpc("com.atproto.admin.disableInviteCodes", { 630 method: "POST", 631 token, 632 body: { codes, accounts }, 633 }); 634 }, 635 636 getAccountInfo(token: AccessToken, did: Did): Promise<AccountInfo> { 637 return xrpc("com.atproto.admin.getAccountInfo", { token, params: { did } }); 638 }, 639 640 async disableAccountInvites(token: AccessToken, account: Did): Promise<void> { 641 await xrpc("com.atproto.admin.disableAccountInvites", { 642 method: "POST", 643 token, 644 body: { account }, 645 }); 646 }, 647 648 async enableAccountInvites(token: AccessToken, account: Did): Promise<void> { 649 await xrpc("com.atproto.admin.enableAccountInvites", { 650 method: "POST", 651 token, 652 body: { account }, 653 }); 654 }, 655 656 async adminDeleteAccount(token: AccessToken, did: Did): Promise<void> { 657 await xrpc("com.atproto.admin.deleteAccount", { 658 method: "POST", 659 token, 660 body: { did }, 661 }); 662 }, 663 664 describeRepo(token: AccessToken, repo: Did): Promise<RepoDescription> { 665 return xrpc("com.atproto.repo.describeRepo", { 666 token, 667 params: { repo }, 668 }); 669 }, 670 671 listRecords(token: AccessToken, repo: Did, collection: Nsid, options?: { 672 limit?: number; 673 cursor?: string; 674 reverse?: boolean; 675 }): Promise<ListRecordsResponse> { 676 const params: Record<string, string> = { repo, collection }; 677 if (options?.limit) params.limit = String(options.limit); 678 if (options?.cursor) params.cursor = options.cursor; 679 if (options?.reverse) params.reverse = "true"; 680 return xrpc("com.atproto.repo.listRecords", { token, params }); 681 }, 682 683 getRecord( 684 token: AccessToken, 685 repo: Did, 686 collection: Nsid, 687 rkey: Rkey, 688 ): Promise<RecordResponse> { 689 return xrpc("com.atproto.repo.getRecord", { 690 token, 691 params: { repo, collection, rkey }, 692 }); 693 }, 694 695 createRecord( 696 token: AccessToken, 697 repo: Did, 698 collection: Nsid, 699 record: unknown, 700 rkey?: Rkey, 701 ): Promise<CreateRecordResponse> { 702 return xrpc("com.atproto.repo.createRecord", { 703 method: "POST", 704 token, 705 body: { repo, collection, record, rkey }, 706 }); 707 }, 708 709 putRecord( 710 token: AccessToken, 711 repo: Did, 712 collection: Nsid, 713 rkey: Rkey, 714 record: unknown, 715 ): Promise<CreateRecordResponse> { 716 return xrpc("com.atproto.repo.putRecord", { 717 method: "POST", 718 token, 719 body: { repo, collection, rkey, record }, 720 }); 721 }, 722 723 async deleteRecord( 724 token: AccessToken, 725 repo: Did, 726 collection: Nsid, 727 rkey: Rkey, 728 ): Promise<void> { 729 await xrpc("com.atproto.repo.deleteRecord", { 730 method: "POST", 731 token, 732 body: { repo, collection, rkey }, 733 }); 734 }, 735 736 getTotpStatus(token: AccessToken): Promise<TotpStatus> { 737 return xrpc("com.atproto.server.getTotpStatus", { token }); 738 }, 739 740 createTotpSecret(token: AccessToken): Promise<TotpSecret> { 741 return xrpc("com.atproto.server.createTotpSecret", { 742 method: "POST", 743 token, 744 }); 745 }, 746 747 enableTotp(token: AccessToken, code: string): Promise<EnableTotpResponse> { 748 return xrpc("com.atproto.server.enableTotp", { 749 method: "POST", 750 token, 751 body: { code }, 752 }); 753 }, 754 755 disableTotp( 756 token: AccessToken, 757 password: string, 758 code: string, 759 ): Promise<SuccessResponse> { 760 return xrpc("com.atproto.server.disableTotp", { 761 method: "POST", 762 token, 763 body: { password, code }, 764 }); 765 }, 766 767 regenerateBackupCodes( 768 token: AccessToken, 769 password: string, 770 code: string, 771 ): Promise<RegenerateBackupCodesResponse> { 772 return xrpc("com.atproto.server.regenerateBackupCodes", { 773 method: "POST", 774 token, 775 body: { password, code }, 776 }); 777 }, 778 779 startPasskeyRegistration( 780 token: AccessToken, 781 friendlyName?: string, 782 ): Promise<StartPasskeyRegistrationResponse> { 783 return xrpc("com.atproto.server.startPasskeyRegistration", { 784 method: "POST", 785 token, 786 body: { friendlyName }, 787 }); 788 }, 789 790 finishPasskeyRegistration( 791 token: AccessToken, 792 credential: unknown, 793 friendlyName?: string, 794 ): Promise<FinishPasskeyRegistrationResponse> { 795 return xrpc("com.atproto.server.finishPasskeyRegistration", { 796 method: "POST", 797 token, 798 body: { credential, friendlyName }, 799 }); 800 }, 801 802 listPasskeys(token: AccessToken): Promise<ListPasskeysResponse> { 803 return xrpc("com.atproto.server.listPasskeys", { token }); 804 }, 805 806 async deletePasskey(token: AccessToken, id: string): Promise<void> { 807 await xrpc("com.atproto.server.deletePasskey", { 808 method: "POST", 809 token, 810 body: { id }, 811 }); 812 }, 813 814 async updatePasskey( 815 token: AccessToken, 816 id: string, 817 friendlyName: string, 818 ): Promise<void> { 819 await xrpc("com.atproto.server.updatePasskey", { 820 method: "POST", 821 token, 822 body: { id, friendlyName }, 823 }); 824 }, 825 826 listTrustedDevices(token: AccessToken): Promise<ListTrustedDevicesResponse> { 827 return xrpc("_account.listTrustedDevices", { token }); 828 }, 829 830 revokeTrustedDevice( 831 token: AccessToken, 832 deviceId: string, 833 ): Promise<SuccessResponse> { 834 return xrpc("_account.revokeTrustedDevice", { 835 method: "POST", 836 token, 837 body: { deviceId }, 838 }); 839 }, 840 841 updateTrustedDevice( 842 token: AccessToken, 843 deviceId: string, 844 friendlyName: string, 845 ): Promise<SuccessResponse> { 846 return xrpc("_account.updateTrustedDevice", { 847 method: "POST", 848 token, 849 body: { deviceId, friendlyName }, 850 }); 851 }, 852 853 getReauthStatus(token: AccessToken): Promise<ReauthStatus> { 854 return xrpc("_account.getReauthStatus", { token }); 855 }, 856 857 reauthPassword( 858 token: AccessToken, 859 password: string, 860 ): Promise<ReauthResponse> { 861 return xrpc("_account.reauthPassword", { 862 method: "POST", 863 token, 864 body: { password }, 865 }); 866 }, 867 868 reauthTotp(token: AccessToken, code: string): Promise<ReauthResponse> { 869 return xrpc("_account.reauthTotp", { 870 method: "POST", 871 token, 872 body: { code }, 873 }); 874 }, 875 876 reauthPasskeyStart(token: AccessToken): Promise<ReauthPasskeyStartResponse> { 877 return xrpc("_account.reauthPasskeyStart", { 878 method: "POST", 879 token, 880 }); 881 }, 882 883 reauthPasskeyFinish( 884 token: AccessToken, 885 credential: unknown, 886 ): Promise<ReauthResponse> { 887 return xrpc("_account.reauthPasskeyFinish", { 888 method: "POST", 889 token, 890 body: { credential }, 891 }); 892 }, 893 894 reserveSigningKey(did?: Did): Promise<ReserveSigningKeyResponse> { 895 return xrpc("com.atproto.server.reserveSigningKey", { 896 method: "POST", 897 body: { did }, 898 }); 899 }, 900 901 getRecommendedDidCredentials( 902 token: AccessToken, 903 ): Promise<RecommendedDidCredentials> { 904 return xrpc("com.atproto.identity.getRecommendedDidCredentials", { token }); 905 }, 906 907 async activateAccount(token: AccessToken): Promise<void> { 908 await xrpc("com.atproto.server.activateAccount", { 909 method: "POST", 910 token, 911 }); 912 }, 913 914 async createPasskeyAccount(params: { 915 handle: Handle; 916 email?: EmailAddress; 917 inviteCode?: string; 918 didType?: DidType; 919 did?: Did; 920 signingKey?: string; 921 verificationChannel?: VerificationChannel; 922 discordId?: string; 923 telegramUsername?: string; 924 signalNumber?: string; 925 }, byodToken?: string): Promise<PasskeyAccountCreateResponse> { 926 const url = `${API_BASE}/_account.createPasskeyAccount`; 927 const headers: Record<string, string> = { 928 "Content-Type": "application/json", 929 }; 930 if (byodToken) { 931 headers["Authorization"] = `Bearer ${byodToken}`; 932 } 933 const res = await fetch(url, { 934 method: "POST", 935 headers, 936 body: JSON.stringify(params), 937 }); 938 if (!res.ok) { 939 const errData = await res.json().catch(() => ({ 940 error: "Unknown", 941 message: res.statusText, 942 })); 943 throw new ApiError(res.status, errData.error, errData.message); 944 } 945 return res.json(); 946 }, 947 948 startPasskeyRegistrationForSetup( 949 did: Did, 950 setupToken: string, 951 friendlyName?: string, 952 ): Promise<StartPasskeyRegistrationResponse> { 953 return xrpc("_account.startPasskeyRegistrationForSetup", { 954 method: "POST", 955 body: { did, setupToken, friendlyName }, 956 }); 957 }, 958 959 completePasskeySetup( 960 did: Did, 961 setupToken: string, 962 passkeyCredential: unknown, 963 passkeyFriendlyName?: string, 964 ): Promise<CompletePasskeySetupResponse> { 965 return xrpc("_account.completePasskeySetup", { 966 method: "POST", 967 body: { did, setupToken, passkeyCredential, passkeyFriendlyName }, 968 }); 969 }, 970 971 requestPasskeyRecovery(email: EmailAddress): Promise<SuccessResponse> { 972 return xrpc("_account.requestPasskeyRecovery", { 973 method: "POST", 974 body: { email }, 975 }); 976 }, 977 978 recoverPasskeyAccount( 979 did: Did, 980 recoveryToken: string, 981 newPassword: string, 982 ): Promise<SuccessResponse> { 983 return xrpc("_account.recoverPasskeyAccount", { 984 method: "POST", 985 body: { did, recoveryToken, newPassword }, 986 }); 987 }, 988 989 verifyMigrationEmail( 990 token: string, 991 email: EmailAddress, 992 ): Promise<VerifyMigrationEmailResponse> { 993 return xrpc("com.atproto.server.verifyMigrationEmail", { 994 method: "POST", 995 body: { token, email }, 996 }); 997 }, 998 999 resendMigrationVerification( 1000 email: EmailAddress, 1001 ): Promise<ResendMigrationVerificationResponse> { 1002 return xrpc("com.atproto.server.resendMigrationVerification", { 1003 method: "POST", 1004 body: { email }, 1005 }); 1006 }, 1007 1008 verifyToken( 1009 token: string, 1010 identifier: string, 1011 accessToken?: AccessToken, 1012 ): Promise<VerifyTokenResponse> { 1013 return xrpc("_account.verifyToken", { 1014 method: "POST", 1015 body: { token, identifier }, 1016 token: accessToken, 1017 }); 1018 }, 1019 1020 getDidDocument(token: AccessToken): Promise<DidDocument> { 1021 return xrpc("_account.getDidDocument", { token }); 1022 }, 1023 1024 updateDidDocument( 1025 token: AccessToken, 1026 params: { 1027 verificationMethods?: VerificationMethod[]; 1028 alsoKnownAs?: string[]; 1029 serviceEndpoint?: string; 1030 }, 1031 ): Promise<SuccessResponse> { 1032 return xrpc("_account.updateDidDocument", { 1033 method: "POST", 1034 token, 1035 body: params, 1036 }); 1037 }, 1038 1039 async deactivateAccount( 1040 token: AccessToken, 1041 deleteAfter?: string, 1042 ): Promise<void> { 1043 await xrpc("com.atproto.server.deactivateAccount", { 1044 method: "POST", 1045 token, 1046 body: { deleteAfter }, 1047 }); 1048 }, 1049 1050 async getRepo(token: AccessToken, did: Did): Promise<ArrayBuffer> { 1051 const url = `${API_BASE}/com.atproto.sync.getRepo?did=${ 1052 encodeURIComponent(did) 1053 }`; 1054 const res = await fetch(url, { 1055 headers: { Authorization: `Bearer ${token}` }, 1056 }); 1057 if (!res.ok) { 1058 const errData = await res.json().catch(() => ({ 1059 error: "Unknown", 1060 message: res.statusText, 1061 })); 1062 throw new ApiError(res.status, errData.error, errData.message); 1063 } 1064 return res.arrayBuffer(); 1065 }, 1066 1067 listBackups(token: AccessToken): Promise<ListBackupsResponse> { 1068 return xrpc("_backup.listBackups", { token }); 1069 }, 1070 1071 async getBackup(token: AccessToken, id: string): Promise<Blob> { 1072 const url = `${API_BASE}/_backup.getBackup?id=${encodeURIComponent(id)}`; 1073 const res = await fetch(url, { 1074 headers: { Authorization: `Bearer ${token}` }, 1075 }); 1076 if (!res.ok) { 1077 const errData = await res.json().catch(() => ({ 1078 error: "Unknown", 1079 message: res.statusText, 1080 })); 1081 throw new ApiError(res.status, errData.error, errData.message); 1082 } 1083 return res.blob(); 1084 }, 1085 1086 createBackup(token: AccessToken): Promise<CreateBackupResponse> { 1087 return xrpc("_backup.createBackup", { 1088 method: "POST", 1089 token, 1090 }); 1091 }, 1092 1093 async deleteBackup(token: AccessToken, id: string): Promise<void> { 1094 await xrpc("_backup.deleteBackup", { 1095 method: "POST", 1096 token, 1097 params: { id }, 1098 }); 1099 }, 1100 1101 setBackupEnabled( 1102 token: AccessToken, 1103 enabled: boolean, 1104 ): Promise<SetBackupEnabledResponse> { 1105 return xrpc("_backup.setEnabled", { 1106 method: "POST", 1107 token, 1108 body: { enabled }, 1109 }); 1110 }, 1111 1112 async importRepo(token: AccessToken, car: Uint8Array): Promise<void> { 1113 const url = `${API_BASE}/com.atproto.repo.importRepo`; 1114 const res = await fetch(url, { 1115 method: "POST", 1116 headers: { 1117 Authorization: `Bearer ${token}`, 1118 "Content-Type": "application/vnd.ipld.car", 1119 }, 1120 body: car as unknown as BodyInit, 1121 }); 1122 if (!res.ok) { 1123 const errData = await res.json().catch(() => ({ 1124 error: "Unknown", 1125 message: res.statusText, 1126 })); 1127 throw new ApiError(res.status, errData.error, errData.message); 1128 } 1129 }, 1130}; 1131 1132export const typedApi = { 1133 createSession( 1134 identifier: string, 1135 password: string, 1136 ): Promise<Result<Session, ApiError>> { 1137 return xrpcResult<Session>("com.atproto.server.createSession", { 1138 method: "POST", 1139 body: { identifier, password }, 1140 }).then((r) => r.ok ? ok(castSession(r.value)) : r); 1141 }, 1142 1143 getSession(token: AccessToken): Promise<Result<Session, ApiError>> { 1144 return xrpcResult<Session>("com.atproto.server.getSession", { token }) 1145 .then((r) => r.ok ? ok(castSession(r.value)) : r); 1146 }, 1147 1148 refreshSession(refreshJwt: RefreshToken): Promise<Result<Session, ApiError>> { 1149 return xrpcResult<Session>("com.atproto.server.refreshSession", { 1150 method: "POST", 1151 token: refreshJwt, 1152 }).then((r) => r.ok ? ok(castSession(r.value)) : r); 1153 }, 1154 1155 describeServer(): Promise<Result<ServerDescription, ApiError>> { 1156 return xrpcResult("com.atproto.server.describeServer"); 1157 }, 1158 1159 listAppPasswords( 1160 token: AccessToken, 1161 ): Promise<Result<{ passwords: AppPassword[] }, ApiError>> { 1162 return xrpcResult("com.atproto.server.listAppPasswords", { token }); 1163 }, 1164 1165 createAppPassword( 1166 token: AccessToken, 1167 name: string, 1168 scopes?: string, 1169 ): Promise<Result<CreatedAppPassword, ApiError>> { 1170 return xrpcResult("com.atproto.server.createAppPassword", { 1171 method: "POST", 1172 token, 1173 body: { name, scopes }, 1174 }); 1175 }, 1176 1177 revokeAppPassword( 1178 token: AccessToken, 1179 name: string, 1180 ): Promise<Result<void, ApiError>> { 1181 return xrpcResult<void>("com.atproto.server.revokeAppPassword", { 1182 method: "POST", 1183 token, 1184 body: { name }, 1185 }); 1186 }, 1187 1188 listSessions( 1189 token: AccessToken, 1190 ): Promise<Result<ListSessionsResponse, ApiError>> { 1191 return xrpcResult("_account.listSessions", { token }); 1192 }, 1193 1194 revokeSession( 1195 token: AccessToken, 1196 sessionId: string, 1197 ): Promise<Result<void, ApiError>> { 1198 return xrpcResult<void>("_account.revokeSession", { 1199 method: "POST", 1200 token, 1201 body: { sessionId }, 1202 }); 1203 }, 1204 1205 getTotpStatus(token: AccessToken): Promise<Result<TotpStatus, ApiError>> { 1206 return xrpcResult("com.atproto.server.getTotpStatus", { token }); 1207 }, 1208 1209 createTotpSecret(token: AccessToken): Promise<Result<TotpSecret, ApiError>> { 1210 return xrpcResult("com.atproto.server.createTotpSecret", { 1211 method: "POST", 1212 token, 1213 }); 1214 }, 1215 1216 enableTotp( 1217 token: AccessToken, 1218 code: string, 1219 ): Promise<Result<EnableTotpResponse, ApiError>> { 1220 return xrpcResult("com.atproto.server.enableTotp", { 1221 method: "POST", 1222 token, 1223 body: { code }, 1224 }); 1225 }, 1226 1227 disableTotp( 1228 token: AccessToken, 1229 password: string, 1230 code: string, 1231 ): Promise<Result<SuccessResponse, ApiError>> { 1232 return xrpcResult("com.atproto.server.disableTotp", { 1233 method: "POST", 1234 token, 1235 body: { password, code }, 1236 }); 1237 }, 1238 1239 listPasskeys( 1240 token: AccessToken, 1241 ): Promise<Result<ListPasskeysResponse, ApiError>> { 1242 return xrpcResult("com.atproto.server.listPasskeys", { token }); 1243 }, 1244 1245 deletePasskey( 1246 token: AccessToken, 1247 id: string, 1248 ): Promise<Result<void, ApiError>> { 1249 return xrpcResult<void>("com.atproto.server.deletePasskey", { 1250 method: "POST", 1251 token, 1252 body: { id }, 1253 }); 1254 }, 1255 1256 listTrustedDevices( 1257 token: AccessToken, 1258 ): Promise<Result<ListTrustedDevicesResponse, ApiError>> { 1259 return xrpcResult("_account.listTrustedDevices", { token }); 1260 }, 1261 1262 getReauthStatus(token: AccessToken): Promise<Result<ReauthStatus, ApiError>> { 1263 return xrpcResult("_account.getReauthStatus", { token }); 1264 }, 1265 1266 getNotificationPrefs( 1267 token: AccessToken, 1268 ): Promise<Result<NotificationPrefs, ApiError>> { 1269 return xrpcResult("_account.getNotificationPrefs", { token }); 1270 }, 1271 1272 updateHandle( 1273 token: AccessToken, 1274 handle: Handle, 1275 ): Promise<Result<void, ApiError>> { 1276 return xrpcResult<void>("com.atproto.identity.updateHandle", { 1277 method: "POST", 1278 token, 1279 body: { handle }, 1280 }); 1281 }, 1282 1283 describeRepo( 1284 token: AccessToken, 1285 repo: Did, 1286 ): Promise<Result<RepoDescription, ApiError>> { 1287 return xrpcResult("com.atproto.repo.describeRepo", { 1288 token, 1289 params: { repo }, 1290 }); 1291 }, 1292 1293 listRecords( 1294 token: AccessToken, 1295 repo: Did, 1296 collection: Nsid, 1297 options?: { limit?: number; cursor?: string; reverse?: boolean }, 1298 ): Promise<Result<ListRecordsResponse, ApiError>> { 1299 const params: Record<string, string> = { repo, collection }; 1300 if (options?.limit) params.limit = String(options.limit); 1301 if (options?.cursor) params.cursor = options.cursor; 1302 if (options?.reverse) params.reverse = "true"; 1303 return xrpcResult("com.atproto.repo.listRecords", { token, params }); 1304 }, 1305 1306 getRecord( 1307 token: AccessToken, 1308 repo: Did, 1309 collection: Nsid, 1310 rkey: Rkey, 1311 ): Promise<Result<RecordResponse, ApiError>> { 1312 return xrpcResult("com.atproto.repo.getRecord", { 1313 token, 1314 params: { repo, collection, rkey }, 1315 }); 1316 }, 1317 1318 deleteRecord( 1319 token: AccessToken, 1320 repo: Did, 1321 collection: Nsid, 1322 rkey: Rkey, 1323 ): Promise<Result<void, ApiError>> { 1324 return xrpcResult<void>("com.atproto.repo.deleteRecord", { 1325 method: "POST", 1326 token, 1327 body: { repo, collection, rkey }, 1328 }); 1329 }, 1330 1331 searchAccounts( 1332 token: AccessToken, 1333 options?: { handle?: string; cursor?: string; limit?: number }, 1334 ): Promise<Result<SearchAccountsResponse, ApiError>> { 1335 const params: Record<string, string> = {}; 1336 if (options?.handle) params.handle = options.handle; 1337 if (options?.cursor) params.cursor = options.cursor; 1338 if (options?.limit) params.limit = String(options.limit); 1339 return xrpcResult("com.atproto.admin.searchAccounts", { token, params }); 1340 }, 1341 1342 getAccountInfo( 1343 token: AccessToken, 1344 did: Did, 1345 ): Promise<Result<AccountInfo, ApiError>> { 1346 return xrpcResult("com.atproto.admin.getAccountInfo", { 1347 token, 1348 params: { did }, 1349 }); 1350 }, 1351 1352 getServerStats(token: AccessToken): Promise<Result<ServerStats, ApiError>> { 1353 return xrpcResult("_admin.getServerStats", { token }); 1354 }, 1355 1356 listBackups( 1357 token: AccessToken, 1358 ): Promise<Result<ListBackupsResponse, ApiError>> { 1359 return xrpcResult("_backup.listBackups", { token }); 1360 }, 1361 1362 createBackup( 1363 token: AccessToken, 1364 ): Promise<Result<CreateBackupResponse, ApiError>> { 1365 return xrpcResult("_backup.createBackup", { 1366 method: "POST", 1367 token, 1368 }); 1369 }, 1370 1371 getDidDocument(token: AccessToken): Promise<Result<DidDocument, ApiError>> { 1372 return xrpcResult("_account.getDidDocument", { token }); 1373 }, 1374 1375 deleteSession(token: AccessToken): Promise<Result<void, ApiError>> { 1376 return xrpcResult<void>("com.atproto.server.deleteSession", { 1377 method: "POST", 1378 token, 1379 }); 1380 }, 1381 1382 revokeAllSessions( 1383 token: AccessToken, 1384 ): Promise<Result<{ revokedCount: number }, ApiError>> { 1385 return xrpcResult("_account.revokeAllSessions", { 1386 method: "POST", 1387 token, 1388 }); 1389 }, 1390 1391 getAccountInviteCodes( 1392 token: AccessToken, 1393 ): Promise<Result<{ codes: InviteCodeInfo[] }, ApiError>> { 1394 return xrpcResult("com.atproto.server.getAccountInviteCodes", { token }); 1395 }, 1396 1397 createInviteCode( 1398 token: AccessToken, 1399 useCount: number = 1, 1400 ): Promise<Result<{ code: string }, ApiError>> { 1401 return xrpcResult("com.atproto.server.createInviteCode", { 1402 method: "POST", 1403 token, 1404 body: { useCount }, 1405 }); 1406 }, 1407 1408 changePassword( 1409 token: AccessToken, 1410 currentPassword: string, 1411 newPassword: string, 1412 ): Promise<Result<void, ApiError>> { 1413 return xrpcResult<void>("_account.changePassword", { 1414 method: "POST", 1415 token, 1416 body: { currentPassword, newPassword }, 1417 }); 1418 }, 1419 1420 getPasswordStatus( 1421 token: AccessToken, 1422 ): Promise<Result<PasswordStatus, ApiError>> { 1423 return xrpcResult("_account.getPasswordStatus", { token }); 1424 }, 1425 1426 getServerConfig(): Promise<Result<ServerConfig, ApiError>> { 1427 return xrpcResult("_server.getConfig"); 1428 }, 1429 1430 getLegacyLoginPreference( 1431 token: AccessToken, 1432 ): Promise<Result<LegacyLoginPreference, ApiError>> { 1433 return xrpcResult("_account.getLegacyLoginPreference", { token }); 1434 }, 1435 1436 updateLegacyLoginPreference( 1437 token: AccessToken, 1438 allowLegacyLogin: boolean, 1439 ): Promise<Result<UpdateLegacyLoginResponse, ApiError>> { 1440 return xrpcResult("_account.updateLegacyLoginPreference", { 1441 method: "POST", 1442 token, 1443 body: { allowLegacyLogin }, 1444 }); 1445 }, 1446 1447 getNotificationHistory( 1448 token: AccessToken, 1449 ): Promise<Result<NotificationHistoryResponse, ApiError>> { 1450 return xrpcResult("_account.getNotificationHistory", { token }); 1451 }, 1452 1453 updateNotificationPrefs( 1454 token: AccessToken, 1455 prefs: { 1456 preferredChannel?: string; 1457 discordId?: string; 1458 telegramUsername?: string; 1459 signalNumber?: string; 1460 }, 1461 ): Promise<Result<SuccessResponse, ApiError>> { 1462 return xrpcResult("_account.updateNotificationPrefs", { 1463 method: "POST", 1464 token, 1465 body: prefs, 1466 }); 1467 }, 1468 1469 revokeTrustedDevice( 1470 token: AccessToken, 1471 deviceId: string, 1472 ): Promise<Result<SuccessResponse, ApiError>> { 1473 return xrpcResult("_account.revokeTrustedDevice", { 1474 method: "POST", 1475 token, 1476 body: { deviceId }, 1477 }); 1478 }, 1479 1480 updateTrustedDevice( 1481 token: AccessToken, 1482 deviceId: string, 1483 friendlyName: string, 1484 ): Promise<Result<SuccessResponse, ApiError>> { 1485 return xrpcResult("_account.updateTrustedDevice", { 1486 method: "POST", 1487 token, 1488 body: { deviceId, friendlyName }, 1489 }); 1490 }, 1491 1492 reauthPassword( 1493 token: AccessToken, 1494 password: string, 1495 ): Promise<Result<ReauthResponse, ApiError>> { 1496 return xrpcResult("_account.reauthPassword", { 1497 method: "POST", 1498 token, 1499 body: { password }, 1500 }); 1501 }, 1502 1503 reauthTotp( 1504 token: AccessToken, 1505 code: string, 1506 ): Promise<Result<ReauthResponse, ApiError>> { 1507 return xrpcResult("_account.reauthTotp", { 1508 method: "POST", 1509 token, 1510 body: { code }, 1511 }); 1512 }, 1513 1514 reauthPasskeyStart( 1515 token: AccessToken, 1516 ): Promise<Result<ReauthPasskeyStartResponse, ApiError>> { 1517 return xrpcResult("_account.reauthPasskeyStart", { 1518 method: "POST", 1519 token, 1520 }); 1521 }, 1522 1523 reauthPasskeyFinish( 1524 token: AccessToken, 1525 credential: unknown, 1526 ): Promise<Result<ReauthResponse, ApiError>> { 1527 return xrpcResult("_account.reauthPasskeyFinish", { 1528 method: "POST", 1529 token, 1530 body: { credential }, 1531 }); 1532 }, 1533 1534 confirmSignup( 1535 did: Did, 1536 verificationCode: string, 1537 ): Promise<Result<ConfirmSignupResult, ApiError>> { 1538 return xrpcResult("com.atproto.server.confirmSignup", { 1539 method: "POST", 1540 body: { did, verificationCode }, 1541 }); 1542 }, 1543 1544 resendVerification( 1545 did: Did, 1546 ): Promise<Result<{ success: boolean }, ApiError>> { 1547 return xrpcResult("com.atproto.server.resendVerification", { 1548 method: "POST", 1549 body: { did }, 1550 }); 1551 }, 1552 1553 requestEmailUpdate( 1554 token: AccessToken, 1555 ): Promise<Result<EmailUpdateResponse, ApiError>> { 1556 return xrpcResult("com.atproto.server.requestEmailUpdate", { 1557 method: "POST", 1558 token, 1559 }); 1560 }, 1561 1562 updateEmail( 1563 token: AccessToken, 1564 email: string, 1565 emailToken?: string, 1566 ): Promise<Result<void, ApiError>> { 1567 return xrpcResult<void>("com.atproto.server.updateEmail", { 1568 method: "POST", 1569 token, 1570 body: { email, token: emailToken }, 1571 }); 1572 }, 1573 1574 requestAccountDelete(token: AccessToken): Promise<Result<void, ApiError>> { 1575 return xrpcResult<void>("com.atproto.server.requestAccountDelete", { 1576 method: "POST", 1577 token, 1578 }); 1579 }, 1580 1581 deleteAccount( 1582 did: Did, 1583 password: string, 1584 deleteToken: string, 1585 ): Promise<Result<void, ApiError>> { 1586 return xrpcResult<void>("com.atproto.server.deleteAccount", { 1587 method: "POST", 1588 body: { did, password, token: deleteToken }, 1589 }); 1590 }, 1591 1592 updateDidDocument( 1593 token: AccessToken, 1594 params: { 1595 verificationMethods?: VerificationMethod[]; 1596 alsoKnownAs?: string[]; 1597 serviceEndpoint?: string; 1598 }, 1599 ): Promise<Result<SuccessResponse, ApiError>> { 1600 return xrpcResult("_account.updateDidDocument", { 1601 method: "POST", 1602 token, 1603 body: params, 1604 }); 1605 }, 1606 1607 deactivateAccount( 1608 token: AccessToken, 1609 deleteAfter?: string, 1610 ): Promise<Result<void, ApiError>> { 1611 return xrpcResult<void>("com.atproto.server.deactivateAccount", { 1612 method: "POST", 1613 token, 1614 body: { deleteAfter }, 1615 }); 1616 }, 1617 1618 activateAccount(token: AccessToken): Promise<Result<void, ApiError>> { 1619 return xrpcResult<void>("com.atproto.server.activateAccount", { 1620 method: "POST", 1621 token, 1622 }); 1623 }, 1624 1625 setBackupEnabled( 1626 token: AccessToken, 1627 enabled: boolean, 1628 ): Promise<Result<SetBackupEnabledResponse, ApiError>> { 1629 return xrpcResult("_backup.setEnabled", { 1630 method: "POST", 1631 token, 1632 body: { enabled }, 1633 }); 1634 }, 1635 1636 deleteBackup( 1637 token: AccessToken, 1638 id: string, 1639 ): Promise<Result<void, ApiError>> { 1640 return xrpcResult<void>("_backup.deleteBackup", { 1641 method: "POST", 1642 token, 1643 params: { id }, 1644 }); 1645 }, 1646 1647 createRecord( 1648 token: AccessToken, 1649 repo: Did, 1650 collection: Nsid, 1651 record: unknown, 1652 rkey?: Rkey, 1653 ): Promise<Result<CreateRecordResponse, ApiError>> { 1654 return xrpcResult("com.atproto.repo.createRecord", { 1655 method: "POST", 1656 token, 1657 body: { repo, collection, record, rkey }, 1658 }); 1659 }, 1660 1661 putRecord( 1662 token: AccessToken, 1663 repo: Did, 1664 collection: Nsid, 1665 rkey: Rkey, 1666 record: unknown, 1667 ): Promise<Result<CreateRecordResponse, ApiError>> { 1668 return xrpcResult("com.atproto.repo.putRecord", { 1669 method: "POST", 1670 token, 1671 body: { repo, collection, rkey, record }, 1672 }); 1673 }, 1674 1675 getInviteCodes( 1676 token: AccessToken, 1677 options?: { sort?: "recent" | "usage"; cursor?: string; limit?: number }, 1678 ): Promise<Result<GetInviteCodesResponse, ApiError>> { 1679 const params: Record<string, string> = {}; 1680 if (options?.sort) params.sort = options.sort; 1681 if (options?.cursor) params.cursor = options.cursor; 1682 if (options?.limit) params.limit = String(options.limit); 1683 return xrpcResult("com.atproto.admin.getInviteCodes", { token, params }); 1684 }, 1685 1686 disableAccountInvites( 1687 token: AccessToken, 1688 account: Did, 1689 ): Promise<Result<void, ApiError>> { 1690 return xrpcResult<void>("com.atproto.admin.disableAccountInvites", { 1691 method: "POST", 1692 token, 1693 body: { account }, 1694 }); 1695 }, 1696 1697 enableAccountInvites( 1698 token: AccessToken, 1699 account: Did, 1700 ): Promise<Result<void, ApiError>> { 1701 return xrpcResult<void>("com.atproto.admin.enableAccountInvites", { 1702 method: "POST", 1703 token, 1704 body: { account }, 1705 }); 1706 }, 1707 1708 adminDeleteAccount( 1709 token: AccessToken, 1710 did: Did, 1711 ): Promise<Result<void, ApiError>> { 1712 return xrpcResult<void>("com.atproto.admin.deleteAccount", { 1713 method: "POST", 1714 token, 1715 body: { did }, 1716 }); 1717 }, 1718 1719 startPasskeyRegistration( 1720 token: AccessToken, 1721 friendlyName?: string, 1722 ): Promise<Result<StartPasskeyRegistrationResponse, ApiError>> { 1723 return xrpcResult("com.atproto.server.startPasskeyRegistration", { 1724 method: "POST", 1725 token, 1726 body: { friendlyName }, 1727 }); 1728 }, 1729 1730 finishPasskeyRegistration( 1731 token: AccessToken, 1732 credential: unknown, 1733 friendlyName?: string, 1734 ): Promise<Result<FinishPasskeyRegistrationResponse, ApiError>> { 1735 return xrpcResult("com.atproto.server.finishPasskeyRegistration", { 1736 method: "POST", 1737 token, 1738 body: { credential, friendlyName }, 1739 }); 1740 }, 1741 1742 updatePasskey( 1743 token: AccessToken, 1744 id: string, 1745 friendlyName: string, 1746 ): Promise<Result<void, ApiError>> { 1747 return xrpcResult<void>("com.atproto.server.updatePasskey", { 1748 method: "POST", 1749 token, 1750 body: { id, friendlyName }, 1751 }); 1752 }, 1753 1754 regenerateBackupCodes( 1755 token: AccessToken, 1756 password: string, 1757 code: string, 1758 ): Promise<Result<RegenerateBackupCodesResponse, ApiError>> { 1759 return xrpcResult("com.atproto.server.regenerateBackupCodes", { 1760 method: "POST", 1761 token, 1762 body: { password, code }, 1763 }); 1764 }, 1765 1766 updateLocale( 1767 token: AccessToken, 1768 preferredLocale: string, 1769 ): Promise<Result<UpdateLocaleResponse, ApiError>> { 1770 return xrpcResult("_account.updateLocale", { 1771 method: "POST", 1772 token, 1773 body: { preferredLocale }, 1774 }); 1775 }, 1776 1777 confirmChannelVerification( 1778 token: AccessToken, 1779 channel: string, 1780 identifier: string, 1781 code: string, 1782 ): Promise<Result<SuccessResponse, ApiError>> { 1783 return xrpcResult("_account.confirmChannelVerification", { 1784 method: "POST", 1785 token, 1786 body: { channel, identifier, code }, 1787 }); 1788 }, 1789 1790 removePassword( 1791 token: AccessToken, 1792 ): Promise<Result<SuccessResponse, ApiError>> { 1793 return xrpcResult("_account.removePassword", { 1794 method: "POST", 1795 token, 1796 }); 1797 }, 1798};