@atproto/pds 0.5.12 → 0.5.14

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.
Files changed (322) hide show
  1. package/CHANGELOG.md +36 -0
  2. package/dist/api/app/bsky/notification/index.d.ts.map +1 -1
  3. package/dist/api/app/bsky/notification/index.js +2 -0
  4. package/dist/api/app/bsky/notification/index.js.map +1 -1
  5. package/dist/api/app/bsky/notification/unregisterPush.d.ts +4 -0
  6. package/dist/api/app/bsky/notification/unregisterPush.d.ts.map +1 -0
  7. package/dist/api/app/bsky/notification/unregisterPush.js +48 -0
  8. package/dist/api/app/bsky/notification/unregisterPush.js.map +1 -0
  9. package/package.json +42 -38
  10. package/build.templates.cjs +0 -22
  11. package/example.env +0 -42
  12. package/jest.config.cjs +0 -27
  13. package/src/account-manager/account-manager.ts +0 -916
  14. package/src/account-manager/db/index.ts +0 -21
  15. package/src/account-manager/db/migrations/001-init.ts +0 -115
  16. package/src/account-manager/db/migrations/002-account-deactivation.ts +0 -17
  17. package/src/account-manager/db/migrations/003-privileged-app-passwords.ts +0 -12
  18. package/src/account-manager/db/migrations/004-oauth.ts +0 -122
  19. package/src/account-manager/db/migrations/005-oauth-account-management.ts +0 -136
  20. package/src/account-manager/db/migrations/006-oauth-permission-sets.ts +0 -20
  21. package/src/account-manager/db/migrations/007-lexicon-failures-index.ts +0 -14
  22. package/src/account-manager/db/migrations/index.ts +0 -17
  23. package/src/account-manager/db/schema/account-device.ts +0 -14
  24. package/src/account-manager/db/schema/account.ts +0 -16
  25. package/src/account-manager/db/schema/actor.ts +0 -17
  26. package/src/account-manager/db/schema/app-password.ts +0 -13
  27. package/src/account-manager/db/schema/authorization-request.ts +0 -30
  28. package/src/account-manager/db/schema/authorized-client.ts +0 -23
  29. package/src/account-manager/db/schema/device.ts +0 -18
  30. package/src/account-manager/db/schema/email-token.ts +0 -19
  31. package/src/account-manager/db/schema/index.ts +0 -43
  32. package/src/account-manager/db/schema/invite-code.ts +0 -24
  33. package/src/account-manager/db/schema/lexicon.ts +0 -15
  34. package/src/account-manager/db/schema/refresh-token.ts +0 -11
  35. package/src/account-manager/db/schema/repo-root.ts +0 -12
  36. package/src/account-manager/db/schema/token.ts +0 -38
  37. package/src/account-manager/db/schema/used-refresh-token.ts +0 -13
  38. package/src/account-manager/helpers/account-device.ts +0 -63
  39. package/src/account-manager/helpers/account.ts +0 -355
  40. package/src/account-manager/helpers/auth.ts +0 -222
  41. package/src/account-manager/helpers/authorization-request.ts +0 -90
  42. package/src/account-manager/helpers/authorized-client.ts +0 -75
  43. package/src/account-manager/helpers/device.ts +0 -47
  44. package/src/account-manager/helpers/email-token.ts +0 -87
  45. package/src/account-manager/helpers/invite.ts +0 -263
  46. package/src/account-manager/helpers/lexicon.ts +0 -67
  47. package/src/account-manager/helpers/password.ts +0 -136
  48. package/src/account-manager/helpers/repo.ts +0 -24
  49. package/src/account-manager/helpers/scrypt.ts +0 -53
  50. package/src/account-manager/helpers/token.ts +0 -158
  51. package/src/account-manager/helpers/used-refresh-token.ts +0 -30
  52. package/src/account-manager/oauth-store.ts +0 -880
  53. package/src/account-manager/scope-reference-getter.ts +0 -106
  54. package/src/actor-store/actor-store-reader.ts +0 -45
  55. package/src/actor-store/actor-store-resources.ts +0 -8
  56. package/src/actor-store/actor-store-transactor.ts +0 -31
  57. package/src/actor-store/actor-store-writer.ts +0 -17
  58. package/src/actor-store/actor-store.ts +0 -210
  59. package/src/actor-store/blob/reader.ts +0 -160
  60. package/src/actor-store/blob/transactor.ts +0 -383
  61. package/src/actor-store/db/index.ts +0 -20
  62. package/src/actor-store/db/migrations/001-init.ts +0 -105
  63. package/src/actor-store/db/migrations/index.ts +0 -5
  64. package/src/actor-store/db/schema/account-pref.ts +0 -11
  65. package/src/actor-store/db/schema/backlink.ts +0 -9
  66. package/src/actor-store/db/schema/blob.ts +0 -14
  67. package/src/actor-store/db/schema/index.ts +0 -23
  68. package/src/actor-store/db/schema/record-blob.ts +0 -8
  69. package/src/actor-store/db/schema/record.ts +0 -14
  70. package/src/actor-store/db/schema/repo-block.ts +0 -10
  71. package/src/actor-store/db/schema/repo-root.ts +0 -10
  72. package/src/actor-store/migrate.ts +0 -39
  73. package/src/actor-store/preference/reader.ts +0 -48
  74. package/src/actor-store/preference/transactor.ts +0 -55
  75. package/src/actor-store/preference/util.ts +0 -39
  76. package/src/actor-store/record/reader.ts +0 -374
  77. package/src/actor-store/record/transactor.ts +0 -111
  78. package/src/actor-store/repo/reader.ts +0 -31
  79. package/src/actor-store/repo/sql-repo-reader.ts +0 -150
  80. package/src/actor-store/repo/sql-repo-transactor.ts +0 -105
  81. package/src/actor-store/repo/transactor.ts +0 -227
  82. package/src/api/app/bsky/actor/getPreferences.ts +0 -57
  83. package/src/api/app/bsky/actor/getProfile.ts +0 -41
  84. package/src/api/app/bsky/actor/getProfiles.ts +0 -51
  85. package/src/api/app/bsky/actor/index.ts +0 -13
  86. package/src/api/app/bsky/actor/putPreferences.ts +0 -62
  87. package/src/api/app/bsky/feed/getActorLikes.ts +0 -63
  88. package/src/api/app/bsky/feed/getAuthorFeed.ts +0 -84
  89. package/src/api/app/bsky/feed/getFeed.ts +0 -47
  90. package/src/api/app/bsky/feed/getPostThread.ts +0 -251
  91. package/src/api/app/bsky/feed/getTimeline.ts +0 -50
  92. package/src/api/app/bsky/feed/index.ts +0 -15
  93. package/src/api/app/bsky/index.ts +0 -11
  94. package/src/api/app/bsky/notification/index.ts +0 -7
  95. package/src/api/app/bsky/notification/registerPush.ts +0 -71
  96. package/src/api/app/bsky/util/resolver.ts +0 -20
  97. package/src/api/com/atproto/admin/deleteAccount.ts +0 -22
  98. package/src/api/com/atproto/admin/disableAccountInvites.ts +0 -18
  99. package/src/api/com/atproto/admin/disableInviteCodes.ts +0 -21
  100. package/src/api/com/atproto/admin/enableAccountInvites.ts +0 -18
  101. package/src/api/com/atproto/admin/getAccountInfo.ts +0 -32
  102. package/src/api/com/atproto/admin/getAccountInfos.ts +0 -34
  103. package/src/api/com/atproto/admin/getInviteCodes.ts +0 -126
  104. package/src/api/com/atproto/admin/getSubjectStatus.ts +0 -76
  105. package/src/api/com/atproto/admin/index.ts +0 -31
  106. package/src/api/com/atproto/admin/sendEmail.ts +0 -47
  107. package/src/api/com/atproto/admin/updateAccountEmail.ts +0 -32
  108. package/src/api/com/atproto/admin/updateAccountHandle.ts +0 -47
  109. package/src/api/com/atproto/admin/updateAccountPassword.ts +0 -34
  110. package/src/api/com/atproto/admin/updateSubjectStatus.ts +0 -68
  111. package/src/api/com/atproto/admin/util.ts +0 -66
  112. package/src/api/com/atproto/identity/getRecommendedDidCredentials.ts +0 -50
  113. package/src/api/com/atproto/identity/index.ts +0 -17
  114. package/src/api/com/atproto/identity/requestPlcOperationSignature.ts +0 -59
  115. package/src/api/com/atproto/identity/resolveHandle.ts +0 -50
  116. package/src/api/com/atproto/identity/signPlcOperation.ts +0 -85
  117. package/src/api/com/atproto/identity/submitPlcOperation.ts +0 -65
  118. package/src/api/com/atproto/identity/updateHandle.ts +0 -66
  119. package/src/api/com/atproto/index.ts +0 -19
  120. package/src/api/com/atproto/moderation/createReport.ts +0 -41
  121. package/src/api/com/atproto/moderation/index.ts +0 -7
  122. package/src/api/com/atproto/repo/applyWrites.ts +0 -226
  123. package/src/api/com/atproto/repo/createRecord.ts +0 -143
  124. package/src/api/com/atproto/repo/deleteRecord.ts +0 -122
  125. package/src/api/com/atproto/repo/describeRepo.ts +0 -43
  126. package/src/api/com/atproto/repo/getRecord.ts +0 -40
  127. package/src/api/com/atproto/repo/importRepo.ts +0 -101
  128. package/src/api/com/atproto/repo/index.ts +0 -25
  129. package/src/api/com/atproto/repo/listMissingBlobs.ts +0 -29
  130. package/src/api/com/atproto/repo/listRecords.ts +0 -36
  131. package/src/api/com/atproto/repo/putRecord.ts +0 -211
  132. package/src/api/com/atproto/repo/uploadBlob.ts +0 -60
  133. package/src/api/com/atproto/server/activateAccount.ts +0 -37
  134. package/src/api/com/atproto/server/checkAccountStatus.ts +0 -51
  135. package/src/api/com/atproto/server/confirmEmail.ts +0 -39
  136. package/src/api/com/atproto/server/createAccount.ts +0 -327
  137. package/src/api/com/atproto/server/createAppPassword.ts +0 -53
  138. package/src/api/com/atproto/server/createInviteCode.ts +0 -38
  139. package/src/api/com/atproto/server/createInviteCodes.ts +0 -42
  140. package/src/api/com/atproto/server/createSession.ts +0 -97
  141. package/src/api/com/atproto/server/deactivateAccount.ts +0 -41
  142. package/src/api/com/atproto/server/deleteAccount.ts +0 -85
  143. package/src/api/com/atproto/server/deleteSession.ts +0 -23
  144. package/src/api/com/atproto/server/describeServer.ts +0 -29
  145. package/src/api/com/atproto/server/getAccountInviteCodes.ts +0 -142
  146. package/src/api/com/atproto/server/getServiceAuth.ts +0 -111
  147. package/src/api/com/atproto/server/getSession.ts +0 -80
  148. package/src/api/com/atproto/server/index.ts +0 -55
  149. package/src/api/com/atproto/server/listAppPasswords.ts +0 -45
  150. package/src/api/com/atproto/server/refreshSession.ts +0 -72
  151. package/src/api/com/atproto/server/requestAccountDelete.ts +0 -66
  152. package/src/api/com/atproto/server/requestEmailConfirmation.ts +0 -68
  153. package/src/api/com/atproto/server/requestEmailUpdate.ts +0 -86
  154. package/src/api/com/atproto/server/requestPasswordReset.ts +0 -52
  155. package/src/api/com/atproto/server/reserveSigningKey.ts +0 -15
  156. package/src/api/com/atproto/server/resetPassword.ts +0 -50
  157. package/src/api/com/atproto/server/revokeAppPassword.ts +0 -42
  158. package/src/api/com/atproto/server/updateEmail.ts +0 -52
  159. package/src/api/com/atproto/server/util.ts +0 -136
  160. package/src/api/com/atproto/sync/deprecated/getCheckout.ts +0 -27
  161. package/src/api/com/atproto/sync/deprecated/getHead.ts +0 -33
  162. package/src/api/com/atproto/sync/getBlob.ts +0 -61
  163. package/src/api/com/atproto/sync/getBlocks.ts +0 -37
  164. package/src/api/com/atproto/sync/getLatestCommit.ts +0 -33
  165. package/src/api/com/atproto/sync/getRecord.ts +0 -49
  166. package/src/api/com/atproto/sync/getRepo.ts +0 -75
  167. package/src/api/com/atproto/sync/getRepoStatus.ts +0 -34
  168. package/src/api/com/atproto/sync/index.ts +0 -27
  169. package/src/api/com/atproto/sync/listBlobs.ts +0 -33
  170. package/src/api/com/atproto/sync/listRepos.ts +0 -74
  171. package/src/api/com/atproto/sync/subscribeRepos.ts +0 -73
  172. package/src/api/com/atproto/sync/util.ts +0 -37
  173. package/src/api/com/atproto/temp/checkSignupQueue.ts +0 -34
  174. package/src/api/com/atproto/temp/index.ts +0 -7
  175. package/src/api/index.ts +0 -10
  176. package/src/api/proxy.ts +0 -44
  177. package/src/app-view.ts +0 -24
  178. package/src/auth-output.ts +0 -52
  179. package/src/auth-routes.ts +0 -64
  180. package/src/auth-scope.ts +0 -40
  181. package/src/auth-verifier.ts +0 -668
  182. package/src/background.ts +0 -65
  183. package/src/basic-routes.ts +0 -52
  184. package/src/bsky-app-view.ts +0 -33
  185. package/src/config/config.ts +0 -553
  186. package/src/config/env.ts +0 -167
  187. package/src/config/index.ts +0 -3
  188. package/src/config/secrets.ts +0 -54
  189. package/src/context.ts +0 -523
  190. package/src/crawlers.ts +0 -46
  191. package/src/db/cast.ts +0 -52
  192. package/src/db/db.ts +0 -140
  193. package/src/db/index.ts +0 -4
  194. package/src/db/migrator.ts +0 -40
  195. package/src/db/pagination.ts +0 -132
  196. package/src/db/tables/moderation.ts +0 -80
  197. package/src/db/util.ts +0 -108
  198. package/src/did-cache/db/index.ts +0 -21
  199. package/src/did-cache/db/migrations.ts +0 -17
  200. package/src/did-cache/db/schema.ts +0 -9
  201. package/src/did-cache/index.ts +0 -131
  202. package/src/disk-blobstore.ts +0 -172
  203. package/src/error.ts +0 -19
  204. package/src/handle/explicit-slurs.ts +0 -22
  205. package/src/handle/index.ts +0 -49
  206. package/src/handle/reserved.ts +0 -1059
  207. package/src/image/image-url-builder.ts +0 -16
  208. package/src/index.ts +0 -189
  209. package/src/lexicons.ts +0 -4
  210. package/src/logger.ts +0 -35
  211. package/src/mailer/index.ts +0 -111
  212. package/src/mailer/moderation.ts +0 -33
  213. package/src/mailer/templates/confirm-email.d.ts +0 -4
  214. package/src/mailer/templates/confirm-email.hbs +0 -158
  215. package/src/mailer/templates/delete-account.d.ts +0 -4
  216. package/src/mailer/templates/delete-account.hbs +0 -156
  217. package/src/mailer/templates/plc-operation.d.ts +0 -4
  218. package/src/mailer/templates/plc-operation.hbs +0 -153
  219. package/src/mailer/templates/reset-password.d.ts +0 -4
  220. package/src/mailer/templates/reset-password.hbs +0 -154
  221. package/src/mailer/templates/update-email.d.ts +0 -4
  222. package/src/mailer/templates/update-email.hbs +0 -153
  223. package/src/mailer/templates.ts +0 -17
  224. package/src/pipethrough.ts +0 -716
  225. package/src/rate-limits.ts +0 -59
  226. package/src/read-after-write/index.ts +0 -3
  227. package/src/read-after-write/types.ts +0 -35
  228. package/src/read-after-write/util.ts +0 -101
  229. package/src/read-after-write/viewer.ts +0 -290
  230. package/src/redis.ts +0 -25
  231. package/src/repo/index.ts +0 -2
  232. package/src/repo/prepare.ts +0 -266
  233. package/src/repo/types.ts +0 -65
  234. package/src/scripts/README.md +0 -40
  235. package/src/scripts/index.ts +0 -20
  236. package/src/scripts/publish-identity.ts +0 -60
  237. package/src/scripts/rebuild-repo.ts +0 -119
  238. package/src/scripts/rotate-keys.ts +0 -146
  239. package/src/scripts/sequencer-recovery/index.ts +0 -23
  240. package/src/scripts/sequencer-recovery/recoverer.ts +0 -297
  241. package/src/scripts/sequencer-recovery/recovery-db.ts +0 -65
  242. package/src/scripts/sequencer-recovery/repair-repos.ts +0 -49
  243. package/src/scripts/sequencer-recovery/user-queues.ts +0 -44
  244. package/src/scripts/util.ts +0 -7
  245. package/src/sequencer/db/index.ts +0 -21
  246. package/src/sequencer/db/migrations/001-init.ts +0 -35
  247. package/src/sequencer/db/migrations/index.ts +0 -5
  248. package/src/sequencer/db/schema.ts +0 -19
  249. package/src/sequencer/events.ts +0 -199
  250. package/src/sequencer/index.ts +0 -3
  251. package/src/sequencer/outbox.ts +0 -123
  252. package/src/sequencer/sequencer.ts +0 -290
  253. package/src/util/compression.ts +0 -16
  254. package/src/util/debug.ts +0 -10
  255. package/src/util/http.ts +0 -31
  256. package/src/util/types.ts +0 -7
  257. package/src/well-known.ts +0 -30
  258. package/test.env +0 -2
  259. package/tests/__snapshots__/takedown-appeal.test.ts.snap +0 -43
  260. package/tests/_oauth_client_assets_middleware.ts +0 -23
  261. package/tests/_puppeteer.ts +0 -147
  262. package/tests/_types.d.ts +0 -16
  263. package/tests/_util.ts +0 -191
  264. package/tests/account-deactivation.test.ts +0 -204
  265. package/tests/account-deletion.test.ts +0 -300
  266. package/tests/account-manager.test.ts +0 -462
  267. package/tests/account-migration.test.ts +0 -221
  268. package/tests/account-status.test.ts +0 -206
  269. package/tests/account.test.ts +0 -595
  270. package/tests/app-passwords.test.ts +0 -262
  271. package/tests/auth.test.ts +0 -405
  272. package/tests/blob-deletes.test.ts +0 -204
  273. package/tests/create-post.test.ts +0 -79
  274. package/tests/crud.test.ts +0 -1595
  275. package/tests/db.test.ts +0 -170
  276. package/tests/email-confirmation.test.ts +0 -227
  277. package/tests/entryway-mock.ts +0 -323
  278. package/tests/entryway.test.ts +0 -145
  279. package/tests/file-uploads.test.ts +0 -301
  280. package/tests/get-service-auth.test.ts +0 -81
  281. package/tests/handle-validation.test.ts +0 -56
  282. package/tests/handles.test.ts +0 -274
  283. package/tests/invite-codes.test.ts +0 -367
  284. package/tests/invites-admin.test.ts +0 -252
  285. package/tests/moderation.test.ts +0 -280
  286. package/tests/moderator-auth.test.ts +0 -177
  287. package/tests/oauth.test.ts +0 -334
  288. package/tests/plc-operations.test.ts +0 -239
  289. package/tests/preferences.test.ts +0 -352
  290. package/tests/proxied/__snapshots__/admin.test.ts.snap +0 -516
  291. package/tests/proxied/__snapshots__/feedgen.test.ts.snap +0 -215
  292. package/tests/proxied/__snapshots__/views.test.ts.snap +0 -4456
  293. package/tests/proxied/admin.test.ts +0 -340
  294. package/tests/proxied/feedgen.test.ts +0 -66
  295. package/tests/proxied/notif.test.ts +0 -85
  296. package/tests/proxied/procedures.test.ts +0 -175
  297. package/tests/proxied/proxy-catchall.test.ts +0 -256
  298. package/tests/proxied/proxy-header.test.ts +0 -239
  299. package/tests/proxied/proxy-oauth-aud.test.ts +0 -182
  300. package/tests/proxied/read-after-write.test.ts +0 -382
  301. package/tests/proxied/views.test.ts +0 -608
  302. package/tests/races.test.ts +0 -89
  303. package/tests/rate-limits.test.ts +0 -70
  304. package/tests/recovery.test.ts +0 -180
  305. package/tests/seeds/basic.ts +0 -165
  306. package/tests/seeds/follows.ts +0 -57
  307. package/tests/seeds/likes.ts +0 -14
  308. package/tests/seeds/reposts.ts +0 -18
  309. package/tests/seeds/thread.ts +0 -40
  310. package/tests/seeds/users-bulk.ts +0 -246
  311. package/tests/seeds/users.ts +0 -67
  312. package/tests/sequencer.test.ts +0 -251
  313. package/tests/server.test.ts +0 -151
  314. package/tests/sync/invertible-ops.test.ts +0 -99
  315. package/tests/sync/list.test.ts +0 -43
  316. package/tests/sync/subscribe-repos.test.ts +0 -672
  317. package/tests/sync/sync.test.ts +0 -316
  318. package/tests/takedown-appeal.test.ts +0 -166
  319. package/tsconfig.build.json +0 -9
  320. package/tsconfig.build.tsbuildinfo +0 -1
  321. package/tsconfig.json +0 -7
  322. package/tsconfig.tests.json +0 -8
