Tailwind duct-tape wallets

Issue #442.November 20, 2025.2 Minute read.
Bytes

Today’s issue: The great UI purge, becoming an Anthropic yes-man, and just one more VS Code fork bro.

Welcome to #442.


Eyeballs logo

The Main Thing

Close up of a painting of a person crying

Trying to style a React Native app in 2025

Tailwind duct-tape wallets

React Native developers have been duct-taping Tailwind workflows into their mobile apps for years now – and just like those duct-tape wallets I used to build in middle school, the final result has usually been pretty janky.

That’s why the Unistyles team just released Uniwind, which brings true Tailwind-style className support to React Native at build time, not runtime.

It does this by shipping a custom, high-performance CSS parser that can parse the latest Tailwind 4 syntax and plain CSS files. That lets you use the same Tailwind classes and utilities for your React Native app that you would use on the web, and still get consistent cross-platform styling without needing to add a bunch of hacks and workarounds.

Here’s what else it gets you:

  • Zero-config className bindings — Every core React Native component supports className out of the box, plus extras like colorClassName for styling things that aren’t normal style props.

  • Simple multi-theming – Add unlimited light, dark, and custom themes directly in your Metro config, and Uniwind will automatically swap variables across platforms.

  • 2.5x faster than NativeWind – Uniwind uses build-time caching and a Nitro-module pipeline to avoid all runtime style parsing and per-render overhead, which means you won’t see slowdowns as your UI grows.

Bottom Line: I just came up with the perfect tagline for Uniwind that no one has ever said in the history of software: “Write once, run anywhere.” Ship it.


QA Wolf logo

Our Friends
(With Benefits)

A guy in a devil costume talking to a little kid

The devil tempting me to ship without running my team's janky test suite

Beat your EOY deadlines with QA Wolf

December ship panic is real, but QA Wolf can help your team hit its goals before the end of the year.

They provide fully automated test coverage for your web and mobile applications, so you can catch more bugs and ship faster.

Here’s how:

  • They build and maintain hundreds of automated Playwright tests for your app

  • You get unlimited parallel test runs on their infrastructure, with pass/fail results in 3 min.

  • Zero flakes, because every failed test gets reviewed by their human QA engineers

Get a personalized demo for your team – and see how they save their average customer $10,000 per engineer every month.


Pop Quiz logo

Pop Quiz

Sponsored by Sentry

They just launched AI Code Review, which lets you bring Sentry into your PRs to catch broken code before it ever hits prod.

How could this code be improved?

document.getElementById("thumbnail").addEventListener("click", () => {
  const img = new Image();
  img.src = "path_to_high_res_image.jpg";
  document.getElementById("gallery").appendChild(img);

  img.onload = async () => {
    const metadata = await fetch("path_to_metadata_API").then((res) =>
      res.json()
    );
    document.getElementById("metadata").innerText = metadata.description;
  };
});

Cool Bits logo

Cool Bits

  1. Cloudflare CEO, Matthew Prince wrote a debrief on Tuesday’s massive outage. I was a little surprised when he blamed everything on Rust furries developers, but I’m sure his crisis PR team had their reasons.

  2. GitHub is removing all toasts from their UI because of the accessibility and usability issues.

  3. Zed’s next-gen code editor is shockingly fast and designed for smooth collaboration with AI and other humans. It’s written from scratch in Rust (not Electron 🙏), lets you chat and work with teammates, and integrates LLMs into your workflow in helpful ways. [sponsored]

  4. TkDodo wrote about how tooltip components should not exist. So if you enjoy tooltips and/or toasts, just make sure you’ve got a solid safehouse when the great UI Purge begins.

  5. Chrome DevTools released a new CDP editor that makes it easier to write Chrome DevTools Protocol commands.

  6. Token Vault lets you securely integrate your apps and AI agents with third-party APIs – without needing to handle access and refresh tokens for your users. Just set up one single Auth0 integration, and everything just works. [sponsored]

  7. Remix maintainer, Pedro Cattori wrote about what “Just JavaScript” means to him – aka my favorite Stevie Wonder Christmas song.

  8. Anthropic wrote about building more efficient agents with MCP. Some are calling this an admission of defeat on how they’ve implemented MCP so far, but I won’t do that because I want Dario to give me thousands of stock options to be his yes man to be a nice guy.

  9. The State of Cloud Security report analyzes data from thousands of organizations to pull out the biggest threats and vulnerabilities facing teams today. [sponsored]

  10. dvcrn has been thinking way too hard about Cloudflare Zero Trust tunnels, and yes, I realize that this week isn’t the best time to be using the words “Cloudflare” and “Zero Trust” in the same sentence but here we are.

  11. Aiden Bai created React Grab, a <script> tag that lets you grab any element in your app and give it to your coding agent.

  12. Karboosx’s tutorial on building your own simple search engine means you no longer have to rely on Elasticsearch or Algolia. It also means you’re just one VS Code fork away from creating the next Google.


Pop Quiz logo

Pop Quiz: Answer

Sponsored by Sentry

Whenever you ask “how could this code be improved?”, you open the (email) floodgate. But…

One way is that instead of waiting for the image to load before fetching the metadata, we can start fetching the metadata immediately by moving the fetch call outside of the onload handler. This will allow the metadata to load in parallel with the image.

document.getElementById("thumbnail").addEventListener("click", () => {
  const metadataPromise = fetch("path_to_metadata_API").then((res) =>
    res.json()
  );

  const img = new Image();
  img.src = "path_to_high_res_image.jpg";
  document.getElementById("gallery").appendChild(img);

  img.onload = async () => {
    const metadata = await metadataPromise;
    document.getElementById("metadata").innerText = metadata.description;
  };
});