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

@rimitive/react

v0.2.3

Published

React bindings for Rimitive signals and stores

Readme

@rimitive/react

React bindings for rimitive signals and behaviors.

Quick Start

import { SignalProvider, useSignal, useSubscribe } from '@rimitive/react';

function Counter() {
  const [count, setCount] = useSignal(0);
  return <button onClick={() => setCount((c) => c + 1)}>Count: {count}</button>;
}

function App() {
  return (
    <SignalProvider>
      <Counter />
    </SignalProvider>
  );
}

Hooks

useSignal

Create a signal scoped to the component. Returns [value, setter] like useState.

const [count, setCount] = useSignal(0);
setCount((prev) => prev + 1); // Updater functions work too

useSubscribe

Subscribe to an external signal. Re-renders when the signal changes.

function Display({ count }: { count: Readable<number> }) {
  const value = useSubscribe(count);
  return <span>{value}</span>;
}

useSelector

Subscribe with a selector. Only re-renders when the selected value changes.

function UserName({ user }: { user: Readable<User> }) {
  const name = useSelector(user, (u) => u.name);
  return <span>{name}</span>;
}
// Only re-renders when name changes, not email

useSignalSvc

Access the signal service directly:

const svc = useSignalSvc();
const count = useRef(svc.signal(0));

SignalProvider

Wraps your app to provide signal context. Optionally pass a custom service:

import { compose } from '@rimitive/core';
import { SignalModule, ComputedModule, EffectModule } from '@rimitive/signals/extend';

const svc = compose(SignalModule, ComputedModule, EffectModule);

function App() {
  return (
    <SignalProvider svc={svc}>
      <YourApp />
    </SignalProvider>
  );
}

createHook

Convert a portable rimitive behavior into a React hook:

import { createHook, useSubscribe } from '@rimitive/react';

const counter = (svc) => (initial: number) => {
  const count = svc.signal(initial);
  return {
    count,
    increment: () => count(count() + 1),
    decrement: () => count(count() - 1),
  };
};

const useCounter = createHook(counter);

function Counter() {
  const { count, increment, decrement } = useCounter(0);
  const value = useSubscribe(count);

  return (
    <div>
      <button onClick={decrement}>-</button>
      <span>{value}</span>
      <button onClick={increment}>+</button>
    </div>
  );
}

The behavior is instantiated once at mount (like useRef's initial value).


React Bridge

Embed React components inside a Rimitive application. Useful for gradual migration or when you need React-specific libraries (like @xyflow/react).

createReactBridge

Mount a React component with reactive props. Returns a ref callback for use with el().ref().

import { createReactBridge } from '@rimitive/react';
import { ReactFlow } from '@xyflow/react';

const GraphView = (svc) => {
  const { el, signal, effect } = svc;
  const nodes = signal([]);
  const edges = signal([]);

  // Create a ref that mounts ReactFlow with reactive props
  const graphRef = createReactBridge(effect, ReactFlow, () => ({
    nodes: nodes(),
    edges: edges(),
    onNodesChange: (changes) => { /* handle changes */ },
  }));

  return el('div').props({ className: 'graph-container' }).ref(graphRef)();
};

The component re-renders automatically when signal dependencies in getProps change.

renderReact

Render arbitrary JSX with reactive dependencies. Lower-level alternative for more control.

import { renderReact } from '@rimitive/react';

const StatusIndicator = (svc) => {
  const { el, signal, effect } = svc;
  const status = signal<'idle' | 'loading' | 'error'>('idle');

  const statusRef = renderReact(effect, () => (
    <Badge variant={status() === 'error' ? 'destructive' : 'default'}>
      {status()}
    </Badge>
  ));

  return el('div').ref(statusRef)();
};

Both functions handle cleanup automatically—the React component unmounts and the effect stops when the Rimitive element is removed.