Consent platform
- Usercentrics
- Cookiebot
- OneTrust
- consentmanager.net
- Didomi
- iubenda
- Osano
- TrustArc
- Klaro
- Any TCF CMP
- Any GPP CMP
- libconsent banner
libconsent
Your components
useConsent()read & act<CookieService />gate a scriptuseHasConsent()one boolean
Handle cookie consent the React way
Consent Banners are programmed to pass a law, not to give you a good developer experience.
libconsent is the React API that sits between your components and any banner, so you can gate scripts and open the settings dialog with beautiful, native React code: useConsent(), useHasConsent() and <CookieService>
MIT · TypeScript · no runtime dependencies
“May we run marketing scripts?”
libconsent gives you the React API that sits between your components and any banner, so you can gate scripts and manage the banner dialog easily.
Talking to the platform directly
const [hotjarConsent, setHotjarConsent] = useState(false);useEffect(() => { const read = () => { const groups = window.OnetrustActiveGroups ?? ""; setHotjarConsent(groups.includes("C0004")); // "Targeting" }; // OneTrust calls this global once it initialises window.OptanonWrapper = read; window.OneTrust?.OnConsentChanged(read); read();}, []);if (!hotjarConsent) return null;return <HotjarScript />;With libconsent, on any of them
<ConsentScript id="hotjar" src="https://static.hotjar.com/c/hotjar-123.js?sv=6"/>Which banner are you on?
Install the core package and the adapter for your platform, then wrap your app once. That is the whole setup.
npm i @libconsent/core @libconsent/usercentricsimport { ConsentProvider } from "@libconsent/core";import { usercentrics } from "@libconsent/usercentrics";<ConsentProvider adapter={usercentrics({ settingsId: "AbCdEf123" })}> {children}</ConsentProvider>Usercentrics keeps drawing its own banner. openSettings() opens its second layer. Details
Also consentmanager.net, iubenda, Osano, TrustArc, Klaro and IAB GPP. Nothing that fits? An adapter is one function — load a script, subscribe to an event, report what it says. The built-in ones are 100–200 lines each.
Then gate things
A real <ConsentProvider> running the built-in banner. Left is the source, right is what it renders right now.
Running the real provider. Answer the banner and watch the right column.
const { categories } = useConsent();- essential: true
- functional: false
- analytics: false
- marketing: false
<CookieService id="google-analytics"> <GoogleAnalytics gaId="G-XXXXXXX" /></CookieService>nothing rendered — no analytics consent
<CookieService id="youtube" fallback={<Poster />}> <YouTubeEmbed id="dQw4w9WgXcQ" /></CookieService>Also in the box
- Services, not just categories
Two dozen are built in, with the names each platform files them under.
- The dialog lists what you load
Gated services register themselves, so the preferences UI follows your tree.
- A denial is final
Switched off by the user means off — whatever the category says.
- Google Consent Mode v2
Written from the same state, and skipped when your platform handles it.
- Server-side reads
Swap localStorage for a cookie and read the decision in middleware or an RSC.
- A banner in 11 languages
shadcn/ui components you own, with per-service switches.
- Standards, not just vendors
One adapter for every IAB TCF CMP, and one for US opt-out signals over GPP.
Wrap your app and gate one script.
The whole setup is an adapter and a provider.
npm i @libconsent/coreGet started →