A semantic reactivity system for modern applications. Separate reactive state (pulse) from business conditions (guards) with a declarative, composable, and proxied approach.
Official Documentation
Pulse differs from traditional signals or state managers by treating Conditions as first-class citizens. Instead of embedding complex boolean logic inside components, you define Semantic Guards that are observed, composed, and debugged independently.
bun add @pulse-js/core @pulse-js/tools
pulse() creates a deep reactive Proxy. Use it for complex objects and arrays. Track property access automatically and mutate state directly.
import { pulse } from "@pulse-js/core";
const user = pulse({
name: "Alice",
role: "admin",
increment() {
this.stats.clicks++;
},
stats: { clicks: 0 },
});
// Mutate directly - it's reactive!
user.name = "Bob";
user.increment();
Sources are primitive containers for your application state. They hold values and notify dependents when those values change.
import { source } from "@pulse-js/core";
const count = source(0);
count.set(5);
Guards represent business rules or derivations. They act as high-performance Selectors with built-in dependency tracking and rich failure context.
import { guard } from "@pulse-js/core";
const isAuthorized = guard("auth-check", async () => {
const u = user();
if (!u) return false;
return true;
});
Get a structured tree of the current status, failure reasons, and the status of all direct dependencies.
const explanation = canCheckout.explain();
// { status: 'fail', reason: { code: 'AUTH', message: '...' }, dependencies: [...] }
Pulse provides official adapters for all major frameworks.
| Framework | Package | Status |
|---|---|---|
| Astro | @pulse-js/astro |
NEW |
| React | @pulse-js/react |
Stable |
| Vue | @pulse-js/vue |
Stable |
| Svelte | @pulse-js/svelte |
Stable |
| TanStack | @pulse-js/tanstack |
NEW |
Debug your reactive graph with Pulse Tools, a decoupled Agent-Client inspector.
@pulse-js/tools.