// Auto-generated from lexicons. Do not edit. import type { LexDef, LexProcedure, LexQuery, LexRecord, LexServerParams, Checked, Prettify, StrictArg } from '@hatk/hatk/lex-types' import type { XrpcContext } from '@hatk/hatk/xrpc' import { callXrpc as _callXrpc } from '@hatk/hatk/xrpc' import { defineFeed as _defineFeed, type FeedResult, type FeedContext, type BaseContext, type Row } from '@hatk/hatk/feeds' import { seed as _seed, type SeedOpts } from '@hatk/hatk/seed' // ─── Lexicon Definitions ──────────────────────────────────────────── const bskyActorDefsLex = {"id":"app.bsky.actor.defs","defs":{"nux":{"type":"object","required":["id","completed"],"properties":{"id":{"type":"string","maxLength":100},"data":{"type":"string","maxLength":3000,"description":"Arbitrary data for the NUX. The structure is defined by the NUX itself. Limited to 300 characters.","maxGraphemes":300},"completed":{"type":"boolean","default":false},"expiresAt":{"type":"string","format":"datetime","description":"The date and time at which the NUX will expire and should be considered completed."}},"description":"A new user experiences (NUX) storage object"},"mutedWord":{"type":"object","required":["value","targets"],"properties":{"id":{"type":"string"},"value":{"type":"string","maxLength":10000,"description":"The muted word itself.","maxGraphemes":1000},"targets":{"type":"array","items":{"ref":"app.bsky.actor.defs#mutedWordTarget","type":"ref"},"description":"The intended targets of the muted word."},"expiresAt":{"type":"string","format":"datetime","description":"The date and time at which the muted word will expire and no longer be applied."},"actorTarget":{"type":"string","default":"all","description":"Groups of users to apply the muted word to. If undefined, applies to all users.","knownValues":["all","exclude-following"]}},"description":"A word that the account owner has muted."},"savedFeed":{"type":"object","required":["id","type","value","pinned"],"properties":{"id":{"type":"string"},"type":{"type":"string","knownValues":["feed","list","timeline"]},"value":{"type":"string"},"pinned":{"type":"boolean"}}},"statusView":{"type":"object","required":["status","record"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"embed":{"refs":["app.bsky.embed.external#view"],"type":"union","description":"An optional embed associated with the status."},"record":{"type":"unknown"},"status":{"type":"string","description":"The status for the account.","knownValues":["app.bsky.actor.status#live"]},"isActive":{"type":"boolean","description":"True if the status is not expired, false if it is expired. Only present if expiration was set."},"expiresAt":{"type":"string","format":"datetime","description":"The date when this status will expire. The application might choose to no longer return the status after expiration."},"isDisabled":{"type":"boolean","description":"True if the user's go-live access has been disabled by a moderator, false otherwise."}}},"preferences":{"type":"array","items":{"refs":["#adultContentPref","#contentLabelPref","#savedFeedsPref","#savedFeedsPrefV2","#personalDetailsPref","#declaredAgePref","#feedViewPref","#threadViewPref","#interestsPref","#mutedWordsPref","#hiddenPostsPref","#bskyAppStatePref","#labelersPref","#postInteractionSettingsPref","#verificationPrefs","#liveEventPreferences"],"type":"union"}},"profileView":{"type":"object","required":["did","handle"],"properties":{"did":{"type":"string","format":"did"},"debug":{"type":"unknown","description":"Debug information for internal development"},"avatar":{"type":"string","format":"uri"},"handle":{"type":"string","format":"handle"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"status":{"ref":"#statusView","type":"ref"},"viewer":{"ref":"#viewerState","type":"ref"},"pronouns":{"type":"string"},"createdAt":{"type":"string","format":"datetime"},"indexedAt":{"type":"string","format":"datetime"},"associated":{"ref":"#profileAssociated","type":"ref"},"description":{"type":"string","maxLength":2560,"maxGraphemes":256},"displayName":{"type":"string","maxLength":640,"maxGraphemes":64},"verification":{"ref":"#verificationState","type":"ref"}}},"viewerState":{"type":"object","properties":{"muted":{"type":"boolean"},"blocking":{"type":"string","format":"at-uri"},"blockedBy":{"type":"boolean"},"following":{"type":"string","format":"at-uri"},"followedBy":{"type":"string","format":"at-uri"},"mutedByList":{"ref":"app.bsky.graph.defs#listViewBasic","type":"ref"},"blockingByList":{"ref":"app.bsky.graph.defs#listViewBasic","type":"ref"},"knownFollowers":{"ref":"#knownFollowers","type":"ref","description":"This property is present only in selected cases, as an optimization."},"activitySubscription":{"ref":"app.bsky.notification.defs#activitySubscription","type":"ref","description":"This property is present only in selected cases, as an optimization."}},"description":"Metadata about the requesting account's relationship with the subject account. Only has meaningful content for authed requests."},"feedViewPref":{"type":"object","required":["feed"],"properties":{"feed":{"type":"string","description":"The URI of the feed, or an identifier which describes the feed."},"hideReplies":{"type":"boolean","description":"Hide replies in the feed."},"hideReposts":{"type":"boolean","description":"Hide reposts in the feed."},"hideQuotePosts":{"type":"boolean","description":"Hide quote posts in the feed."},"hideRepliesByLikeCount":{"type":"integer","description":"Hide replies in the feed if they do not have this number of likes."},"hideRepliesByUnfollowed":{"type":"boolean","default":true,"description":"Hide replies in the feed if they are not by followed users."}}},"labelersPref":{"type":"object","required":["labelers"],"properties":{"labelers":{"type":"array","items":{"ref":"#labelerPrefItem","type":"ref"}}}},"interestsPref":{"type":"object","required":["tags"],"properties":{"tags":{"type":"array","items":{"type":"string","maxLength":640,"maxGraphemes":64},"maxLength":100,"description":"A list of tags which describe the account owner's interests gathered during onboarding."}}},"knownFollowers":{"type":"object","required":["count","followers"],"properties":{"count":{"type":"integer"},"followers":{"type":"array","items":{"ref":"#profileViewBasic","type":"ref"},"maxLength":5,"minLength":0}},"description":"The subject's followers whom you also follow"},"mutedWordsPref":{"type":"object","required":["items"],"properties":{"items":{"type":"array","items":{"ref":"app.bsky.actor.defs#mutedWord","type":"ref"},"description":"A list of words the account owner has muted."}}},"savedFeedsPref":{"type":"object","required":["pinned","saved"],"properties":{"saved":{"type":"array","items":{"type":"string","format":"at-uri"}},"pinned":{"type":"array","items":{"type":"string","format":"at-uri"}},"timelineIndex":{"type":"integer"}}},"threadViewPref":{"type":"object","properties":{"sort":{"type":"string","description":"Sorting mode for threads.","knownValues":["oldest","newest","most-likes","random","hotness"]}}},"declaredAgePref":{"type":"object","properties":{"isOverAge13":{"type":"boolean","description":"Indicates if the user has declared that they are over 13 years of age."},"isOverAge16":{"type":"boolean","description":"Indicates if the user has declared that they are over 16 years of age."},"isOverAge18":{"type":"boolean","description":"Indicates if the user has declared that they are over 18 years of age."}},"description":"Read-only preference containing value(s) inferred from the user's declared birthdate. Absence of this preference object in the response indicates that the user has not made a declaration."},"hiddenPostsPref":{"type":"object","required":["items"],"properties":{"items":{"type":"array","items":{"type":"string","format":"at-uri"},"description":"A list of URIs of posts the account owner has hidden."}}},"labelerPrefItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"}}},"mutedWordTarget":{"type":"string","maxLength":640,"knownValues":["content","tag"],"maxGraphemes":64},"adultContentPref":{"type":"object","required":["enabled"],"properties":{"enabled":{"type":"boolean","default":false}}},"bskyAppStatePref":{"type":"object","properties":{"nuxs":{"type":"array","items":{"ref":"app.bsky.actor.defs#nux","type":"ref"},"maxLength":100,"description":"Storage for NUXs the user has encountered."},"queuedNudges":{"type":"array","items":{"type":"string","maxLength":100},"maxLength":1000,"description":"An array of tokens which identify nudges (modals, popups, tours, highlight dots) that should be shown to the user."},"activeProgressGuide":{"ref":"#bskyAppProgressGuide","type":"ref"}},"description":"A grab bag of state that's specific to the bsky.app program. Third-party apps shouldn't use this."},"contentLabelPref":{"type":"object","required":["label","visibility"],"properties":{"label":{"type":"string"},"labelerDid":{"type":"string","format":"did","description":"Which labeler does this preference apply to? If undefined, applies globally."},"visibility":{"type":"string","knownValues":["ignore","show","warn","hide"]}}},"profileViewBasic":{"type":"object","required":["did","handle"],"properties":{"did":{"type":"string","format":"did"},"debug":{"type":"unknown","description":"Debug information for internal development"},"avatar":{"type":"string","format":"uri"},"handle":{"type":"string","format":"handle"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"status":{"ref":"#statusView","type":"ref"},"viewer":{"ref":"#viewerState","type":"ref"},"pronouns":{"type":"string"},"createdAt":{"type":"string","format":"datetime"},"associated":{"ref":"#profileAssociated","type":"ref"},"displayName":{"type":"string","maxLength":640,"maxGraphemes":64},"verification":{"ref":"#verificationState","type":"ref"}}},"savedFeedsPrefV2":{"type":"object","required":["items"],"properties":{"items":{"type":"array","items":{"ref":"app.bsky.actor.defs#savedFeed","type":"ref"}}}},"verificationView":{"type":"object","required":["issuer","uri","isValid","createdAt"],"properties":{"uri":{"type":"string","format":"at-uri","description":"The AT-URI of the verification record."},"issuer":{"type":"string","format":"did","description":"The user who issued this verification."},"isValid":{"type":"boolean","description":"True if the verification passes validation, otherwise false."},"createdAt":{"type":"string","format":"datetime","description":"Timestamp when the verification was created."}},"description":"An individual verification for an associated subject."},"profileAssociated":{"type":"object","properties":{"chat":{"ref":"#profileAssociatedChat","type":"ref"},"germ":{"ref":"#profileAssociatedGerm","type":"ref"},"lists":{"type":"integer"},"labeler":{"type":"boolean"},"feedgens":{"type":"integer"},"starterPacks":{"type":"integer"},"activitySubscription":{"ref":"#profileAssociatedActivitySubscription","type":"ref"}}},"verificationPrefs":{"type":"object","required":[],"properties":{"hideBadges":{"type":"boolean","default":false,"description":"Hide the blue check badges for verified accounts and trusted verifiers."}},"description":"Preferences for how verified accounts appear in the app."},"verificationState":{"type":"object","required":["verifications","verifiedStatus","trustedVerifierStatus"],"properties":{"verifications":{"type":"array","items":{"ref":"#verificationView","type":"ref"},"description":"All verifications issued by trusted verifiers on behalf of this user. Verifications by untrusted verifiers are not included."},"verifiedStatus":{"type":"string","description":"The user's status as a verified account.","knownValues":["valid","invalid","none"]},"trustedVerifierStatus":{"type":"string","description":"The user's status as a trusted verifier.","knownValues":["valid","invalid","none"]}},"description":"Represents the verification information about the user this object is attached to."},"personalDetailsPref":{"type":"object","properties":{"birthDate":{"type":"string","format":"datetime","description":"The birth date of account owner."}}},"profileViewDetailed":{"type":"object","required":["did","handle"],"properties":{"did":{"type":"string","format":"did"},"debug":{"type":"unknown","description":"Debug information for internal development"},"avatar":{"type":"string","format":"uri"},"banner":{"type":"string","format":"uri"},"handle":{"type":"string","format":"handle"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"status":{"ref":"#statusView","type":"ref"},"viewer":{"ref":"#viewerState","type":"ref"},"website":{"type":"string","format":"uri"},"pronouns":{"type":"string"},"createdAt":{"type":"string","format":"datetime"},"indexedAt":{"type":"string","format":"datetime"},"associated":{"ref":"#profileAssociated","type":"ref"},"pinnedPost":{"ref":"com.atproto.repo.strongRef","type":"ref"},"postsCount":{"type":"integer"},"description":{"type":"string","maxLength":2560,"maxGraphemes":256},"displayName":{"type":"string","maxLength":640,"maxGraphemes":64},"followsCount":{"type":"integer"},"verification":{"ref":"#verificationState","type":"ref"},"followersCount":{"type":"integer"},"joinedViaStarterPack":{"ref":"app.bsky.graph.defs#starterPackViewBasic","type":"ref"}}},"bskyAppProgressGuide":{"type":"object","required":["guide"],"properties":{"guide":{"type":"string","maxLength":100}},"description":"If set, an active progress guide. Once completed, can be set to undefined. Should have unspecced fields tracking progress."},"liveEventPreferences":{"type":"object","properties":{"hideAllFeeds":{"type":"boolean","default":false,"description":"Whether to hide all feeds from live events."},"hiddenFeedIds":{"type":"array","items":{"type":"string"},"description":"A list of feed IDs that the user has hidden from live events."}},"description":"Preferences for live events."},"profileAssociatedChat":{"type":"object","required":["allowIncoming"],"properties":{"allowIncoming":{"type":"string","knownValues":["all","none","following"]}}},"profileAssociatedGerm":{"type":"object","required":["showButtonTo","messageMeUrl"],"properties":{"messageMeUrl":{"type":"string","format":"uri"},"showButtonTo":{"type":"string","knownValues":["usersIFollow","everyone"]}}},"postInteractionSettingsPref":{"type":"object","required":[],"properties":{"threadgateAllowRules":{"type":"array","items":{"refs":["app.bsky.feed.threadgate#mentionRule","app.bsky.feed.threadgate#followerRule","app.bsky.feed.threadgate#followingRule","app.bsky.feed.threadgate#listRule"],"type":"union"},"maxLength":5,"description":"Matches threadgate record. List of rules defining who can reply to this users posts. If value is an empty array, no one can reply. If value is undefined, anyone can reply."},"postgateEmbeddingRules":{"type":"array","items":{"refs":["app.bsky.feed.postgate#disableRule"],"type":"union"},"maxLength":5,"description":"Matches postgate record. List of rules defining who can embed this users posts. If value is an empty array or is undefined, no particular rules apply and anyone can embed."}},"description":"Default post interaction settings for the account. These values should be applied as default values when creating new posts. These refs should mirror the threadgate and postgate records exactly."},"profileAssociatedActivitySubscription":{"type":"object","required":["allowSubscriptions"],"properties":{"allowSubscriptions":{"type":"string","knownValues":["followers","mutuals","none"]}}}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const bskyActorProfileLex = {"lexicon":1,"id":"app.bsky.actor.profile","defs":{"main":{"type":"record","key":"literal:self","description":"A user profile record","record":{"type":"object","properties":{"displayName":{"type":"string","maxGraphemes":64,"maxLength":640},"description":{"type":"string","maxGraphemes":256,"maxLength":2560},"avatar":{"type":"blob","accept":["image/png","image/jpeg"],"maxSize":1000000},"banner":{"type":"blob","accept":["image/png","image/jpeg"],"maxSize":1000000},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const bskyEmbedDefsLex = {"id":"app.bsky.embed.defs","defs":{"aspectRatio":{"type":"object","required":["width","height"],"properties":{"width":{"type":"integer","minimum":1},"height":{"type":"integer","minimum":1}},"description":"width:height represents an aspect ratio. It may be approximate, and may not correspond to absolute dimensions in any given unit."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const externalLex = {"id":"app.bsky.embed.external","defs":{"main":{"type":"object","required":["external"],"properties":{"external":{"ref":"#external","type":"ref"}},"description":"A representation of some externally linked content (eg, a URL and 'card'), embedded in a Bluesky record (eg, a post)."},"view":{"type":"object","required":["external"],"properties":{"external":{"ref":"#viewExternal","type":"ref"}}},"external":{"type":"object","required":["uri","title","description"],"properties":{"uri":{"type":"string","format":"uri"},"thumb":{"type":"blob","accept":["image/*"],"maxSize":1000000},"title":{"type":"string"},"description":{"type":"string"}}},"viewExternal":{"type":"object","required":["uri","title","description"],"properties":{"uri":{"type":"string","format":"uri"},"thumb":{"type":"string","format":"uri"},"title":{"type":"string"},"description":{"type":"string"}}}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const imagesLex = {"id":"app.bsky.embed.images","defs":{"main":{"type":"object","required":["images"],"properties":{"images":{"type":"array","items":{"ref":"#image","type":"ref"},"maxLength":4}}},"view":{"type":"object","required":["images"],"properties":{"images":{"type":"array","items":{"ref":"#viewImage","type":"ref"},"maxLength":4}}},"image":{"type":"object","required":["image","alt"],"properties":{"alt":{"type":"string","description":"Alt text description of the image, for accessibility."},"image":{"type":"blob","accept":["image/*"],"maxSize":1000000},"aspectRatio":{"ref":"app.bsky.embed.defs#aspectRatio","type":"ref"}}},"viewImage":{"type":"object","required":["thumb","fullsize","alt"],"properties":{"alt":{"type":"string","description":"Alt text description of the image, for accessibility."},"thumb":{"type":"string","format":"uri","description":"Fully-qualified URL where a thumbnail of the image can be fetched. For example, CDN location provided by the App View."},"fullsize":{"type":"string","format":"uri","description":"Fully-qualified URL where a large version of the image can be fetched. May or may not be the exact original blob. For example, CDN location provided by the App View."},"aspectRatio":{"ref":"app.bsky.embed.defs#aspectRatio","type":"ref"}}}},"$type":"com.atproto.lexicon.schema","lexicon":1,"description":"A set of images embedded in a Bluesky record (eg, a post)."} as const const recordLex = {"id":"app.bsky.embed.record","defs":{"main":{"type":"object","required":["record"],"properties":{"record":{"ref":"com.atproto.repo.strongRef","type":"ref"}}},"view":{"type":"object","required":["record"],"properties":{"record":{"refs":["#viewRecord","#viewNotFound","#viewBlocked","#viewDetached","app.bsky.feed.defs#generatorView","app.bsky.graph.defs#listView","app.bsky.labeler.defs#labelerView","app.bsky.graph.defs#starterPackViewBasic"],"type":"union"}}},"viewRecord":{"type":"object","required":["uri","cid","author","value","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"value":{"type":"unknown","description":"The record data itself."},"author":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref"},"embeds":{"type":"array","items":{"refs":["app.bsky.embed.images#view","app.bsky.embed.video#view","app.bsky.embed.external#view","app.bsky.embed.record#view","app.bsky.embed.recordWithMedia#view"],"type":"union"}},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"indexedAt":{"type":"string","format":"datetime"},"likeCount":{"type":"integer"},"quoteCount":{"type":"integer"},"replyCount":{"type":"integer"},"repostCount":{"type":"integer"}}},"viewBlocked":{"type":"object","required":["uri","blocked","author"],"properties":{"uri":{"type":"string","format":"at-uri"},"author":{"ref":"app.bsky.feed.defs#blockedAuthor","type":"ref"},"blocked":{"type":"boolean","const":true}}},"viewDetached":{"type":"object","required":["uri","detached"],"properties":{"uri":{"type":"string","format":"at-uri"},"detached":{"type":"boolean","const":true}}},"viewNotFound":{"type":"object","required":["uri","notFound"],"properties":{"uri":{"type":"string","format":"at-uri"},"notFound":{"type":"boolean","const":true}}}},"$type":"com.atproto.lexicon.schema","lexicon":1,"description":"A representation of a record embedded in a Bluesky record (eg, a post). For example, a quote-post, or sharing a feed generator record."} as const const recordWithMediaLex = {"id":"app.bsky.embed.recordWithMedia","defs":{"main":{"type":"object","required":["record","media"],"properties":{"media":{"refs":["app.bsky.embed.images","app.bsky.embed.video","app.bsky.embed.external"],"type":"union"},"record":{"ref":"app.bsky.embed.record","type":"ref"}}},"view":{"type":"object","required":["record","media"],"properties":{"media":{"refs":["app.bsky.embed.images#view","app.bsky.embed.video#view","app.bsky.embed.external#view"],"type":"union"},"record":{"ref":"app.bsky.embed.record#view","type":"ref"}}}},"$type":"com.atproto.lexicon.schema","lexicon":1,"description":"A representation of a record embedded in a Bluesky record (eg, a post), alongside other compatible embeds. For example, a quote post and image, or a quote post and external URL card."} as const const videoLex = {"id":"app.bsky.embed.video","defs":{"main":{"type":"object","required":["video"],"properties":{"alt":{"type":"string","maxLength":10000,"description":"Alt text description of the video, for accessibility.","maxGraphemes":1000},"video":{"type":"blob","accept":["video/mp4"],"maxSize":100000000,"description":"The mp4 video file. May be up to 100mb, formerly limited to 50mb."},"captions":{"type":"array","items":{"ref":"#caption","type":"ref"},"maxLength":20},"aspectRatio":{"ref":"app.bsky.embed.defs#aspectRatio","type":"ref"},"presentation":{"type":"string","description":"A hint to the client about how to present the video.","knownValues":["default","gif"]}}},"view":{"type":"object","required":["cid","playlist"],"properties":{"alt":{"type":"string","maxLength":10000,"maxGraphemes":1000},"cid":{"type":"string","format":"cid"},"playlist":{"type":"string","format":"uri"},"thumbnail":{"type":"string","format":"uri"},"aspectRatio":{"ref":"app.bsky.embed.defs#aspectRatio","type":"ref"},"presentation":{"type":"string","description":"A hint to the client about how to present the video.","knownValues":["default","gif"]}}},"caption":{"type":"object","required":["lang","file"],"properties":{"file":{"type":"blob","accept":["text/vtt"],"maxSize":20000},"lang":{"type":"string","format":"language"}}}},"$type":"com.atproto.lexicon.schema","lexicon":1,"description":"A video embedded in a Bluesky record (eg, a post)."} as const const bskyFeedDefsLex = {"id":"app.bsky.feed.defs","defs":{"postView":{"type":"object","required":["uri","cid","author","record","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"debug":{"type":"unknown","description":"Debug information for internal development"},"embed":{"refs":["app.bsky.embed.images#view","app.bsky.embed.video#view","app.bsky.embed.external#view","app.bsky.embed.record#view","app.bsky.embed.recordWithMedia#view"],"type":"union"},"author":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"record":{"type":"unknown"},"viewer":{"ref":"#viewerState","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"likeCount":{"type":"integer"},"quoteCount":{"type":"integer"},"replyCount":{"type":"integer"},"threadgate":{"ref":"#threadgateView","type":"ref"},"repostCount":{"type":"integer"},"bookmarkCount":{"type":"integer"}}},"replyRef":{"type":"object","required":["root","parent"],"properties":{"root":{"refs":["#postView","#notFoundPost","#blockedPost"],"type":"union"},"parent":{"refs":["#postView","#notFoundPost","#blockedPost"],"type":"union"},"grandparentAuthor":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref","description":"When parent is a reply to another post, this is the author of that post."}}},"reasonPin":{"type":"object","properties":{}},"blockedPost":{"type":"object","required":["uri","blocked","author"],"properties":{"uri":{"type":"string","format":"at-uri"},"author":{"ref":"#blockedAuthor","type":"ref"},"blocked":{"type":"boolean","const":true}}},"interaction":{"type":"object","properties":{"item":{"type":"string","format":"at-uri"},"event":{"type":"string","knownValues":["app.bsky.feed.defs#requestLess","app.bsky.feed.defs#requestMore","app.bsky.feed.defs#clickthroughItem","app.bsky.feed.defs#clickthroughAuthor","app.bsky.feed.defs#clickthroughReposter","app.bsky.feed.defs#clickthroughEmbed","app.bsky.feed.defs#interactionSeen","app.bsky.feed.defs#interactionLike","app.bsky.feed.defs#interactionRepost","app.bsky.feed.defs#interactionReply","app.bsky.feed.defs#interactionQuote","app.bsky.feed.defs#interactionShare"]},"reqId":{"type":"string","maxLength":100,"description":"Unique identifier per request that may be passed back alongside interactions."},"feedContext":{"type":"string","maxLength":2000,"description":"Context on a feed item that was originally supplied by the feed generator on getFeedSkeleton."}}},"requestLess":{"type":"token","description":"Request that less content like the given feed item be shown in the feed"},"requestMore":{"type":"token","description":"Request that more content like the given feed item be shown in the feed"},"viewerState":{"type":"object","properties":{"like":{"type":"string","format":"at-uri"},"pinned":{"type":"boolean"},"repost":{"type":"string","format":"at-uri"},"bookmarked":{"type":"boolean"},"threadMuted":{"type":"boolean"},"replyDisabled":{"type":"boolean"},"embeddingDisabled":{"type":"boolean"}},"description":"Metadata about the requesting account's relationship with the subject content. Only has meaningful content for authed requests."},"feedViewPost":{"type":"object","required":["post"],"properties":{"post":{"ref":"#postView","type":"ref"},"reply":{"ref":"#replyRef","type":"ref"},"reqId":{"type":"string","maxLength":100,"description":"Unique identifier per request that may be passed back alongside interactions."},"reason":{"refs":["#reasonRepost","#reasonPin"],"type":"union"},"feedContext":{"type":"string","maxLength":2000,"description":"Context provided by feed generator that may be passed back alongside interactions."}}},"notFoundPost":{"type":"object","required":["uri","notFound"],"properties":{"uri":{"type":"string","format":"at-uri"},"notFound":{"type":"boolean","const":true}}},"reasonRepost":{"type":"object","required":["by","indexedAt"],"properties":{"by":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref"},"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"indexedAt":{"type":"string","format":"datetime"}}},"blockedAuthor":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"viewer":{"ref":"app.bsky.actor.defs#viewerState","type":"ref"}}},"generatorView":{"type":"object","required":["uri","cid","did","creator","displayName","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"did":{"type":"string","format":"did"},"uri":{"type":"string","format":"at-uri"},"avatar":{"type":"string","format":"uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"viewer":{"ref":"#generatorViewerState","type":"ref"},"creator":{"ref":"app.bsky.actor.defs#profileView","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"likeCount":{"type":"integer","minimum":0},"contentMode":{"type":"string","knownValues":["app.bsky.feed.defs#contentModeUnspecified","app.bsky.feed.defs#contentModeVideo"]},"description":{"type":"string","maxLength":3000,"maxGraphemes":300},"displayName":{"type":"string"},"descriptionFacets":{"type":"array","items":{"ref":"app.bsky.richtext.facet","type":"ref"}},"acceptsInteractions":{"type":"boolean"}}},"threadContext":{"type":"object","properties":{"rootAuthorLike":{"type":"string","format":"at-uri"}},"description":"Metadata about this post within the context of the thread it is in."},"threadViewPost":{"type":"object","required":["post"],"properties":{"post":{"ref":"#postView","type":"ref"},"parent":{"refs":["#threadViewPost","#notFoundPost","#blockedPost"],"type":"union"},"replies":{"type":"array","items":{"refs":["#threadViewPost","#notFoundPost","#blockedPost"],"type":"union"}},"threadContext":{"ref":"#threadContext","type":"ref"}}},"threadgateView":{"type":"object","properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"lists":{"type":"array","items":{"ref":"app.bsky.graph.defs#listViewBasic","type":"ref"}},"record":{"type":"unknown"}}},"interactionLike":{"type":"token","description":"User liked the feed item"},"interactionSeen":{"type":"token","description":"Feed item was seen by user"},"clickthroughItem":{"type":"token","description":"User clicked through to the feed item"},"contentModeVideo":{"type":"token","description":"Declares the feed generator returns posts containing app.bsky.embed.video embeds."},"interactionQuote":{"type":"token","description":"User quoted the feed item"},"interactionReply":{"type":"token","description":"User replied to the feed item"},"interactionShare":{"type":"token","description":"User shared the feed item"},"skeletonFeedPost":{"type":"object","required":["post"],"properties":{"post":{"type":"string","format":"at-uri"},"reason":{"refs":["#skeletonReasonRepost","#skeletonReasonPin"],"type":"union"},"feedContext":{"type":"string","maxLength":2000,"description":"Context that will be passed through to client and may be passed to feed generator back alongside interactions."}}},"clickthroughEmbed":{"type":"token","description":"User clicked through to the embedded content of the feed item"},"interactionRepost":{"type":"token","description":"User reposted the feed item"},"skeletonReasonPin":{"type":"object","properties":{}},"clickthroughAuthor":{"type":"token","description":"User clicked through to the author of the feed item"},"clickthroughReposter":{"type":"token","description":"User clicked through to the reposter of the feed item"},"generatorViewerState":{"type":"object","properties":{"like":{"type":"string","format":"at-uri"}}},"skeletonReasonRepost":{"type":"object","required":["repost"],"properties":{"repost":{"type":"string","format":"at-uri"}}},"contentModeUnspecified":{"type":"token","description":"Declares the feed generator returns any types of posts."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const postLex = {"id":"app.bsky.feed.post","defs":{"main":{"key":"tid","type":"record","record":{"type":"object","required":["text","createdAt"],"properties":{"tags":{"type":"array","items":{"type":"string","maxLength":640,"maxGraphemes":64},"maxLength":8,"description":"Additional hashtags, in addition to any included in post text and facets."},"text":{"type":"string","maxLength":3000,"description":"The primary post content. May be an empty string, if there are embeds.","maxGraphemes":300},"embed":{"refs":["app.bsky.embed.images","app.bsky.embed.video","app.bsky.embed.external","app.bsky.embed.record","app.bsky.embed.recordWithMedia"],"type":"union"},"langs":{"type":"array","items":{"type":"string","format":"language"},"maxLength":3,"description":"Indicates human language of post primary text content."},"reply":{"ref":"#replyRef","type":"ref"},"facets":{"type":"array","items":{"ref":"app.bsky.richtext.facet","type":"ref"},"description":"Annotations of text (mentions, URLs, hashtags, etc)"},"labels":{"refs":["com.atproto.label.defs#selfLabels"],"type":"union","description":"Self-label values for this post. Effectively content warnings."},"entities":{"type":"array","items":{"ref":"#entity","type":"ref"},"description":"DEPRECATED: replaced by app.bsky.richtext.facet."},"createdAt":{"type":"string","format":"datetime","description":"Client-declared timestamp when this post was originally created."}}},"description":"Record containing a Bluesky post."},"entity":{"type":"object","required":["index","type","value"],"properties":{"type":{"type":"string","description":"Expected values are 'mention' and 'link'."},"index":{"ref":"#textSlice","type":"ref"},"value":{"type":"string"}},"description":"Deprecated: use facets instead."},"replyRef":{"type":"object","required":["root","parent"],"properties":{"root":{"ref":"com.atproto.repo.strongRef","type":"ref"},"parent":{"ref":"com.atproto.repo.strongRef","type":"ref"}}},"textSlice":{"type":"object","required":["start","end"],"properties":{"end":{"type":"integer","minimum":0},"start":{"type":"integer","minimum":0}},"description":"Deprecated. Use app.bsky.richtext instead -- A text segment. Start is inclusive, end is exclusive. Indices are for utf16-encoded strings."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const postgateLex = {"id":"app.bsky.feed.postgate","defs":{"main":{"key":"tid","type":"record","record":{"type":"object","required":["post","createdAt"],"properties":{"post":{"type":"string","format":"at-uri","description":"Reference (AT-URI) to the post record."},"createdAt":{"type":"string","format":"datetime"},"embeddingRules":{"type":"array","items":{"refs":["#disableRule"],"type":"union"},"maxLength":5,"description":"List of rules defining who can embed this post. If value is an empty array or is undefined, no particular rules apply and anyone can embed."},"detachedEmbeddingUris":{"type":"array","items":{"type":"string","format":"at-uri"},"maxLength":50,"description":"List of AT-URIs embedding this post that the author has detached from."}}},"description":"Record defining interaction rules for a post. The record key (rkey) of the postgate record must match the record key of the post, and that record must be in the same repository."},"disableRule":{"type":"object","properties":{},"description":"Disables embedding of this post."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const threadgateLex = {"id":"app.bsky.feed.threadgate","defs":{"main":{"key":"tid","type":"record","record":{"type":"object","required":["post","createdAt"],"properties":{"post":{"type":"string","format":"at-uri","description":"Reference (AT-URI) to the post record."},"allow":{"type":"array","items":{"refs":["#mentionRule","#followerRule","#followingRule","#listRule"],"type":"union"},"maxLength":5,"description":"List of rules defining who can reply to this post. If value is an empty array, no one can reply. If value is undefined, anyone can reply."},"createdAt":{"type":"string","format":"datetime"},"hiddenReplies":{"type":"array","items":{"type":"string","format":"at-uri"},"maxLength":300,"description":"List of hidden reply URIs."}}},"description":"Record defining interaction gating rules for a thread (aka, reply controls). The record key (rkey) of the threadgate record must match the record key of the thread's root post, and that record must be in the same repository."},"listRule":{"type":"object","required":["list"],"properties":{"list":{"type":"string","format":"at-uri"}},"description":"Allow replies from actors on a list."},"mentionRule":{"type":"object","properties":{},"description":"Allow replies from actors mentioned in your post."},"followerRule":{"type":"object","properties":{},"description":"Allow replies from actors who follow you."},"followingRule":{"type":"object","properties":{},"description":"Allow replies from actors you follow."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const bskyGraphDefsLex = {"id":"app.bsky.graph.defs","defs":{"modlist":{"type":"token","description":"A list of actors to apply an aggregate moderation action (mute/block) on."},"listView":{"type":"object","required":["uri","cid","creator","name","purpose","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"name":{"type":"string","maxLength":64,"minLength":1},"avatar":{"type":"string","format":"uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"viewer":{"ref":"#listViewerState","type":"ref"},"creator":{"ref":"app.bsky.actor.defs#profileView","type":"ref"},"purpose":{"ref":"#listPurpose","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"description":{"type":"string","maxLength":3000,"maxGraphemes":300},"listItemCount":{"type":"integer","minimum":0},"descriptionFacets":{"type":"array","items":{"ref":"app.bsky.richtext.facet","type":"ref"}}}},"curatelist":{"type":"token","description":"A list of actors used for curation purposes such as list feeds or interaction gating."},"listPurpose":{"type":"string","knownValues":["app.bsky.graph.defs#modlist","app.bsky.graph.defs#curatelist","app.bsky.graph.defs#referencelist"]},"listItemView":{"type":"object","required":["uri","subject"],"properties":{"uri":{"type":"string","format":"at-uri"},"subject":{"ref":"app.bsky.actor.defs#profileView","type":"ref"}}},"relationship":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"blocking":{"type":"string","format":"at-uri","description":"if the actor blocks this DID, this is the AT-URI of the block record"},"blockedBy":{"type":"string","format":"at-uri","description":"if the actor is blocked by this DID, contains the AT-URI of the block record"},"following":{"type":"string","format":"at-uri","description":"if the actor follows this DID, this is the AT-URI of the follow record"},"followedBy":{"type":"string","format":"at-uri","description":"if the actor is followed by this DID, contains the AT-URI of the follow record"},"blockedByList":{"type":"string","format":"at-uri","description":"if the actor is blocked by this DID via a block list, contains the AT-URI of the listblock record"},"blockingByList":{"type":"string","format":"at-uri","description":"if the actor blocks this DID via a block list, this is the AT-URI of the listblock record"}},"description":"lists the bi-directional graph relationships between one actor (not indicated in the object), and the target actors (the DID included in the object)"},"listViewBasic":{"type":"object","required":["uri","cid","name","purpose"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"name":{"type":"string","maxLength":64,"minLength":1},"avatar":{"type":"string","format":"uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"viewer":{"ref":"#listViewerState","type":"ref"},"purpose":{"ref":"#listPurpose","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"listItemCount":{"type":"integer","minimum":0}}},"notFoundActor":{"type":"object","required":["actor","notFound"],"properties":{"actor":{"type":"string","format":"at-identifier"},"notFound":{"type":"boolean","const":true}},"description":"indicates that a handle or DID could not be resolved"},"referencelist":{"type":"token","description":"A list of actors used for only for reference purposes such as within a starter pack."},"listViewerState":{"type":"object","properties":{"muted":{"type":"boolean"},"blocked":{"type":"string","format":"at-uri"}}},"starterPackView":{"type":"object","required":["uri","cid","record","creator","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"list":{"ref":"#listViewBasic","type":"ref"},"feeds":{"type":"array","items":{"ref":"app.bsky.feed.defs#generatorView","type":"ref"},"maxLength":3},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"record":{"type":"unknown"},"creator":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"joinedWeekCount":{"type":"integer","minimum":0},"listItemsSample":{"type":"array","items":{"ref":"#listItemView","type":"ref"},"maxLength":12},"joinedAllTimeCount":{"type":"integer","minimum":0}}},"starterPackViewBasic":{"type":"object","required":["uri","cid","record","creator","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"record":{"type":"unknown"},"creator":{"ref":"app.bsky.actor.defs#profileViewBasic","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"listItemCount":{"type":"integer","minimum":0},"joinedWeekCount":{"type":"integer","minimum":0},"joinedAllTimeCount":{"type":"integer","minimum":0}}}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const bskyGraphFollowLex = {"lexicon":1,"id":"app.bsky.graph.follow","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["subject","createdAt"],"properties":{"subject":{"type":"string"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const bskyLabelerDefsLex = {"id":"app.bsky.labeler.defs","defs":{"labelerView":{"type":"object","required":["uri","cid","creator","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"viewer":{"ref":"#labelerViewerState","type":"ref"},"creator":{"ref":"app.bsky.actor.defs#profileView","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"likeCount":{"type":"integer","minimum":0}}},"labelerPolicies":{"type":"object","required":["labelValues"],"properties":{"labelValues":{"type":"array","items":{"ref":"com.atproto.label.defs#labelValue","type":"ref"},"description":"The label values which this labeler publishes. May include global or custom labels."},"labelValueDefinitions":{"type":"array","items":{"ref":"com.atproto.label.defs#labelValueDefinition","type":"ref"},"description":"Label values created by this labeler and scoped exclusively to it. Labels defined here will override global label definitions for this labeler."}}},"labelerViewerState":{"type":"object","properties":{"like":{"type":"string","format":"at-uri"}}},"labelerViewDetailed":{"type":"object","required":["uri","cid","creator","policies","indexedAt"],"properties":{"cid":{"type":"string","format":"cid"},"uri":{"type":"string","format":"at-uri"},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"viewer":{"ref":"#labelerViewerState","type":"ref"},"creator":{"ref":"app.bsky.actor.defs#profileView","type":"ref"},"policies":{"ref":"app.bsky.labeler.defs#labelerPolicies","type":"ref"},"indexedAt":{"type":"string","format":"datetime"},"likeCount":{"type":"integer","minimum":0},"reasonTypes":{"type":"array","items":{"ref":"com.atproto.moderation.defs#reasonType","type":"ref"},"description":"The set of report reason 'codes' which are in-scope for this service to review and action. These usually align to policy categories. If not defined (distinct from empty array), all reason types are allowed."},"subjectTypes":{"type":"array","items":{"ref":"com.atproto.moderation.defs#subjectType","type":"ref"},"description":"The set of subject types (account, record, etc) this service accepts reports on."},"subjectCollections":{"type":"array","items":{"type":"string","format":"nsid"},"description":"Set of record types (collection NSIDs) which can be reported to this service. If not defined (distinct from empty array), default is any record type."}}}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const bskyNotificationDefsLex = {"id":"app.bsky.notification.defs","defs":{"preference":{"type":"object","required":["list","push"],"properties":{"list":{"type":"boolean"},"push":{"type":"boolean"}}},"preferences":{"type":"object","required":["chat","follow","like","likeViaRepost","mention","quote","reply","repost","repostViaRepost","starterpackJoined","subscribedPost","unverified","verified"],"properties":{"chat":{"ref":"#chatPreference","type":"ref"},"like":{"ref":"#filterablePreference","type":"ref"},"quote":{"ref":"#filterablePreference","type":"ref"},"reply":{"ref":"#filterablePreference","type":"ref"},"follow":{"ref":"#filterablePreference","type":"ref"},"repost":{"ref":"#filterablePreference","type":"ref"},"mention":{"ref":"#filterablePreference","type":"ref"},"verified":{"ref":"#preference","type":"ref"},"unverified":{"ref":"#preference","type":"ref"},"likeViaRepost":{"ref":"#filterablePreference","type":"ref"},"subscribedPost":{"ref":"#preference","type":"ref"},"repostViaRepost":{"ref":"#filterablePreference","type":"ref"},"starterpackJoined":{"ref":"#preference","type":"ref"}}},"recordDeleted":{"type":"object","properties":{}},"chatPreference":{"type":"object","required":["include","push"],"properties":{"push":{"type":"boolean"},"include":{"type":"string","knownValues":["all","accepted"]}}},"activitySubscription":{"type":"object","required":["post","reply"],"properties":{"post":{"type":"boolean"},"reply":{"type":"boolean"}}},"filterablePreference":{"type":"object","required":["include","list","push"],"properties":{"list":{"type":"boolean"},"push":{"type":"boolean"},"include":{"type":"string","knownValues":["all","follows"]}}},"subjectActivitySubscription":{"type":"object","required":["subject","activitySubscription"],"properties":{"subject":{"type":"string","format":"did"},"activitySubscription":{"ref":"#activitySubscription","type":"ref"}},"description":"Object used to store activity subscription data in stash."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const facetLex = {"id":"app.bsky.richtext.facet","defs":{"tag":{"type":"object","required":["tag"],"properties":{"tag":{"type":"string","maxLength":640,"maxGraphemes":64}},"description":"Facet feature for a hashtag. The text usually includes a '#' prefix, but the facet reference should not (except in the case of 'double hash tags')."},"link":{"type":"object","required":["uri"],"properties":{"uri":{"type":"string","format":"uri"}},"description":"Facet feature for a URL. The text URL may have been simplified or truncated, but the facet reference should be a complete URL."},"main":{"type":"object","required":["index","features"],"properties":{"index":{"ref":"#byteSlice","type":"ref"},"features":{"type":"array","items":{"refs":["#mention","#link","#tag"],"type":"union"}}},"description":"Annotation of a sub-string within rich text."},"mention":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"}},"description":"Facet feature for mention of another account. The text is usually a handle, including a '@' prefix, but the facet reference is a DID."},"byteSlice":{"type":"object","required":["byteStart","byteEnd"],"properties":{"byteEnd":{"type":"integer","minimum":0},"byteStart":{"type":"integer","minimum":0}},"description":"Specifies the sub-string range a facet feature applies to. Start index is inclusive, end index is exclusive. Indices are zero-indexed, counting bytes of the UTF-8 encoded text. NOTE: some languages, like Javascript, use UTF-16 or Unicode codepoints for string slice indexing; in these languages, convert to byte arrays before working with facets."}},"$type":"com.atproto.lexicon.schema","lexicon":1} as const const atprotoLabelDefsLex = {"lexicon":1,"id":"com.atproto.label.defs","defs":{"label":{"type":"object","description":"Metadata tag on an atproto resource (eg, repo or record).","required":["src","uri","val","cts"],"properties":{"ver":{"type":"integer"},"src":{"type":"string","format":"did"},"uri":{"type":"string","format":"uri"},"cid":{"type":"string","format":"cid"},"val":{"type":"string","maxLength":128},"neg":{"type":"boolean"},"cts":{"type":"string","format":"datetime"},"exp":{"type":"string","format":"datetime"},"sig":{"type":"bytes"}}},"selfLabels":{"type":"object","description":"Metadata tags on an atproto record, published by the author within the record.","required":["values"],"properties":{"values":{"type":"array","items":{"type":"ref","ref":"#selfLabel"},"maxLength":10}}},"selfLabel":{"type":"object","required":["val"],"properties":{"val":{"type":"string","maxLength":128}}},"labelValueDefinition":{"type":"object","description":"Declares a label value and its expected interpretations and behaviors.","required":["identifier","severity","blurs","locales"],"properties":{"identifier":{"type":"string","maxLength":100},"severity":{"type":"string","knownValues":["inform","alert","none"]},"blurs":{"type":"string","knownValues":["content","media","none"]},"defaultSetting":{"type":"string","knownValues":["ignore","warn","hide"]},"adultOnly":{"type":"boolean"},"locales":{"type":"array","items":{"type":"ref","ref":"#labelValueDefinitionStrings"}}}},"labelValueDefinitionStrings":{"type":"object","required":["lang","name","description"],"properties":{"lang":{"type":"string","format":"language"},"name":{"type":"string","maxLength":640},"description":{"type":"string","maxLength":100000}}},"labelValue":{"type":"string","knownValues":["!hide","!no-promote","!warn","!no-unauthenticated","dmca-violation","doxxing","porn","sexual","nudity","nsfl","gore"]}}} as const const atprotoModerationDefsLex = {"lexicon":1,"id":"com.atproto.moderation.defs","defs":{"reasonType":{"type":"string","knownValues":["com.atproto.moderation.defs#reasonSpam","com.atproto.moderation.defs#reasonViolation","com.atproto.moderation.defs#reasonMisleading","com.atproto.moderation.defs#reasonSexual","com.atproto.moderation.defs#reasonRude","com.atproto.moderation.defs#reasonOther","com.atproto.moderation.defs#reasonAppeal"]},"reasonSpam":{"type":"token","description":"Spam: frequent unwanted promotion, replies, mentions."},"reasonViolation":{"type":"token","description":"Direct violation of server rules, laws, terms of service."},"reasonMisleading":{"type":"token","description":"Misleading identity, affiliation, or content."},"reasonSexual":{"type":"token","description":"Unwanted or mislabeled sexual content."},"reasonRude":{"type":"token","description":"Rude, harassing, explicit, or otherwise unwelcoming behavior."},"reasonOther":{"type":"token","description":"Reports not falling under another report category."},"reasonAppeal":{"type":"token","description":"Appeal a previously taken moderation action."},"subjectType":{"type":"string","description":"Tag describing a type of subject that might be reported.","knownValues":["account","record","chat"]}}} as const const strongRefLex = {"lexicon":1,"id":"com.atproto.repo.strongRef","description":"A URI with a content-hash fingerprint.","defs":{"main":{"type":"object","required":["uri","cid"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"}}}}} as const const germnetworkDeclarationLex = {"lexicon":1,"id":"com.germnetwork.declaration","defs":{"main":{"type":"record","description":"A declaration of a Germ Network account","key":"literal:self","record":{"type":"object","required":["version","currentKey"],"properties":{"version":{"type":"string","description":"Semver version number, without pre-release or build information, for the format of opaque content","minLength":5,"maxLength":14},"currentKey":{"type":"bytes","description":"Opaque value, an ed25519 public key prefixed with a byte enum"},"messageMe":{"type":"ref","description":"Controls who can message this account","ref":"#messageMe"},"keyPackage":{"type":"bytes","description":"Opaque value, contains MLS KeyPackage(s), and other signature data, and is signed by the currentKey"},"continuityProofs":{"type":"array","description":"Array of opaque values to allow for key rolling","items":{"type":"bytes"},"maxLength":1000}}}},"messageMe":{"type":"object","required":["showButtonTo","messageMeUrl"],"properties":{"messageMeUrl":{"type":"string","description":"A URL to present to an account that does not have its own com.germnetwork.declaration record, where the app should fill in the fragment component with the DIDs of the two accounts who wish to message each other","format":"uri","minLength":1,"maxLength":2047},"showButtonTo":{"type":"string","knownValues":["none","usersIFollow","everyone"],"description":"The policy of who can message the account, this value is included in the keyPackage, but is duplicated here to allow applications to decide if they should show a 'Message on Germ' button to the viewer.","minLength":1,"maxLength":100}}}}} as const const addressLex = {"lexicon":1,"id":"community.lexicon.location.address","defs":{"main":{"type":"object","description":"A physical location in the form of a street address.","required":["country"],"properties":{"country":{"type":"string","description":"The ISO 3166 country code. Preferably the 2-letter code.","minLength":2,"maxLength":10},"postalCode":{"type":"string","description":"The postal code of the location."},"region":{"type":"string","description":"The administrative region of the country. For example, a state in the USA."},"locality":{"type":"string","description":"The locality of the region. For example, a city in the USA."},"street":{"type":"string","description":"The street address."},"name":{"type":"string","description":"The name of the location."}}}}} as const const geoLex = {"lexicon":1,"id":"community.lexicon.location.geo","defs":{"main":{"type":"object","description":"A physical location in the form of a WGS84 coordinate.","required":["latitude","longitude"],"properties":{"latitude":{"type":"string"},"longitude":{"type":"string"},"altitude":{"type":"string"},"name":{"type":"string","description":"The name of the location."}}}}} as const const hthreeLex = {"lexicon":1,"id":"community.lexicon.location.hthree","defs":{"main":{"type":"object","description":"A physical location in the form of a H3 encoded location.","required":["value"],"properties":{"value":{"type":"string","description":"The h3 encoded location."},"name":{"type":"string","description":"The name of the location."}}}}} as const const opensocialDeclarationLex = {"lexicon":1,"id":"community.opensocial.declaration","defs":{"main":{"type":"record","key":"literal:self","description":"Marks a DID as a community. Lives in the public repo. Points at the about space. Discovery only.","record":{"type":"object","required":["about","createdAt"],"properties":{"about":{"type":"string","format":"space-ref","description":"The community's about space."},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const memberLex = {"lexicon":1,"id":"community.opensocial.member","defs":{"main":{"type":"record","key":"any","description":"The community's public attestation that an account is a member — one record per member, keyed by their DID, in the public repo of a discoverable community. Maintained by the host from the members space: written when a membership appears, deleted when it goes. The private membership record stays the source of truth (it carries roles; this carries none). It exists so an app that only reads public data can gate on membership — who may submit to a pool, who counts as a member — and so ejection is visible where it matters.","record":{"type":"object","required":["member","createdAt"],"properties":{"member":{"type":"string","format":"did"},"createdAt":{"type":"string","format":"datetime","description":"When the membership began."}}}}}} as const const opensocialProfileLex = {"lexicon":1,"id":"community.opensocial.profile","defs":{"main":{"type":"record","key":"literal:self","description":"The community's profile. Written by the community authority into the about space.","record":{"type":"object","required":["displayName","joinPolicy","createdAt"],"properties":{"displayName":{"type":"string","maxGraphemes":64,"maxLength":640},"description":{"type":"string","maxGraphemes":300,"maxLength":3000},"avatar":{"type":"blob","accept":["image/png","image/jpeg"],"maxSize":1000000},"banner":{"type":"blob","accept":["image/png","image/jpeg"],"maxSize":1000000},"url":{"type":"string","format":"uri","description":"The community's own site, if it keeps one. A third-party app that shows the community can link back to it."},"joinPolicy":{"type":"string","knownValues":["community.opensocial.profile#open","community.opensocial.profile#request","community.opensocial.profile#invite"],"description":"How new members get in: anyone may join, requests are reviewed, or invite only."},"createdAt":{"type":"string","format":"datetime"}}}},"open":{"type":"token","description":"Anyone may join by calling requestJoin; admitted immediately."},"request":{"type":"token","description":"requestJoin creates a pending request that a member with the admit action reviews."},"invite":{"type":"token","description":"Only holders of an outstanding invite may join."}}} as const const ruleLex = {"lexicon":1,"id":"community.opensocial.rule","defs":{"main":{"type":"record","key":"tid","description":"One community rule, with a stable URI a moderation action can cite.","record":{"type":"object","required":["title","createdAt"],"properties":{"title":{"type":"string","maxGraphemes":100,"maxLength":1000},"text":{"type":"string","maxGraphemes":2000,"maxLength":20000},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const applyWritesLex = {"lexicon":1,"id":"dev.hatk.applyWrites","defs":{"main":{"type":"procedure","description":"Apply multiple record writes in a single atomic PDS transaction.","input":{"encoding":"application/json","schema":{"type":"object","required":["writes"],"properties":{"writes":{"type":"array","items":{"type":"union","refs":["#create","#update","#delete"]}}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"results":{"type":"array","items":{"type":"union","refs":["#createResult","#updateResult","#deleteResult"]}}}}}},"create":{"type":"object","required":["collection","value"],"properties":{"collection":{"type":"string"},"rkey":{"type":"string"},"value":{"type":"unknown"}}},"update":{"type":"object","required":["collection","rkey","value"],"properties":{"collection":{"type":"string"},"rkey":{"type":"string"},"value":{"type":"unknown"}}},"delete":{"type":"object","required":["collection","rkey"],"properties":{"collection":{"type":"string"},"rkey":{"type":"string"}}},"createResult":{"type":"object","required":["uri","cid"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"}}},"updateResult":{"type":"object","required":["uri","cid"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"}}},"deleteResult":{"type":"object","properties":{}}}} as const const createRecordLex = {"lexicon":1,"id":"dev.hatk.createRecord","defs":{"main":{"type":"procedure","description":"Create a record via the user's PDS.","input":{"encoding":"application/json","schema":{"type":"object","required":["collection","repo","record"],"properties":{"collection":{"type":"string"},"repo":{"type":"string","format":"did"},"record":{"type":"unknown"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"}}}}}}} as const const createReportLex = {"lexicon":1,"id":"dev.hatk.createReport","defs":{"main":{"type":"procedure","description":"Report an account or record for moderation review.","input":{"encoding":"application/json","schema":{"type":"object","required":["subject","label"],"properties":{"subject":{"type":"union","description":"The account or record being reported.","refs":["#repoRef","com.atproto.repo.strongRef"]},"label":{"type":"string","description":"Label identifier for the report reason."},"reason":{"type":"string","maxLength":2000,"description":"Optional free-text explanation."}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["id","subject","label","reportedBy","createdAt"],"properties":{"id":{"type":"integer"},"subject":{"type":"unknown"},"label":{"type":"string"},"reason":{"type":"string"},"reportedBy":{"type":"string","format":"did"},"createdAt":{"type":"string","format":"datetime"}}}}},"repoRef":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"}}}}} as const const deleteRecordLex = {"lexicon":1,"id":"dev.hatk.deleteRecord","defs":{"main":{"type":"procedure","description":"Delete a record via the user's PDS.","input":{"encoding":"application/json","schema":{"type":"object","required":["collection","rkey"],"properties":{"collection":{"type":"string"},"rkey":{"type":"string"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const describeCollectionsLex = {"lexicon":1,"id":"dev.hatk.describeCollections","defs":{"main":{"type":"query","description":"List indexed collections and their schemas.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"collections":{"type":"array","items":{"type":"object","required":["collection"],"properties":{"collection":{"type":"string"},"columns":{"type":"array","items":{"type":"object","required":["name","originalName","type","required"],"properties":{"name":{"type":"string"},"originalName":{"type":"string"},"type":{"type":"string"},"required":{"type":"boolean"}}}}}}}}}}}}} as const const describeFeedsLex = {"lexicon":1,"id":"dev.hatk.describeFeeds","defs":{"main":{"type":"query","description":"List available feeds.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"feeds":{"type":"array","items":{"type":"object","required":["name","label"],"properties":{"name":{"type":"string"},"label":{"type":"string"}}}}}}}}}} as const const describeLabelsLex = {"lexicon":1,"id":"dev.hatk.describeLabels","defs":{"main":{"type":"query","description":"List available label definitions.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"definitions":{"type":"array","items":{"type":"ref","ref":"#labelDefinition"}}}}}},"labelDefinition":{"type":"object","required":["identifier","severity","blurs","defaultSetting"],"properties":{"identifier":{"type":"string"},"severity":{"type":"string"},"blurs":{"type":"string"},"defaultSetting":{"type":"string"},"locales":{"type":"array","items":{"type":"ref","ref":"#labelLocale"}}}},"labelLocale":{"type":"object","required":["lang","name","description"],"properties":{"lang":{"type":"string"},"name":{"type":"string"},"description":{"type":"string"}}}}} as const const getFeedLex = {"lexicon":1,"id":"dev.hatk.getFeed","defs":{"main":{"type":"query","description":"Retrieve a named feed of items.","parameters":{"type":"params","required":["feed"],"properties":{"feed":{"type":"string","description":"Feed name"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":30},"cursor":{"type":"string"},"actor":{"type":"string","format":"did","description":"Filter by actor DID"},"camera":{"type":"string","description":"Filter by camera make and model"},"location":{"type":"string","description":"Filter by H3 cell index"},"tag":{"type":"string","description":"Filter by hashtag"},"group":{"type":"string","format":"did","description":"Filter by group DID"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.gallery.defs#galleryView"}},"cursor":{"type":"string"}}}}}}} as const const getPreferencesLex = {"lexicon":1,"id":"dev.hatk.getPreferences","defs":{"main":{"type":"query","description":"Get all preferences for the authenticated user.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"preferences":{"type":"unknown"}}}}}}} as const const getRecordLex = {"lexicon":1,"id":"dev.hatk.getRecord","defs":{"main":{"type":"query","description":"Fetch a single record by AT URI.","parameters":{"type":"params","required":["uri"],"properties":{"uri":{"type":"string","format":"at-uri"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"record":{"type":"unknown"}}}}}}} as const const getRecordsLex = {"lexicon":1,"id":"dev.hatk.getRecords","defs":{"main":{"type":"query","description":"List records from a collection with optional filters.","parameters":{"type":"params","required":["collection"],"properties":{"collection":{"type":"string"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":20},"cursor":{"type":"string"},"sort":{"type":"string"},"order":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"unknown"}},"cursor":{"type":"string"}}}}}}} as const const putPreferenceLex = {"lexicon":1,"id":"dev.hatk.putPreference","defs":{"main":{"type":"procedure","description":"Set a single preference by key.","input":{"encoding":"application/json","schema":{"type":"object","required":["key","value"],"properties":{"key":{"type":"string"},"value":{"type":"unknown"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const putRecordLex = {"lexicon":1,"id":"dev.hatk.putRecord","defs":{"main":{"type":"procedure","description":"Create or update a record via the user's PDS.","input":{"encoding":"application/json","schema":{"type":"object","required":["collection","rkey","record"],"properties":{"collection":{"type":"string"},"rkey":{"type":"string"},"record":{"type":"unknown"},"repo":{"type":"string","format":"did"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"}}}}}}} as const const searchRecordsLex = {"lexicon":1,"id":"dev.hatk.searchRecords","defs":{"main":{"type":"query","description":"Full-text search across a collection.","parameters":{"type":"params","required":["collection","q"],"properties":{"collection":{"type":"string"},"q":{"type":"string","description":"Search query"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":20},"cursor":{"type":"string"},"fuzzy":{"type":"boolean","default":true}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"unknown"}},"cursor":{"type":"string"}}}}}}} as const const uploadBlobLex = {"lexicon":1,"id":"dev.hatk.uploadBlob","defs":{"main":{"type":"procedure","description":"Upload a blob via the user's PDS.","input":{"encoding":"*/*"},"output":{"encoding":"application/json","schema":{"type":"object","required":["blob"],"properties":{"blob":{"type":"blob"}}}}}}} as const const searchLex = {"lexicon":1,"id":"parts.page.mention.search","defs":{"main":{"type":"query","description":"Search a mention service for matching results.","parameters":{"type":"params","required":["service"],"properties":{"service":{"type":"string","format":"at-uri","description":"AT URI of the parts.page.mention.service record"},"search":{"type":"string","description":"Search query string"},"scope":{"type":"string","description":"Optional scope identifier to narrow results"},"limit":{"type":"integer","minimum":1,"maximum":50,"default":20}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["results"],"properties":{"results":{"type":"array","items":{"type":"ref","ref":"#result"},"maxLength":50}}}}},"result":{"type":"object","required":["uri","name"],"properties":{"uri":{"type":"string"},"name":{"type":"string"},"description":{"type":"string"},"labels":{"type":"array","items":{"type":"ref","ref":"#mentionLabel"}},"href":{"type":"string","format":"uri"},"icon":{"type":"string","format":"uri"},"embed":{"type":"ref","ref":"#embedInfo"},"subscope":{"type":"ref","ref":"#subscopeInfo"}}},"mentionLabel":{"type":"object","properties":{"text":{"type":"string"}}},"embedInfo":{"type":"object","required":["src"],"properties":{"src":{"type":"string","format":"uri"},"width":{"type":"integer","minimum":16,"maximum":3200},"height":{"type":"integer","minimum":16,"maximum":3200},"aspectRatio":{"type":"ref","ref":"#aspectRatio"}}},"aspectRatio":{"type":"object","required":["width","height"],"properties":{"width":{"type":"integer"},"height":{"type":"integer"}}},"subscopeInfo":{"type":"object","required":["scope","label"],"properties":{"scope":{"type":"string"},"label":{"type":"string","maxLength":100}}}}} as const const grainActorDefsLex = {"lexicon":1,"id":"social.grain.actor.defs","defs":{"profileView":{"type":"object","required":["cid","did","handle"],"properties":{"cid":{"type":"string","format":"cid"},"did":{"type":"string","format":"did"},"handle":{"type":"string","format":"handle"},"displayName":{"type":"string","maxGraphemes":64,"maxLength":640},"description":{"type":"string","maxLength":2560,"maxGraphemes":256},"labels":{"type":"array","items":{"ref":"com.atproto.label.defs#label","type":"ref"}},"avatar":{"type":"string","format":"uri"},"createdAt":{"type":"string","format":"datetime"}}},"profileViewDetailed":{"type":"object","required":["cid","did","handle"],"properties":{"cid":{"type":"string","format":"cid"},"did":{"type":"string","format":"did"},"handle":{"type":"string","format":"handle"},"displayName":{"type":"string","maxGraphemes":64,"maxLength":640},"description":{"type":"string","maxGraphemes":256,"maxLength":2560},"avatar":{"type":"string","format":"uri"},"cameras":{"type":"array","items":{"type":"string"},"description":"List of camera make and models used by this actor derived from EXIF data of photos linked to galleries."},"followersCount":{"type":"integer"},"followsCount":{"type":"integer"},"galleryCount":{"type":"integer"},"indexedAt":{"type":"string","format":"datetime"},"createdAt":{"type":"string","format":"datetime"},"messageMe":{"type":"ref","ref":"#messageMe"},"viewer":{"type":"ref","ref":"#viewerState"},"labels":{"type":"array","items":{"type":"ref","ref":"com.atproto.label.defs#label"}}}},"messageMe":{"type":"object","required":["showButtonTo","messageMeUrl"],"properties":{"messageMeUrl":{"type":"string","format":"uri"},"showButtonTo":{"type":"string","knownValues":["usersIFollow","everyone"]}}},"viewerState":{"type":"object","description":"Metadata about the requesting account's relationship with the subject account. Only has meaningful content for authed requests.","properties":{"following":{"type":"string","format":"at-uri"},"followedBy":{"type":"string","format":"at-uri"},"blocking":{"type":"string","format":"at-uri"},"blockedBy":{"type":"boolean"},"muted":{"type":"boolean"}}}}} as const const grainActorProfileLex = {"lexicon":1,"id":"social.grain.actor.profile","defs":{"main":{"type":"record","description":"A declaration of a basic account profile.","key":"literal:self","record":{"type":"object","properties":{"displayName":{"type":"string","maxGraphemes":64,"maxLength":640},"description":{"type":"string","description":"Free-form profile description text.","maxGraphemes":256,"maxLength":2560},"avatar":{"type":"blob","description":"Small image to be displayed next to posts from account. AKA, 'profile picture'","accept":["image/png","image/jpeg"],"maxSize":1000000},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const commentLex = {"lexicon":1,"id":"social.grain.comment","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["text","subject","createdAt"],"properties":{"text":{"type":"string","maxLength":3000,"maxGraphemes":300},"facets":{"type":"array","description":"Annotations of description text (mentions and URLs, hashtags, etc)","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"subject":{"type":"string","format":"at-uri"},"focus":{"type":"string","format":"at-uri"},"replyTo":{"type":"string","format":"at-uri"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainCommentDefsLex = {"lexicon":1,"id":"social.grain.comment.defs","defs":{"commentView":{"type":"object","required":["uri","cid","author","text","createdAt"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"author":{"type":"ref","ref":"social.grain.actor.defs#profileView"},"record":{"type":"unknown"},"text":{"type":"string","maxLength":3000,"maxGraphemes":300},"facets":{"type":"array","description":"Annotations of description text (mentions and URLs, hashtags, etc)","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"subject":{"type":"union","refs":["social.grain.gallery.defs#galleryView"],"description":"The subject of the comment, which can be a gallery or a photo."},"focus":{"type":"union","refs":["social.grain.photo.defs#photoView"],"description":"The photo that the comment is focused on, if applicable."},"replyTo":{"type":"string","format":"at-uri","description":"The URI of the comment this comment is replying to, if applicable."},"createdAt":{"type":"string","format":"datetime"},"favCount":{"type":"integer"},"viewer":{"type":"ref","ref":"#viewerState"},"muted":{"type":"boolean","description":"True if the viewer has muted the comment author. Client should show collapsed with option to expand."}}},"viewerState":{"type":"object","description":"Metadata about the requesting account's relationship with the comment. Only has meaningful content for authed requests.","properties":{"fav":{"type":"string","format":"at-uri"}}}}} as const const grainDefsLex = {"lexicon":1,"id":"social.grain.defs","defs":{"aspectRatio":{"type":"object","description":"width:height represents an aspect ratio. It may be approximate, and may not correspond to absolute dimensions in any given unit.","required":["width","height"],"properties":{"width":{"type":"integer","minimum":1},"height":{"type":"integer","minimum":1}}}}} as const const favoriteLex = {"lexicon":1,"id":"social.grain.favorite","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["createdAt","subject"],"properties":{"createdAt":{"type":"string","format":"datetime"},"subject":{"type":"string","format":"at-uri"}}}}}} as const const galleryLex = {"lexicon":1,"id":"social.grain.gallery","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["title","createdAt"],"properties":{"title":{"type":"string","maxLength":100},"description":{"type":"string","maxLength":1000},"facets":{"type":"array","description":"Annotations of description text (mentions, URLs, hashtags, etc)","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"labels":{"type":"union","description":"Self-label values for this post. Effectively content warnings.","refs":["com.atproto.label.defs#selfLabels"]},"location":{"type":"ref","ref":"community.lexicon.location.hthree"},"address":{"type":"ref","ref":"community.lexicon.location.address"},"updatedAt":{"type":"string","format":"datetime"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainGalleryDefsLex = {"lexicon":1,"id":"social.grain.gallery.defs","defs":{"galleryView":{"type":"object","required":["uri","cid","creator","record","indexedAt"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"title":{"type":"string"},"description":{"type":"string"},"cameras":{"type":"array","description":"List of camera make and models used in this gallery derived from EXIF data.","items":{"type":"string"}},"location":{"type":"ref","ref":"community.lexicon.location.hthree"},"address":{"type":"ref","ref":"community.lexicon.location.address"},"locationDisplay":{"type":"string","description":"Formatted location label for display."},"facets":{"type":"array","description":"Annotations of description text (mentions, URLs, hashtags, etc)","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"creator":{"type":"ref","ref":"social.grain.actor.defs#profileView"},"record":{"type":"unknown"},"items":{"type":"array","items":{"type":"union","refs":["social.grain.photo.defs#photoView"]}},"favCount":{"type":"integer"},"favedByFollowing":{"type":"array","description":"Profiles of accounts the viewer follows who favorited this gallery. Capped for display — see favCount for the total. Excludes the viewer.","items":{"type":"ref","ref":"social.grain.actor.defs#profileView"}},"commentCount":{"type":"integer"},"labels":{"type":"array","items":{"type":"ref","ref":"com.atproto.label.defs#label"}},"createdAt":{"type":"string","format":"datetime"},"indexedAt":{"type":"string","format":"datetime"},"viewer":{"type":"ref","ref":"#viewerState"},"crossPost":{"type":"ref","ref":"#crossPostInfo"},"group":{"type":"ref","ref":"social.grain.group.defs#groupRef","description":"The group whose pool this gallery is in, if any."}}},"crossPostInfo":{"type":"object","required":["url"],"properties":{"url":{"type":"string","format":"uri","description":"URL to the cross-posted Bluesky post."}}},"viewerState":{"type":"object","description":"Metadata about the requesting account's relationship with the subject content. Only has meaningful content for authed requests.","properties":{"fav":{"type":"string","format":"at-uri"}}}}} as const const grainGalleryItemLex = {"lexicon":1,"id":"social.grain.gallery.item","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["createdAt","gallery","item"],"properties":{"createdAt":{"type":"string","format":"datetime"},"gallery":{"type":"string","format":"at-uri"},"item":{"type":"string","format":"at-uri"},"position":{"type":"integer","default":0}}}}}} as const const blockLex = {"lexicon":1,"id":"social.grain.graph.block","defs":{"main":{"key":"tid","type":"record","record":{"type":"object","required":["subject","createdAt"],"properties":{"subject":{"type":"string","format":"did"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainGraphFollowLex = {"lexicon":1,"id":"social.grain.graph.follow","defs":{"main":{"key":"tid","type":"record","record":{"type":"object","required":["subject","createdAt"],"properties":{"subject":{"type":"string","format":"did"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const muteActorLex = {"lexicon":1,"id":"social.grain.graph.muteActor","defs":{"main":{"type":"procedure","description":"Mute an actor. Mutes are private and only affect the muter's feeds.","input":{"encoding":"application/json","schema":{"type":"object","required":["actor"],"properties":{"actor":{"type":"string","format":"did"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const unmuteActorLex = {"lexicon":1,"id":"social.grain.graph.unmuteActor","defs":{"main":{"type":"procedure","description":"Unmute an actor.","input":{"encoding":"application/json","schema":{"type":"object","required":["actor"],"properties":{"actor":{"type":"string","format":"did"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const declineLex = {"lexicon":1,"id":"social.grain.group.decline","defs":{"main":{"type":"record","key":"tid","description":"A group turning a submission down. Written into the group's repo by whoever is acting as it; the submission leaves the queue for good and stays in the member's repo as their own record. Delete this to reconsider.","record":{"type":"object","required":["submission","gallery","createdAt"],"properties":{"submission":{"type":"string","format":"at-uri"},"gallery":{"type":"string","format":"at-uri"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainGroupDefsLex = {"lexicon":1,"id":"social.grain.group.defs","defs":{"groupView":{"type":"object","required":["did","handle"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"url":{"type":"string","format":"uri","description":"The community's own site, from its opensocial profile. Where the group is actually run."},"avatar":{"type":"string","format":"uri"},"poolCount":{"type":"integer","description":"Galleries in the pool."},"pendingCount":{"type":"integer","description":"Submissions awaiting review. Only present for a viewer acting as the group."},"lastActivityAt":{"type":"string","format":"datetime","description":"When the pool last changed."},"viewer":{"type":"ref","ref":"#viewerState"},"memberCount":{"type":"integer","description":"Members, as the community publicly attests (community.opensocial.member records)."},"joinPolicy":{"type":"string","knownValues":["open","request","invite"],"description":"How to get in, from the community's public profile."},"rules":{"type":"array","items":{"type":"ref","ref":"#rule"}}}},"viewerState":{"type":"object","properties":{"acting":{"type":"boolean","description":"The viewer is signed in as this group, so may accept and remove."},"submission":{"type":"ref","ref":"#submissionState","description":"The viewer's standing for the gallery named in the request, if one was."},"member":{"type":"boolean","description":"The viewer is on the group's public roster."}}},"submissionState":{"type":"object","required":["uri","status"],"properties":{"uri":{"type":"string","format":"at-uri","description":"The submission record."},"status":{"type":"string","knownValues":["pending","accepted","declined"]},"item":{"type":"string","format":"at-uri","description":"The group's item record, once accepted."}}},"groupRef":{"type":"object","required":["did","handle","item"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"item":{"type":"string","format":"at-uri","description":"The social.grain.group.item that pools this gallery."}}},"submissionView":{"type":"object","required":["uri","cid","group","gallery","createdAt"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"group":{"type":"string","format":"did"},"gallery":{"type":"ref","ref":"social.grain.gallery.defs#galleryView"},"createdAt":{"type":"string","format":"datetime"}}},"rule":{"type":"object","required":["uri","title"],"properties":{"uri":{"type":"string","format":"at-uri"},"title":{"type":"string"},"text":{"type":"string"}}}}} as const const grainGroupItemLex = {"lexicon":1,"id":"social.grain.group.item","defs":{"main":{"type":"record","key":"tid","description":"A gallery in a group's pool. Written into the group's own repo by whoever is acting as it; the gallery itself stays in its author's repo. Accept a submission by creating one of these, remove from the pool by deleting it.","record":{"type":"object","required":["gallery","createdAt"],"properties":{"gallery":{"type":"string","format":"at-uri","description":"The pooled gallery (social.grain.gallery)."},"submission":{"type":"string","format":"at-uri","description":"The social.grain.group.submission this accepted, if any."},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const submissionLex = {"lexicon":1,"id":"social.grain.group.submission","defs":{"main":{"type":"record","key":"tid","description":"A member offering one of their own galleries to a group's pool. Lives in the member's repo; the group answers with a social.grain.group.item.","record":{"type":"object","required":["group","gallery","createdAt"],"properties":{"group":{"type":"string","format":"did","description":"The group (a community DID)."},"gallery":{"type":"string","format":"at-uri","description":"One of the submitter's galleries."},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const photoLex = {"lexicon":1,"id":"social.grain.photo","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["photo","aspectRatio","createdAt"],"properties":{"photo":{"type":"blob","accept":["image/*"],"maxSize":1000000},"alt":{"type":"string","description":"Alt text description of the image, for accessibility."},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainPhotoDefsLex = {"lexicon":1,"id":"social.grain.photo.defs","defs":{"photoView":{"type":"object","required":["uri","cid","thumb","fullsize","aspectRatio"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"thumb":{"type":"string","format":"uri","description":"Fully-qualified URL where a thumbnail of the image can be fetched. For example, CDN location provided by the App View."},"fullsize":{"type":"string","format":"uri","description":"Fully-qualified URL where a large version of the image can be fetched. May or may not be the exact original blob. For example, CDN location provided by the App View."},"alt":{"type":"string","description":"Alt text description of the image, for accessibility."},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"},"exif":{"type":"ref","ref":"social.grain.photo.defs#exifView","description":"EXIF metadata for the photo, if available."},"gallery":{"type":"ref","ref":"#galleryState"}}},"exifView":{"type":"object","required":["uri","cid","photo","createdAt"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"photo":{"type":"string","format":"at-uri"},"createdAt":{"type":"string","format":"datetime"},"dateTimeOriginal":{"type":"string"},"exposureTime":{"type":"string"},"fNumber":{"type":"string"},"flash":{"type":"string"},"focalLengthIn35mmFormat":{"type":"string"},"iSO":{"type":"integer"},"lensMake":{"type":"string"},"lensModel":{"type":"string"},"make":{"type":"string"},"model":{"type":"string"}}},"galleryState":{"type":"object","required":["item","itemCreatedAt","itemPosition"],"description":"Metadata about the photo's relationship with the subject content. Only has meaningful content when photo is attached to a gallery.","properties":{"item":{"type":"string","format":"at-uri"},"itemCreatedAt":{"type":"string","format":"datetime"},"itemPosition":{"type":"integer"}}}}} as const const exifLex = {"lexicon":1,"id":"social.grain.photo.exif","defs":{"main":{"type":"record","description":"Basic EXIF metadata for a photo. Integers are scaled by 1000000 to accommodate decimal values and potentially other tags in the future.","key":"tid","record":{"type":"object","required":["photo","createdAt"],"properties":{"photo":{"type":"string","format":"at-uri"},"createdAt":{"type":"string","format":"datetime"},"dateTimeOriginal":{"type":"string","format":"datetime"},"exposureTime":{"type":"integer"},"fNumber":{"type":"integer"},"flash":{"type":"string"},"focalLengthIn35mmFormat":{"type":"integer"},"iSO":{"type":"integer"},"lensMake":{"type":"string"},"lensModel":{"type":"string"},"make":{"type":"string"},"model":{"type":"string"}}}}}} as const const storyLex = {"lexicon":1,"id":"social.grain.story","defs":{"main":{"type":"record","key":"tid","record":{"type":"object","required":["media","aspectRatio","createdAt"],"properties":{"media":{"type":"blob","accept":["image/*","video/*"],"maxSize":5000000},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"},"location":{"type":"ref","ref":"community.lexicon.location.hthree"},"address":{"type":"ref","ref":"community.lexicon.location.address"},"labels":{"type":"union","description":"Self-label values for this story. Effectively content warnings.","refs":["com.atproto.label.defs#selfLabels"]},"createdAt":{"type":"string","format":"datetime"}}}}}} as const const grainStoryDefsLex = {"lexicon":1,"id":"social.grain.story.defs","defs":{"storyView":{"type":"object","required":["uri","cid","creator","thumb","fullsize","aspectRatio","createdAt"],"properties":{"uri":{"type":"string","format":"at-uri"},"cid":{"type":"string","format":"cid"},"creator":{"type":"ref","ref":"social.grain.actor.defs#profileView"},"thumb":{"type":"string","format":"uri","description":"Thumbnail URL for the story image."},"fullsize":{"type":"string","format":"uri","description":"Full-size URL for the story image."},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"},"location":{"type":"ref","ref":"community.lexicon.location.hthree"},"address":{"type":"ref","ref":"community.lexicon.location.address"},"locationDisplay":{"type":"string","description":"Formatted location label for display."},"createdAt":{"type":"string","format":"datetime"},"labels":{"type":"array","items":{"type":"ref","ref":"com.atproto.label.defs#label"}},"expired":{"type":"boolean","description":"Whether the story has passed its 24-hour window."},"commentCount":{"type":"integer"},"viewer":{"type":"ref","ref":"#viewerState"},"crossPost":{"type":"ref","ref":"social.grain.gallery.defs#crossPostInfo"}}},"viewerState":{"type":"object","description":"Metadata about the requesting account's relationship with the story.","properties":{"fav":{"type":"string","format":"at-uri"},"viewed":{"type":"boolean","description":"Whether the requesting account has watched this story. Only present when true."}}}}} as const const addSpaceMemberLex = {"lexicon":1,"id":"social.grain.unspecced.addSpaceMember","defs":{"main":{"type":"procedure","description":"Share an existing private gallery with another account. Adds them to the space's member list on the author's PDS, which is what the authority consults when it mints a credential.","input":{"encoding":"application/json","schema":{"type":"object","required":["space","actor"],"properties":{"space":{"type":"string"},"actor":{"type":"string","description":"Handle or DID of the account to share with."}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"}}}},"errors":[{"name":"NotAuthorized","description":"Only the gallery's author may add members."},{"name":"ActorNotFound","description":"The handle could not be resolved."}]}}} as const const createPoolCommentLex = {"lexicon":1,"id":"social.grain.unspecced.createPoolComment","defs":{"main":{"type":"procedure","description":"Comment on a gallery in a community's pool. The comment is the viewer's own record, written into the pool beside the gallery it answers, so only that community's members can read it.","input":{"encoding":"application/json","schema":{"type":"object","required":["group","gallery","text"],"properties":{"group":{"type":"string","format":"did"},"gallery":{"type":"string","format":"at-uri"},"text":{"type":"string","maxLength":3000},"facets":{"type":"array","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"replyTo":{"type":"string","format":"at-uri"}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["uri","rkey"],"properties":{"uri":{"type":"string","format":"at-uri"},"rkey":{"type":"string"}}}},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this pool."}]}}} as const const createPoolGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.createPoolGallery","defs":{"main":{"type":"procedure","description":"Add a gallery to a community's pool: one permissioned space (social.grain.group) anchored on the community, holding every member's galleries. The gallery, its photos and its items are the author's own records in their own repo, written inside that space — so only the community's members can read them, and they leave with the author.","input":{"encoding":"application/json","schema":{"type":"object","required":["group","rkey","title"],"properties":{"group":{"type":"string","format":"did","description":"The community whose pool this goes into."},"rkey":{"type":"string","description":"Record key for the gallery, in the author's repo.","maxLength":64},"title":{"type":"string","maxLength":100},"description":{"type":"string","maxLength":1000},"photos":{"type":"array","maxLength":100,"items":{"type":"ref","ref":"#photoInput"}}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["space","uri"],"properties":{"space":{"type":"string","description":"The pool space it was written into."},"uri":{"type":"string","format":"at-uri"}}}},"errors":[{"name":"SpacesUnsupported","description":"The author's PDS does not serve permissioned spaces."},{"name":"NotAuthorized","description":"The viewer is not a member of this community's pool."}]},"photoInput":{"type":"object","required":["photo","aspectRatio"],"properties":{"photo":{"type":"blob","accept":["image/*"],"maxSize":1000000},"alt":{"type":"string"},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"}}}}} as const const createPrivateGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.createPrivateGallery","defs":{"main":{"type":"procedure","description":"Create a gallery that lives in a permissioned space (proposal 0016) rather than in the public repo. The gallery, its photos and its items are written to the author's space repo, and only the accounts named in members can read them.","input":{"encoding":"application/json","schema":{"type":"object","required":["rkey","title"],"properties":{"rkey":{"type":"string","description":"Record key for the gallery. Doubles as the space's skey, so one gallery is one space.","maxLength":64},"title":{"type":"string","maxLength":100},"description":{"type":"string","maxLength":1000},"members":{"type":"array","description":"Handles or DIDs allowed to read the gallery. The author always can.","maxLength":100,"items":{"type":"string"}},"photos":{"type":"array","maxLength":100,"items":{"type":"ref","ref":"#photoInput"}}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["space","uri"],"properties":{"space":{"type":"string","description":"The space URI the gallery lives in."},"uri":{"type":"string","format":"at-uri"}}}},"errors":[{"name":"SpacesUnsupported","description":"The author's PDS does not serve permissioned spaces."},{"name":"ActorNotFound","description":"One of the named members could not be resolved."}]},"photoInput":{"type":"object","required":["photo","aspectRatio"],"properties":{"photo":{"type":"blob","accept":["image/*"],"maxSize":1000000},"alt":{"type":"string"},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"}}}}} as const const deleteAccountLex = {"lexicon":1,"id":"social.grain.unspecced.deleteAccount","defs":{"main":{"type":"procedure","description":"Delete the authenticated user's Grain account. Removes all of their Grain records from their PDS and clears supporting server-side state (mutes, preferences, push tokens, OAuth session). Reports and labels are preserved.","output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const deleteGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.deleteGallery","defs":{"main":{"type":"procedure","description":"Delete a gallery and all associated records (items, photos, EXIF, favorites, comments).","input":{"encoding":"application/json","schema":{"type":"object","required":["rkey"],"properties":{"rkey":{"type":"string","description":"Record key of the gallery to delete."}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const deletePoolCommentLex = {"lexicon":1,"id":"social.grain.unspecced.deletePoolComment","defs":{"main":{"type":"procedure","description":"Delete one of your own comments from a community's pool.","input":{"encoding":"application/json","schema":{"type":"object","required":["group","rkey"],"properties":{"group":{"type":"string","format":"did"},"rkey":{"type":"string"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"deleted":{"type":"boolean"}}}}}}} as const const getActorFavoritesLex = {"lexicon":1,"id":"social.grain.unspecced.getActorFavorites","defs":{"main":{"type":"query","description":"Get galleries favorited by the authenticated actor. Only the actor themselves can view their favorites.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":30},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["items"],"properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.gallery.defs#galleryView"}},"cursor":{"type":"string"}}}}}}} as const const getActorProfileLex = {"lexicon":1,"id":"social.grain.unspecced.getActorProfile","defs":{"main":{"type":"query","description":"Get an actor's profile with gallery stats and follow relationships.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"viewer":{"type":"string","format":"did"}}},"output":{"encoding":"application/json","schema":{"type":"ref","ref":"social.grain.actor.defs#profileViewDetailed"}}}}} as const const getBlocksLex = {"lexicon":1,"id":"social.grain.unspecced.getBlocks","defs":{"main":{"type":"query","description":"Get the viewer's blocked users.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getBlocks#blockItem"}},"cursor":{"type":"string"}}}}},"blockItem":{"type":"object","required":["did","blockUri"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string"},"blockUri":{"type":"string","format":"at-uri"}}}}} as const const getCamerasLex = {"lexicon":1,"id":"social.grain.unspecced.getCameras","defs":{"main":{"type":"query","description":"Get top cameras by photo count.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"cameras":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getCameras#cameraItem"}}}}}},"cameraItem":{"type":"object","required":["camera","photoCount"],"properties":{"camera":{"type":"string"},"photoCount":{"type":"integer"},"thumbs":{"type":"array","description":"Up to four representative photo thumbnails, most recent first. Lets the index render without a feed request per camera.","maxLength":4,"items":{"type":"string","format":"uri"}}}}}} as const const getCommentThreadLex = {"lexicon":1,"id":"social.grain.unspecced.getCommentThread","defs":{"main":{"type":"query","description":"Get comments for a subject (gallery or story), sorted oldest-first with author profiles.","parameters":{"type":"params","required":["subject"],"properties":{"subject":{"type":"string","format":"at-uri","description":"The subject URI to fetch comments for."},"limit":{"type":"integer","minimum":1,"maximum":100,"default":20},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["comments"],"properties":{"comments":{"type":"array","items":{"type":"ref","ref":"social.grain.comment.defs#commentView"}},"cursor":{"type":"string"},"totalCount":{"type":"integer"}}}}}}} as const const getFollowersLex = {"lexicon":1,"id":"social.grain.unspecced.getFollowers","defs":{"main":{"type":"query","description":"Get followers for a given user.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"viewer":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"totalCount":{"type":"integer"},"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getFollowers#followerItem"}},"cursor":{"type":"string"}}}}},"followerItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"},"viewer":{"type":"ref","ref":"social.grain.unspecced.getFollowers#viewerState"}}},"viewerState":{"type":"object","properties":{"following":{"type":"string","format":"at-uri"}}}}} as const const getFollowingLex = {"lexicon":1,"id":"social.grain.unspecced.getFollowing","defs":{"main":{"type":"query","description":"Get users that a given user follows.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"viewer":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"totalCount":{"type":"integer"},"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getFollowing#followingItem"}},"cursor":{"type":"string"}}}}},"followingItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"},"viewer":{"type":"ref","ref":"social.grain.unspecced.getFollowing#viewerState"}}},"viewerState":{"type":"object","properties":{"following":{"type":"string","format":"at-uri"}}}}} as const const getGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.getGallery","defs":{"main":{"type":"query","description":"Get a single gallery view by AT URI.","parameters":{"type":"params","required":["gallery"],"properties":{"gallery":{"type":"string","format":"at-uri","description":"The gallery AT URI."}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["gallery"],"properties":{"gallery":{"type":"ref","ref":"social.grain.gallery.defs#galleryView"}}}}}}} as const const getGalleryFavoritesLex = {"lexicon":1,"id":"social.grain.unspecced.getGalleryFavorites","defs":{"main":{"type":"query","description":"Get the accounts that have favorited a gallery, most recent first.","parameters":{"type":"params","required":["gallery"],"properties":{"gallery":{"type":"string","format":"at-uri"},"viewer":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"totalCount":{"type":"integer"},"cursor":{"type":"string"},"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getGalleryFavorites#favoriteItem"}}}}}},"favoriteItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"},"viewer":{"type":"ref","ref":"social.grain.actor.defs#viewerState"}}}}} as const const getGroupLex = {"lexicon":1,"id":"social.grain.unspecced.getGroup","defs":{"main":{"type":"query","description":"A group: a community DID that has declared itself and shows up in Grain as an author whose pool is other people's galleries.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","description":"DID or handle."}}},"output":{"encoding":"application/json","schema":{"type":"ref","ref":"social.grain.group.defs#groupView"}}}}} as const const getGroupSubmissionsLex = {"lexicon":1,"id":"social.grain.unspecced.getGroupSubmissions","defs":{"main":{"type":"query","description":"Submissions to a group that no item has answered yet — the review queue.","parameters":{"type":"params","required":["group"],"properties":{"group":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":30},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["submissions"],"properties":{"submissions":{"type":"array","items":{"type":"ref","ref":"social.grain.group.defs#submissionView"}},"cursor":{"type":"string"}}}}}}} as const const getKnownFollowersLex = {"lexicon":1,"id":"social.grain.unspecced.getKnownFollowers","defs":{"main":{"type":"query","description":"Get followers of a given actor that the viewer also follows.","parameters":{"type":"params","required":["actor","viewer"],"properties":{"actor":{"type":"string","format":"did"},"viewer":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":50,"default":50}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getKnownFollowers#followerItem"}}}}}},"followerItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"}}}}} as const const getLocationsLex = {"lexicon":1,"id":"social.grain.unspecced.getLocations","defs":{"main":{"type":"query","description":"Get top locations by gallery count.","output":{"encoding":"application/json","schema":{"type":"object","properties":{"locations":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getLocations#locationItem"}}}}},"parameters":{"type":"params","properties":{"pins":{"type":"boolean","description":"Return every place carrying only what a map needs — name, h3Index, galleryCount — instead of the top 30 with thumbnails and cell lists. The full shape is ~1.1KB per place, so all of them would be ~780KB; lean it is ~70 bytes each."}}}},"locationItem":{"type":"object","required":["name","h3Index","galleryCount"],"properties":{"name":{"type":"string"},"h3Index":{"type":"string","description":"Canonical H3 cell for the place (densest cell in the group)."},"galleryCount":{"type":"integer"},"h3Cells":{"type":"array","description":"All H3 cells whose galleries map to this place. Ordered by gallery count desc.","items":{"type":"string"}},"thumbs":{"type":"array","description":"Up to four representative photo thumbnails, most recent first. Lets the index render without a feed request per location.","maxLength":4,"items":{"type":"string","format":"uri"}}}}}} as const const getMutesLex = {"lexicon":1,"id":"social.grain.unspecced.getMutes","defs":{"main":{"type":"query","description":"Get the viewer's muted users.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getMutes#muteItem"}},"cursor":{"type":"string"}}}}},"muteItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string"}}}}} as const const getNotificationsLex = {"lexicon":1,"id":"social.grain.unspecced.getNotifications","defs":{"main":{"type":"query","description":"Get notifications for the authenticated user.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":100,"default":20},"cursor":{"type":"string"},"countOnly":{"type":"boolean","description":"If true, only return unseenCount without hydrating notifications."}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["notifications"],"properties":{"notifications":{"type":"array","items":{"type":"ref","ref":"#notificationItem"}},"cursor":{"type":"string"},"unseenCount":{"type":"integer"}}}}},"notificationItem":{"type":"object","required":["uri","reason","createdAt","author"],"properties":{"uri":{"type":"string","format":"at-uri"},"reason":{"type":"string","knownValues":["gallery-favorite","gallery-comment","gallery-comment-mention","gallery-mention","comment-favorite","story-favorite","story-comment","reply","follow"]},"createdAt":{"type":"string","format":"datetime"},"author":{"type":"ref","ref":"social.grain.actor.defs#profileView"},"galleryUri":{"type":"string","format":"at-uri"},"galleryTitle":{"type":"string"},"galleryThumb":{"type":"string"},"storyUri":{"type":"string","format":"at-uri"},"storyThumb":{"type":"string"},"commentText":{"type":"string"},"replyToText":{"type":"string"}}}}} as const const getPoolGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.getPoolGallery","defs":{"main":{"type":"query","description":"One gallery from a community's pool, read from the repo that holds it through a credential the community's host issues.","parameters":{"type":"params","required":["group","did","rkey"],"properties":{"group":{"type":"string","format":"did"},"did":{"type":"string","format":"did","description":"Whose gallery it is."},"rkey":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["space","did","items"],"properties":{"space":{"type":"string"},"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"viewerIsAuthor":{"type":"boolean"},"gallery":{"type":"ref","ref":"social.grain.unspecced.getPrivateGallery#privateGallery"},"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getPrivateGallery#privateItem"}},"avatar":{"type":"string"},"favCount":{"type":"integer"},"viewerFav":{"type":"string","description":"The rkey of the viewer's own favourite, when they have one."},"commentCount":{"type":"integer"},"comments":{"type":"array","items":{"type":"ref","ref":"#poolComment"}}}}},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this pool."}]},"poolComment":{"type":"object","required":["uri","rkey","text","author"],"properties":{"uri":{"type":"string","format":"at-uri"},"rkey":{"type":"string"},"text":{"type":"string"},"facets":{"type":"array","items":{"type":"ref","ref":"app.bsky.richtext.facet"}},"replyTo":{"type":"string","format":"at-uri"},"createdAt":{"type":"string","format":"datetime"},"author":{"type":"ref","ref":"#poolAuthor"}}},"poolAuthor":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string"}}}}} as const const getPrivateBlobLex = {"lexicon":1,"id":"social.grain.unspecced.getPrivateBlob","defs":{"main":{"type":"query","description":"Serve a blob referenced by a permissioned space, to a viewer the space admits. These cannot go through the CDN: the space serves a blob only to a credential holder, and a CDN is an unauthenticated cache keyed by a public URL.","parameters":{"type":"params","required":["space","did","cid"],"properties":{"space":{"type":"string","description":"Space URI the blob is referenced from."},"did":{"type":"string","format":"did","description":"Repo that holds the blob."},"cid":{"type":"string","format":"cid"}}},"output":{"encoding":"*/*"},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this space."}]}}} as const const getPrivateGalleryLex = {"lexicon":1,"id":"social.grain.unspecced.getPrivateGallery","defs":{"main":{"type":"query","description":"Assemble a gallery that lives in a permissioned space. Read from the repos that hold it at request time — space records never reach a firehose, so none of this is in the index.","parameters":{"type":"params","required":["space"],"properties":{"space":{"type":"string","description":"Space URI: at:///space/social.grain.gallery/"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["space","authority","items"],"properties":{"space":{"type":"string"},"authority":{"type":"string","format":"did"},"viewerIsAuthor":{"type":"boolean"},"gallery":{"type":"ref","ref":"#privateGallery"},"items":{"type":"array","items":{"type":"ref","ref":"#privateItem"}}}}},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this space."}]},"privateGallery":{"type":"object","required":["uri","title"],"properties":{"uri":{"type":"string","format":"at-uri"},"title":{"type":"string"},"description":{"type":"string"},"createdAt":{"type":"string","format":"datetime"}}},"privateItem":{"type":"object","required":["uri","did","cid","position"],"properties":{"uri":{"type":"string","description":"Space URI of the photo record."},"did":{"type":"string","format":"did","description":"Repo holding the photo, and its blob."},"cid":{"type":"string","format":"cid","description":"Blob CID. Fetch through the space, never the CDN."},"alt":{"type":"string"},"aspectRatio":{"type":"ref","ref":"social.grain.defs#aspectRatio"},"position":{"type":"integer"}}}}} as const const getSpaceMembersLex = {"lexicon":1,"id":"social.grain.unspecced.getSpaceMembers","defs":{"main":{"type":"query","description":"Who a private gallery is shared with. Read from the space's authority, which is the only place the member list exists, so only the gallery's author can ask.","parameters":{"type":"params","required":["space"],"properties":{"space":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["members"],"properties":{"members":{"type":"array","items":{"type":"ref","ref":"#memberView"}}}}},"errors":[{"name":"NotAuthorized","description":"Only the gallery's author may list its members."}]},"memberView":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string","format":"uri"}}}}} as const const getSpaceSupportLex = {"lexicon":1,"id":"social.grain.unspecced.getSpaceSupport","defs":{"main":{"type":"query","description":"Whether the viewer's PDS serves permissioned spaces (proposal 0016). Answered from a cached probe of community.lexicon.service.describe.","parameters":{"type":"params","properties":{"force":{"type":"boolean","description":"Probe the PDS again rather than answering from cache. For a viewer whose server has just gained spaces and does not want to wait for the cached answer to age out."}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["supported","pds"],"properties":{"supported":{"type":"boolean","description":"True when the PDS serves every space method grain needs."},"pds":{"type":"string","description":"The PDS endpoint that was probed."},"checkedAt":{"type":"string","format":"datetime"},"missing":{"type":"array","description":"Space methods grain needs that this PDS does not serve. Empty when supported; the full list when the PDS answers no describe at all.","items":{"type":"string"}}}}}}}} as const const getStoriesLex = {"lexicon":1,"id":"social.grain.unspecced.getStories","defs":{"main":{"type":"query","description":"Get a user's active stories (posted within the last 24 hours).","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["stories"],"properties":{"stories":{"type":"array","items":{"type":"ref","ref":"social.grain.story.defs#storyView"}}}}}}}} as const const getStoryLex = {"lexicon":1,"id":"social.grain.unspecced.getStory","defs":{"main":{"type":"query","parameters":{"type":"params","required":["story"],"properties":{"story":{"type":"string","format":"at-uri"}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"story":{"type":"ref","ref":"social.grain.story.defs#storyView"}}}}}}} as const const getStoryArchiveLex = {"lexicon":1,"id":"social.grain.unspecced.getStoryArchive","defs":{"main":{"type":"query","description":"Get all stories for an actor, including expired ones. For archive browsing.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["stories"],"properties":{"stories":{"type":"array","items":{"type":"ref","ref":"social.grain.story.defs#storyView"}},"cursor":{"type":"string"}}}}}}} as const const getStoryAuthorsLex = {"lexicon":1,"id":"social.grain.unspecced.getStoryAuthors","defs":{"main":{"type":"query","description":"Get authors who have active stories (posted within the last 24 hours).","output":{"encoding":"application/json","schema":{"type":"object","required":["authors"],"properties":{"authors":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getStoryAuthors#storyAuthor"}}}}}},"storyAuthor":{"type":"object","required":["profile","storyCount","latestAt"],"properties":{"profile":{"type":"ref","ref":"social.grain.actor.defs#profileView"},"storyCount":{"type":"integer"},"latestAt":{"type":"string","format":"datetime"},"lastViewedAt":{"type":"string","format":"datetime","description":"createdAt of the newest of this author's live stories the requesting account has watched. Compare against latestAt to tell whether the viewer is caught up. Only present for an authenticated viewer who has watched at least one."},"unviewedCount":{"type":"integer","description":"How many of this author's live stories the requesting account has not watched. Only present for an authenticated viewer."}}}}} as const const getSuggestedFollowsLex = {"lexicon":1,"id":"social.grain.unspecced.getSuggestedFollows","defs":{"main":{"type":"query","description":"Get suggested profiles to follow based on bsky follow graph.","parameters":{"type":"params","required":["actor"],"properties":{"actor":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":20,"default":10}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getSuggestedFollows#suggestedItem"}}}}}},"suggestedItem":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"},"followersCount":{"type":"integer"}}}}} as const const joinGroupLex = {"lexicon":1,"id":"social.grain.unspecced.joinGroup","defs":{"main":{"type":"procedure","description":"Ask a group's community host to admit the viewer: Grain mints service auth for the host from the viewer's PDS and calls community.opensocial.requestJoin. Admitted immediately when the group is open; queued for its moderators when it takes requests.","input":{"encoding":"application/json","schema":{"type":"object","required":["group"],"properties":{"group":{"type":"string","format":"did"},"message":{"type":"string","maxLength":1000}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["status"],"properties":{"status":{"type":"string","knownValues":["admitted","pending"]}}}}}}} as const const leaveGroupLex = {"lexicon":1,"id":"social.grain.unspecced.leaveGroup","defs":{"main":{"type":"procedure","description":"Leave a group: community.opensocial.leaveCommunity on its host, with service auth from the viewer's PDS.","input":{"encoding":"application/json","schema":{"type":"object","required":["group"],"properties":{"group":{"type":"string","format":"did"}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const listGroupsLex = {"lexicon":1,"id":"social.grain.unspecced.listGroups","defs":{"main":{"type":"query","description":"Groups worth browsing, most recently active first. With `gallery`, each group carries the viewer's standing for that gallery.","parameters":{"type":"params","properties":{"gallery":{"type":"string","format":"at-uri"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50},"cursor":{"type":"string"}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["groups"],"properties":{"groups":{"type":"array","items":{"type":"ref","ref":"social.grain.group.defs#groupView"}},"cursor":{"type":"string"}}}}}}} as const const listPoolFeedLex = {"lexicon":1,"id":"social.grain.unspecced.listPoolFeed","defs":{"main":{"type":"query","description":"Every gallery in every pool the viewer is a member of, newest first. Assembled per viewer at request time: which communities they belong to is a public fact in the index, but what is in each pool is a permissioned space, read with a credential that community's host issues. Nothing here is shared between viewers or cached.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":100,"default":30}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["galleries","groups"],"properties":{"galleries":{"type":"array","items":{"type":"ref","ref":"#poolFeedItem"}},"groups":{"type":"array","description":"The pools these came out of, so a card can say whose it is.","items":{"type":"ref","ref":"social.grain.group.defs#groupView"}}}}},"errors":[{"name":"NotAuthorized","description":"No pool the viewer belongs to would answer."}]},"poolFeedItem":{"type":"object","required":["space","group","did","rkey","title","photoCount","items"],"properties":{"space":{"type":"string"},"group":{"type":"string","format":"did","description":"Whose pool it is in."},"did":{"type":"string","format":"did","description":"Whose gallery it is."},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string","description":"The author's Grain profile picture, a public record of their own."},"rkey":{"type":"string"},"title":{"type":"string"},"description":{"type":"string"},"createdAt":{"type":"string","format":"datetime"},"photoCount":{"type":"integer"},"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.getPrivateGallery#privateItem"}},"uri":{"type":"string","format":"at-uri","description":"What a favourite or a comment names."},"favCount":{"type":"integer"},"viewerFav":{"type":"string"},"commentCount":{"type":"integer"}}}}} as const const listPoolGalleriesLex = {"lexicon":1,"id":"social.grain.unspecced.listPoolGalleries","defs":{"main":{"type":"query","description":"Every gallery in a community's pool, newest first. Assembled at request time from the repos of the members who wrote them — a pool space never reaches a firehose, so none of it is in the index — and readable only by a member the community's host issues a credential to.","parameters":{"type":"params","required":["group"],"properties":{"group":{"type":"string","format":"did"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":50}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["space","galleries"],"properties":{"space":{"type":"string"},"galleries":{"type":"array","items":{"type":"ref","ref":"#poolGallery"}}}}},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this pool."}]},"poolGallery":{"type":"object","required":["space","did","rkey","title","photoCount"],"properties":{"space":{"type":"string"},"did":{"type":"string","format":"did","description":"Whose gallery it is."},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string","description":"The author's Grain profile picture, a public record of their own."},"rkey":{"type":"string"},"title":{"type":"string"},"description":{"type":"string"},"createdAt":{"type":"string","format":"datetime"},"photoCount":{"type":"integer"},"cover":{"type":"ref","ref":"social.grain.unspecced.getPrivateGallery#privateItem"},"uri":{"type":"string","format":"at-uri","description":"What a favourite or a comment names."},"favCount":{"type":"integer"},"viewerFav":{"type":"string"},"commentCount":{"type":"integer"}}}}} as const const listPrivateGalleriesLex = {"lexicon":1,"id":"social.grain.unspecced.listPrivateGalleries","defs":{"main":{"type":"query","description":"The viewer's own private galleries, read from the spaces their PDS holds. Authors only: a space tells its members nothing about itself, so an account added to someone else's gallery cannot enumerate it and needs the link.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":100,"default":50}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["galleries"],"properties":{"galleries":{"type":"array","items":{"type":"ref","ref":"#privateGalleryRef"}}}}}},"privateGalleryRef":{"type":"object","required":["space","skey"],"properties":{"space":{"type":"string","description":"Space URI the gallery lives in."},"skey":{"type":"string","description":"Also the gallery record's rkey."},"title":{"type":"string"},"createdAt":{"type":"string","format":"datetime"}}}}} as const const listSharedGalleriesLex = {"lexicon":1,"id":"social.grain.unspecced.listSharedGalleries","defs":{"main":{"type":"query","description":"Private galleries other accounts have shared with the viewer. Answered from grain's own record of who a gallery was shared with, because a space leaves no trace on a member's PDS — then confirmed against the authority, so a gallery the viewer was removed from does not appear.","parameters":{"type":"params","properties":{"limit":{"type":"integer","minimum":1,"maximum":50,"default":25}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["galleries"],"properties":{"galleries":{"type":"array","items":{"type":"ref","ref":"#sharedGalleryRef"}}}}}},"sharedGalleryRef":{"type":"object","required":["space","skey","author"],"properties":{"space":{"type":"string"},"skey":{"type":"string"},"author":{"type":"string","format":"did"},"authorHandle":{"type":"string"},"title":{"type":"string"},"createdAt":{"type":"string","format":"datetime"}}}}} as const const markStoriesViewedLex = {"lexicon":1,"id":"social.grain.unspecced.markStoriesViewed","defs":{"main":{"type":"procedure","description":"Record that the requesting account has watched these stories. Viewed state is private to the viewer and held by the appview, not written to the repo, so it follows the account across web, iOS and Android without being visible to anyone else.","input":{"encoding":"application/json","schema":{"type":"object","required":["stories"],"properties":{"stories":{"type":"array","description":"AT URIs of the stories that were watched.","items":{"type":"string","format":"at-uri"},"minLength":1,"maxLength":100}}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{}}}}}} as const const putPoolFavoriteLex = {"lexicon":1,"id":"social.grain.unspecced.putPoolFavorite","defs":{"main":{"type":"procedure","description":"Favourite, or unfavourite, a gallery in a community's pool. The record is the viewer's own, written into the pool rather than their public repo: in the public repo it would name a private gallery to the whole network.","input":{"encoding":"application/json","schema":{"type":"object","required":["group","gallery","on"],"properties":{"group":{"type":"string","format":"did"},"gallery":{"type":"string","format":"at-uri","description":"The gallery being favourited, by the uri it would have in its author's repo."},"on":{"type":"boolean"}}}},"output":{"encoding":"application/json","schema":{"type":"object","required":["on"],"properties":{"on":{"type":"boolean"},"rkey":{"type":"string","description":"The favourite record, when there is one."}}}},"errors":[{"name":"NotAuthorized","description":"The viewer is not a member of this pool."}]}}} as const const searchActorsTypeaheadLex = {"lexicon":1,"id":"social.grain.unspecced.searchActorsTypeahead","defs":{"main":{"type":"query","description":"Typeahead search for actors, merging bsky and grain profiles.","parameters":{"type":"params","required":["q"],"properties":{"q":{"type":"string","description":"Search query"},"limit":{"type":"integer","minimum":1,"maximum":10,"default":5}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"actors":{"type":"array","items":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"avatar":{"type":"string"}}}}}}}}}} as const const searchGalleriesLex = {"lexicon":1,"id":"social.grain.unspecced.searchGalleries","defs":{"main":{"type":"query","description":"Full-text search for galleries, returning full gallery views.","parameters":{"type":"params","required":["q"],"properties":{"q":{"type":"string","description":"Search query"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":30},"cursor":{"type":"string"},"fuzzy":{"type":"boolean","default":true}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.gallery.defs#galleryView"}},"cursor":{"type":"string"}}}}}}} as const const searchProfilesLex = {"lexicon":1,"id":"social.grain.unspecced.searchProfiles","defs":{"main":{"type":"query","description":"Full-text search for user profiles.","parameters":{"type":"params","required":["q"],"properties":{"q":{"type":"string","description":"Search query"},"limit":{"type":"integer","minimum":1,"maximum":100,"default":30},"cursor":{"type":"string"},"fuzzy":{"type":"boolean","default":true}}},"output":{"encoding":"application/json","schema":{"type":"object","properties":{"items":{"type":"array","items":{"type":"ref","ref":"social.grain.unspecced.searchProfiles#profileSearchResult"}},"cursor":{"type":"string"}}}}},"profileSearchResult":{"type":"object","required":["did"],"properties":{"did":{"type":"string","format":"did"},"handle":{"type":"string"},"displayName":{"type":"string"},"description":{"type":"string"},"avatar":{"type":"string"}}}}} as const // ─── Type Registry ────────────────────────────────────────────────── type Registry = { 'app.bsky.actor.defs': typeof bskyActorDefsLex 'app.bsky.actor.profile': typeof bskyActorProfileLex 'app.bsky.embed.defs': typeof bskyEmbedDefsLex 'app.bsky.embed.external': typeof externalLex 'app.bsky.embed.images': typeof imagesLex 'app.bsky.embed.record': typeof recordLex 'app.bsky.embed.recordWithMedia': typeof recordWithMediaLex 'app.bsky.embed.video': typeof videoLex 'app.bsky.feed.defs': typeof bskyFeedDefsLex 'app.bsky.feed.post': typeof postLex 'app.bsky.feed.postgate': typeof postgateLex 'app.bsky.feed.threadgate': typeof threadgateLex 'app.bsky.graph.defs': typeof bskyGraphDefsLex 'app.bsky.graph.follow': typeof bskyGraphFollowLex 'app.bsky.labeler.defs': typeof bskyLabelerDefsLex 'app.bsky.notification.defs': typeof bskyNotificationDefsLex 'app.bsky.richtext.facet': typeof facetLex 'com.atproto.label.defs': typeof atprotoLabelDefsLex 'com.atproto.moderation.defs': typeof atprotoModerationDefsLex 'com.atproto.repo.strongRef': typeof strongRefLex 'com.germnetwork.declaration': typeof germnetworkDeclarationLex 'community.lexicon.location.address': typeof addressLex 'community.lexicon.location.geo': typeof geoLex 'community.lexicon.location.hthree': typeof hthreeLex 'community.opensocial.declaration': typeof opensocialDeclarationLex 'community.opensocial.member': typeof memberLex 'community.opensocial.profile': typeof opensocialProfileLex 'community.opensocial.rule': typeof ruleLex 'dev.hatk.applyWrites': typeof applyWritesLex 'dev.hatk.createRecord': typeof createRecordLex 'dev.hatk.createReport': typeof createReportLex 'dev.hatk.deleteRecord': typeof deleteRecordLex 'dev.hatk.describeCollections': typeof describeCollectionsLex 'dev.hatk.describeFeeds': typeof describeFeedsLex 'dev.hatk.describeLabels': typeof describeLabelsLex 'dev.hatk.getFeed': typeof getFeedLex 'dev.hatk.getPreferences': typeof getPreferencesLex 'dev.hatk.getRecord': typeof getRecordLex 'dev.hatk.getRecords': typeof getRecordsLex 'dev.hatk.putPreference': typeof putPreferenceLex 'dev.hatk.putRecord': typeof putRecordLex 'dev.hatk.searchRecords': typeof searchRecordsLex 'dev.hatk.uploadBlob': typeof uploadBlobLex 'parts.page.mention.search': typeof searchLex 'social.grain.actor.defs': typeof grainActorDefsLex 'social.grain.actor.profile': typeof grainActorProfileLex 'social.grain.comment': typeof commentLex 'social.grain.comment.defs': typeof grainCommentDefsLex 'social.grain.defs': typeof grainDefsLex 'social.grain.favorite': typeof favoriteLex 'social.grain.gallery': typeof galleryLex 'social.grain.gallery.defs': typeof grainGalleryDefsLex 'social.grain.gallery.item': typeof grainGalleryItemLex 'social.grain.graph.block': typeof blockLex 'social.grain.graph.follow': typeof grainGraphFollowLex 'social.grain.graph.muteActor': typeof muteActorLex 'social.grain.graph.unmuteActor': typeof unmuteActorLex 'social.grain.group.decline': typeof declineLex 'social.grain.group.defs': typeof grainGroupDefsLex 'social.grain.group.item': typeof grainGroupItemLex 'social.grain.group.submission': typeof submissionLex 'social.grain.photo': typeof photoLex 'social.grain.photo.defs': typeof grainPhotoDefsLex 'social.grain.photo.exif': typeof exifLex 'social.grain.story': typeof storyLex 'social.grain.story.defs': typeof grainStoryDefsLex 'social.grain.unspecced.addSpaceMember': typeof addSpaceMemberLex 'social.grain.unspecced.createPoolComment': typeof createPoolCommentLex 'social.grain.unspecced.createPoolGallery': typeof createPoolGalleryLex 'social.grain.unspecced.createPrivateGallery': typeof createPrivateGalleryLex 'social.grain.unspecced.deleteAccount': typeof deleteAccountLex 'social.grain.unspecced.deleteGallery': typeof deleteGalleryLex 'social.grain.unspecced.deletePoolComment': typeof deletePoolCommentLex 'social.grain.unspecced.getActorFavorites': typeof getActorFavoritesLex 'social.grain.unspecced.getActorProfile': typeof getActorProfileLex 'social.grain.unspecced.getBlocks': typeof getBlocksLex 'social.grain.unspecced.getCameras': typeof getCamerasLex 'social.grain.unspecced.getCommentThread': typeof getCommentThreadLex 'social.grain.unspecced.getFollowers': typeof getFollowersLex 'social.grain.unspecced.getFollowing': typeof getFollowingLex 'social.grain.unspecced.getGallery': typeof getGalleryLex 'social.grain.unspecced.getGalleryFavorites': typeof getGalleryFavoritesLex 'social.grain.unspecced.getGroup': typeof getGroupLex 'social.grain.unspecced.getGroupSubmissions': typeof getGroupSubmissionsLex 'social.grain.unspecced.getKnownFollowers': typeof getKnownFollowersLex 'social.grain.unspecced.getLocations': typeof getLocationsLex 'social.grain.unspecced.getMutes': typeof getMutesLex 'social.grain.unspecced.getNotifications': typeof getNotificationsLex 'social.grain.unspecced.getPoolGallery': typeof getPoolGalleryLex 'social.grain.unspecced.getPrivateBlob': typeof getPrivateBlobLex 'social.grain.unspecced.getPrivateGallery': typeof getPrivateGalleryLex 'social.grain.unspecced.getSpaceMembers': typeof getSpaceMembersLex 'social.grain.unspecced.getSpaceSupport': typeof getSpaceSupportLex 'social.grain.unspecced.getStories': typeof getStoriesLex 'social.grain.unspecced.getStory': typeof getStoryLex 'social.grain.unspecced.getStoryArchive': typeof getStoryArchiveLex 'social.grain.unspecced.getStoryAuthors': typeof getStoryAuthorsLex 'social.grain.unspecced.getSuggestedFollows': typeof getSuggestedFollowsLex 'social.grain.unspecced.joinGroup': typeof joinGroupLex 'social.grain.unspecced.leaveGroup': typeof leaveGroupLex 'social.grain.unspecced.listGroups': typeof listGroupsLex 'social.grain.unspecced.listPoolFeed': typeof listPoolFeedLex 'social.grain.unspecced.listPoolGalleries': typeof listPoolGalleriesLex 'social.grain.unspecced.listPrivateGalleries': typeof listPrivateGalleriesLex 'social.grain.unspecced.listSharedGalleries': typeof listSharedGalleriesLex 'social.grain.unspecced.markStoriesViewed': typeof markStoriesViewedLex 'social.grain.unspecced.putPoolFavorite': typeof putPoolFavoriteLex 'social.grain.unspecced.searchActorsTypeahead': typeof searchActorsTypeaheadLex 'social.grain.unspecced.searchGalleries': typeof searchGalleriesLex 'social.grain.unspecced.searchProfiles': typeof searchProfilesLex } // ─── Record & Method Types ────────────────────────────────────────── export type BskyActorProfile = Prettify> export type Post = Prettify> export type Postgate = Prettify> export type Threadgate = Prettify> export type BskyGraphFollow = Prettify> export type GermnetworkDeclaration = Prettify> export type OpensocialDeclaration = Prettify> export type Member = Prettify> export type OpensocialProfile = Prettify> export type Rule = Prettify> export type ApplyWrites = Prettify> export type CreateReport = Prettify> export type DescribeCollections = Prettify> export type DescribeFeeds = Prettify> export type DescribeLabels = Prettify> export type GetFeed = Prettify> export type GetPreferences = Prettify> export type GetRecord = Prettify> export type GetRecords = Prettify> export type PutPreference = Prettify> export type SearchRecords = Prettify> export type UploadBlob = Prettify> export type Search = Prettify> export type GrainActorProfile = Prettify> export type Comment = Prettify> export type Favorite = Prettify> export type Gallery = Prettify> export type GrainGalleryItem = Prettify> export type Block = Prettify> export type GrainGraphFollow = Prettify> export type MuteActor = Prettify> export type UnmuteActor = Prettify> export type Decline = Prettify> export type GrainGroupItem = Prettify> export type Submission = Prettify> export type Photo = Prettify> export type Exif = Prettify> export type Story = Prettify> export type AddSpaceMember = Prettify> export type CreatePoolComment = Prettify> export type CreatePoolGallery = Prettify> export type CreatePrivateGallery = Prettify> export type DeleteAccount = Prettify> export type DeleteGallery = Prettify> export type DeletePoolComment = Prettify> export type GetActorFavorites = Prettify> export type GetActorProfile = Prettify> export type GetBlocks = Prettify> export type GetCameras = Prettify> export type GetCommentThread = Prettify> export type GetFollowers = Prettify> export type GetFollowing = Prettify> export type GetGallery = Prettify> export type GetGalleryFavorites = Prettify> export type GetGroup = Prettify> export type GetGroupSubmissions = Prettify> export type GetKnownFollowers = Prettify> export type GetLocations = Prettify> export type GetMutes = Prettify> export type GetNotifications = Prettify> export type GetPoolGallery = Prettify> export type GetPrivateBlob = Prettify> export type GetPrivateGallery = Prettify> export type GetSpaceMembers = Prettify> export type GetSpaceSupport = Prettify> export type GetStories = Prettify> export type GetStory = Prettify> export type GetStoryArchive = Prettify> export type GetStoryAuthors = Prettify> export type GetSuggestedFollows = Prettify> export type JoinGroup = Prettify> export type LeaveGroup = Prettify> export type ListGroups = Prettify> export type ListPoolFeed = Prettify> export type ListPoolGalleries = Prettify> export type ListPrivateGalleries = Prettify> export type ListSharedGalleries = Prettify> export type MarkStoriesViewed = Prettify> export type PutPoolFavorite = Prettify> export type SearchActorsTypeahead = Prettify> export type SearchGalleries = Prettify> export type SearchProfiles = Prettify> export type RecordRegistry = { 'app.bsky.actor.profile': BskyActorProfile 'app.bsky.feed.post': Post 'app.bsky.feed.postgate': Postgate 'app.bsky.feed.threadgate': Threadgate 'app.bsky.graph.follow': BskyGraphFollow 'com.germnetwork.declaration': GermnetworkDeclaration 'community.opensocial.declaration': OpensocialDeclaration 'community.opensocial.member': Member 'community.opensocial.profile': OpensocialProfile 'community.opensocial.rule': Rule 'social.grain.actor.profile': GrainActorProfile 'social.grain.comment': Comment 'social.grain.favorite': Favorite 'social.grain.gallery': Gallery 'social.grain.gallery.item': GrainGalleryItem 'social.grain.graph.block': Block 'social.grain.graph.follow': GrainGraphFollow 'social.grain.group.decline': Decline 'social.grain.group.item': GrainGroupItem 'social.grain.group.submission': Submission 'social.grain.photo': Photo 'social.grain.photo.exif': Exif 'social.grain.story': Story } export type CreateRecord = { params: {} input: { [K in keyof RecordRegistry]: { collection: K; record: RecordRegistry[K]; repo?: string } }[keyof RecordRegistry] output: { uri?: string; cid?: string } } export type DeleteRecord = { params: {} input: { [K in keyof RecordRegistry]: { collection: K; rkey: string } }[keyof RecordRegistry] output: {} } export type PutRecord = { params: {} input: { [K in keyof RecordRegistry]: { collection: K; rkey: string; record: RecordRegistry[K]; repo?: string } }[keyof RecordRegistry] output: { uri?: string; cid?: string } } // ─── Named Defs (Views, Objects) ──────────────────────────────────── export type Nux = Prettify> export type MutedWord = Prettify> export type SavedFeed = Prettify> export type StatusView = Prettify> export type BskyActorDefsProfileView = Prettify> export type BskyActorDefsViewerState = Prettify> export type FeedViewPref = Prettify> export type LabelersPref = Prettify> export type InterestsPref = Prettify> export type KnownFollowers = Prettify> export type MutedWordsPref = Prettify> export type SavedFeedsPref = Prettify> export type ThreadViewPref = Prettify> export type DeclaredAgePref = Prettify> export type HiddenPostsPref = Prettify> export type LabelerPrefItem = Prettify> export type AdultContentPref = Prettify> export type BskyAppStatePref = Prettify> export type ContentLabelPref = Prettify> export type ProfileViewBasic = Prettify> export type SavedFeedsPrefV2 = Prettify> export type VerificationView = Prettify> export type ProfileAssociated = Prettify> export type VerificationPrefs = Prettify> export type VerificationState = Prettify> export type PersonalDetailsPref = Prettify> export type BskyActorDefsProfileViewDetailed = Prettify> export type BskyAppProgressGuide = Prettify> export type LiveEventPreferences = Prettify> export type ProfileAssociatedChat = Prettify> export type ProfileAssociatedGerm = Prettify> export type PostInteractionSettingsPref = Prettify> export type ProfileAssociatedActivitySubscription = Prettify> export type BskyEmbedDefsAspectRatio = Prettify> export type ExternalView = Prettify> export type External = Prettify> export type ViewExternal = Prettify> export type ImagesView = Prettify> export type Image = Prettify> export type ViewImage = Prettify> export type RecordView = Prettify> export type ViewRecord = Prettify> export type ViewBlocked = Prettify> export type ViewDetached = Prettify> export type ViewNotFound = Prettify> export type RecordWithMediaView = Prettify> export type VideoView = Prettify> export type Caption = Prettify> export type PostView = Prettify> export type BskyFeedDefsReplyRef = Prettify> export type ReasonPin = Prettify> export type BlockedPost = Prettify> export type Interaction = Prettify> export type BskyFeedDefsViewerState = Prettify> export type FeedViewPost = Prettify> export type NotFoundPost = Prettify> export type ReasonRepost = Prettify> export type BlockedAuthor = Prettify> export type GeneratorView = Prettify> export type ThreadContext = Prettify> export type ThreadViewPost = Prettify> export type ThreadgateView = Prettify> export type SkeletonFeedPost = Prettify> export type SkeletonReasonPin = Prettify> export type GeneratorViewerState = Prettify> export type SkeletonReasonRepost = Prettify> export type Entity = Prettify> export type PostReplyRef = Prettify> export type TextSlice = Prettify> export type DisableRule = Prettify> export type ListRule = Prettify> export type MentionRule = Prettify> export type FollowerRule = Prettify> export type FollowingRule = Prettify> export type ListView = Prettify> export type ListItemView = Prettify> export type Relationship = Prettify> export type ListViewBasic = Prettify> export type NotFoundActor = Prettify> export type ListViewerState = Prettify> export type StarterPackView = Prettify> export type StarterPackViewBasic = Prettify> export type LabelerView = Prettify> export type LabelerPolicies = Prettify> export type LabelerViewerState = Prettify> export type LabelerViewDetailed = Prettify> export type Preference = Prettify> export type Preferences = Prettify> export type RecordDeleted = Prettify> export type ChatPreference = Prettify> export type ActivitySubscription = Prettify> export type FilterablePreference = Prettify> export type SubjectActivitySubscription = Prettify> export type Tag = Prettify> export type Link = Prettify> export type Mention = Prettify> export type ByteSlice = Prettify> export type Label = Prettify> export type SelfLabels = Prettify> export type SelfLabel = Prettify> export type LabelValueDefinition = Prettify> export type LabelValueDefinitionStrings = Prettify> export type GermnetworkDeclarationMessageMe = Prettify> export type Create = Prettify> export type Update = Prettify> export type Delete = Prettify> export type CreateResult = Prettify> export type UpdateResult = Prettify> export type DeleteResult = Prettify> export type RepoRef = Prettify> export type LabelDefinition = Prettify> export type LabelLocale = Prettify> export type Result = Prettify> export type MentionLabel = Prettify> export type EmbedInfo = Prettify> export type SearchAspectRatio = Prettify> export type SubscopeInfo = Prettify> export type GrainActorDefsProfileView = Prettify> export type GrainActorDefsProfileViewDetailed = Prettify> export type GrainActorDefsMessageMe = Prettify> export type GrainActorDefsViewerState = Prettify> export type CommentView = Prettify> export type GrainCommentDefsViewerState = Prettify> export type GrainDefsAspectRatio = Prettify> export type GalleryView = Prettify> export type CrossPostInfo = Prettify> export type GrainGalleryDefsViewerState = Prettify> export type GroupView = Prettify> export type GrainGroupDefsViewerState = Prettify> export type SubmissionState = Prettify> export type GroupRef = Prettify> export type SubmissionView = Prettify> export type GrainGroupDefsRule = Prettify> export type PhotoView = Prettify> export type ExifView = Prettify> export type GalleryState = Prettify> export type StoryView = Prettify> export type GrainStoryDefsViewerState = Prettify> export type CreatePoolGalleryPhotoInput = Prettify> export type CreatePrivateGalleryPhotoInput = Prettify> export type BlockItem = Prettify> export type CameraItem = Prettify> export type GetFollowersFollowerItem = Prettify> export type GetFollowersViewerState = Prettify> export type FollowingItem = Prettify> export type GetFollowingViewerState = Prettify> export type FavoriteItem = Prettify> export type GetKnownFollowersFollowerItem = Prettify> export type LocationItem = Prettify> export type MuteItem = Prettify> export type NotificationItem = Prettify> export type PoolComment = Prettify> export type PoolAuthor = Prettify> export type PrivateGallery = Prettify> export type PrivateItem = Prettify> export type MemberView = Prettify> export type StoryAuthor = Prettify> export type SuggestedItem = Prettify> export type PoolFeedItem = Prettify> export type PoolGallery = Prettify> export type PrivateGalleryRef = Prettify> export type SharedGalleryRef = Prettify> export type ProfileSearchResult = Prettify> // ─── XRPC Schema ──────────────────────────────────────────────────── export type XrpcSchema = { 'dev.hatk.applyWrites': ApplyWrites 'dev.hatk.createRecord': CreateRecord 'dev.hatk.createReport': CreateReport 'dev.hatk.deleteRecord': DeleteRecord 'dev.hatk.describeCollections': DescribeCollections 'dev.hatk.describeFeeds': DescribeFeeds 'dev.hatk.describeLabels': DescribeLabels 'dev.hatk.getFeed': GetFeed 'dev.hatk.getPreferences': GetPreferences 'dev.hatk.getRecord': GetRecord 'dev.hatk.getRecords': GetRecords 'dev.hatk.putPreference': PutPreference 'dev.hatk.putRecord': PutRecord 'dev.hatk.searchRecords': SearchRecords 'dev.hatk.uploadBlob': UploadBlob 'parts.page.mention.search': Search 'social.grain.graph.muteActor': MuteActor 'social.grain.graph.unmuteActor': UnmuteActor 'social.grain.unspecced.addSpaceMember': AddSpaceMember 'social.grain.unspecced.createPoolComment': CreatePoolComment 'social.grain.unspecced.createPoolGallery': CreatePoolGallery 'social.grain.unspecced.createPrivateGallery': CreatePrivateGallery 'social.grain.unspecced.deleteAccount': DeleteAccount 'social.grain.unspecced.deleteGallery': DeleteGallery 'social.grain.unspecced.deletePoolComment': DeletePoolComment 'social.grain.unspecced.getActorFavorites': GetActorFavorites 'social.grain.unspecced.getActorProfile': GetActorProfile 'social.grain.unspecced.getBlocks': GetBlocks 'social.grain.unspecced.getCameras': GetCameras 'social.grain.unspecced.getCommentThread': GetCommentThread 'social.grain.unspecced.getFollowers': GetFollowers 'social.grain.unspecced.getFollowing': GetFollowing 'social.grain.unspecced.getGallery': GetGallery 'social.grain.unspecced.getGalleryFavorites': GetGalleryFavorites 'social.grain.unspecced.getGroup': GetGroup 'social.grain.unspecced.getGroupSubmissions': GetGroupSubmissions 'social.grain.unspecced.getKnownFollowers': GetKnownFollowers 'social.grain.unspecced.getLocations': GetLocations 'social.grain.unspecced.getMutes': GetMutes 'social.grain.unspecced.getNotifications': GetNotifications 'social.grain.unspecced.getPoolGallery': GetPoolGallery 'social.grain.unspecced.getPrivateBlob': GetPrivateBlob 'social.grain.unspecced.getPrivateGallery': GetPrivateGallery 'social.grain.unspecced.getSpaceMembers': GetSpaceMembers 'social.grain.unspecced.getSpaceSupport': GetSpaceSupport 'social.grain.unspecced.getStories': GetStories 'social.grain.unspecced.getStory': GetStory 'social.grain.unspecced.getStoryArchive': GetStoryArchive 'social.grain.unspecced.getStoryAuthors': GetStoryAuthors 'social.grain.unspecced.getSuggestedFollows': GetSuggestedFollows 'social.grain.unspecced.joinGroup': JoinGroup 'social.grain.unspecced.leaveGroup': LeaveGroup 'social.grain.unspecced.listGroups': ListGroups 'social.grain.unspecced.listPoolFeed': ListPoolFeed 'social.grain.unspecced.listPoolGalleries': ListPoolGalleries 'social.grain.unspecced.listPrivateGalleries': ListPrivateGalleries 'social.grain.unspecced.listSharedGalleries': ListSharedGalleries 'social.grain.unspecced.markStoriesViewed': MarkStoriesViewed 'social.grain.unspecced.putPoolFavorite': PutPoolFavorite 'social.grain.unspecced.searchActorsTypeahead': SearchActorsTypeahead 'social.grain.unspecced.searchGalleries': SearchGalleries 'social.grain.unspecced.searchProfiles': SearchProfiles } // ─── XRPC Helpers ─────────────────────────────────────────────────── export type { BaseContext, Row } from '@hatk/hatk/feeds' export { InvalidRequestError, NotFoundError } from '@hatk/hatk/xrpc' export { defineSetup } from '@hatk/hatk/setup' export { defineHook } from '@hatk/hatk/hooks' export { defineLabel } from '@hatk/hatk/labels' export { defineOG } from '@hatk/hatk/opengraph' export { defineRenderer } from '@hatk/hatk/renderer' export type Ctx = XrpcContext< LexServerParams, RecordRegistry, K extends keyof XrpcSchema ? InputOf : unknown > type OutputOf = XrpcSchema[K]['output'] type InputOf = XrpcSchema[K] extends { input: infer I } ? I : unknown export function defineQuery( nsid: K, handler: (ctx: Ctx & { ok: >(value: StrictArg>) => Checked> }) => Promise>>, ) { return { __type: 'query' as const, nsid, handler: (ctx: any) => handler({ ...ctx, ok: (v: any) => v }) } } export function defineProcedure( nsid: K, handler: (ctx: Ctx & { ok: >(value: StrictArg>) => Checked> }) => Promise>>, ) { return { __type: 'procedure' as const, nsid, handler: (ctx: any) => handler({ ...ctx, ok: (v: any) => v }) } } // ─── Server-side XRPC Caller ──────────────────────────────────────── type ExtractParams = T extends { params: infer P } ? P : Record export async function callXrpc( nsid: K, params?: ExtractParams, ): Promise> { return _callXrpc(nsid, params as any) as Promise> } // ─── Feed & Seed Helpers ──────────────────────────────────────────── type FeedGenerate = (ctx: FeedContext & { ok: (value: FeedResult) => Checked }) => Promise> export function defineFeed( opts: { collection: K; view?: string; label: string; generate: FeedGenerate; hydrate?: (ctx: BaseContext, items: Row[]) => Promise } ): ReturnType export function defineFeed( opts: { collection?: never; view?: never; label: string; generate: FeedGenerate; hydrate: (ctx: BaseContext, items: Row[]) => Promise } ): ReturnType export function defineFeed(opts: any) { return _defineFeed(opts) } export function seed(opts?: SeedOpts) { return _seed(opts) } // View identity helpers — wrap object literals to enable excess property checking. // Usage: rows.map(r => views.statusView({ ...fields })) catches extra properties. export const views = { statusView: (v: StatusView): StatusView => v, bskyActorDefsProfileView: (v: BskyActorDefsProfileView): BskyActorDefsProfileView => v, profileViewBasic: (v: ProfileViewBasic): ProfileViewBasic => v, verificationView: (v: VerificationView): VerificationView => v, bskyActorDefsProfileViewDetailed: (v: BskyActorDefsProfileViewDetailed): BskyActorDefsProfileViewDetailed => v, postView: (v: PostView): PostView => v, generatorView: (v: GeneratorView): GeneratorView => v, threadgateView: (v: ThreadgateView): ThreadgateView => v, listView: (v: ListView): ListView => v, listItemView: (v: ListItemView): ListItemView => v, listViewBasic: (v: ListViewBasic): ListViewBasic => v, starterPackView: (v: StarterPackView): StarterPackView => v, starterPackViewBasic: (v: StarterPackViewBasic): StarterPackViewBasic => v, labelerView: (v: LabelerView): LabelerView => v, labelerViewDetailed: (v: LabelerViewDetailed): LabelerViewDetailed => v, grainActorDefsProfileView: (v: GrainActorDefsProfileView): GrainActorDefsProfileView => v, grainActorDefsProfileViewDetailed: (v: GrainActorDefsProfileViewDetailed): GrainActorDefsProfileViewDetailed => v, commentView: (v: CommentView): CommentView => v, galleryView: (v: GalleryView): GalleryView => v, groupView: (v: GroupView): GroupView => v, submissionView: (v: SubmissionView): SubmissionView => v, photoView: (v: PhotoView): PhotoView => v, exifView: (v: ExifView): ExifView => v, storyView: (v: StoryView): StoryView => v, memberView: (v: MemberView): MemberView => v, } as const