Add cashtag support for stock ticker discussions (#9689)
* Add cashtag support for stock ticker discussions Display cashtags ($TICKER format) as clickable links with dedicated menu actions and search feed, alongside hashtags. Includes composer highlighting and proper formatting. Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com> * Fix cashtag search query to use # prefix Cashtags need to be searched as "#$BTC" rather than just "$BTC" to work with the search API. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * Update @atproto/api to 0.18.14 with cashtag support The updated package includes native CASHTAG_REGEX detection for stock ticker symbols like $AAPL and $BTC. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * Fix todo, remove redundant validation --------- Co-authored-by: Claude Haiku 4.5 <noreply@anthropic.com> Co-authored-by: Eric Bailey <git@esb.lol>
This commit is contained in:
+21
-8
@@ -46,13 +46,22 @@ export default function HashtagScreen({
|
||||
const {tag, author} = route.params
|
||||
const {_} = useLingui()
|
||||
|
||||
const fullTag = React.useMemo(() => {
|
||||
return `#${decodeURIComponent(tag)}`
|
||||
const decodedTag = React.useMemo(() => {
|
||||
return decodeURIComponent(tag)
|
||||
}, [tag])
|
||||
|
||||
const isCashtag = decodedTag.startsWith('$')
|
||||
|
||||
const fullTag = React.useMemo(() => {
|
||||
// Cashtags already include the $ prefix, hashtags need # added
|
||||
return isCashtag ? decodedTag : `#${decodedTag}`
|
||||
}, [decodedTag, isCashtag])
|
||||
|
||||
const headerTitle = React.useMemo(() => {
|
||||
return enforceLen(fullTag.toLowerCase(), 24, true, 'middle')
|
||||
}, [fullTag])
|
||||
// Keep cashtags uppercase, lowercase hashtags
|
||||
const displayTag = isCashtag ? fullTag.toUpperCase() : fullTag.toLowerCase()
|
||||
return enforceLen(displayTag, 24, true, 'middle')
|
||||
}, [fullTag, isCashtag])
|
||||
|
||||
const sanitizedAuthor = React.useMemo(() => {
|
||||
if (!author) return
|
||||
@@ -172,10 +181,14 @@ function HashtagScreenTab({
|
||||
const {hasSession} = useSession()
|
||||
const trackPostView = usePostViewTracking('Hashtag')
|
||||
|
||||
const isCashtag = fullTag.startsWith('$')
|
||||
|
||||
const queryParam = React.useMemo(() => {
|
||||
if (!author) return fullTag
|
||||
return `${fullTag} from:${author}`
|
||||
}, [fullTag, author])
|
||||
// Cashtags need # prefix for search: "#$BTC" or "#$BTC from:author"
|
||||
const searchTag = isCashtag ? `#${fullTag}` : fullTag
|
||||
if (!author) return searchTag
|
||||
return `${searchTag} from:${author}`
|
||||
}, [fullTag, author, isCashtag])
|
||||
|
||||
const {
|
||||
data,
|
||||
@@ -255,7 +268,7 @@ function HashtagScreenTab({
|
||||
isError={isError}
|
||||
onRetry={refetch}
|
||||
emptyType="results"
|
||||
emptyMessage={_(msg`We couldn't find any results for that hashtag.`)}
|
||||
emptyMessage={_(msg`We couldn't find any results for that tag.`)}
|
||||
/>
|
||||
) : (
|
||||
<List
|
||||
|
||||
Reference in New Issue
Block a user