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

@basis-theory/web-elements

v3.0.0

Published

Secure, PCI-compliant elements for creating payment input forms

Downloads

193,998

Readme

@basis-theory/web-elements

Secure, PCI-compliant iframe elements for collecting sensitive data in web applications. Card data never touches your servers.

Installation

npm

npm install @basis-theory/web-elements@beta

yarn

yarn add @basis-theory/web-elements@beta

CDN

<script src="https://js.basistheory.com/3.0.0-beta.2/web-elements/basis-theory.js"></script>

Quick Start

import BasisTheory from '@basis-theory/web-elements';

// Initialize (synchronous -- returns immediately)
const bt = BasisTheory('pk_test_...');

// Create elements
const cardNumberEl = bt.createElement('cardNumber', {
  placeholder: '4242 4242 4242 4242',
});
const expiryEl = bt.createElement('expiry', {
  placeholder: 'MM/YY',
});
const cvvEl = bt.createElement('cvv', {
  placeholder: '123',
});

// Mount to DOM (async -- creates secure iframes)
await Promise.all([
  cardNumberEl.mount('#card-number'),
  expiryEl.mount('#expiry'),
  cvvEl.mount('#cvv'),
]);

// Listen for validation changes
cardNumberEl.on('change', (event) => {
  console.log('Valid:', event.detail.isValid);
  console.log('Brand:', event.detail.cardBrand);
});

// Tokenize on form submission
const token = await bt.tokens.create({
  type: 'card',
  data: {
    number: cardNumberEl,
    expiration_month: expiryEl,
    expiration_year: expiryEl,
    cvc: cvvEl,
  },
});

console.log('Token ID:', token.id);

CDN Usage

<script src="https://js.basistheory.com/3.0.0-beta.2/web-elements/basis-theory.js"></script>
<script>
  document.addEventListener('DOMContentLoaded', async () => {
    const bt = BasisTheory('pk_test_...');

    const cardNumberEl = bt.createElement('cardNumber');
    const expiryEl = bt.createElement('expiry');
    const cvvEl = bt.createElement('cvv');

    await Promise.all([
      cardNumberEl.mount('#card-number'),
      expiryEl.mount('#expiry'),
      cvvEl.mount('#cvv'),
    ]);
  });
</script>

Element Types

| Type | createElement key | Description | |------|---------------------|-------------| | Card Number | 'cardNumber' | PAN input with Luhn validation and brand detection | | Expiry | 'expiry' | MM/YY expiration date input | | CVV | 'cvv' | Card verification code input | | Text | 'text' | General-purpose secure text input (SSN, routing numbers, etc.) |

Shared Options

All element types accept these options in createElement() and element.update():

| Option | Type | Default | Description | |--------|------|---------|-------------| | placeholder | string | -- | Placeholder text shown when the input is empty | | ariaLabel | string | Element-specific | ARIA label for screen readers | | disabled | boolean | false | Disables the input | | readOnly | boolean | false | Makes the input read-only |

Text Element Options

| Option | Type | Description | |--------|------|-------------| | validation | RegExp | Pattern the value must match to be valid | | required | boolean | Whether the field is required | | maxLength | number | Maximum character length | | password | boolean | Renders as a password field | | inputMode | string | Mobile keyboard hint ('numeric', 'tel', etc.) | | mask | (RegExp \| string)[] | Character-by-character input mask | | transform | [RegExp, string] | Transform applied before tokenization |

CVV Element Options

| Option | Type | Default | Description | |--------|------|---------|-------------| | showToggle | boolean | false | Renders a show/hide toggle button inside the field |

Element Methods

Every element exposes the same interface:

| Method | Signature | Description | |--------|-----------|-------------| | mount | (selector: string \| HTMLElement) => Promise<void> | Attaches the iframe to the DOM | | unmount | () => void | Removes the iframe from the DOM | | update | (options) => Promise<void> | Updates options on a mounted element | | focus | () => void | Focuses the input | | blur | () => void | Blurs the input | | clear | () => void | Clears the current value | | on | (event, listener) => () => void | Subscribes to an event; returns an unsubscribe function |

Properties: id (string), type (ElementType), mounted (boolean).

Events

| Event | Fires when | |-------|-----------| | ready | Element iframe is loaded and interactive | | change | Input value changes | | focus | Element receives focus | | blur | Element loses focus | | error | An infrastructure or API error occurs |

