npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

schwi

v0.8.0

Published

An HTTP client that uses native APIs on each JS runtimes, supporting Browsers, Node.js, Deno, Bun, React Native and Tauri.

Readme

Schwi

Motivation

While building JS/TS librairies for LiterateInk and Papillon, I had a lot of issues concerning compatibility across runtimes.

Let's see an example about Set-Cookie headers.

// Browsers, Bun, Deno, Node.js
new Headers([
  ["Set-Cookie", "hello=1"],
  ["Set-Cookie", "world=2"],
]).getSetCookie();
// This simply works, we get the following.
// > ["hello=1", "world=2"]

// React Native
new Headers([
  ["Set-Cookie", "hello=1"],
  ["Set-Cookie", "world=2"],
]).getSetCookie();
// This does NOT work because they're using
// https://www.npmjs.com/package/whatwg-fetch
// and `getSetCookie` is not implemented there.
// You can fix this by using the following code instead:
new Headers([
  ["Set-Cookie", "hello=1"],
  ["Set-Cookie", "world=2"],
]).get("Set-Cookie");
// > "hello=1, world=2"
// Now this works, but as you can see the output is not the same...
// We have to handle this properly !

So we have to use different code for React Native and the rest of the runtimes and also handle the fact that the output is not the same ! As you can see, this is very frustrating.

Now let's query an API that is not allowing CORS through Tauri.

// Tauri
const response = await fetch("https://api.example.com");
// > Error: CORS
// To fix this issue, you have to instead use the
// `fetch` API from official Tauri plugins.

// Node.js, Bun, Deno, React Native
const response = await fetch("https://api.example.com");
// > 200 OK
// Simply works !

Now you can see that the CORS policy is not the same across runtimes. It's completely normal and compliant behavior, but it can be frustrating when you want to build a cross-platform library that should work everywhere.

Note that you should really only use this library if you want to build a cross-platform library which needs to either interact with Set-Cookie headers (such as Set-Cookie), either manipulate request headers (such as User-Agent, Origin or Referer) or simply ignore CORS.

The goal of this library is to provide a consistent API across runtimes. This means that you can use the same HTTP API across all runtimes, and it will behave the same way.

Features

Installation

npm add schwi
pnpm add schwi
yarn add schwi
bun add schwi

Tauri

You're required to setup Tauri's HTTP plugin, see https://tauri.app/plugin/http-client/ for more details.

tauri add http

Do not forget to configure capabilities for the Tauri HTTP client.

React Native

You can optionally opt-in react-native-real-fetch to use features that are not supported with the default fetch implementation in React Native.

If you don't have the following packages installed, it'll use the global fetch.

Bare

npm add [email protected] react-native-nitro-modules@^0.29.3
cd ios && pod install

Expo

npx expo add [email protected] react-native-nitro-modules@^0.29.3
npx expo prebuild

Optional Features

# Enables `HttpResponse.toHTML()`, otherwise you'll get an error during runtime.
pnpm add cheerio

# Enables `HttpResponse.toXML()`, otherwise you'll get an error during runtime.
pnpm add fast-xml-parser

Usage

import { HttpRequest, send } from "schwi";

const request = new HttpRequest.Builder("https://postman-echo.com/cookies/set")
  .setUrlSearchParameter("foo1", "bar1")
  .setUrlSearchParameter("foo2", "bar2")
  .setRedirection(HttpRequest.Redirection.MANUAL)
  .build();

const response = await send(request);
console.log(response.headers.getSetCookie());

const body = await response.toString();
console.log(body);

You can browse the examples folder to see how to use the library in different runtimes.