@atproto/pds 0.4.68 → 0.4.70
Sign up to get free protection for your applications and to get access to all the features.
- package/CHANGELOG.md +26 -0
- package/dist/api/app/bsky/feed/getPostThread.d.ts.map +1 -1
- package/dist/api/app/bsky/feed/getPostThread.js +11 -6
- package/dist/api/app/bsky/feed/getPostThread.js.map +1 -1
- package/dist/config/config.d.ts +1 -0
- package/dist/config/config.d.ts.map +1 -1
- package/dist/config/config.js +3 -0
- package/dist/config/config.js.map +1 -1
- package/dist/config/env.d.ts +1 -0
- package/dist/config/env.d.ts.map +1 -1
- package/dist/config/env.js +1 -0
- package/dist/config/env.js.map +1 -1
- package/dist/context.d.ts +2 -2
- package/dist/context.d.ts.map +1 -1
- package/dist/context.js +8 -1
- package/dist/context.js.map +1 -1
- package/dist/lexicon/index.d.ts +13 -0
- package/dist/lexicon/index.d.ts.map +1 -1
- package/dist/lexicon/index.js +36 -1
- package/dist/lexicon/index.js.map +1 -1
- package/dist/lexicon/lexicons.d.ts +396 -0
- package/dist/lexicon/lexicons.d.ts.map +1 -1
- package/dist/lexicon/lexicons.js +439 -3
- package/dist/lexicon/lexicons.js.map +1 -1
- package/dist/lexicon/types/app/bsky/unspecced/getConfig.d.ts +34 -0
- package/dist/lexicon/types/app/bsky/unspecced/getConfig.d.ts.map +1 -0
- package/dist/lexicon/types/app/bsky/unspecced/getConfig.js +3 -0
- package/dist/lexicon/types/app/bsky/unspecced/getConfig.js.map +1 -0
- package/dist/lexicon/types/tools/ozone/moderation/defs.d.ts +60 -2
- package/dist/lexicon/types/tools/ozone/moderation/defs.d.ts.map +1 -1
- package/dist/lexicon/types/tools/ozone/moderation/defs.js +50 -0
- package/dist/lexicon/types/tools/ozone/moderation/defs.js.map +1 -1
- package/dist/lexicon/types/tools/ozone/moderation/emitEvent.d.ts +1 -1
- package/dist/lexicon/types/tools/ozone/moderation/emitEvent.d.ts.map +1 -1
- package/dist/lexicon/types/tools/ozone/moderation/queryStatuses.d.ts +10 -0
- package/dist/lexicon/types/tools/ozone/moderation/queryStatuses.d.ts.map +1 -1
- package/dist/lexicon/types/tools/ozone/setting/defs.d.ts +20 -0
- package/dist/lexicon/types/tools/ozone/setting/defs.d.ts.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/defs.js +15 -0
- package/dist/lexicon/types/tools/ozone/setting/defs.js.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/listOptions.d.ts +43 -0
- package/dist/lexicon/types/tools/ozone/setting/listOptions.d.ts.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/listOptions.js +3 -0
- package/dist/lexicon/types/tools/ozone/setting/listOptions.js.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/removeOptions.d.ts +40 -0
- package/dist/lexicon/types/tools/ozone/setting/removeOptions.d.ts.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/removeOptions.js +3 -0
- package/dist/lexicon/types/tools/ozone/setting/removeOptions.js.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/upsertOption.d.ts +45 -0
- package/dist/lexicon/types/tools/ozone/setting/upsertOption.d.ts.map +1 -0
- package/dist/lexicon/types/tools/ozone/setting/upsertOption.js +3 -0
- package/dist/lexicon/types/tools/ozone/setting/upsertOption.js.map +1 -0
- package/dist/pipethrough.d.ts +0 -1
- package/dist/pipethrough.d.ts.map +1 -1
- package/dist/pipethrough.js +11 -10
- package/dist/pipethrough.js.map +1 -1
- package/example.env +1 -1
- package/package.json +11 -11
- package/src/api/app/bsky/feed/getPostThread.ts +15 -4
- package/src/config/config.ts +5 -0
- package/src/config/env.ts +2 -0
- package/src/context.ts +11 -3
- package/src/lexicon/index.ts +58 -0
- package/src/lexicon/lexicons.ts +449 -3
- package/src/lexicon/types/app/bsky/unspecced/getConfig.ts +43 -0
- package/src/lexicon/types/tools/ozone/moderation/defs.ts +132 -0
- package/src/lexicon/types/tools/ozone/moderation/emitEvent.ts +3 -0
- package/src/lexicon/types/tools/ozone/moderation/queryStatuses.ts +10 -0
- package/src/lexicon/types/tools/ozone/setting/defs.ts +37 -0
- package/src/lexicon/types/tools/ozone/setting/listOptions.ts +53 -0
- package/src/lexicon/types/tools/ozone/setting/removeOptions.ts +49 -0
- package/src/lexicon/types/tools/ozone/setting/upsertOption.ts +58 -0
- package/src/pipethrough.ts +13 -12
- package/tests/proxied/__snapshots__/admin.test.ts.snap +12 -0
- package/tests/proxied/proxy-catchall.test.ts +1 -1
- package/tests/proxied/read-after-write.test.ts +20 -1
- package/tsconfig.build.tsbuildinfo +1 -1
@@ -30,6 +30,9 @@ export interface ModEventView {
|
|
30
30
|
| ModEventResolveAppeal
|
31
31
|
| ModEventDivert
|
32
32
|
| ModEventTag
|
33
|
+
| AccountEvent
|
34
|
+
| IdentityEvent
|
35
|
+
| RecordEvent
|
33
36
|
| { $type: string; [k: string]: unknown }
|
34
37
|
subject:
|
35
38
|
| ComAtprotoAdminDefs.RepoRef
|
@@ -74,6 +77,9 @@ export interface ModEventViewDetail {
|
|
74
77
|
| ModEventResolveAppeal
|
75
78
|
| ModEventDivert
|
76
79
|
| ModEventTag
|
80
|
+
| AccountEvent
|
81
|
+
| IdentityEvent
|
82
|
+
| RecordEvent
|
77
83
|
| { $type: string; [k: string]: unknown }
|
78
84
|
subject:
|
79
85
|
| RepoView
|
@@ -105,6 +111,10 @@ export interface SubjectStatusView {
|
|
105
111
|
| ComAtprotoAdminDefs.RepoRef
|
106
112
|
| ComAtprotoRepoStrongRef.Main
|
107
113
|
| { $type: string; [k: string]: unknown }
|
114
|
+
hosting?:
|
115
|
+
| AccountHosting
|
116
|
+
| RecordHosting
|
117
|
+
| { $type: string; [k: string]: unknown }
|
108
118
|
subjectBlobCids?: string[]
|
109
119
|
subjectRepoHandle?: string
|
110
120
|
/** Timestamp referencing when the last update was made to the moderation status of the subject */
|
@@ -472,6 +482,78 @@ export function validateModEventTag(v: unknown): ValidationResult {
|
|
472
482
|
return lexicons.validate('tools.ozone.moderation.defs#modEventTag', v)
|
473
483
|
}
|
474
484
|
|
485
|
+
/** Logs account status related events on a repo subject. Normally captured by automod from the firehose and emitted to ozone for historical tracking. */
|
486
|
+
export interface AccountEvent {
|
487
|
+
comment?: string
|
488
|
+
/** Indicates that the account has a repository which can be fetched from the host that emitted this event. */
|
489
|
+
active: boolean
|
490
|
+
status?:
|
491
|
+
| 'unknown'
|
492
|
+
| 'deactivated'
|
493
|
+
| 'deleted'
|
494
|
+
| 'takendown'
|
495
|
+
| 'suspended'
|
496
|
+
| 'tombstoned'
|
497
|
+
| (string & {})
|
498
|
+
timestamp: string
|
499
|
+
[k: string]: unknown
|
500
|
+
}
|
501
|
+
|
502
|
+
export function isAccountEvent(v: unknown): v is AccountEvent {
|
503
|
+
return (
|
504
|
+
isObj(v) &&
|
505
|
+
hasProp(v, '$type') &&
|
506
|
+
v.$type === 'tools.ozone.moderation.defs#accountEvent'
|
507
|
+
)
|
508
|
+
}
|
509
|
+
|
510
|
+
export function validateAccountEvent(v: unknown): ValidationResult {
|
511
|
+
return lexicons.validate('tools.ozone.moderation.defs#accountEvent', v)
|
512
|
+
}
|
513
|
+
|
514
|
+
/** Logs identity related events on a repo subject. Normally captured by automod from the firehose and emitted to ozone for historical tracking. */
|
515
|
+
export interface IdentityEvent {
|
516
|
+
comment?: string
|
517
|
+
handle?: string
|
518
|
+
pdsHost?: string
|
519
|
+
tombstone?: boolean
|
520
|
+
timestamp: string
|
521
|
+
[k: string]: unknown
|
522
|
+
}
|
523
|
+
|
524
|
+
export function isIdentityEvent(v: unknown): v is IdentityEvent {
|
525
|
+
return (
|
526
|
+
isObj(v) &&
|
527
|
+
hasProp(v, '$type') &&
|
528
|
+
v.$type === 'tools.ozone.moderation.defs#identityEvent'
|
529
|
+
)
|
530
|
+
}
|
531
|
+
|
532
|
+
export function validateIdentityEvent(v: unknown): ValidationResult {
|
533
|
+
return lexicons.validate('tools.ozone.moderation.defs#identityEvent', v)
|
534
|
+
}
|
535
|
+
|
536
|
+
/** Logs lifecycle event on a record subject. Normally captured by automod from the firehose and emitted to ozone for historical tracking. */
|
537
|
+
export interface RecordEvent {
|
538
|
+
comment?: string
|
539
|
+
op: 'create' | 'update' | 'delete' | (string & {})
|
540
|
+
cid?: string
|
541
|
+
timestamp: string
|
542
|
+
[k: string]: unknown
|
543
|
+
}
|
544
|
+
|
545
|
+
export function isRecordEvent(v: unknown): v is RecordEvent {
|
546
|
+
return (
|
547
|
+
isObj(v) &&
|
548
|
+
hasProp(v, '$type') &&
|
549
|
+
v.$type === 'tools.ozone.moderation.defs#recordEvent'
|
550
|
+
)
|
551
|
+
}
|
552
|
+
|
553
|
+
export function validateRecordEvent(v: unknown): ValidationResult {
|
554
|
+
return lexicons.validate('tools.ozone.moderation.defs#recordEvent', v)
|
555
|
+
}
|
556
|
+
|
475
557
|
export interface RepoView {
|
476
558
|
did: string
|
477
559
|
handle: string
|
@@ -483,6 +565,7 @@ export interface RepoView {
|
|
483
565
|
invitesDisabled?: boolean
|
484
566
|
inviteNote?: string
|
485
567
|
deactivatedAt?: string
|
568
|
+
threatSignatures?: ComAtprotoAdminDefs.ThreatSignature[]
|
486
569
|
[k: string]: unknown
|
487
570
|
}
|
488
571
|
|
@@ -512,6 +595,7 @@ export interface RepoViewDetail {
|
|
512
595
|
inviteNote?: string
|
513
596
|
emailConfirmedAt?: string
|
514
597
|
deactivatedAt?: string
|
598
|
+
threatSignatures?: ComAtprotoAdminDefs.ThreatSignature[]
|
515
599
|
[k: string]: unknown
|
516
600
|
}
|
517
601
|
|
@@ -703,3 +787,51 @@ export function isVideoDetails(v: unknown): v is VideoDetails {
|
|
703
787
|
export function validateVideoDetails(v: unknown): ValidationResult {
|
704
788
|
return lexicons.validate('tools.ozone.moderation.defs#videoDetails', v)
|
705
789
|
}
|
790
|
+
|
791
|
+
export interface AccountHosting {
|
792
|
+
status:
|
793
|
+
| 'takendown'
|
794
|
+
| 'suspended'
|
795
|
+
| 'deleted'
|
796
|
+
| 'deactivated'
|
797
|
+
| 'unknown'
|
798
|
+
| (string & {})
|
799
|
+
updatedAt?: string
|
800
|
+
createdAt?: string
|
801
|
+
deletedAt?: string
|
802
|
+
deactivatedAt?: string
|
803
|
+
reactivatedAt?: string
|
804
|
+
[k: string]: unknown
|
805
|
+
}
|
806
|
+
|
807
|
+
export function isAccountHosting(v: unknown): v is AccountHosting {
|
808
|
+
return (
|
809
|
+
isObj(v) &&
|
810
|
+
hasProp(v, '$type') &&
|
811
|
+
v.$type === 'tools.ozone.moderation.defs#accountHosting'
|
812
|
+
)
|
813
|
+
}
|
814
|
+
|
815
|
+
export function validateAccountHosting(v: unknown): ValidationResult {
|
816
|
+
return lexicons.validate('tools.ozone.moderation.defs#accountHosting', v)
|
817
|
+
}
|
818
|
+
|
819
|
+
export interface RecordHosting {
|
820
|
+
status: 'deleted' | 'unknown' | (string & {})
|
821
|
+
updatedAt?: string
|
822
|
+
createdAt?: string
|
823
|
+
deletedAt?: string
|
824
|
+
[k: string]: unknown
|
825
|
+
}
|
826
|
+
|
827
|
+
export function isRecordHosting(v: unknown): v is RecordHosting {
|
828
|
+
return (
|
829
|
+
isObj(v) &&
|
830
|
+
hasProp(v, '$type') &&
|
831
|
+
v.$type === 'tools.ozone.moderation.defs#recordHosting'
|
832
|
+
)
|
833
|
+
}
|
834
|
+
|
835
|
+
export function validateRecordHosting(v: unknown): ValidationResult {
|
836
|
+
return lexicons.validate('tools.ozone.moderation.defs#recordHosting', v)
|
837
|
+
}
|
@@ -29,6 +29,9 @@ export interface InputSchema {
|
|
29
29
|
| ToolsOzoneModerationDefs.ModEventResolveAppeal
|
30
30
|
| ToolsOzoneModerationDefs.ModEventEmail
|
31
31
|
| ToolsOzoneModerationDefs.ModEventTag
|
32
|
+
| ToolsOzoneModerationDefs.AccountEvent
|
33
|
+
| ToolsOzoneModerationDefs.IdentityEvent
|
34
|
+
| ToolsOzoneModerationDefs.RecordEvent
|
32
35
|
| { $type: string; [k: string]: unknown }
|
33
36
|
subject:
|
34
37
|
| ComAtprotoAdminDefs.RepoRef
|
@@ -22,6 +22,16 @@ export interface QueryParams {
|
|
22
22
|
reportedBefore?: string
|
23
23
|
/** Search subjects reviewed after a given timestamp */
|
24
24
|
reviewedAfter?: string
|
25
|
+
/** Search subjects where the associated record/account was deleted after a given timestamp */
|
26
|
+
hostingDeletedAfter?: string
|
27
|
+
/** Search subjects where the associated record/account was deleted before a given timestamp */
|
28
|
+
hostingDeletedBefore?: string
|
29
|
+
/** Search subjects where the associated record/account was updated after a given timestamp */
|
30
|
+
hostingUpdatedAfter?: string
|
31
|
+
/** Search subjects where the associated record/account was updated before a given timestamp */
|
32
|
+
hostingUpdatedBefore?: string
|
33
|
+
/** Search subjects by the status of the associated record/account */
|
34
|
+
hostingStatuses?: string[]
|
25
35
|
/** Search subjects reviewed before a given timestamp */
|
26
36
|
reviewedBefore?: string
|
27
37
|
/** By default, we don't include muted subjects in the results. Set this to true to include them. */
|
@@ -0,0 +1,37 @@
|
|
1
|
+
/**
|
2
|
+
* GENERATED CODE - DO NOT MODIFY
|
3
|
+
*/
|
4
|
+
import { ValidationResult, BlobRef } from '@atproto/lexicon'
|
5
|
+
import { lexicons } from '../../../../lexicons'
|
6
|
+
import { isObj, hasProp } from '../../../../util'
|
7
|
+
import { CID } from 'multiformats/cid'
|
8
|
+
|
9
|
+
export interface Option {
|
10
|
+
key: string
|
11
|
+
did: string
|
12
|
+
value: {}
|
13
|
+
description?: string
|
14
|
+
createdAt?: string
|
15
|
+
updatedAt?: string
|
16
|
+
managerRole?:
|
17
|
+
| 'tools.ozone.team.defs#roleModerator'
|
18
|
+
| 'tools.ozone.team.defs#roleTriage'
|
19
|
+
| 'tools.ozone.team.defs#roleAdmin'
|
20
|
+
| (string & {})
|
21
|
+
scope: 'instance' | 'personal' | (string & {})
|
22
|
+
createdBy: string
|
23
|
+
lastUpdatedBy: string
|
24
|
+
[k: string]: unknown
|
25
|
+
}
|
26
|
+
|
27
|
+
export function isOption(v: unknown): v is Option {
|
28
|
+
return (
|
29
|
+
isObj(v) &&
|
30
|
+
hasProp(v, '$type') &&
|
31
|
+
v.$type === 'tools.ozone.setting.defs#option'
|
32
|
+
)
|
33
|
+
}
|
34
|
+
|
35
|
+
export function validateOption(v: unknown): ValidationResult {
|
36
|
+
return lexicons.validate('tools.ozone.setting.defs#option', v)
|
37
|
+
}
|
@@ -0,0 +1,53 @@
|
|
1
|
+
/**
|
2
|
+
* GENERATED CODE - DO NOT MODIFY
|
3
|
+
*/
|
4
|
+
import express from 'express'
|
5
|
+
import { ValidationResult, BlobRef } from '@atproto/lexicon'
|
6
|
+
import { lexicons } from '../../../../lexicons'
|
7
|
+
import { isObj, hasProp } from '../../../../util'
|
8
|
+
import { CID } from 'multiformats/cid'
|
9
|
+
import { HandlerAuth, HandlerPipeThrough } from '@atproto/xrpc-server'
|
10
|
+
import * as ToolsOzoneSettingDefs from './defs'
|
11
|
+
|
12
|
+
export interface QueryParams {
|
13
|
+
limit: number
|
14
|
+
cursor?: string
|
15
|
+
scope: 'instance' | 'personal' | (string & {})
|
16
|
+
/** Filter keys by prefix */
|
17
|
+
prefix?: string
|
18
|
+
/** Filter for only the specified keys. Ignored if prefix is provided */
|
19
|
+
keys?: string[]
|
20
|
+
}
|
21
|
+
|
22
|
+
export type InputSchema = undefined
|
23
|
+
|
24
|
+
export interface OutputSchema {
|
25
|
+
cursor?: string
|
26
|
+
options: ToolsOzoneSettingDefs.Option[]
|
27
|
+
[k: string]: unknown
|
28
|
+
}
|
29
|
+
|
30
|
+
export type HandlerInput = undefined
|
31
|
+
|
32
|
+
export interface HandlerSuccess {
|
33
|
+
encoding: 'application/json'
|
34
|
+
body: OutputSchema
|
35
|
+
headers?: { [key: string]: string }
|
36
|
+
}
|
37
|
+
|
38
|
+
export interface HandlerError {
|
39
|
+
status: number
|
40
|
+
message?: string
|
41
|
+
}
|
42
|
+
|
43
|
+
export type HandlerOutput = HandlerError | HandlerSuccess | HandlerPipeThrough
|
44
|
+
export type HandlerReqCtx<HA extends HandlerAuth = never> = {
|
45
|
+
auth: HA
|
46
|
+
params: QueryParams
|
47
|
+
input: HandlerInput
|
48
|
+
req: express.Request
|
49
|
+
res: express.Response
|
50
|
+
}
|
51
|
+
export type Handler<HA extends HandlerAuth = never> = (
|
52
|
+
ctx: HandlerReqCtx<HA>,
|
53
|
+
) => Promise<HandlerOutput> | HandlerOutput
|
@@ -0,0 +1,49 @@
|
|
1
|
+
/**
|
2
|
+
* GENERATED CODE - DO NOT MODIFY
|
3
|
+
*/
|
4
|
+
import express from 'express'
|
5
|
+
import { ValidationResult, BlobRef } from '@atproto/lexicon'
|
6
|
+
import { lexicons } from '../../../../lexicons'
|
7
|
+
import { isObj, hasProp } from '../../../../util'
|
8
|
+
import { CID } from 'multiformats/cid'
|
9
|
+
import { HandlerAuth, HandlerPipeThrough } from '@atproto/xrpc-server'
|
10
|
+
|
11
|
+
export interface QueryParams {}
|
12
|
+
|
13
|
+
export interface InputSchema {
|
14
|
+
keys: string[]
|
15
|
+
scope: 'instance' | 'personal' | (string & {})
|
16
|
+
[k: string]: unknown
|
17
|
+
}
|
18
|
+
|
19
|
+
export interface OutputSchema {
|
20
|
+
[k: string]: unknown
|
21
|
+
}
|
22
|
+
|
23
|
+
export interface HandlerInput {
|
24
|
+
encoding: 'application/json'
|
25
|
+
body: InputSchema
|
26
|
+
}
|
27
|
+
|
28
|
+
export interface HandlerSuccess {
|
29
|
+
encoding: 'application/json'
|
30
|
+
body: OutputSchema
|
31
|
+
headers?: { [key: string]: string }
|
32
|
+
}
|
33
|
+
|
34
|
+
export interface HandlerError {
|
35
|
+
status: number
|
36
|
+
message?: string
|
37
|
+
}
|
38
|
+
|
39
|
+
export type HandlerOutput = HandlerError | HandlerSuccess | HandlerPipeThrough
|
40
|
+
export type HandlerReqCtx<HA extends HandlerAuth = never> = {
|
41
|
+
auth: HA
|
42
|
+
params: QueryParams
|
43
|
+
input: HandlerInput
|
44
|
+
req: express.Request
|
45
|
+
res: express.Response
|
46
|
+
}
|
47
|
+
export type Handler<HA extends HandlerAuth = never> = (
|
48
|
+
ctx: HandlerReqCtx<HA>,
|
49
|
+
) => Promise<HandlerOutput> | HandlerOutput
|
@@ -0,0 +1,58 @@
|
|
1
|
+
/**
|
2
|
+
* GENERATED CODE - DO NOT MODIFY
|
3
|
+
*/
|
4
|
+
import express from 'express'
|
5
|
+
import { ValidationResult, BlobRef } from '@atproto/lexicon'
|
6
|
+
import { lexicons } from '../../../../lexicons'
|
7
|
+
import { isObj, hasProp } from '../../../../util'
|
8
|
+
import { CID } from 'multiformats/cid'
|
9
|
+
import { HandlerAuth, HandlerPipeThrough } from '@atproto/xrpc-server'
|
10
|
+
import * as ToolsOzoneSettingDefs from './defs'
|
11
|
+
|
12
|
+
export interface QueryParams {}
|
13
|
+
|
14
|
+
export interface InputSchema {
|
15
|
+
key: string
|
16
|
+
scope: 'instance' | 'personal' | (string & {})
|
17
|
+
value: {}
|
18
|
+
description?: string
|
19
|
+
managerRole?:
|
20
|
+
| 'tools.ozone.team.defs#roleModerator'
|
21
|
+
| 'tools.ozone.team.defs#roleTriage'
|
22
|
+
| 'tools.ozone.team.defs#roleAdmin'
|
23
|
+
| (string & {})
|
24
|
+
[k: string]: unknown
|
25
|
+
}
|
26
|
+
|
27
|
+
export interface OutputSchema {
|
28
|
+
option: ToolsOzoneSettingDefs.Option
|
29
|
+
[k: string]: unknown
|
30
|
+
}
|
31
|
+
|
32
|
+
export interface HandlerInput {
|
33
|
+
encoding: 'application/json'
|
34
|
+
body: InputSchema
|
35
|
+
}
|
36
|
+
|
37
|
+
export interface HandlerSuccess {
|
38
|
+
encoding: 'application/json'
|
39
|
+
body: OutputSchema
|
40
|
+
headers?: { [key: string]: string }
|
41
|
+
}
|
42
|
+
|
43
|
+
export interface HandlerError {
|
44
|
+
status: number
|
45
|
+
message?: string
|
46
|
+
}
|
47
|
+
|
48
|
+
export type HandlerOutput = HandlerError | HandlerSuccess | HandlerPipeThrough
|
49
|
+
export type HandlerReqCtx<HA extends HandlerAuth = never> = {
|
50
|
+
auth: HA
|
51
|
+
params: QueryParams
|
52
|
+
input: HandlerInput
|
53
|
+
req: express.Request
|
54
|
+
res: express.Response
|
55
|
+
}
|
56
|
+
export type Handler<HA extends HandlerAuth = never> = (
|
57
|
+
ctx: HandlerReqCtx<HA>,
|
58
|
+
) => Promise<HandlerOutput> | HandlerOutput
|
package/src/pipethrough.ts
CHANGED
@@ -357,9 +357,9 @@ async function pipethroughRequest(
|
|
357
357
|
|
358
358
|
function handleUpstreamRequestError(
|
359
359
|
err: unknown,
|
360
|
-
message = '
|
360
|
+
message = 'Upstream service unreachable',
|
361
361
|
): never {
|
362
|
-
httpLogger.
|
362
|
+
httpLogger.error({ err }, message)
|
363
363
|
throw new XRPCServerError(ResponseType.UpstreamFailure, message, undefined, {
|
364
364
|
cause: err,
|
365
365
|
})
|
@@ -520,18 +520,11 @@ async function tryParsingError(
|
|
520
520
|
}
|
521
521
|
}
|
522
522
|
|
523
|
-
|
523
|
+
async function bufferUpstreamResponse(
|
524
524
|
readable: Readable,
|
525
525
|
contentEncoding?: string | string[],
|
526
526
|
): Promise<Buffer> {
|
527
527
|
try {
|
528
|
-
// Needed for type-safety (should never happen irl)
|
529
|
-
if (Array.isArray(contentEncoding)) {
|
530
|
-
throw new TypeError(
|
531
|
-
'upstream service returned multiple content-encoding headers',
|
532
|
-
)
|
533
|
-
}
|
534
|
-
|
535
528
|
return await streamToNodeBuffer(decodeStream(readable, contentEncoding))
|
536
529
|
} catch (err) {
|
537
530
|
if (!readable.destroyed) readable.destroy()
|
@@ -561,7 +554,11 @@ export async function asPipeThroughBuffer(
|
|
561
554
|
// Response parsing/forwarding
|
562
555
|
// -------------------
|
563
556
|
|
564
|
-
const RES_HEADERS_TO_FORWARD = [
|
557
|
+
const RES_HEADERS_TO_FORWARD = [
|
558
|
+
'atproto-repo-rev',
|
559
|
+
'atproto-content-labelers',
|
560
|
+
'retry-after',
|
561
|
+
]
|
565
562
|
|
566
563
|
function* responseHeaders(
|
567
564
|
headers: IncomingHttpHeaders,
|
@@ -584,7 +581,11 @@ function* responseHeaders(
|
|
584
581
|
for (let i = 0; i < RES_HEADERS_TO_FORWARD.length; i++) {
|
585
582
|
const name = RES_HEADERS_TO_FORWARD[i]
|
586
583
|
const val = headers[name]
|
587
|
-
|
584
|
+
|
585
|
+
if (val != null) {
|
586
|
+
const value: string = Array.isArray(val) ? val.join(',') : val
|
587
|
+
yield [name, value]
|
588
|
+
}
|
588
589
|
}
|
589
590
|
}
|
590
591
|
|
@@ -122,6 +122,10 @@ Object {
|
|
122
122
|
"moderation": Object {
|
123
123
|
"subjectStatus": Object {
|
124
124
|
"createdAt": "1970-01-01T00:00:00.000Z",
|
125
|
+
"hosting": Object {
|
126
|
+
"$type": "tools.ozone.moderation.defs#accountHosting",
|
127
|
+
"status": "unknown",
|
128
|
+
},
|
125
129
|
"id": 1,
|
126
130
|
"lastReportedAt": "1970-01-01T00:00:00.000Z",
|
127
131
|
"lastReviewedAt": "1970-01-01T00:00:00.000Z",
|
@@ -214,6 +218,10 @@ Object {
|
|
214
218
|
"moderation": Object {
|
215
219
|
"subjectStatus": Object {
|
216
220
|
"createdAt": "1970-01-01T00:00:00.000Z",
|
221
|
+
"hosting": Object {
|
222
|
+
"$type": "tools.ozone.moderation.defs#recordHosting",
|
223
|
+
"status": "unknown",
|
224
|
+
},
|
217
225
|
"id": 4,
|
218
226
|
"lastReviewedAt": "1970-01-01T00:00:00.000Z",
|
219
227
|
"lastReviewedBy": "user(1)",
|
@@ -271,6 +279,10 @@ Object {
|
|
271
279
|
"moderation": Object {
|
272
280
|
"subjectStatus": Object {
|
273
281
|
"createdAt": "1970-01-01T00:00:00.000Z",
|
282
|
+
"hosting": Object {
|
283
|
+
"$type": "tools.ozone.moderation.defs#accountHosting",
|
284
|
+
"status": "unknown",
|
285
|
+
},
|
274
286
|
"id": 1,
|
275
287
|
"lastReportedAt": "1970-01-01T00:00:00.000Z",
|
276
288
|
"lastReviewedAt": "1970-01-01T00:00:00.000Z",
|
@@ -101,12 +101,22 @@ describe('proxy read after write', () => {
|
|
101
101
|
{ uri: sc.posts[alice][0].ref.uriStr },
|
102
102
|
{ headers: { ...sc.getHeaders(alice) } },
|
103
103
|
)
|
104
|
-
const
|
104
|
+
const thread = res.data.thread as ThreadViewPost
|
105
|
+
const layerOne = thread.replies as ThreadViewPost[]
|
105
106
|
expect(layerOne.length).toBe(1)
|
106
107
|
expect(layerOne[0].post.uri).toEqual(reply1.ref.uriStr)
|
107
108
|
const layerTwo = layerOne[0].replies as ThreadViewPost[]
|
108
109
|
expect(layerTwo.length).toBe(1)
|
109
110
|
expect(layerTwo[0].post.uri).toEqual(reply2.ref.uriStr)
|
111
|
+
|
112
|
+
const aliceHandle = sc.accounts[alice].handle
|
113
|
+
const handleUriStr = thread.post.uri.replace(alice, aliceHandle)
|
114
|
+
expect(handleUriStr).not.toEqual(thread.post.uri)
|
115
|
+
const handleRes = await agent.api.app.bsky.feed.getPostThread(
|
116
|
+
{ uri: handleUriStr },
|
117
|
+
{ headers: { ...sc.getHeaders(alice) } },
|
118
|
+
)
|
119
|
+
expect(handleRes.data.thread).toEqual(res.data.thread)
|
110
120
|
})
|
111
121
|
|
112
122
|
it('handles read after write on a thread that is not found on appview', async () => {
|
@@ -123,6 +133,15 @@ describe('proxy read after write', () => {
|
|
123
133
|
expect((thread.replies?.at(0) as ThreadViewPost).post.uri).toEqual(
|
124
134
|
replyRef2.uriStr,
|
125
135
|
)
|
136
|
+
|
137
|
+
const aliceHandle = sc.accounts[alice].handle
|
138
|
+
const handleUriStr = thread.post.uri.replace(alice, aliceHandle)
|
139
|
+
expect(handleUriStr).not.toEqual(thread.post.uri)
|
140
|
+
const handleRes = await agent.api.app.bsky.feed.getPostThread(
|
141
|
+
{ uri: handleUriStr },
|
142
|
+
{ headers: { ...sc.getHeaders(alice) } },
|
143
|
+
)
|
144
|
+
expect(handleRes.data.thread).toEqual(res.data.thread)
|
126
145
|
})
|
127
146
|
|
128
147
|
it('handles read after write on threads with record embeds', async () => {
|