Skip to content

Fix XSS vulnerabilities, implement shadowban, and charge for status posts#563

Merged
asim merged 2 commits intomainfrom
claude/add-wallet-transfers-74PHC
Apr 16, 2026
Merged

Fix XSS vulnerabilities, implement shadowban, and charge for status posts#563
asim merged 2 commits intomainfrom
claude/add-wallet-transfers-74PHC

Conversation

@asim
Copy link
Copy Markdown
Member

@asim asim commented Apr 16, 2026

No description provided.

claude added 2 commits April 16, 2026 04:20
Security — XSS in status rendering:
Profile page (/@user) was injecting status text directly into HTML
without escaping. Both current status and history entries, plus the
edit form's value attribute, were vulnerable. Fixed by wrapping all
three in htmlpkg.EscapeString. The home card stream was already
escaped (RenderStatusStream uses htmlpkg.EscapeString).

Shadowban — silent platform-wide mute:
Added Account.Shadowban flag. IsShadowbanned / ShadowbanAccount /
UnshadowbanAccount in auth package. Shadowbanned users can still
browse and post, but their content is invisible to everyone else —
they don't know they're muted. Applied to:
- Status stream (StatusStreamCapped skips shadowbanned profiles)
- Social feed, replies, and card view
- Blog post listings (all five IsHidden call sites)

Auto-shadowban on moderation trigger:
moderateStatus runs flag.CheckContent asynchronously after each
status post. If the LLM classifier flags the content (SPAM, TEST,
LOW_QUALITY, HARMFUL), the user is auto-shadowbanned — their entire
account goes silent without notification. No manual admin action
needed.

AI response moderation:
ModerateAIResponse checks AI-generated @micro replies BEFORE they
are posted. If the LLM flags the response as harmful, the reply is
silently dropped and the asker (who tried to trick the AI) is
shadowbanned. The AIReplyHook also skips shadowbanned users to
avoid wasting AI credits.

Charge for status posts:
StatusHandler now requires CanPost (email verification), checks
CheckPostRate, and charges 1 credit (wallet.OpSocialPost) per
status. Clearing status (empty string) is exempt from all gates.

Admin console commands:
- shadowban <user_id> — silent mute
- unshadowban <user_id> — lift mute
- clear-status <user_id> — wipes current status + full history
- user <id> now shows shadowban status

Delete redirect bug:
The ⋯ menu's Delete action (internal/app/content.go renderMenu)
had window.location='/blog' hardcoded regardless of content type.
Changed to document.referrer||'/' so deleting a social thread
returns to the social feed, not the blog page.

https://claude.ai/code/session_01GRGLA9yj7BpqKiyi6xFwnm
Renamed Shadowban/IsShadowbanned/ShadowbanAccount throughout to
Banned/IsBanned/BanAccount. JSON field changed from 'shadowban'
to 'banned'. Admin console commands are now 'ban' and 'unban'.

Added clear-status all — wipes every user's status + history in
one command. For when the feed is full of garbage.

https://claude.ai/code/session_01GRGLA9yj7BpqKiyi6xFwnm
@asim asim merged commit c887913 into main Apr 16, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants