A/B tests wherever you run code.
One script tag runs experiments on your site. 15 published packages cover everywhere else you run code. You also get a documented REST API, a command line tool, and a browser extension that debugs a live page without an account. The same statistics sit under all of it.
1<!-- In your <head>, as high as possible -->2<script3 src="//cdn.avsb.cloud/snippet.js"4 data-avsb="YOUR_SNIPPET_KEY"5></script>6
7<!-- Record a conversion anywhere in your app -->8<script>9 window.avsb.track.event('purchase', { revenue: 49 })10</script>One script tag. No dependencies.
About 34 KB over the wire, measured from the build on 2026-08-20. That is what a visitor downloads: 35,048 bytes compressed, from 111,720 bytes minified. We enforce that size rather than promise it. A build that grows past 37 KB compressed fails instead of shipping.
Your visitors never see the original page flash past first. Anti-flicker holds the page for up to 3 seconds while the variation applies.
The same visitor always gets the same variation. The browser works it out with a fixed calculation, so there is no server round trip. A first-party cookie called _avsb_visitor, lasting a year, keeps the choice sticky across visits.
Single-page apps work without extra wiring. The script spots a route change and re-applies the variation. Turn on consent mode and nothing runs and nothing is tracked until your consent tool says yes, and the queued events are then sent.
Events are batched and sent every 2 seconds, or as soon as 10 have built up. The script also spots which analytics tool is on your page and starts forwarding events to it, retrying for 30 seconds in case that tool loads late.
1<!-- In your <head>, as high as possible -->2<script src="//cdn.avsb.cloud/snippet.js" data-avsb="YOUR_SNIPPET_KEY"></script>3
4<!-- Record a conversion anywhere in your app -->5<script>6 window.avsb.track.event('purchase', { revenue: 49 })7</script>
What it records
- ExposureA visitor was put into a variation.
- ClickAn element matching your selector was clicked.
- PageviewA page load, or a route change inside your app.
- CustomAnything you fire yourself, with your own properties.
- SegmentA membership signal for a reusable audience.
What you can call
- getVariationWhich variation this visitor is in, for one experiment.
- getActiveExperimentsEverything running on this page right now.
- forceVariationPin a visitor to a variation, with tracking on or off.
- track.eventRecord a conversion, with your own properties.
- readyRun your code once bucketing has finished.
Write variations in your own code.
Use JavaScript or TypeScript, with CSS or SCSS. You get a real editor with autocomplete and inline documentation for every helper you are handed, so you are never guessing at what is available.
You find out about a mistake before your visitors do. Linting has three levels, off, on, or strict, and on strict a type error blocks the save.
Share type definitions at two levels. shared.d.ts is visible to every file in one experiment, and project-shared.d.ts is visible across the whole project. Both carry types only, so nothing extra ships to the browser.
Send any variation to a reviewer with a preview link. They need no account and are never counted in your results. The link expires within 30 to 90 days, and you can revoke it at any time.
1// Runs for visitors bucketed into this variation.2function initVariation(options) {3 const btn = document.querySelector<HTMLButtonElement>('.checkout-cta')4 if (!btn) return5
6 btn.textContent = 'Claim 30% discount'7 btn.classList.add('avsb-variant-b')8
9 options.track.event('purchase', { revenue: 49 })10
11 // Self-cleaning: undone on removal and on route changes.12 options.onRemove(() => btn.classList.remove('avsb-variant-b'))13}
A client for every place you run code.
15 packages are published and installable today. 13 of them are the client libraries below. The other 2 are the command line tool and a stub that points an older install name at the browser client. Together the clients cover the browser, your server, the edge, every major JavaScript framework, and your test suite.
@avsbhq/browser
Framework-free browser client.
@avsbhq/node
Express and Fastify middleware, shared sticky assignment, live streaming.
@avsbhq/react
React hooks and a provider. Wrap the tree once, then read a flag anywhere. Components re-render when a value changes.
@avsbhq/core
Pure evaluation engine and shared types every other package builds on.
@avsbhq/utils
Shared plumbing: streaming, shared-store adapters, decision-log sinks.
@avsbhq/edge
Cloudflare Workers, Vercel Edge, Fastly Compute, Netlify Edge, Deno Deploy, Bun, and AWS Lambda@Edge.
@avsbhq/next
Next.js: App Router and Pages Router, server and client.
@avsbhq/react-native
React Native: hooks for iOS and Android.
@avsbhq/test
Test helpers: assert on flag and experiment behaviour in your own test suite.
@avsbhq/vue
Vue 3 bindings: flags and tracking.
@avsbhq/svelte
Svelte bindings: flags and tracking.
@avsbhq/solid
SolidJS bindings: flags and tracking.
@avsbhq/angular
Angular: injectable service with RxJS helpers.
1import { AvsbClient } from '@avsbhq/browser'2
3const client = new AvsbClient({4 sdkKey: process.env.NEXT_PUBLIC_AVSB_SDK_KEY!,5 context: { kind: 'user', key: 'u_123', plan: 'pro' },6})7
8await client.onReady()9
10const flag = client.getBoolFlag('new-checkout-flow', false)11if (flag.isEnabled()) {12 renderNewCheckout()13}14
15client.track('checkout_started', { value: 99.0 })6 more SDKs cover other languages. They are not on the public registries yet, and we can publish them there on request.
- PythonPyPI
- GoGo modules
- RubyRubyGems
- PHPPackagist
- JavaMaven Central
- .NETNuGet
Do everything the dashboard does.
The REST API covers experiments, flags, metrics, audiences, segments, members, roles, webhooks and more. Every resource has its own reference page.
Tokens belong to your organisation rather than to a person, so they outlive whoever created them. Each one carries read and write scopes per resource, and an optional expiry of up to a year. You can rotate a token without losing its history, revoke it outright, and see when it was last used. Tokens are hashed, and the secret is shown to you once.
A repeated request will not run twice. Send an idempotency key and a retry returns the original result. Rate limits are enforced and documented, and every response tells you where you stand against them.
Every write is recorded in the audit log with who did it, what changed before and after, and whether it came from the dashboard, the API, the command line, or the system itself.
Read the API authentication reference1curl https://app.avsb.cloud/api/v1/projects \2 -X POST \3 -H "Authorization: Bearer $AVSB_TOKEN" \4 -H "Content-Type: application/json" \5 -H "Idempotency-Key: $(uuidgen)" \6 -d '{ "name": "Storefront" }'
Edit variations where you already work.
Clone an experiment’s code onto your machine, push your edits back, and pull the latest down. The tool checks for changes made since you cloned, and warns you about a conflict before anything is overwritten.
It also runs a local development server with live reloading, so a change in your editor shows up straight away on the page you are testing against.
Read the command line reference1npm install -g @avsbhq/cliEdit and debug on the live page.
AvsB Dev Tools is the extension that holds both the visual editor and the event debugger. It runs in Chrome, and you install it from the guide below.
The visual editor
Open it from your experiment and it loads on top of your live page. There are 8 kinds of change you can make by pointing and clicking, with no code:
- Text
- Style
- Visibility
- Image
- Reorder
- Insert
- Move
- Section
The remaining kinds of change come only from the copilot. A click never issues them:
- Remove element
- Custom behaviour
Press Cmd+K for the command palette, with a shortcut reference beside it, and use the page-structure tree to pick exactly the element you mean. Every change can be limited to one screen size: all widths, mobile, tablet, desktop, or a custom range you set.
The live event debugger
It works on any site with the tracking script installed, and it needs no account. It tells you whether the script is present, lists the experiments it can see, shows which variation the current visitor is in, and streams events as they fire.
While you work you can switch between reloading the page and injecting your changes live. Live injection is labelled experimental in the product, so reloading stays the safe default.


