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 🙏

© 2026 – Pkg Stats / Ryan Hefner

@spitch/reader

v0.3.4

Published

Embeddable audio reader that renders a rich audio player for articles in African languages.

Readme

@spitch/reader

Add a ready-made audio player to your articles. @spitch/reader drops a player onto the page that reads the current article aloud — in English plus Yoruba, Hausa, and Igbo — with playback controls, language switching, and a live visualizer. Ships first-class wrappers for React and Vue, plus a framework-agnostic API.

Not using a bundler? You can embed the same player with a single <script> tag — see the CDN guide.

Install

npm install @spitch/reader

react + react-dom (for the /react entry) and vue (for the /vue entry) are optional peer dependencies — install only the one your app already uses. The core entry is self-contained, so vanilla and Vue apps don't need React.

Quick start

React / Next.js

import { Reader } from '@spitch/reader/react'

export function Article() {
  return (
    <article>
      <Reader />
      <h1>…</h1>
      <p>…</p>
    </article>
  )
}

<Reader /> renders an inline container and mounts the player into it, right where you place the component. It attaches to the surrounding article and tears itself down when the component unmounts.

Next.js App Router: render <Reader /> from a Client Component (the file needs 'use client') — the wrapper mounts the player in an effect.

Vue / Nuxt

<script setup>
import { Reader } from '@spitch/reader/vue'
</script>

<template>
  <article>
    <Reader />
    <h1>…</h1>
    <p>…</p>
  </article>
</template>

Vanilla JS / other frameworks

The package root exposes an imperative API:

import { mount } from '@spitch/reader'

// Mount into a specific element (CSS selector or Element)…
const handle = mount('#listen-here')

// …or omit the target to auto-place the player above the article:
// const handle = mount()

// Tear it down when you're done:
handle.destroy()

API

<Reader /> — React

| Prop | Type | Default | Description | | --- | --- | --- | --- | | target | string \| Element | component's own container | Where to mount the player — a CSS selector or element. | | className | string | — | Class applied to the container element. | | style | CSSProperties | — | Inline styles applied to the container element. |

<Reader /> — Vue

| Prop | Type | Default | Description | | --- | --- | --- | --- | | target | string \| Element | component's own container | Where to mount the player — a CSS selector or element. |

Standard attributes (e.g. class, style) fall through to the container element.

mount(target?) — imperative

function mount(target?: string | Element): { destroy(): void }

Mounts the player and returns a handle. Pass a selector or element to choose where it renders; omit target to let the Reader find the article and insert itself above the first readable block. Call handle.destroy() to remove it. The React and Vue components wrap this call and manage the lifecycle for you.

Requirements

The Reader talks to the Spitch backend, which only serves registered, secure origins. Two things to know before it will render:

  • HTTPS + a registered domain. Register your site's domain with Spitch (via your Spitch dashboard, or email [email protected]). The player checks the page origin and stays hidden on any origin it can't serve — including plain http://, localhost, and loopback IPs. To test locally, point at a deployed HTTPS origin (or a tunnel to one) that you've registered.
  • Article content in the DOM. The player reads the article HTML already on the page, so the content must be server-rendered (SSR/SSG) or otherwise present before the player mounts. The React and Vue wrappers mount on the client, so they're safe to render during SSR — they simply attach once hydrated.

Entry points

| Import | Use when | Peer deps | | --- | --- | --- | | @spitch/reader/react | React / Next.js apps | react, react-dom (>=18) | | @spitch/reader/vue | Vue 3 / Nuxt apps | vue (>=3) | | @spitch/reader | Vanilla JS or any other framework | none |

The /react entry uses your app's React instance, so the player shares it; the core and /vue entries bundle their own renderer and need no React installed.

TypeScript

Types ship with the package — every entry point is fully typed, with no @types/* to install.

Links