docs/static/v0.8/project/contributing/contributing-ui-schemas/index.html
Meshery aims to decouple the UI logic from hardcoded structures and become fully schema-driven. This allows the UI to dynamically adapt based on changes in the underlying schema without requiring constant manual updates. This document explains how to integrate schema definitions from the meshery/schemas repository into the Meshery UI using a code-generation approach.
Meshery’s schemas define the structure of data (constructs) using JSON Schema and their behavior (API operations) using OpenAPI specifications. From these definitions, Meshery auto-generates:
This approach ensures the schemas remain the single source of truth.
All schema definitions live in the meshery/schemas repository.
schemas/
constructs/
v1beta1/
design/
design.json # JSON schema for the noun
design_template.json # JSON template (generated)
design_template.yaml # YAML template (generated)
openapi.yml # OpenAPI spec defining operations
subschemas/ # Optional reusable schema parts
<construct>.json : Defines structure (noun) — e.g., what a Design looks like.openapi.yml : Describes operations (verbs) — e.g., how to GET, POST, or DELETE a design.Templates : Valid, default-filled, resolved objects from the schema.Meshery follows a schema-first approach where the UI is driven by JSON schemas and OpenAPI specifications. Here’s how you can contribute to and use these schemas in the Meshery UI.
If you’re introducing or modifying a UI feature that requires a new schema:
Navigate to the appropriate schema directory:
Define the schema structure in <construct>.json using JSON Schema v7.
Define API operations related to this schema in openapi.yml using OpenAPI v3. This helps generate consistent API types and models that align with your UI needs.
Use the following command to generate TypeScript types and JavaScript schema objects:
make generate-types
This will:
Generate .ts and .d.ts files under:
Create:
After generation:
Open typescript/index.ts
Build the TypeScript package to make the changes usable:
To consume the schema in the UI:
Install the schema package locally:
This will update your package.json to something like:
Now you can import types and schema objects in your UI components:
import { DesignTypes } from "@meshery/schema";
// Type safety!
const renderDesignCard = (design: Design) => <div>{design.name}</div>;
import { DesignSchema } from "@meshery/schema";
const validateDesign = (data) => {
const isValid = ajv.validate(DesignSchema, data);
return isValid;
};
If you're trying to import a schema object or type in the UI but it's missing, it's likely because it hasn't been exported yet from the schemas package.
To keep the package lightweight, only actively used types and objects are exported by default. If you need access to a new schema, simply export it in the Meshery Schemas repository and regenerate the package.
Meshery uses react-jsonschema-form to render forms dynamically based on JSON schemas. All of Meshery’s RJSF schemas are defined in the @sistent/sistent package, which extends schemas from the @meshery/schema package.
This approach enables us to generate forms that automatically adapt to the schema structure without hardcoding field properties like type, enum, description, and others.
import { DesignSchema } from "@meshery/schema";
const designSchema = {
...DesignSchema,
properties: {
...DesignSchema.properties,
name: {
...DesignSchema.properties.name,
description: DesignSchema.properties.description,
ui: {
label: DesignSchema.properties.name.title,
placeholder: DesignSchema.properties.name.description,
},
},
// Other properties with UI-specific enhancements
},
};
OpenAPI schemas (especially request bodies for POST/PUT operations) serve as the foundation for building form logic. These definitions include:
required, format, maxLength)string, integer, date-time)x-rjsf-* for layoutThis ensures alignment between frontend form behavior and backend expectations.
import { DesignTypes } from "@meshery/schema";
const DesignForm = ({ design }: { design: DesignTypes }) => (
<form>
<input type="text" value={design.name} />
</form>
);
Any UI-specific metadata—such as name, type, hints, descriptions, defaults, etc.—is defined directly within the relevant schema object. Elements like tooltips, descriptions, and other metadata are frequently needed across the UI, so having a single source of truth in the schema object ensures consistency and reduces duplication.
For example, if we have a Design schema, the UI retrieves details like the design’s name, description, and other properties directly from the schema object.
Generated TypeScript types from the schema ensure UI components are type-safe and consistent with backend contracts.
import { DesignTypes } from "@meshery/schema";
const DesignCard = ({ design }: { design: DesignTypes }) => (
<div>
<h2>{design.name}</h2>
<p>{design.description}</p>
</div>
);