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

@zhama/a2ui-core

v0.9.0

Published

A2UI Protocol Core Library - Framework-agnostic TypeScript types and builders for A2UI protocol

Readme

@zhama/a2ui-core

A2UI Protocol Core Library - Framework-agnostic TypeScript types and builders for A2UI v0.9 protocol.

Note: This library uses A2UI v0.9 format exclusively. While v0.9 is still in draft status according to a2ui.org, it offers a cleaner and more modern API.

Overview

A2UI (Agent to UI) is a JSON-based streaming UI protocol for dynamically rendering user interfaces. This library provides:

  • Types: Complete TypeScript type definitions for A2UI v0.9
  • Builders: Convenient functions to build messages and components
  • Surface: Surface ID constants and creation utilities
  • Validators: Message validation utilities
  • Utils: Utility functions for path bindings and data manipulation

Installation

npm install @zhama/a2ui-core
# or
pnpm add @zhama/a2ui-core

Quick Start

import {
  // Builders
  text, column, button, h1,
  createSurface, updateComponents, updateDataModel,
  createMessages,
  
  // Surface
  SURFACE_IDS, createA2UISurface,
  
  // Validators
  validateMessage,
  
  // Utils
  path, generateId,
  
  // Types
  type ComponentInstance,
  type ServerToClientMessage,
} from '@zhama/a2ui-core';

// Create components
const title = h1('Hello World', { id: 'title' });
const greeting = text({ path: '/user/name' }, { id: 'greeting' });
const root = column(['title', 'greeting'], { id: 'root' });

// Create messages
const messages = createMessages({
  surfaceId: SURFACE_IDS.CHAT,
  components: [title, greeting, root],
  dataModel: { user: { name: 'John' } },
});

// Validate messages
const result = validateMessage(messages[0]);
console.log(result.valid); // true

Modular Imports

You can import specific modules for tree-shaking:

// Types only
import type { ComponentInstance, ServerToClientMessage } from '@zhama/a2ui-core/types';

// Builders only
import { text, column, createMessages } from '@zhama/a2ui-core/builders';

// Validators only
import { validateMessage, validateMessages } from '@zhama/a2ui-core/validators';

// Utils only
import { path, uuid, deepMerge } from '@zhama/a2ui-core/utils';

// Surface utilities
import { SURFACE_IDS, createA2UISurface, createChatSurface } from '@zhama/a2ui-core/surface';

API Reference

Component Builders

// Content components
text(content: StringOrPath, options?: TextOptions): ComponentInstance
image(url: StringOrPath, options?: ImageOptions): ComponentInstance
icon(name: StringOrPath, options?: IconOptions): ComponentInstance
video(url: StringOrPath, options?: VideoOptions): ComponentInstance
audioPlayer(url: StringOrPath, options?: AudioPlayerOptions): ComponentInstance

// Layout components
row(children: ChildrenProperty, options?: LayoutOptions): ComponentInstance
column(children: ChildrenProperty, options?: LayoutOptions): ComponentInstance
list(children: ChildrenProperty, options?: ListOptions): ComponentInstance
card(childId: string, options?: CardOptions): ComponentInstance
tabs(items: TabItem[], options?: TabsOptions): ComponentInstance
divider(options?: DividerOptions): ComponentInstance
modal(triggerId: string, contentId: string, options?: ModalOptions): ComponentInstance

// Interactive components
button(childId: string, action: Action, options?: ButtonOptions): ComponentInstance
checkbox(label: StringOrPath, value: BooleanOrPath, options?: CheckBoxOptions): ComponentInstance
textField(label: StringOrPath, text?: StringOrPath, options?: TextFieldOptions): ComponentInstance
dateTimeInput(value: StringOrPath, options?: DateTimeInputOptions): ComponentInstance
choicePicker(options: ChoiceOption[], value: StringArrayOrPath, usageHint: string, opts?: ChoicePickerOptions): ComponentInstance
slider(value: NumberOrPath, options?: SliderOptions): ComponentInstance

