Delegate independent tasks to specialized agents working concurrently with isolated context.
Account & Local Cache State
account-state
Account state and in-memory event store patterns in Amethyst. Use when working with `Account.kt` (per-user StateFlow properties — follow list, relays, settings, mutes, bookmarks), `LocalCache` (the object-level event store backed by `LargeCache`), `User`/`Note` model classes, or any ViewModel tha...
SKILL.md
Full skill instructions
Account & Local Cache State
The backbone of Amethyst's client state: one Account per signed-in user, plus the singleton LocalCache that holds every Note and User the client has seen.
When to Use This Skill
- Working on
amethyst/src/main/java/com/vitorpamplona/amethyst/model/Account.kt - Working on
amethyst/src/main/java/com/vitorpamplona/amethyst/model/LocalCache.kt - Adding a new account-scoped setting (mutes, bookmarks, custom relay lists, private lists)
- Reading/writing user metadata (
User) or note state (Note) - Deciding whether to query
LocalCachevs subscribe to anAccountStateFlow
Mental Model
Relay frame ──► LocalCache.insertOrUpdateNote() ──► LocalCacheFlow emits change
│
▼
Account observes relevant kinds (3, 10002, 10000, …)
│
▼
Account StateFlow updates (followList, relays, mutes, …)
│
▼
ViewModels collect
│
▼
Composables render
LocalCache is the event store. Account is the derived per-user view (follow list, relays, mutes, emojis, bookmarks, etc.). UI listens to Account's StateFlows, not directly to LocalCache, except for note-level rendering.
Key Files
Account.kt (singleton-per-session)
class Account(...)— holds 50+ StateFlow properties, each wired to a specific Nostr kind:followListFlow← NIP-02 ContactList (kind 3)relayListFlow← NIP-65 RelayList (kind 10002)muteListFlow← NIP-51 Lists (kind 10000)bookmarkListFlow← NIP-51 Lists (kind 10003)topNavFeedsFlow,marmotGroupsFlow,customEmojisFlow,privateBookmarksFlow, etc.- Settings:
defaultZapAmountsFlow,theme,language,proxyFlow,showSensitiveContentFlow, …
- Each flow has a private
MutableStateFlowand a public read-onlyStateFlowview. Mutation goes through specific methods (sendPost,follow(pubKey),addBookmark(...)) that both update the flow and publish the signed replaceable event. - Uses
CoroutinesExt.launchIOfor network / crypto; UI reads viacollectAsStateWithLifecycleon Android andcollectAsStateon Desktop. - Sibling files per feature live alongside:
AccountSettings.kt,AccountSyncedSettings.kt, plus per-NIP state objects undermodel/nip02FollowLists/,model/nip51Lists/,model/nip65RelayList/, etc.
LocalCache.kt
object LocalCache : ILocalCache, ICacheProvider— the singleton event store.- Primary structures (all
LargeCache— seenostr-expert/references/large-cache.md):notes: LargeCache<HexKey, Note>— every seen event (regular + addressable + replaceable) keyed by id or d-address.users: LargeCache<HexKey, User>— every seen pubkey, lazily populated.addressables: LargeCache<Address, Note>— secondary index forkind:pubkey:d-taglookups.channels,deletionIndex,hashtagIndex, …
LocalCacheFlowemits coarse-grained "something changed, recheck" signals. Fine-grained reactivity lives inAccount's per-kind StateFlows.- Eviction is driven by
MemoryTrimmingService(android service) under pressure.
Model classes
User.kt— mutable profile holder. Contains metadata, follow/follower counts, relay lists, liveset of notes authored.Note.kt— mutable note holder. Contains the underlyingEvent, replies, reactions, zaps. Mutation viaaddReply,addReaction,addZap, emitted onNote.flowSetflows.Constants.kt— DEFAULT_RELAYS, magic kinds/limits not covered by quartz.
Adding a New Account-Scoped Setting
Typical recipe:
- If the setting is persisted as a Nostr event, pick the right kind (e.g. NIP-51 list, NIP-78 app-specific data, NIP-65 relay list).
- Add a model folder under
amethyst/.../model/nipXX…/with anExtState/builder class if needed. - In
Account.kt:- Add a private
MutableStateFlow<T>. - Expose a
StateFlow<T>read view. - Subscribe to the relay (via the relayClient subscription pattern — see
relay-clientskill). - On event arrival, parse with the quartz event class and update the flow.
- Write a mutation method (
updateX(...)) that builds a new event via the correspondingTagArrayBuilder, signs throughNostrSigner, and publishes.
- Add a private
- Add UI that
collects the flow. Settings screens live inamethyst/.../ui/screen/loggedIn/settings/.
LocalCache vs Account Flow — Which to Read?
- Are you rendering a specific note / user you hold an id for? →
LocalCache.getOrCreateNote(id)+ collectnote.flowSet.metadata. - Are you rendering "my follows", "my mutes", "my relays"? →
Account.<featureFlow>. - Are you rendering a feed? → Use a
FeedFilter+FeedViewModel(seefeed-patternsskill). Don't scanLocalCachein a composable.
Gotchas
LocalCacheis a singleton across accounts. Switching accounts doesn't wipe it —Accountre-derives its flows from the same cache.- Don't store Flows inside
Note/Userexpecting them to survive eviction. Eviction drops the whole object. - Mutations to
Accountflows must also publish the signing event. A flow update without a publish means other clients won't see it. Noteis mutable — treat instances as identity-based (same id → same Note). Use.flowSetwhen you need reactive state.MemoryTrimmingServicecan evict aggressively on Android under pressure. Don't assume a previously-seen note is still resident.
References
references/account-state-flow.md— catalog of majorAccountStateFlow properties and their source kinds.references/local-cache.md—LocalCacheinternals, insertion path, indexes.- Complements:
nostr-expert(event parsing),relay-client(subscription wiring),feed-patterns(how feeds consume this state),auth-signers(how mutation signs events).
More Other skills
brand-guidelines
Applies Anthropic's official brand colors and typography to any sort of artifact that may benefit from having Anthropic's look-and-feel. Use it when brand colors or style guidelines, visual formatting, or company design standards apply.
theme-factory
Toolkit for styling artifacts with a theme. These artifacts can be slides, docs, reportings, HTML landing pages, etc. There are 10 pre-set themes with colors/fonts that you can apply to any artifact that has been creating, or can generate a new theme on-the-fly.
internal-comms
A set of resources to help me write all kinds of internal communications, using the formats that my company likes to use. Claude should use this skill whenever asked to write some sort of internal communications (status reports, leadership updates, 3P updates, company newsletters, FAQs, incident reports, project updates, etc.).
Fundamental design principles for writing maintainable, testable Python code.
responsive-design
Modern responsive layouts using container queries, fluid typography, CSS Grid, and mobile-first strategies.
Generate Playwright tests from scenarios using interactive browser exploration and validation.
Automated website exploration and test case generation using Playwright.
Modern React state management with Redux Toolkit, Zustand, Jotai, and React Query for every state category.
gdpr-data-handling
GDPR-compliant data handling with consent management, data subject rights, and privacy controls.
Python error handling patterns including input validation, exception hierarchies, and partial failure handling. Use when implementing validation logic, designing exception strategies, handling batch processing failures, or building robust APIs.
refactor-plan
Detailed multi-file refactor planning with safety checks and rollback guidance.
