diff --git a/src/components/Note/index.tsx b/src/components/Note/index.tsx
index 15fbb5b..1098bfa 100644
--- a/src/components/Note/index.tsx
+++ b/src/components/Note/index.tsx
@@ -16,6 +16,7 @@ import Nip05 from '../Nip05'
import NoteOptions from '../NoteOptions'
import ParentNotePreview from '../ParentNotePreview'
import TranslateButton from '../TranslateButton'
+import TrustScoreBadge from '../TrustScoreBadge'
import UserAvatar from '../UserAvatar'
import Username from '../Username'
import CommunityDefinition from './CommunityDefinition'
@@ -125,6 +126,7 @@ export default function Note({
skeletonClassName={size === 'small' ? 'h-3' : 'h-4'}
/>
+
diff --git a/src/components/Profile/index.tsx b/src/components/Profile/index.tsx
index 6d98f7d..aea4e98 100644
--- a/src/components/Profile/index.tsx
+++ b/src/components/Profile/index.tsx
@@ -19,13 +19,14 @@ import { useCallback, useEffect, useMemo, useState } from 'react'
import { useTranslation } from 'react-i18next'
import NotFound from '../NotFound'
import SearchInput from '../SearchInput'
+import TextWithEmojis from '../TextWithEmojis'
+import TrustScoreBadge from '../TrustScoreBadge'
+import AvatarWithLightbox from './AvatarWithLightbox'
+import BannerWithLightbox from './BannerWithLightbox'
import FollowedBy from './FollowedBy'
import Followings from './Followings'
import ProfileFeed from './ProfileFeed'
import Relays from './Relays'
-import TextWithEmojis from '../TextWithEmojis'
-import AvatarWithLightbox from './AvatarWithLightbox'
-import BannerWithLightbox from './BannerWithLightbox'
export default function Profile({ id }: { id?: string }) {
const { t } = useTranslation()
@@ -143,6 +144,7 @@ export default function Profile({ id }: { id?: string }) {
emojis={emojis}
className="text-xl font-semibold truncate select-text"
/>
+
{isFollowingYou && (
{t('Follows you')}
diff --git a/src/components/ProfileCard/index.tsx b/src/components/ProfileCard/index.tsx
index 96e1f16..b2a4c3b 100644
--- a/src/components/ProfileCard/index.tsx
+++ b/src/components/ProfileCard/index.tsx
@@ -4,6 +4,8 @@ import { useMemo } from 'react'
import FollowButton from '../FollowButton'
import Nip05 from '../Nip05'
import ProfileAbout from '../ProfileAbout'
+import TextWithEmojis from '../TextWithEmojis'
+import TrustScoreBadge from '../TrustScoreBadge'
import { SimpleUserAvatar } from '../UserAvatar'
export default function ProfileCard({ userId }: { userId: string }) {
@@ -18,7 +20,14 @@ export default function ProfileCard({ userId }: { userId: string }) {
{about && (
diff --git a/src/components/TrustScoreBadge/index.tsx b/src/components/TrustScoreBadge/index.tsx
new file mode 100644
index 0000000..86210c8
--- /dev/null
+++ b/src/components/TrustScoreBadge/index.tsx
@@ -0,0 +1,64 @@
+import { cn } from '@/lib/utils'
+import { useNostr } from '@/providers/NostrProvider'
+import trustScoreService from '@/services/trust-score.service'
+import { AlertTriangle, ShieldAlert } from 'lucide-react'
+import { useEffect, useState } from 'react'
+import { useTranslation } from 'react-i18next'
+
+export default function TrustScoreBadge({
+ pubkey,
+ className
+}: {
+ pubkey: string
+ className?: string
+}) {
+ const { t } = useTranslation()
+ const { pubkey: currentPubkey } = useNostr()
+ const [percentile, setPercentile] = useState
(null)
+ const [loading, setLoading] = useState(true)
+
+ useEffect(() => {
+ if (currentPubkey === pubkey) {
+ setLoading(false)
+ setPercentile(null)
+ return
+ }
+
+ const fetchScore = async () => {
+ try {
+ const data = await trustScoreService.fetchTrustScore(pubkey)
+ if (data) {
+ setPercentile(data.percentile)
+ }
+ } catch (error) {
+ console.error('Failed to fetch trust score:', error)
+ } finally {
+ setLoading(false)
+ }
+ }
+
+ fetchScore()
+ }, [pubkey, currentPubkey])
+
+ if (loading || percentile === null) return null
+
+ // percentile < 50: likely spam (red alert)
+ // percentile < 75: suspicious (yellow warning)
+ if (percentile < 50) {
+ return (
+
+
+
+ )
+ }
+
+ if (percentile < 75) {
+ return (
+
+ )
+ }
+
+ return null
+}
diff --git a/src/components/UserItem/index.tsx b/src/components/UserItem/index.tsx
index 7dfc628..dc2eef6 100644
--- a/src/components/UserItem/index.tsx
+++ b/src/components/UserItem/index.tsx
@@ -7,6 +7,7 @@ import { userIdToPubkey } from '@/lib/pubkey'
import { cn } from '@/lib/utils'
import { useMemo } from 'react'
import FollowingBadge from '../FollowingBadge'
+import TrustScoreBadge from '../TrustScoreBadge'
export default function UserItem({
userId,
@@ -32,6 +33,7 @@ export default function UserItem({
skeletonClassName="h-4"
/>
{showFollowingBadge && }
+