Sign in

jenna

@jjenzz.com
338 followers 78 following 36 posts

👩🏻‍💻 codes 🤘 gigs 😴 sleeps ♻️ repeats. creating tokenami.style, previously radix-ui.com/primitives. brain dump at jjenzz.com.

PostsRepliesMedia
jenna @jjenzz.com · 05/06/2026
jjenzz.com/best-loading...
jjenzz.com
The Best Loading States Are No Loading States
Applications often end up with all sorts of UI whose sole purpose is to occupy the space where data should eventually appear. We're all spending a surprising amount of time solving the same problem, a...
1102
jenna @jjenzz.com · 24/11/2025
jjenzz.com/judging-apis...
jjenzz.com
Why Judging APIs by Syntax is Misleading You
APIs often behave very differently underneath. What matters is not just how an API looks on the surface, but also the abstraction layer it belongs to.
030
jenna @jjenzz.com · 12/09/2025
as web devs i think we all have an element of head up ass in us tbf
010
jenna @jjenzz.com · 22/05/2025
things browser natively supports yet ppl rebuild, but tbh mostly ppl just slap directive at top of large comps instead of abstracting piece that needs it. import helps here—simpler to abstract piece & import as client into original than change all imports for original.
020
jenna @jjenzz.com · 22/05/2025
from my perspective tho “flipping” things just isn’t that common, and if we do, part of that flip is to refactor imports, like any refactor, you clean up. eslint cld flag redundant client imports
100
jenna @jjenzz.com · 22/05/2025
i agree with everything you are saying tho re imports getting stuck in client, no solution is perfect here. i actually love RSC so our switch bk to SPA makes me a bit sad 😅
100
jenna @jjenzz.com · 22/05/2025
i mean ppl reach for client features immediately cos it’s easier to add directive than consider how to achieve it w/o client features. app becomes unnecessarily client heavy again, at which point the mental overhead of RSC becomes less worth dealing with. we moving bk to SPA for this reason.
100
jenna @jjenzz.com · 22/05/2025
yeh i understood the intent here but in practice i have found it bumpy, even for code i have written entirely myself. we add directive as soon as we want (not need) state. becomes a client app again bcos ppl comfortable there, instead of being deliberate. rsc feels redundant at that stage
100
jenna @jjenzz.com · 21/05/2025
exactly
100
jenna @jjenzz.com · 21/05/2025
ppl tend to resort to client features prematurely (myself incl.) so i found the plugin helps minimise that, which in my mind is a main benefit of RSC
000
jenna @jjenzz.com · 21/05/2025
i found that framing a bit awkward tbh. i don’t rlly want comp author to decide what’s in my client bundle. it wld ideally be my choice when i consume it. for example, if i import and it fails, i might rebuild it myself 1/2
200
jenna @jjenzz.com · 17/01/2025
i'll probably be the only that finds this useful but just in case—i've published a plugin for nextjs to declare a server/client boundary w/ import attributes ✨ github.com/jjenzz/next-...
0110
jenna @jjenzz.com · 21/12/2024
oh okay, i take it back 😉
010
jenna @jjenzz.com · 20/12/2024
~12 years in one spot 😳 that’s unheard of. impressive. congrats on the new gig 🎉🥂
110
jenna @jjenzz.com · 19/12/2024
yeah, i get your concern 😞 i can’t imagine you fading into obscurity tho, ariakit is awesome. i’ve recommended your lib often since radix went stale. realistically tho i doubt we’d have yet another dialog to choose from if the aim wasn’t one-to-rule-them-all
010
jenna @jjenzz.com · 19/12/2024
i’d be surprised if they didn’t take inspo here tho tbh, but ariakit is competition for them so it prolly wldn’t be the smartest business move to mention it front & centre in such a saturated comp market—the USPs are limited haha
110
jenna @jjenzz.com · 19/12/2024
reality is, we don’t _know_ if our work was the inspo. render prop has been around forever & ppl often reach same conclusions through their own exploration. reach ui tried to claim credit for radix compound design for ex, but i’d built comps that way for years and had no idea reach even existed lol
140
jenna @jjenzz.com · 19/12/2024
i hear you, ppl replace the word radix in their vocab with shadcn, even when they completely restyle it. others copied impl details we spent ages on, but i learnt to find it flattering. the swedish have a great word for this and it contributes to why they rank so high on global happiness—Jantelagen
190
jenna @jjenzz.com · 10/12/2024
similar vibes 😅
000
jenna @jjenzz.com · 07/12/2024
mine thinks i am matt so we’re off to a bad start
010
jenna @jjenzz.com · 03/12/2024
100%. i really feel it might contribute to why ppl love CSR + RQ so much. they can't reach into hoisted loaders/server easily so can't comprehend the alternative—no option but to colocate granular queries everywhere (thick clients)
010
jenna @jjenzz.com · 03/12/2024
ppl tend to do left instead of right so it's obvious why RSC is a struggle there. makes it harder to reach into server so you're inevitably fighting that friction. context is our friend here tbh—`Chat` can be a client comp w/o making `Header`, `Logo`, `Heading` one too etc.
const Page = () => <Chat />;

