{
"id": "com.getorbyt.community.defs",
"defs": {
"rule": {
"type": "object",
"required": [
"text"
],
"properties": {
"text": {
"type": "string",
"maxLength": 500
}
},
"description": "One Community rule. An object rather than a bare string so a title, an ordinal or a createdAt can be added later without a schema break."
},
"view": {
"type": "object",
"required": [
"uri",
"cid",
"name",
"ownerDid",
"createdAt"
],
"properties": {
"cid": {
"type": "string",
"format": "cid"
},
"uri": {
"type": "string",
"format": "at-uri"
},
"name": {
"type": "string",
"maxLength": 63,
"minLength": 2
},
"rules": {
"type": "array",
"items": {
"ref": "#rule",
"type": "ref"
},
"maxLength": 20
},
"access": {
"type": "string",
"description": "How Community content is accessed. Public is the only enabled value; clients must fail closed for unknown values.",
"knownValues": [
"public"
]
},
"avatar": {
"type": "string",
"format": "uri",
"description": "The Community's artwork as an image. Animated where the source was, and the only artwork field a client without a video player should read."
},
"labels": {
"type": "array",
"items": {
"ref": "com.atproto.label.defs#label",
"type": "ref"
},
"description": "Labels applied to this Community. Clients moderate against these exactly as they do app.bsky.feed.defs#postView labels."
},
"viewer": {
"ref": "#viewerState",
"type": "ref"
},
"ownerDid": {
"type": "string",
"format": "did",
"description": "The account whose repository holds the Community declaration record. Clients hydrate it to a profile through their authenticated Bluesky AppView."
},
"createdAt": {
"type": "string",
"format": "datetime"
},
"postCount": {
"type": "integer",
"minimum": 0
},
"updatedAt": {
"type": "string",
"format": "datetime"
},
"postPolicy": {
"type": "string",
"description": "The raw value its owner wrote, not the value this service resolved. Absent means anyone, which is also how a server that predates this field behaves.",
"knownValues": [
"anyone",
"members",
"moderators"
]
},
"accentColor": {
"type": "string",
"maxLength": 32
},
"avatarVideo": {
"type": "string",
"format": "uri",
"description": "A looping, silent MP4 rendition of the same artwork, when the owner supplied one. Clients that can play video use it for a full-bleed header and fall back to `avatar`; clients that cannot ignore it. It never replaces `avatar`, which stays the still or animated image every surface that is not a video player renders."
},
"description": {
"type": "string",
"maxLength": 2000
},
"memberCount": {
"type": "integer",
"minimum": 0
},
"viewerActions": {
"type": "array",
"items": {
"type": "string",
"knownValues": [
"edit",
"unpublish",
"publish",
"transfer",
"delete",
"view-reports",
"view-audit-log"
]
},
"maxLength": 32,
"description": "Actions the authenticated viewer may perform, decided by the service. Clients render only recognized values and infer nothing from role."
},
"avatarFallback": {
"type": "string",
"format": "uri",
"description": "A still JPEG or WebP rendition of avatar for constrained or reduced-data connections. Full-capability clients continue to prefer avatar for animated image surfaces."
},
"declarationUri": {
"type": "string",
"format": "at-uri",
"description": "The live declaration record. Absent means it is the same as uri."
},
"publicationState": {
"type": "string",
"description": "Service-owned lifecycle state. Absent means published. Unknown values must be treated as unavailable.",
"knownValues": [
"published",
"unpublished",
"deleting",
"deleted"
]
}
},
"description": "A hydrated Community. Only the fields that identify the Community are required; counts and viewer state are optional so a cheaper view can omit them without a schema break."
},
"feedItem": {
"type": "object",
"required": [
"post"
],
"properties": {
"post": {
"type": "string",
"format": "at-uri",
"description": "The linked app.bsky.feed.post URI. Clients hydrate it through their authenticated Bluesky AppView."
},
"pinned": {
"type": "boolean",
"default": false
},
"status": {
"type": "string",
"description": "Community-level state; absent means visible. `removed` is a moderator removal scoped to this Community; the underlying app.bsky.feed.post remains live on the network. Only the author and Community moderators receive removed items.",
"knownValues": [
"visible",
"removed"
]
},
"removedAt": {
"type": "string",
"format": "datetime"
},
"removedBy": {
"type": "string",
"format": "did"
},
"playbackToken": {
"type": "string",
"description": "Server-issued, viewer-bound token proving this item was served to this viewer for this post. Clients pass it back to com.getorbyt.video.recordLoop after a completed playback."
},
"removedReason": {
"type": "string",
"maxLength": 1000,
"description": "Present only for the post author and Community moderators."
},
"removalActionId": {
"type": "string",
"maxLength": 128,
"description": "Stable identifier for this specific removal. Present to the author and moderators and used to bind one appeal to one removal."
}
}
},
"appealView": {
"type": "object",
"required": [
"id",
"community",
"post",
"removalActionId",
"authorDid",
"text",
"status",
"createdAt"
],
"properties": {
"id": {
"type": "string",
"maxLength": 128
},
"post": {
"type": "string",
"format": "at-uri"
},
"text": {
"type": "string",
"maxLength": 2000
},
"status": {
"type": "string",
"knownValues": [
"open",
"resolved"
]
},
"authorDid": {
"type": "string",
"format": "did"
},
"community": {
"type": "string",
"format": "at-uri"
},
"createdAt": {
"type": "string",
"format": "datetime"
},
"resolution": {
"type": "string",
"knownValues": [
"upheld",
"restored"
]
},
"resolvedAt": {
"type": "string",
"format": "datetime"
},
"resolvedByDid": {
"type": "string",
"format": "did"
},
"resolutionNote": {
"type": "string",
"maxLength": 2000
},
"removalActionId": {
"type": "string",
"maxLength": 128
}
}
},
"auditEvent": {
"type": "object",
"required": [
"id",
"community",
"kind",
"actorDid",
"createdAt"
],
"properties": {
"id": {
"type": "string",
"maxLength": 128
},
"kind": {
"type": "string",
"knownValues": [
"published",
"unpublished",
"deletion-begun",
"deletion-cancelled",
"deleted",
"transfer-invited",
"transfer-accepted",
"transfer-cancelled",
"transfer-completed",
"member-role-changed",
"member-muted",
"member-unmuted",
"member-banned",
"member-unbanned",
"post-removed",
"post-restored",
"post-pinned",
"post-unpinned",
"report-created",
"report-resolved",
"appeal-created",
"appeal-resolved"
]
},
"summary": {
"type": "string",
"maxLength": 2000
},
"actorDid": {
"type": "string",
"format": "did"
},
"community": {
"type": "string",
"format": "at-uri"
},
"createdAt": {
"type": "string",
"format": "datetime"
},
"subjectDid": {
"type": "string",
"format": "did"
},
"subjectUri": {
"type": "string",
"format": "at-uri"
}
}
},
"memberView": {
"type": "object",
"required": [
"did"
],
"properties": {
"did": {
"type": "string",
"format": "did"
},
"role": {
"type": "string",
"description": "Absent means member.",
"knownValues": [
"owner",
"moderator",
"member"
]
},
"status": {
"type": "string",
"description": "Absent means active.",
"knownValues": [
"active",
"muted",
"banned"
]
},
"joinedAt": {
"type": "string",
"format": "datetime"
},
"membershipUri": {
"type": "string",
"format": "at-uri"
},
"viewerActions": {
"type": "array",
"items": {
"type": "string",
"knownValues": [
"setRole",
"mute",
"unmute",
"ban",
"unban"
]
},
"maxLength": 16,
"description": "The manageMember actions this viewer may take on this member, decided by the service. A client renders only the values it recognises and offers nothing else, so a change to who may do what reaches installed clients without a release. Absent means the service predates this field, not that no action is permitted — a client should fall back to its own rules only then."
}
}
},
"reportView": {
"type": "object",
"required": [
"id",
"community",
"post",
"reporterDid",
"reason",
"status",
"createdAt"
],
"properties": {
"id": {
"type": "string",
"maxLength": 128
},
"post": {
"type": "string",
"format": "at-uri"
},
"reason": {
"type": "string",
"maxLength": 2000
},
"status": {
"type": "string",
"knownValues": [
"open",
"resolved"
]
},
"community": {
"type": "string",
"format": "at-uri"
},
"createdAt": {
"type": "string",
"format": "datetime"
},
"resolution": {
"type": "string",
"knownValues": [
"removed",
"dismissed"
]
},
"resolvedAt": {
"type": "string",
"format": "datetime"
},
"reporterDid": {
"type": "string",
"format": "did"
},
"resolvedByDid": {
"type": "string",
"format": "did"
},
"resolutionNote": {
"type": "string",
"maxLength": 2000
}
}
},
"viewerState": {
"type": "object",
"properties": {
"role": {
"type": "string",
"knownValues": [
"owner",
"moderator",
"member"
]
},
"canPost": {
"type": "boolean",
"default": false
},
"canManage": {
"type": "boolean",
"default": false
},
"canModerate": {
"type": "boolean",
"default": false
},
"membershipUri": {
"type": "string",
"format": "at-uri"
},
"canAssignRoles": {
"type": "boolean",
"default": false,
"description": "Whether this viewer may promote or demote another member. Separate from canManage, which is authority over the declaration record itself and belongs only to the repository that holds it. A service may grant administration to an account that does not hold the record."
},
"membershipStatus": {
"type": "string",
"description": "Absent means none.",
"knownValues": [
"none",
"active",
"muted",
"banned"
]
},
"canListRestrictedMembers": {
"type": "boolean",
"default": false,
"description": "Whether listMembers will answer this viewer for a status other than active. Stated rather than inferred from canModerate so the rule can change without a client release; a client that predates this field may fall back to canModerate."
}
},
"description": "The requesting account's relationship to a Community. Every field is optional; an absent field means the viewer holds no membership and no privilege."
},
"writeStatus": {
"type": "object",
"required": [
"uri",
"status"
],
"properties": {
"uri": {
"type": "string",
"format": "at-uri"
},
"error": {
"type": "string",
"maxLength": 1000,
"description": "Why the record was rejected. Present only for `rejected`."
},
"status": {
"type": "string",
"description": "`pending` means the record has not reached this service yet, which is the normal state for a few seconds after a write. `rejected` means it will never be indexed as written.",
"knownValues": [
"indexed",
"pending",
"rejected",
"deleted"
]
},
"indexedAt": {
"type": "string",
"format": "datetime"
}
},
"description": "The fate of one record the caller wrote to their own repository."
},
"transferView": {
"type": "object",
"required": [
"id",
"community",
"fromDid",
"toDid",
"status",
"expiresAt",
"createdAt"
],
"properties": {
"id": {
"type": "string",
"maxLength": 128
},
"toDid": {
"type": "string",
"format": "did"
},
"status": {
"type": "string",
"knownValues": [
"pending",
"accepted",
"completed",
"cancelled",
"expired"
]
},
"fromDid": {
"type": "string",
"format": "did"
},
"community": {
"type": "string",
"format": "at-uri"
},
"createdAt": {
"type": "string",
"format": "datetime"
},
"expiresAt": {
"type": "string",
"format": "datetime"
},
"updatedAt": {
"type": "string",
"format": "datetime"
},
"cancelledByDid": {
"type": "string",
"format": "did",
"description": "Who ended the invitation. Present only once status is cancelled, and the one thing that tells a withdrawal by the inviting account apart from a decline by the invited one."
},
"replacementDeclarationUri": {
"type": "string",
"format": "at-uri"
}
}
}
},
"$type": "com.atproto.lexicon.schema",
"lexicon": 1
}