Skip to content

React bindings

Terminal window
npm install fatigue-kit fatigue-kit-react

Create a persistent engine once in your browser entry point. The button only displays the coupon after tryConsume allows it; the hooks never consume during render or mount.

import { useState } from 'react'
import { createRoot } from 'react-dom/client'
import { createFatigue } from 'fatigue-kit'
import { localStorageAdapter } from 'fatigue-kit/adapters/local-storage'
import { FatigueProvider, useFatigueState } from 'fatigue-kit-react'
const fatigue = createFatigue({ storage: localStorageAdapter() })
function Coupon() {
const [open, setOpen] = useState(false)
const popup = useFatigueState('coupon', [
{ max: 1, every: 'day' },
{ max: 3, window: '7d' },
{ cooldown: '4h' },
])
function showCoupon() {
if (popup.tryConsume().allowed) setOpen(true)
}
return (
<>
<button onClick={showCoupon}>Show coupon</button>
<p>{popup.result.allowed ? 'Available' : 'Frequency cap reached'}</p>
{open && (
<section aria-label="Coupon">
<p>Your coupon content</p>
<button onClick={() => setOpen(false)}>Close</button>
</section>
)}
</>
)
}
const container = document.getElementById('root')
if (container) {
createRoot(container).render(
<FatigueProvider value={fatigue}><Coupon /></FatigueProvider>,
)
}

Use your application’s accessible dialog component for a production popup; the section only illustrates conditional rendering.

createFatigue() alone uses memory and loses records when recreated. This browser example uses localStorage to survive reloads. Namespace and key define record identity; partition keys when users or campaigns change. Storage failures can weaken caps, and cross-tab/device quotas are outside this API’s guarantees.

Operations through useFatigueState notify same-key subscribers. useFatigue() returns the raw instance: direct mutations do not automatically notify React. tryConsume records an allowed attempt before your UI is shown, so call it close to the display action.

This entry uses browser APIs and must not execute on a server. Create request-scoped state for SSR, never a shared user-specific engine at module scope. See the SSR and hydration guide.