const Chat = () => (
  <div>
    <Header />
    <div>
      <Sidebar />
      <Main />
    </div>
  </div>
);

const Header = () => (
  <header>
    <Logo />
    <Heading />
  </header>
);

const Sidebar = () => (
  <aside>
    <ChatMenu />
  </aside>
);

const ChatMenu = () => (
  <ul>
    {items.map(item => <ChatMenuItem />)}
  </ul>
);

const ChatMenuItem = () => <li />;

const Main = () => (
  <main>
    <ChatMessages />
  </main>
)

const ChatMessages = () => (
  <div>
    {messages.map(message => <ChatMessagesItem />)}
  </div>
);

const ChatMessagesItem = () => <div />const Page = () => (
  <Chat>
    <Header>
      <Logo />
      <Heading>Title</Heading>
    </Header>
    <div>
      <Sidebar>
        <ChatMenu>
          {items.map(item => <ChatMenuItem />)}
        </ChatMenu>
      </Sidebar>
      <Main>
        <ChatMessages>
          {messages.map(message => <ChatMessagesItem />)}
        </ChatMessages>
      </Main>
    </div>
  </Chat>
);

const Header = () => <header>{children}</header>;
const Sidebar = () => <aside>{children}</aside>;
const Main = () => <main>{children}</main>;
const Chat = () => <div>{children}</div>;
const ChatMenu = () => <ul>{children}</ul>;
const ChatMenuItem = () => <li>{children}</li>;
const ChatMessages = () => <div>{children}</div>;
const ChatMessagesItem = () => <div />
040
jenna @jjenzz.com · 03/12/2024
i feel the hurdle is indeed education. i wasn’t keen on them initially or on hoisted loaders, but like both now. a huge issue today is that ppl don’t do composition well so it seems painful. when we do tho (flat owner trees), RSC is a no brainer. we need to start there w/ education imo
130
jenna @jjenzz.com · 03/12/2024
this “thick” vs “thin” terminology is fab. i keep calling it “smart” vs “dumb”. thin is the dream but tricky when optimistic updates are needed—shifts “thickness” back into client. i’m desperate for realtime RSCs 🥹
040
jenna @jjenzz.com · 24/11/2024
haha amazing 🥳
000
jenna @jjenzz.com · 24/11/2024
i believe this is what react-party was doing and no, tmk no one has "done" it already as far as making something available we can toy with 😳
110
jenna @jjenzz.com · 23/11/2024
i have just learned that Sunil parked work on it due to other commitments. tis a shame bcos it seems an obvious hole in the market that's screaming for the taking haha
210
jenna @jjenzz.com · 23/11/2024
snap, my thinking precisely
010
jenna @jjenzz.com · 23/11/2024
ah i see what you mean. yeh, doesn't make sense if you want local-first but i have issue w/ client-as-source-of-truth (+ other aspects). zerosync.dev is solving those but Sunil's react-party is what i'm really after—server-as-source-of-truth + dumb client, w/o sacrificing perf. diff levers right
310
jenna @jjenzz.com · 23/11/2024
curious how a reactive db makes HATEOAS redundant?
120
jenna @jjenzz.com · 23/11/2024
i dno, @threepointone.bsky.social has impressive demos that’d be very different, and cld eliminate a whole host of day-to-day maintenance headaches. no need to maintain RPCs, optimistic updates, client-side state, or RQ caches—realtime JSX as the HATEOAS is an area i’d love to see explored more
250
jenna @jjenzz.com · 23/11/2024
i see them as a low-level primitive w/ flexibility that allows for many interpretations. for instance, i’d love to see a framework explore restricting async RSCs to parent and nested route boundaries only, while guiding developers on composition patterns to avoid prop drilling
110
jenna @jjenzz.com · 20/11/2024
oh interesting! i’ll have to look into exstism. my thinking is more along the lines of a component definition format (like storybook CSF) w/ fns to generate fw comps from those CDFs. tricky to explain, but leaning on fws for the portability essentially storybook.js.org/docs/api/csf
storybook.js.org
Docs | Storybook
Storybook is a frontend workshop for building UI components and pages in isolation. Thousands of teams use it for UI development, testing, and documentation. It's open source and free.
010
jenna @jjenzz.com · 19/11/2024
i have, a lot, but without ShadowDOM. it’s on my todo list to build something like the example i conclude with in this blog post, so perhaps not really considered WCs but a native solution nonetheless jjenzz.com/future-for-w...
jjenzz.com
A Future for Web Components Without Shadow DOM
There’s been a lot of buzz around Web Components (WCs) lately. Are the APIs to blame, or are our expectations simply misguided?
150
jenna @jjenzz.com · 19/11/2024
i haven’t tried TanStack Start yet but do you have “type”: “module” in your package.json? if you can’t do that, maybe try vite’s “noExternal” option so vite converts it to correct format, or try dynamically importing it with React.lazy? vite.dev/config/ssr-o...
vite.dev
SSR Options
Next Generation Frontend Tooling
010
jenna @jjenzz.com · 18/11/2024
thanks chap 🥰
010