change Event Payload

All elements include these fields in event.detail:

| Field | Type | Description | |-------|------|-------------| | isValid | boolean | Input passes all validation rules | | isEmpty | boolean | Input is empty | | error | ValidationError \| null | Validation error, or null if valid | | elementType | string | Element type that fired the event | | elementId | string | Unique element ID | | timestamp | number | Unix timestamp (ms) |

The cardNumber element adds: cardBrand, last4, bin, cvvLengths, potentialBrands, and matchStrength.

cardNumberEl.on('change', (event) => {
  const { isValid, cardBrand, last4 } = event.detail;
  console.log(`${cardBrand} ...${last4}`, isValid);
});

error Event Codes

| Code | Description | |------|-------------| | MOUNT_ERROR | Failed to mount the element iframe | | POSTMESSAGE_TIMEOUT | PostMessage timeout | | IFRAME_LOAD_ERROR | Element iframe failed to load | | INITIALIZATION_ERROR | SDK or coordinator failed to initialize | | API_ERROR | Basis Theory API returned an error | | NETWORK_ERROR | Network request failed | | VALIDATION_ERROR | Input failed client-side validation | | INVALID_CONFIGURATION | Invalid SDK or element options | | UNKNOWN_ERROR | Unexpected error |

SDK Options

const bt = BasisTheory('pk_test_...', {
  debug: false,            // Enable verbose debug logging
  themeMode: 'auto',       // 'light' | 'dark' | 'auto'
  theme: { /* ThemeTokens */ },
  darkTheme: { /* ThemeTokens */ },
  timeoutMs: 30000,        // PostMessage timeout (ms)
});

Services

tokens

// Create a token
const token = await bt.tokens.create({
  type: 'card',
  data: {
    number: cardNumberEl,
    expiration_month: expiryEl,
    expiration_year: expiryEl,
    cvc: cvvEl,
  },
});

// Retrieve a token
const retrieved = await bt.tokens.retrieve(token.id, {
  apiKey: sessionApiKey, // from an authorized session
});

// Update a token
await bt.tokens.update(token.id, {
  metadata: { source: 'updated' },
});

// Encrypt with client-side JWE
const encrypted = await bt.tokens.encrypt(
  { type: 'card', data: { number: cardNumberEl, cvc: cvvEl } },
  publicKeyPEM,
  'key-id-123'
);

tokenize

const result = await bt.tokenize({
  number: cardNumberEl,
  cvv: cvvEl,
  expiry: expiryEl,
});

tokenIntents

const intent = await bt.tokenIntents.create({
  type: 'card',
  data: {
    number: cardNumberEl,
    expiration_month: expiryEl,
    expiration_year: expiryEl,
    cvc: cvvEl,
  },
});

const retrieved = await bt.tokenIntents.get(intent.id);

sessions

const session = await bt.sessions.create();
// Send session.nonce to your backend to authorize
// Backend returns an apiKey for elevated access

const token = await bt.tokens.retrieve(tokenId, {
  apiKey: sessionApiKey,
});

Theming

Pass design tokens at initialization and switch modes at runtime:

const bt = BasisTheory('pk_test_...', {
  themeMode: 'auto',
  theme: {
    colors: {
      primary: '#007bff',
      error: '#dc3545',
      success: '#28a745',
      text: { primary: '#1a1a1a', placeholder: '#6c757d' },
      background: { default: '#ffffff' },
      border: { default: '#dee2e6', focus: '#007bff' },
    },
    typography: {
      fontFamily: 'Inter, sans-serif',
      fontSize: { base: '16px' },
      fontWeight: { normal: '400' },
    },
    spacing: { sm: '8px', md: '12px', lg: '16px' },
    borders: {
      radius: { base: '6px' },
      width: { base: '1px' },
    },
  },
});

// Switch theme mode at runtime
await bt.updateThemeMode('dark');

TypeScript

The package ships full type definitions. Key exports:

import type {
  BasisTheorySDK,
  Element,
  ElementType,
  ElementOptions,
  SDKOptions,
  ChangeEventDetail,
  CardNumberChangeEventDetail,
  ReadyEventDetail,
  ErrorEventDetail,
  ErrorCode,
  ValidationError,
  TokenizeResult,
  Session,
} from '@basis-theory/web-elements';

Documentation

Full documentation: https://developers.basistheory.com/docs/sdks/web/web-elements/

License

Apache-2.0