@@ -1,150 +0,0 @@
1
- import { sql } from 'kysely'
2
- import { chunkArray } from '@atproto/common'
3
- import { Cid, parseCid } from '@atproto/lex-data'
4
- import {
5
- BlockMap,
6
- CarBlock,
7
- CidSet,
8
- ReadableBlockstore,
9
- writeCarStream,
10
- } from '@atproto/repo'
11
- import { countAll } from '../../db/index.js'
12
- import { ActorDb } from '../db/index.js'
13
-
14
- export class SqlRepoReader extends ReadableBlockstore {
15
- cache: BlockMap = new BlockMap()
16
-
17
- constructor(public db: ActorDb) {
18
- super()
19
- }
20
-
21
- async getRoot(): Promise<Cid> {
22
- const root = await this.getRootDetailed()
23
- return root.cid
24
- }
25
-
26
- async getRootDetailed(): Promise<{ cid: Cid; rev: string }> {
27
- const res = await this.db.db
28
- .selectFrom('repo_root')
29
- .select(['cid', 'rev'])
30
- .limit(1)
31
- .executeTakeFirstOrThrow()
32
- return {
33
- cid: parseCid(res.cid),
34
- rev: res.rev,
35
- }
36
- }
37
-
38
- async getBytes(cid: Cid): Promise<Uint8Array | null> {
39
- const cached = this.cache.get(cid)
40
- if (cached) return cached
41
- const found = await this.db.db
42
- .selectFrom('repo_block')
43
- .where('repo_block.cid', '=', cid.toString())
44
- .select('content')
45
- .executeTakeFirst()
46
- if (!found) return null
47
- this.cache.set(cid, found.content)
48
- return found.content
49
- }
50
-
51
- async has(cid: Cid): Promise<boolean> {
52
- const got = await this.getBytes(cid)
53
- return !!got
54
- }
55
-
56
- async getBlocks(cids: Cid[]): Promise<{ blocks: BlockMap; missing: Cid[] }> {
57
- const cached = this.cache.getMany(cids)
58
- if (cached.missing.length < 1) return cached
59
- const missing = new CidSet(cached.missing)
60
- const missingStr = cached.missing.map((c) => c.toString())
61
- const blocks = new BlockMap()
62
- for (const batch of chunkArray(missingStr, 500)) {
63
- const res = await this.db.db
64
- .selectFrom('repo_block')
65
- .where('repo_block.cid', 'in', batch)
66
- .select(['repo_block.cid as cid', 'repo_block.content as content'])
67
- .execute()
68
- for (const row of res) {
69
- const cid = parseCid(row.cid)
70
- blocks.set(cid, row.content)
71
- missing.delete(cid)
72
- }
73
- }
74
- this.cache.addMap(blocks)
75
- blocks.addMap(cached.blocks)
76
- return { blocks, missing: missing.toList() }
77
- }
78
-
79
- async getCarStream(since?: string) {
80
- const root = await this.getRoot()
81
- if (!root) {
82
- throw new RepoRootNotFoundError()
83
- }
84
- return writeCarStream(root, this.iterateCarBlocks(since))
85
- }
86
-
87
- async *iterateCarBlocks(since?: string): AsyncIterable<CarBlock> {
88
- let cursor: RevCursor | undefined = undefined
89
- // allow us to write to car while fetching the next page
90
- do {
91
- const res = await this.getBlockRange(since, cursor)
92
- for (const row of res) {
93
- yield {
94
- cid: parseCid(row.cid),
95
- bytes: row.content,
96
- }
97
- }
98
- const lastRow = res.at(-1)
99
- if (lastRow && lastRow.repoRev) {
100
- cursor = {
101
- cid: parseCid(lastRow.cid),
102
- rev: lastRow.repoRev,
103
- }
104
- } else {
105
- cursor = undefined
106
- }
107
- } while (cursor)
108
- }
109
-
110
- async getBlockRange(since?: string, cursor?: RevCursor) {
111
- const { ref } = this.db.db.dynamic
112
- let builder = this.db.db
113
- .selectFrom('repo_block')
114
- .select(['cid', 'repoRev', 'content'])
115
- .orderBy('repoRev', 'desc')
116
- .orderBy('cid', 'desc')
117
- .limit(500)
118
- if (cursor) {
119
- // use this syntax to ensure we hit the index
120
- builder = builder.where(
121
- sql<boolean>`((${ref('repoRev')}, ${ref('cid')}) < (${
122
- cursor.rev
123
- }, ${cursor.cid.toString()}))`,
124
- )
125
- }
126
- if (since) {
127
- builder = builder.where('repoRev', '>', since)
128
- }
129
- return builder.execute()
130
- }
131
-
132
- async countBlocks(): Promise<number> {
133
- const res = await this.db.db
134
- .selectFrom('repo_block')
135
- .select(countAll.as('count'))
136
- .executeTakeFirst()
137
- return res?.count ?? 0
138
- }
139
-
140
- async destroy(): Promise<void> {
141
- throw new Error('Destruction of SQL repo storage not allowed at runtime')
142
- }
143
- }
144
-
145
- type RevCursor = {
146
- cid: Cid
147
- rev: string
148
- }
149
-
150
- export class RepoRootNotFoundError extends Error {}
@@ -1,105 +0,0 @@
1
- import { chunkArray } from '@atproto/common'
2
- import { Cid, parseCid } from '@atproto/lex-data'
3
- import { BlockMap, CommitData, RepoStorage } from '@atproto/repo'
4
- import { ActorDb, RepoBlock } from '../db/index.js'
5
- import { SqlRepoReader } from './sql-repo-reader.js'
6
-
7
- export class SqlRepoTransactor extends SqlRepoReader implements RepoStorage {
8
- cache = new BlockMap()
9
- now: string
10
-
11
- constructor(
12
- public db: ActorDb,
13
- public did: string,
14
- now?: string,
15
- ) {
16
- super(db)
17
- this.now = now ?? new Date().toISOString()
18
- }
19
-
20
- // proactively cache all blocks from a particular commit (to prevent multiple roundtrips)
21
- async cacheRev(rev: string): Promise<void> {
22
- const res = await this.db.db
23
- .selectFrom('repo_block')
24
- .where('repoRev', '=', rev)
25
- .select(['repo_block.cid', 'repo_block.content'])
26
- .limit(15)
27
- .execute()
28
- for (const row of res) {
29
- this.cache.set(parseCid(row.cid), row.content)
30
- }
31
- }
32
-
33
- async putBlock(cid: Cid, block: Uint8Array, rev: string): Promise<void> {
34
- await this.db.db
35
- .insertInto('repo_block')
36
- .values({
37
- cid: cid.toString(),
38
- repoRev: rev,
39
- size: block.length,
40
- content: block,
41
- })
42
- .onConflict((oc) => oc.doNothing())
43
- .execute()
44
- this.cache.set(cid, block)
45
- }
46
-
47
- async putMany(toPut: BlockMap, rev: string): Promise<void> {
48
- const blocks: RepoBlock[] = Array.from(toPut, ([cid, bytes]) => ({
49
- cid: cid.toString(),
50
- repoRev: rev,
51
- size: bytes.length,
52
- content: bytes,
53
- }))
54
-
55
- for (const batch of chunkArray(blocks, 50)) {
56
- await this.db.db
57
- .insertInto('repo_block')
58
- .values(batch)
59
- .onConflict((oc) => oc.doNothing())
60
- .execute()
61
- }
62
- }
63
-
64
- async deleteMany(cids: Cid[]) {
65
- if (cids.length < 1) return
66
- const cidStrs = cids.map((c) => c.toString())
67
- await this.db.db
68
- .deleteFrom('repo_block')
69
- .where('cid', 'in', cidStrs)
70
- .execute()
71
- }
72
-
73
- async applyCommit(commit: CommitData, isCreate?: boolean) {
74
- await this.updateRoot(commit.cid, commit.rev, isCreate)
75
- await this.putMany(commit.newBlocks, commit.rev)
76
- await this.deleteMany(commit.removedCids.toList())
77
- }
78
-
79
- async updateRoot(cid: Cid, rev: string, isCreate = false): Promise<void> {
80
- if (isCreate) {
81
- await this.db.db
82
- .insertInto('repo_root')
83
- .values({
84
- did: this.did,
85
- cid: cid.toString(),
86
- rev: rev,
87
- indexedAt: this.now,
88
- })
89
- .execute()
90
- } else {
91
- await this.db.db
92
- .updateTable('repo_root')
93
- .set({
94
- cid: cid.toString(),
95
- rev: rev,
96
- indexedAt: this.now,
97
- })
98
- .execute()
99
- }
100
- }
101
-
102
- async destroy(): Promise<void> {
103
- throw new Error('Destruction of SQL repo storage not allowed at runtime')
104
- }
105
- }
@@ -1,227 +0,0 @@
1
- import * as crypto from '@atproto/crypto'
2
- import { Cid, parseCid } from '@atproto/lex-data'
3
- import { BlobStore, Repo, WriteOpAction, formatDataKey } from '@atproto/repo'
4
- import { AtUri } from '@atproto/syntax'
5
- import { InvalidRequestError } from '@atproto/xrpc-server'
6
- import { BackgroundQueue } from '../../background.js'
7
- import { createWriteToOp, writeToOp } from '../../repo/index.js'
8
- import {
9
- BadCommitSwapError,
10
- BadRecordSwapError,
11
- CommitDataWithOps,
12
- CommitOp,
13
- PreparedCreate,
14
- PreparedWrite,
15
- } from '../../repo/types.js'
16
- import { BlobTransactor } from '../blob/transactor.js'
17
- import { ActorDb } from '../db/index.js'
18
- import { RecordTransactor } from '../record/transactor.js'
19
- import { RepoReader } from './reader.js'
20
- import { SqlRepoTransactor } from './sql-repo-transactor.js'
21
-
22
- export class RepoTransactor extends RepoReader {
23
- blob: BlobTransactor
24
- record: RecordTransactor
25
- storage: SqlRepoTransactor
26
-
27
- constructor(
28
- public db: ActorDb,
29
- public blobstore: BlobStore,
30
- public did: string,
31
- public signingKey: crypto.Keypair,
32
- public backgroundQueue: BackgroundQueue,
33
- public now: string = new Date().toISOString(),
34
- ) {
35
- super(db, blobstore)
36
- this.blob = new BlobTransactor(db, blobstore, backgroundQueue)
37
- this.record = new RecordTransactor(db, blobstore)
38
- this.storage = new SqlRepoTransactor(db, did, now)
39
- }
40
-
41
- async maybeLoadRepo(): Promise<Repo | null> {
42
- const res = await this.db.db
43
- .selectFrom('repo_root')
44
- .select('cid')
45
- .limit(1)
46
- .executeTakeFirst()
47
- return res ? Repo.load(this.storage, parseCid(res.cid)) : null
48
- }
49
-
50
- async createRepo(writes: PreparedCreate[]): Promise<CommitDataWithOps> {
51
- this.db.assertTransaction()
52
- const commit = await Repo.formatInitCommit(
53
- this.storage,
54
- this.did,
55
- this.signingKey,
56
- writes.map(createWriteToOp),
57
- )
58
- await this.storage.applyCommit(commit, true)
59
- await this.indexWrites(writes, commit.rev)
60
- await this.blob.processWriteBlobs(commit.rev, writes)
61
-
62
- const ops = writes.map((w) => ({
63
- action: 'create' as const,
64
- path: formatDataKey(w.uri.collection, w.uri.rkey),
65
- cid: w.cid,
66
- }))
67
- return {
68
- ...commit,
69
- ops,
70
- prevData: null,
71
- }
72
- }
73
-
74
- async processWrites(
75
- writes: PreparedWrite[],
76
- swapCommitCid?: Cid,
77
- ): Promise<CommitDataWithOps> {
78
- this.db.assertTransaction()
79
- if (writes.length > 200) {
80
- throw new InvalidRequestError('Too many writes. Max: 200')
81
- }
82
-
83
- const commit = await this.formatCommit(writes, swapCommitCid)
84
- // Do not allow commits > 2MB
85
- if (commit.relevantBlocks.byteSize > 2000000) {
86
- throw new InvalidRequestError('Too many writes. Max event size: 2MB')
87
- }
88
-
89
- // persist the commit to repo storage
90
- await this.storage.applyCommit(commit)
91
- // & send to indexing
92
- await this.indexWrites(writes, commit.rev)
93
- // process blobs
94
- await this.blob.processWriteBlobs(commit.rev, writes)
95
-
96
- return commit
97
- }
98
-
99
- async formatCommit(
100
- writes: PreparedWrite[],
101
- swapCommit?: Cid,
102
- ): Promise<CommitDataWithOps> {
103
- // this is not in a txn, so this won't actually hold the lock,
104
- // we just check if it is currently held by another txn
105
- const currRoot = await this.storage.getRootDetailed()
106
- if (!currRoot) {
107
- throw new InvalidRequestError(`No repo root found for ${this.did}`)
108
- }
109
- if (swapCommit && !currRoot.cid.equals(swapCommit)) {
110
- throw new BadCommitSwapError(currRoot.cid)
111
- }
112
- // cache last commit since there's likely overlap
113
- await this.storage.cacheRev(currRoot.rev)
114
- const newRecordCids: Cid[] = []
115
- const delAndUpdateUris: AtUri[] = []
116
- const commitOps: CommitOp[] = []
117
- for (const write of writes) {
118
- const { action, uri, swapCid } = write
119
- if (action !== WriteOpAction.Delete) {
120
- newRecordCids.push(write.cid)
121
- }
122
- if (action !== WriteOpAction.Create) {
123
- delAndUpdateUris.push(uri)
124
- }
125
- const record = await this.record.getRecord(uri, null, true)
126
- const currRecord = record ? parseCid(record.cid) : null
127
-
128
- const op: CommitOp = {
129
- action,
130
- path: formatDataKey(uri.collection, uri.rkey),
131
- cid: write.action === WriteOpAction.Delete ? null : write.cid,
132
- }
133
- if (currRecord) {
134
- op.prev = currRecord
135
- }
136
- commitOps.push(op)
137
- if (swapCid !== undefined) {
138
- if (action === WriteOpAction.Create && swapCid !== null) {
139
- throw new BadRecordSwapError(currRecord) // There should be no current record for a create
140
- }
141
- if (action === WriteOpAction.Update && swapCid === null) {
142
- throw new BadRecordSwapError(currRecord) // There should be a current record for an update
143
- }
144
- if (action === WriteOpAction.Delete && swapCid === null) {
145
- throw new BadRecordSwapError(currRecord) // There should be a current record for a delete
146
- }
147
- if (
148
- // If we have either a current CID or a swap CID
149
- (currRecord || swapCid) &&
150
- // We make sure that both are provided and equal
151
- !(swapCid && currRecord && currRecord.equals(swapCid))
152
- ) {
153
- throw new BadRecordSwapError(currRecord)
154
- }
155
- }
156
- }
157
-
158
- const repo = await Repo.load(this.storage, currRoot.cid)
159
- const prevData = repo.commit.data
160
- const writeOps = writes.map(writeToOp)
161
- const commit = await repo.formatCommit(writeOps, this.signingKey)
162
-
163
- // find blocks that would be deleted but are referenced by another record
164
- const dupeRecordCids = await this.getDuplicateRecordCids(
165
- commit.removedCids.toList(),
166
- delAndUpdateUris,
167
- )
168
- for (const cid of dupeRecordCids) {
169
- commit.removedCids.delete(cid)
170
- }
171
-
172
- // find blocks that are relevant to ops but not included in diff
173
- // (for instance a record that was moved but cid stayed the same)
174
- const newRecordBlocks = commit.relevantBlocks.getMany(newRecordCids)
175
- if (newRecordBlocks.missing.length > 0) {
176
- const missingBlocks = await this.storage.getBlocks(
177
- newRecordBlocks.missing,
178
- )
179
- commit.relevantBlocks.addMap(missingBlocks.blocks)
180
- }
181
- return {
182
- ...commit,
183
- ops: commitOps,
184
- prevData,
185
- }
186
- }
187
-
188
- async indexWrites(writes: PreparedWrite[], rev: string) {
189
- this.db.assertTransaction()
190
-
191
- for (const write of writes) {
192
- if (
193
- write.action === WriteOpAction.Create ||
194
- write.action === WriteOpAction.Update
195
- ) {
196
- await this.record.indexRecord(
197
- write.uri,
198
- write.cid,
199
- write.record,
200
- write.action,
201
- rev,
202
- this.now,
203
- )
204
- } else if (write.action === WriteOpAction.Delete) {
205
- await this.record.deleteRecord(write.uri)
206
- }
207
- }
208
- }
209
-
210
- async getDuplicateRecordCids(
211
- cids: Cid[],
212
- touchedUris: AtUri[],
213
- ): Promise<Cid[]> {
214
- if (touchedUris.length === 0 || cids.length === 0) {
215
- return []
216
- }
217
- const cidStrs = cids.map((c) => c.toString())
218
- const uriStrs = touchedUris.map((u) => u.toString())
219
- const res = await this.db.db
220
- .selectFrom('record')
221
- .where('cid', 'in', cidStrs)
222
- .where('uri', 'not in', uriStrs)
223
- .select('cid')
224
- .execute()
225
- return res.map((row) => parseCid(row.cid))
226
- }
227
- }
@@ -1,57 +0,0 @@
1
- import { Server } from '@atproto/xrpc-server'
2
- import { AuthScope, isAccessFull } from '../../../../auth-scope.js'
3
- import { AppContext } from '../../../../context.js'
4
- import { app } from '../../../../lexicons/index.js'
5
- import {
6
- bareDidFromProxyTo,
7
- computeProxyTo,
8
- pipethrough,
9
- } from '../../../../pipethrough.js'
10
-
11
- export default function (server: Server, ctx: AppContext) {
12
- const { bskyAppView } = ctx
13
- if (!bskyAppView) return
14
-
15
- server.add(app.bsky.actor.getPreferences, {
16
- auth: ctx.authVerifier.authorization({
17
- additional: [AuthScope.Takendown],
18
- authorize: (permissions, { req }) => {
19
- const lxm = app.bsky.actor.getPreferences.$lxm
20
- const aud = computeProxyTo(ctx, req, lxm)
21
- permissions.assertRpc({ aud, lxm })
22
- },
23
- }),
24
- handler: async ({ auth, req }) => {
25
- const { did } = auth.credentials
26
-
27
- // If the request has a proxy header different from the bsky app view,
28
- // we need to proxy the request to the requested app view.
29
- // @TODO This behavior should not be implemented as part of the XRPC framework
30
- const lxm = app.bsky.actor.getPreferences.$lxm
31
- const aud = computeProxyTo(ctx, req, lxm)
32
- if (aud !== `${bskyAppView.did}#bsky_appview`) {
33
- // Phase 1 of service auth updates: outbound JWT keeps bare-DID aud.
34
- return pipethrough(ctx, req, {
35
- iss: did,
36
- aud: bareDidFromProxyTo(aud),
37
- lxm,
38
- })
39
- }
40
-
41
- const hasAccessFull =
42
- auth.credentials.type === 'access' &&
43
- isAccessFull(auth.credentials.scope)
44
-
45
- const preferences = await ctx.actorStore.read(did, (store) => {
46
- return store.pref.getPreferences('app.bsky', {
47
- hasAccessFull,
48
- })
49
- })
50
-
51
- return {
52
- encoding: 'application/json' as const,
53
- body: { preferences },
54
- }
55
- },
56
- })
57
- }
@@ -1,41 +0,0 @@
1
- import { Server } from '@atproto/xrpc-server'
2
- import { AppContext } from '../../../../context.js'
3
- import { app } from '../../../../lexicons/index.js'
4
- import { computeProxyTo } from '../../../../pipethrough.js'
5
- import {
6
- MungeFn,
7
- pipethroughReadAfterWrite,
8
- } from '../../../../read-after-write/index.js'
9
-
10
- export default function (server: Server, ctx: AppContext) {
11
- if (!ctx.bskyAppView) return
12
-
13
- server.add(app.bsky.actor.getProfile, {
14
- auth: ctx.authVerifier.authorization({
15
- authorize: (permissions, { req }) => {
16
- const lxm = app.bsky.actor.getProfile.$lxm
17
- const aud = computeProxyTo(ctx, req, lxm)
18
- permissions.assertRpc({ aud, lxm })
19
- },
20
- }),
21
- handler: async (reqCtx) => {
22
- return pipethroughReadAfterWrite(
23
- ctx,
24
- reqCtx,
25
- app.bsky.actor.getProfile,
26
- getProfileMunge,
27
- )
28
- },
29
- })
30
- }
31
-
32
- const getProfileMunge: MungeFn<app.bsky.actor.getProfile.$OutputBody> = async (
33
- localViewer,
34
- original,
35
- local,
36
- requester,
37
- ) => {
38
- if (!local.profile) return original
39
- if (original.did !== requester) return original
40
- return localViewer.updateProfileDetailed(original, local.profile.record)
41
- }
@@ -1,51 +0,0 @@
1
- import { Server } from '@atproto/xrpc-server'
2
- import { AppContext } from '../../../../context.js'
3
- import { app } from '../../../../lexicons/index.js'
4
- import { computeProxyTo } from '../../../../pipethrough.js'
5
- import {
6
- MungeFn,
7
- pipethroughReadAfterWrite,
8
- } from '../../../../read-after-write/index.js'
9
-
10
- export default function (server: Server, ctx: AppContext) {
11
- if (!ctx.bskyAppView) return
12
-
13
- server.add(app.bsky.actor.getProfiles, {
14
- auth: ctx.authVerifier.authorization({
15
- authorize: (permissions, { req }) => {
16
- const lxm = app.bsky.actor.getProfiles.$lxm
17
- const aud = computeProxyTo(ctx, req, lxm)
18
- permissions.assertRpc({ aud, lxm })
19
- },
20
- }),
21
- opts: {
22
- // @TODO remove after grace period has passed, behavior is non-standard.
23
- // temporarily added for compat w/ previous version of xrpc-server to avoid breakage of a few specified parties.
24
- paramsParseLoose: true,
25
- },
26
- handler: async (reqCtx) => {
27
- return pipethroughReadAfterWrite(
28
- ctx,
29
- reqCtx,
30
- app.bsky.actor.getProfiles,
31
- getProfilesMunge,
32
- )
33
- },
34
- })
35
- }
36
-
37
- const getProfilesMunge: MungeFn<
38
- app.bsky.actor.getProfiles.$OutputBody
39
- > = async (localViewer, original, local, requester) => {
40
- const localProf = local.profile
41
- if (!localProf) return original
42
-
43
- const profiles = original.profiles.map((prof) => {
44
- if (prof.did !== requester) return prof
45
- return localViewer.updateProfileDetailed(prof, localProf.record)
46
- })
47
- return {
48
- ...original,
49
- profiles,
50
- }
51
- }
@@ -1,13 +0,0 @@
1
- import { Server } from '@atproto/xrpc-server'
2
- import { AppContext } from '../../../../context.js'
3
- import getPreferences from './getPreferences.js'
4
- import getProfile from './getProfile.js'
5
- import getProfiles from './getProfiles.js'
6
- import putPreferences from './putPreferences.js'
7
-
8
- export default function (server: Server, ctx: AppContext) {
9
- getPreferences(server, ctx)
10
- getProfile(server, ctx)
11
- getProfiles(server, ctx)
12
- putPreferences(server, ctx)
13
- }