mirror of https://git.lenooby09.tech/LeNooby09/social-app.git
1import { 2 type $Typed, 3 type AppBskyFeedDefs, 4 type AppBskyFeedPost, 5 type AppBskyUnspeccedDefs, 6 type AppBskyUnspeccedGetPostThreadV2, 7 AtUri, 8 moderatePost, 9 type ModerationOpts, 10} from '@atproto/api' 11 12import {makeProfileLink} from '#/lib/routes/links' 13import { 14 type ApiThreadItem, 15 type ThreadItem, 16 type TraversalMetadata, 17} from '#/state/queries/usePostThread/types' 18 19export function threadPostNoUnauthenticated({ 20 uri, 21 depth, 22 value, 23}: ApiThreadItem): Extract<ThreadItem, {type: 'threadPostNoUnauthenticated'}> { 24 return { 25 type: 'threadPostNoUnauthenticated', 26 key: uri, 27 uri, 28 depth, 29 value: value as AppBskyUnspeccedDefs.ThreadItemNoUnauthenticated, 30 // @ts-ignore populated by the traversal 31 ui: {}, 32 } 33} 34 35export function threadPostNotFound({ 36 uri, 37 depth, 38 value, 39}: ApiThreadItem): Extract<ThreadItem, {type: 'threadPostNotFound'}> { 40 return { 41 type: 'threadPostNotFound', 42 key: uri, 43 uri, 44 depth, 45 value: value as AppBskyUnspeccedDefs.ThreadItemNotFound, 46 } 47} 48 49export function threadPostBlocked({ 50 uri, 51 depth, 52 value, 53}: ApiThreadItem): Extract<ThreadItem, {type: 'threadPostBlocked'}> { 54 return { 55 type: 'threadPostBlocked', 56 key: uri, 57 uri, 58 depth, 59 value: value as AppBskyUnspeccedDefs.ThreadItemBlocked, 60 } 61} 62 63export function threadPost({ 64 uri, 65 depth, 66 value, 67 moderationOpts, 68 threadgateHiddenReplies, 69}: { 70 uri: string 71 depth: number 72 value: $Typed<AppBskyUnspeccedDefs.ThreadItemPost> 73 moderationOpts: ModerationOpts 74 threadgateHiddenReplies: Set<string> 75}): Extract<ThreadItem, {type: 'threadPost'}> { 76 const moderation = moderatePost(value.post, moderationOpts) 77 const modui = moderation.ui('contentList') 78 const blurred = modui.blur || modui.filter 79 const muted = (modui.blurs[0] || modui.filters[0])?.type === 'muted' 80 const hiddenByThreadgate = threadgateHiddenReplies.has(uri) 81 const isOwnPost = value.post.author.did === moderationOpts.userDid 82 const isBlurred = (hiddenByThreadgate || blurred || muted) && !isOwnPost 83 return { 84 type: 'threadPost', 85 key: uri, 86 uri, 87 depth, 88 value: { 89 ...value, 90 /* 91 * Do not spread anything here, load bearing for post shadow strict 92 * equality reference checks. 93 */ 94 post: value.post as Omit<AppBskyFeedDefs.PostView, 'record'> & { 95 record: AppBskyFeedPost.Record 96 }, 97 }, 98 isBlurred, 99 moderation, 100 // @ts-ignore populated by the traversal 101 ui: {}, 102 } 103} 104 105export function readMore({ 106 depth, 107 repliesUnhydrated, 108 skippedIndentIndices, 109 postData, 110}: TraversalMetadata): Extract<ThreadItem, {type: 'readMore'}> { 111 const urip = new AtUri(postData.uri) 112 const href = makeProfileLink( 113 { 114 did: urip.host, 115 handle: postData.authorHandle, 116 }, 117 'post', 118 urip.rkey, 119 ) 120 return { 121 type: 'readMore' as const, 122 key: `readMore:${postData.uri}`, 123 href, 124 moreReplies: repliesUnhydrated, 125 depth, 126 skippedIndentIndices, 127 } 128} 129 130export function readMoreUp({ 131 postData, 132}: TraversalMetadata): Extract<ThreadItem, {type: 'readMoreUp'}> { 133 const urip = new AtUri(postData.uri) 134 const href = makeProfileLink( 135 { 136 did: urip.host, 137 handle: postData.authorHandle, 138 }, 139 'post', 140 urip.rkey, 141 ) 142 return { 143 type: 'readMoreUp' as const, 144 key: `readMoreUp:${postData.uri}`, 145 href, 146 } 147} 148 149export function skeleton({ 150 key, 151 item, 152}: Omit<Extract<ThreadItem, {type: 'skeleton'}>, 'type'>): Extract< 153 ThreadItem, 154 {type: 'skeleton'} 155> { 156 return { 157 type: 'skeleton', 158 key, 159 item, 160 } 161} 162 163export function postViewToThreadPlaceholder( 164 post: AppBskyFeedDefs.PostView, 165): $Typed< 166 Omit<AppBskyUnspeccedGetPostThreadV2.ThreadItem, 'value'> & { 167 value: $Typed<AppBskyUnspeccedDefs.ThreadItemPost> 168 } 169> { 170 return { 171 $type: 'app.bsky.unspecced.getPostThreadV2#threadItem', 172 uri: post.uri, 173 depth: 0, // reset to 0 for highlighted post 174 value: { 175 $type: 'app.bsky.unspecced.defs#threadItemPost', 176 post, 177 opThread: false, 178 moreParents: false, 179 moreReplies: 0, 180 hiddenByThreadgate: false, 181 mutedByViewer: false, 182 }, 183 } 184}