// Convenience helpers
textButton(buttonText: string, action: Action, options?: ButtonOptions): [ComponentInstance, ComponentInstance]
h1(content: StringOrPath, options?: TextOptions): ComponentInstance
h2(content: StringOrPath, options?: TextOptions): ComponentInstance
h3(content: StringOrPath, options?: TextOptions): ComponentInstance
h4(content: StringOrPath, options?: TextOptions): ComponentInstance
h5(content: StringOrPath, options?: TextOptions): ComponentInstance
caption(content: StringOrPath, options?: TextOptions): ComponentInstance
body(content: StringOrPath, options?: TextOptions): ComponentInstance

Message Builders

createSurface(surfaceId: string, catalogId?: string): CreateSurfaceMessage
updateComponents(surfaceId: string, components: ComponentInstance[]): UpdateComponentsMessage
updateDataModel(surfaceId: string, value: unknown, path?: string, op?: 'add' | 'replace' | 'remove'): UpdateDataModelMessage
deleteSurface(surfaceId: string): DeleteSurfaceMessage
createMessages(options): ServerToClientMessage[]

// Utilities
messagesToJsonl(messages: ServerToClientMessage[]): string
jsonlToMessages(jsonl: string): ServerToClientMessage[]

Surface Module

// Surface ID constants
SURFACE_IDS.CHAT           // '@chat' - Chat content area
SURFACE_IDS.RECOMMENDATION // '@recommendation' - Agent recommendations
SURFACE_IDS.INPUT_FORM     // '@input-form' - Input collection forms
SURFACE_IDS.ORCHESTRATION  // '@orchestration' - Multi-agent orchestration
SURFACE_IDS.STATUS         // '@status' - Status messages
SURFACE_IDS.RESULT         // '@result' - Agent results
SURFACE_IDS.CONFIRM        // '@confirm' - Confirmation dialogs
SURFACE_IDS.NOTIFICATION   // '@notification' - Notifications

// Surface creation functions
createA2UISurface(rootId: string, components: ComponentInstance[], surfaceId?: string): SurfaceResult
createA2UISurfaceWithData(rootId: string, components: ComponentInstance[], dataModel: DataObject, surfaceId?: string): SurfaceResult
createDeleteSurfaceMessage(surfaceId: string): ServerToClientMessage

// Convenience functions
createChatSurface(rootId: string, components: ComponentInstance[]): SurfaceResult
createRecommendationSurface(rootId: string, components: ComponentInstance[]): SurfaceResult
createInputFormSurface(rootId: string, components: ComponentInstance[]): SurfaceResult
createOrchestrationSurface(rootId: string, components: ComponentInstance[]): SurfaceResult
createStatusSurface(rootId: string, components: ComponentInstance[]): SurfaceResult

Data Model

objectToValueMap(obj: DataObject, prefix?: string): ValueMap[]
valueToValueMap(key: string, value: DataValue): ValueMap
valueMapToObject(valueMaps: ValueMap[]): DataObject
normalizePath(path: string, pathMappings?: PathMappings): string

Validators

validateMessage(message: ServerToClientMessage, options?: ValidationOptions): ValidationResult
validateMessages(messages: ServerToClientMessage[], options?: ValidationOptions): ValidationResult
validateMessage(message: ServerToClientMessage, options?: ValidationOptions): ValidationResult

Utils

path(dataPath: string): { path: string }           // Create data binding
isPathBinding(value): boolean                       // Check if value is a path binding
getLiteralValue<T>(value): T | undefined           // Get literal value
getPathValue(value): string | undefined            // Get path from binding
generateId(prefix?: string): string                // Generate unique component ID
resetIdCounter(): void                             // Reset ID counter
uuid(): string                                     // Generate UUID v4
deepMerge<T>(target: T, source: Partial<T>): T    // Deep merge objects

Constants

STANDARD_CATALOG_ID  // Standard A2UI catalog URL
A2UI_EXTENSION_URI   // A2UI v0.9 extension URI
A2UI_MIME_TYPE       // A2UI MIME type (application/json+a2ui)

v0.9 Message Format

A2UI v0.9 uses a cleaner, flatter format:

// Component format
{ id: 'title', component: 'Text', text: 'Hello World', usageHint: 'h1' }

// Messages
{ createSurface: { surfaceId: '@chat', catalogId: '...' } }
{ updateComponents: { surfaceId: '@chat', components: [...] } }
{ updateDataModel: { surfaceId: '@chat', op: 'replace', value: { ... } } }
{ deleteSurface: { surfaceId: '@chat' } }

License

MIT