Component Schema: The Complete Guide
Introduction
In the Weaverse ecosystem, a component’s schema is the critical link between code and the visual editor. The schema defines how components appear in the Weaverse Studio, what customization options are available, and how components interact with each other. Think of it as both a blueprint and an interface that empowers developers and merchants alike.Component Registration Method
Weaverse components are registered using static exports and configuration. Static Export PatternThe createSchema() Function
Weaverse provides thecreateSchema() function as the modern, recommended way to define component schemas. This function offers several advantages over the traditional manual type definition approach:
Why Use createSchema()?
- Development Diagnostics: Schedules asynchronous Zod validation outside production and logs issues as warnings
- Type Checking: Accepts the public
SchemaType, providing TypeScript checks and autocompletion while authoring - Non-Blocking Runtime: Returns the original schema immediately and does not throw validation or import failures through the call
- Production Footprint: Skips the validation import in production builds
Basic Usage
createSchema() function returns the supplied schema immediately. In development, it starts asynchronous validation and logs any issues as warnings; those warnings do not stop a build or replace the schema.
Import Options
You can importcreateSchema from either package:
Anatomy
TheHydrogenComponentSchema acts as a comprehensive definition for your component, specifying everything from its appearance in the editor to its behavior within the theme. This schema-driven approach ensures consistency, predictability, and a seamless user experience.
Core Schema Structure
The recommended way to define component schemas is using thecreateSchema() function, which provides SchemaType checking and non-blocking development diagnostics:
createSchema() function:
- Returns the schema immediately without waiting for validation
- Schedules asynchronous Zod validation in development and logs issues as warnings
- Does not throw validation or import failures through
createSchema() - Skips the validation path in production
⚠️ Migration Notice: TheEach property serves a specific purpose in defining how your component behaves in the Weaverse ecosystem. Let’s explore each in detail.inspectorproperty has been deprecated in favor ofsettings. Whileinspectoris still supported for backward compatibility, new components should usesettings. The Weaverse system automatically handles both properties during the transition period.
Essential Properties
title and type
title
The title property defines the human-readable name for your component. This name appears in the Weaverse Studio’s Page Outline section and component browser, making it crucial for discoverability and usability.
Best Practices:
- Keep titles concise but descriptive (generally 1-3 words)
- Use Title Case for consistency
- Reflect the component’s purpose or functionality
- Avoid technical jargon that merchants might not understand
type
The type property serves as a unique identifier for your component within the Weaverse ecosystem. This property is used internally to differentiate between components and must be unique across your entire theme.
Under the Hood:
When components are registered with Weaverse, they’re stored in a registry using this type as the key. The WeaverseHydrogen.registerElement() method uses this key to map components to their schemas and loaders.
Best Practices:
- Use kebab-case (e.g.,
product-card,hero-banner) - Make it descriptive of the component’s function
- Keep it concise but clear
- Ensure uniqueness across all components
label
The optional label callback makes repeated elements easier to identify in the Page Outline. Studio keeps the component’s title and appends the returned text as a muted, italic suffix: Heading – Summer sale. The Add menu still uses title alone.
Available with
@weaverse/hydrogen 5.22.0 or later (@weaverse/schema 0.17.0 or later).label to each component schema you want to opt in. Annotate data with your component’s props type, as in Pilot’s Heading component:
- Per-instance content: One callback on the component schema applies to all its instances, each with its own current data. There is no global switch or automatic detection of fields such as
titleorname. - Preview language: Data includes current edits and available translations for the preview’s selected content language. Missing translations follow the preview’s normal fallback, not the Studio interface language. Labels update as content or the preview language changes.
- Synchronous plain text: Keep the callback side-effect-free and return a string,
null, orundefined. Do not return JSX, HTML markup, or a Promise. Studio trims surrounding whitespace; missing callbacks, blank/non-string results, thrown errors and async results show only the component title. - Display only: The preview bridge evaluates the callback and sends only the resulting text to Studio. The derived label is not saved to your content, and
createSchema()validation does not execute the callback. Global-section rows keep their saved global-section name.
settings
settings property defines what customization options are available to users in the Weaverse Studio. It’s organized into groups that appear as collapsible sections in the editor interface.
Note: This property was previously calledinspectorand that name is still supported for backward compatibility. However, new components should usesettingsas the canonical property name.
Settings Group Structure
-
group: A label that categorizes a set of related inputs. Common groups include “Content”, “Style”, “Settings”, etc. -
inputs: An array of input configurations that determine the UI controls available for customization.
settings property is used by the Weaverse Studio to generate the UI controls. When a user changes a value in the settings panel, the Weaverse Studio updates the component’s data, which triggers a re-render with the new values.
The schema also influences data initialization. The generateDataFromSchema utility function extracts default values from your schema to create the initial state of a component when it’s added to a page.
Best Practices:
- Organize inputs logically by grouping related controls
- Keep group names consistent across components
- Place frequently used settings in the most accessible groups
- Follow a consistent order (e.g., Content → Style → Settings → Advanced)
Component Relationships
childTypes
childTypes property determines which components can be nested inside the current component. This creates a parent-child relationship that affects both the component hierarchy and the user interface in Weaverse Studio.
When a user tries to add a child component through the editor, only components with types listed in childTypes will be available as options. If childTypes is not specified, the component won’t accept any children.
Under the Hood:
The Weaverse engine uses the childTypes array to filter the available components when a user tries to add a child component. This relationship also influences how data is structured and how components are rendered in the DOM.
Best Practices:
- Only include child types that make logical sense for your component
- Consider the layout and design implications of nested components
- Keep the list focused to avoid overwhelming users with too many options
- Ensure all specified child types exist in your component library
Standalone and Nested Components
Listing a type in any registered component’schildTypes also changes how Studio classifies that type: it is treated as a child-only component and is hidden from the root Add Section picker, even when enabled evaluates to true. enabled controls insertion availability; it is not an opt-in to root-section classification.
To use one component both as a top-level section and nested inside a parent, keep the parent’s childTypes and the child’s stable type, and add enabledOn.groups with 'body' or '*' to the child:
sections/feature-list.tsx
sections/feature-card.tsx
groups: ['body']restricts the component to the body group;groups: ['*']leaves the group unrestricted. Studio currently evaluates body placement only, so either value makes the component eligible for the root Add Section picker.- Use
['*']for a component that previously omittedgroups(or had an empty list), so the opt-in adds no new group restriction. - Every other rule must still pass, including
enabled(afalseresult still hides it) andenabledOn.pages. - Nested insertion is unaffected: the parent’s
childTypesand the child’senabledrule still govern the nested picker.
enabledOn field on dual-use components while migrating other availability logic to enabled.
presets
presets property defines the default configuration and child components when a component is first added to a page. This ensures a polished, ready-to-use experience for users and reduces setup time.
HydrogenComponentPresets Structure
presets property to initialize the component’s data. This includes creating any child components specified in the children array. The data is then passed to the component as props at render time.
Best Practices:
- Design presets with real-world usage in mind
- Include sensible defaults for all important properties
- Pre-configure child components for a complete experience
- Test presets in various contexts to ensure they’re versatile
Component Limitations and Placement
limit
limit property restricts how many instances of a component can exist within its parent container. If no parent exists, the limit applies to the entire page. This is useful for components that should appear only once or a few times for design or performance reasons.
Under the Hood:
When a user tries to add a component, the Weaverse Studio checks the current count of instances against the limit property. If the limit is reached, the component is disabled in the add component UI.
Common Use Cases:
- Limiting header/footer components to one per section
- Restricting promotional banners to prevent overwhelming users
- Controlling resource-intensive components for performance
- Maintaining design coherence by limiting competing elements
enabledOn (deprecated)
enabledOn property controls where components can be used within a theme, but it is deprecated. Use enabled for both static and context-aware availability rules. Existing schemas remain supported, and when both properties are present both rules must pass.
Current placement support: Studio currently evaluates insertion for the body group. Header and footer placement surfaces are not available yet.
Page Types
Thepages array specifies which page types can include this component. Use '*' to allow the component on all page types.
For components that are not listed in any childTypes, migrate page and group checks directly into enabled:
enabled
enabled to control whether a component can be inserted for the current page. A static boolean handles simple feature switches, while a synchronous callback can inspect the active page:
enabled is combined with enabledOn using AND semantics. A component is available only when both rules allow it. The callback is evaluated synchronously in the storefront preview whenever Studio initializes or refreshes its page context; it is never sent over Studio RPC.
Callbacks must be pure and return a boolean immediately. Returning a Promise or another value, or throwing an error, makes the component unavailable for new insertion without breaking Studio. Existing component instances remain visible and editable even when they are no longer available for insertion.
Current placement support: Studio currently evaluates insertion for thebodygroup. Theheaderandfootervalues are reserved for placement surfaces that support those groups in the future.
Data Flow and Component Lifecycle
Understanding how data flows through the component schema system is crucial for effective component development.Schema to Component Data Flow
- Schema Registration: When you define a component’s schema, you’re creating a blueprint for both its UI representation and data structure.
-
Data Initialization: When a component is added to a page, the
generateDataFromSchemautility extracts default values from your schema to create the initial data state. - Preset Application: If presets are defined, they’re applied on top of the default schema values.
- User Customization: When a user changes settings in the settings panel, those values are saved to the component’s data.
- Component Rendering: The component receives its data as props when rendered, allowing it to display the appropriate UI based on user customizations.
Dynamic Inputs with Conditions
Thecondition property in inputs allows you to create dynamic UIs that respond to user choices. The Weaverse engine supports two types of conditions:
- String-based conditions using the format
bindingName.operator.value(Deprecated) - Function-based conditions that can perform more complex logic (Recommended)
Note to users: String-based conditions are deprecated. For new components, we strongly recommend using function-based conditions which offer more flexibility and better type safety.
Complete Example
Let’s look at a comprehensive, real-world example of a component schema:Advanced Features
Data Revalidation
TheshouldRevalidate property on input settings allows you to trigger data reloading when certain inputs change. This is useful for inputs that affect the data fetched by a component’s loader function.
Custom Heading Inputs
The schema system supports special heading inputs that don’t represent data, but help organize the settings UI with section titles.Common Patterns and Best Practices
Organizing Settings Groups
A consistent approach to settings groups improves usability:- Content: Text, images, and other primary content
- Style: Visual presentation, colors, typography, layouts
- Settings: Configuration options, functional settings
- Advanced: Technical options, performance settings
Conditional Logic
Use thecondition property in inputs to create dynamic UI that responds to user choices:
Schema Composition
For complex components, consider decomposing schemas:Migration Guide
Migration from Inspector to Settings
If you have existing components using theinspector property, here’s how to migrate them:
1. Simple Rename
Defining Schemas with createSchema()
HydrogenComponentSchema remains a current public alias of SchemaType. Direct type annotation is supported; createSchema() is a convenient helper that adds non-blocking development diagnostics.
1. Choose an authoring form
2. Use the helper when you want diagnostics
SchemaType contract. It returns immediately, schedules asynchronous warning-based validation only in development, and adds no validation path in production.
Gradual Inspector Migration
During the transition period you can keep both properties. When only one is present, that one is used —inspector alone additionally logs a deprecation warning. When both are present, Weaverse concatenates them, with the settings groups rendered first and the inspector groups appended after:
Troubleshooting
Common Schema Issues
-
Schema Validation Warnings: In development,
createSchema()may log asynchronous warnings for missing required fields, invalid input types, or malformed configuration. It still returns the original schema and does not fail the build. -
Duplicate Type Error: Each component must have a unique
type. Check for duplicates across your entire theme. -
Missing Required Properties: Ensure
titleandtypeare defined. TypeScript checks these for typed schemas; the development validator can also report them as warnings. -
Invalid Input Types: Verify that input
typevalues match those supported by Weaverse. Development validation reports unsupported values as warnings. -
Child Component Not Available: If a child component doesn’t appear in the editor, check that its type is included in the parent’s
childTypesarray. -
Component Not Appearing on Specific Pages: Verify that the
enabledcallback returnstruefor the active page type, handle, locale, and group. -
Registered Component Missing from Add Section: If the type appears in any component’s
childTypes, Studio treats it as child-only. AddenabledOn: { groups: ['*'] }(or['body']) to the component. See Standalone and Nested Components. -
Data Not Refreshing: For components with loaders, check if relevant inputs have
shouldRevalidate: trueset to trigger data refetching. - Schema Changes Not Reflecting: Remember that schema changes require a server restart to take effect in development mode.
-
Deprecation Warnings: If you see warnings about the
inspectorproperty, update your schema to usesettingsinstead. -
Type Errors with createSchema(): If you’re getting TypeScript errors, ensure you’re importing
createSchemacorrectly and that your schema object matches the expected structure.
Related Resources
- Input Settings Guide: Detailed information on all available input types
- Weaverse Component Guide: Comprehensive guide to creating components
- Example Components: Collection of sample components for reference
Conclusion
TheHydrogenComponentSchema is the foundation of your component’s interaction with the Weaverse ecosystem. A well-designed schema creates an intuitive editing experience, ensures components are used appropriately, and provides the flexibility merchants need.
By understanding the properties and patterns described in this guide, you can create components that are both powerful for developers and accessible to merchants. Remember to use settings for new components and migrate existing inspector properties when convenient.