Add a generic user avatar system with in-app profile picture controls#3549
Draft
adboio wants to merge 4 commits into
Draft
Add a generic user avatar system with in-app profile picture controls#3549adboio wants to merge 4 commits into
adboio wants to merge 4 commits into
Conversation
Resolve staff profile photos from posthog.com's public team roster and render them in the Bluebird avatar slots (channel feed facepile, system rows, thread panel, activity page, mention typeahead), falling back to the existing initials treatment whenever no confident match exists. Generated-By: PostHog Code Task-Id: 66aecb98-c55b-4516-a7aa-42c53cfa8bd2
|
Merging to
After your PR is submitted to the merge queue, this comment will be automatically updated with its status. If the PR fails, failure details will also be posted here |
|
React Doctor found no issues in the changed files. 🎉 Reviewed by React Doctor for commit |
adboio
commented
Jul 17, 2026
adboio
left a comment
Contributor
Author
There was a problem hiding this comment.
posthog agent, if you’re reading this, this is bad
i meant more like a generic profile picture solution, with perhaps a script to import the team photos automatically for internal users
Drop all posthog.com-specific avatar fetching from the app. Avatars now resolve generically: the account's own avatar_url when the backend serves one (field added to UserBasic, awaiting backend support), Gravatar by email otherwise — the same convention PostHog cloud's ProfilePicture uses — with initials as the fallback. Internal users' photos become a backend data backfill instead of client logic. Generated-By: PostHog Code Task-Id: 66aecb98-c55b-4516-a7aa-42c53cfa8bd2
2 tasks
New "Profile picture" row in General settings (flag-gated): preview via
UserAvatar, set/change with an https image URL, and remove. Saves to
the PostHog account through PATCH /api/users/@me/ {avatar_url} (new
updateCurrentUserAvatar client method; backend field lands in
PostHog/posthog#72086). UserAvatar/useUserAvatar props widen to a
structural AvatarUser so the full user object works too.
Generated-By: PostHog Code
Task-Id: 66aecb98-c55b-4516-a7aa-42c53cfa8bd2
The backend now stores profile photos on a UserPersonalization side table exposed via the org members list (and the full /@me/ user), not on UserBasic. useUserAvatar gains a members-index source (shared query key with useOrgMembers, so no extra fetch) between the user's own record and the Gravatar fallback. Generated-By: PostHog Code Task-Id: 66aecb98-c55b-4516-a7aa-42c53cfa8bd2
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
Everywhere a person shows up in the Channels (project-bluebird) space — the channel feed's reply facepile, system rows, the thread panel, the activity page, the @-mention typeahead — they render as bare initials. The app had no user avatar system, and no way for a user to set a profile picture.
Why
Requested in the project-bluebird channel: get real profile pictures showing in the Bluebird UI. The app side is a generic avatar system with no internal-user-specific logic; the photo storage is a
UserPersonalizationside table in the backend (PostHog/posthog#72086), and populating PostHog staff photos is a backfill command stacked on it (PostHog/posthog#72092).Changes
UserAvatarcomponent +useUserAvatarhook (packages/ui/src/features/avatars/): resolves a photo from (1) the user record's ownavatar_url(present on the full/@me/response), (2) the org members list — the backend exposes each member's personalizationavatar_urlthere; the hook sharesuseOrgMembers' query key so this adds no extra fetch, (3) Gravatar keyed by account email (d=404) — PostHog cloud's own convention — and finally the existing initials treatment. Wired into the five Bluebird avatar slots (feed facepile + system rows, thread panel, activity page, mention typeahead)./api/users/@me/(updateCurrentUserAvatar), so the photo follows the user across clients and is visible to teammates.OrganizationMemberBasic.avatar_urloptional field in@posthog/shared/domain-types. Until the backend PRs deploy, Gravatar is the effective source and saving from settings will 400.How did you test this?
packages/ui/src/features/avatars/useUserAvatar.test.ts).vitest run src/features/avatars src/features/canvas src/features/settingsinpackages/ui(183 passed);src/canvasinpackages/core(85 passed).pnpm --filtertypecheck for shared/core/ui/api-client, plus Biome on all touched files.Automatic notifications
Created with PostHog Code