Three engines, fully documented.
3 genuinely different engines, not one formula with settings. Each one answers a different question, and the results page always tells you which engine produced the number in front of you.
Bayesian
Answers "how likely is the challenger actually better", as a plain probability, with no fixed sample size to wait for.
- Probability to beat control
- 95% credible interval
- SRM check
Frequentist
The textbook significance test most stats teams already trust, planned around a sample size you set in advance.
- p-value
- 95% confidence interval
- Sample-size reached
Sequential
Checking the result every day cannot manufacture a false winner.
- Always-valid p-value
- 95% always-valid confidence sequence
- Peek anytime, stop when it lands
The always-valid engine is built on a named, peer-reviewed method, asymptotic confidence sequences (Howard et al., 2021), rather than an in-house approximation.
The Bayesian engine is exact and repeatable: the same data gives the same number every time, with no flicker between refreshes. Its default prior takes no position before it sees your data. You can tell it what size of effect you expect, which updates every number it reports. That option is off by default, and the page says so on screen when it is on.
Confidence level is configurable from 80 to 99 percent, default 95. The Bayesian win bar and the Frequentist confidence level are deliberately two separate settings, so tightening one does not quietly move the other.
There are 6 multiple-comparison correction methods. The default is tiered: the primary metric is corrected across arms, and the secondary metrics are corrected as their own family. Under the always-valid engine, a false-discovery-rate correction is upgraded automatically to a stricter one, because the first is not valid when you peek continuously. The results page tells you it happened.
Guardrail metrics are deliberately kept out of that maths, so correcting them cannot quietly reduce your ability to spot real harm.
Extreme values are capped before analysis, computed from non-zero values only, either pooled across variations or per variation. Ratio metrics get proper variance handling through the delta method, and relative-lift intervals switch to Fieller when the baseline is weakly known. Where an interval genuinely cannot be worked out, the page says so rather than printing a misleading range.
The percentile sizing tool reports its own uncertainty rather than claiming a precision it does not have.
Add the script,
run your first test.
Every package, the API, the command line tool and the extension are on the Free plan, along with all three statistics engines.