Table of Contents
Val Documentation
Val is a Content Management System (CMS) library that treats content as code, storing it in TypeScript or JavaScript files within your Git repository.
Overview
Val enables developers to manage content directly within their codebase, facilitating version control and streamlined development workflows. Currently, Val supports Next.js version 14 and above.
⚠️ Beta Notice
Val is currently in beta. While the API is relatively stable, some features may be incomplete, and the user experience is subject to change.
Key Features
📝 Content as Code
Manage your content directly within your codebase using TypeScript or JavaScript files, enabling version control and seamless integration with your development workflow.
🌍 Remote Internationalization
Val is developing support for remote i18n, allowing you to define certain languages in code while fetching others remotely.
🔄 Version Control Integration
Content changes are tracked alongside code changes in Git, providing full audit trails and collaborative editing capabilities.
Installation
Using the NextJS starter templates
If you're starting from scratch, the easiest way to get up and running with Val and NextJS is to use npm (or similar) create script:
Integrating into an existing project
Make sure you have NextJS (version 14 or higher) installed
Install the packages:
Optionally, but recommend add the eslint-plugin package:
Run the init script:
Manually
It is also possible to setup Val using the manual configuration guide.
See the manual configuration section below for detailed steps.
Additional setup
- •If you have a monorepo, or have a project where the project is located in a subdirectory relative to the github repository see the monorepos section
- •See formatting published content if you use prettier (or similar) Val to do it as well.
- •If you want editors to update content in production, read up on how to setup remote mode.
Getting started
Create your first Val content file
Content in Val is always defined in `.val.ts` (or `.js`) files.
NOTE: the init script will generate an example Val content file (unless you opt out of it).
Val content files are evaluated by Val, therefore they need to abide a set of requirements.
If you use the eslint plugins these requirements will be enforced. You can also validate val files using the @valbuild/cli: `npx -p @valbuild/cli val validate`.
- •they must export a default content definition (`c.define`) where the first argument equals the path of the file relative to the `val.config` file; and
- •they must be declared in the `val.modules` file; and
- •they must have a default export that is `c.define`; and
- •they can only import Val related files or types (using `import type { MyType } from "./otherModule.ts"`)
Val content file example
The `val.modules` file
Once you have created your Val content file, it must be declared in the `val.modules.ts` (or `.js`) file in the project root folder.
Using Val in Client Components
In client components you can access your content with the `useVal` hook:
Using Val in React Server Components
In React Server components you can access your content with the `fetchVal` function:
Schema Types
Val provides a comprehensive set of schema types for defining your content structure:
Primitive Types
s.string()
String type with optional validation
Available methods:
validate
.maxLength(n)
.minLength(n)
.regex(pattern)
Example:
s.number()
Number type with optional validation
Available methods:
validate
.min(n)
.max(n)
Example:
s.boolean()
Boolean type
Available methods:
validate
Example:
s.literal(value)
Literal value type
Available methods:
validate
Example:
Complex Types
s.object({})
Object type with defined properties
Available methods:
validate
Example:
s.array(schema)
Array type with element schema
Available methods:
validate
.maxLength(n)
.minLength(n)
Example:
s.union(...s.literal(value))
Union type (one of multiple literal values)
Available methods:
validate
Example:
s.union("type", ...s.literal(value))
Discriminated (tagged) union type
Available methods:
validate
Example:
s.keyOf(schema)
Key reference to another Val module
Available methods:
validate
Example:
Media Types
s.image()
Image type with metadata
Available methods:
validate
Example:
c.image(path, metadata)
Image content definition
Example:
Rich Content Types
s.richtext(options)
Rich text with configurable formatting options
Available methods:
validate
Example:
Utility Methods
.nullable()
Makes any schema type nullable
Example:
.optional()
Makes any schema type optional
Example:
.validate()
Custom validation function
Example:
Advanced Usage
Type Inference
Extract TypeScript types from your schemas:
Schema Composition
Compose complex schemas from smaller parts:
Conditional Content
Use unions for conditional content structures:
API Documentation
Core Functions
initVal(config)
Normally you do not need to use this function directly, it should be setup by the init script. Initialize Val with configuration options. Returns schema builders and configuration.
Parameters:
config.project
string- Your project identifier (org/repo)config.gitBranch
string- Current git branch (optional)config.gitCommit
string- Current git commit SHA (optional)config.defaultTheme
'light' | 'dark'- Default theme for Val Studio
Returns:
{ s, c, val, config }
Example:
useVal(moduleVal)
Fetch content data from a Val schema definition (server-side only).
Parameters:
moduleVal
ValModule- The module definition to fetch content for
Returns:
T
Example:
useValRoute(moduleVal, params)
Use this with page.val.ts modules that use the .route() method (client-side only).
Parameters:
moduleVal
ValModule- The module definition to fetch content forparams
Promise<Record<string, string>> | unknown- The parameters to fetch content for, used to resolve the path
Returns:
T
Example:
fetchVal(moduleVal)
Fetch content data from a Val module definition (server-side only).
Parameters:
moduleVal
ValModule- The module definition to fetch content for
fetchVal(moduleVal)
Fetch content data from a Val module definition (server-side only).
Parameters:
moduleVal
ValModule- The module definition to fetch content for
Returns:
Promise<T>
Example:
fetchValRoute(moduleVal, params)
Use this with page.val.ts modules that use the .route() method (server-side only).
Parameters:
moduleVal
ValModule- The module definition to fetch content forparams
Promise<Record<string, string>> | unknown- The parameters to fetch content for, used to resolve the path
Returns:
Promise<T>
Example:
c.define(path, schema, data)
Define content with schema validation and default data.
Parameters:
path
string- File path identifierschema
Schema- Schema definitiondata
T- Default content data
Returns:
ValSchema<T>
Example:
React Components
ValProvider
YouContext provider that enables Val functionality throughout your app.
Props:
config
ValConfig- Configuration object from initValchildren
ReactNode- Child components
Example:
ValRichText
Rich text component that displays Val rich text content.
Props:
children
RichText- Val rich text contenttheme
ValRichTextTheme- Val rich text theme
Example:
ValImage
A wrapper around the NextJS image component which can be used with Val image content.
Props:
src
Image- Val image content
Example:
Server-Side Functions
initValRsc(config, modules, nextjs)
Normally you do not need to use this function directly, it should be setup by the init script. Initialize Val for React Server Components with Next.js integration.
Parameters:
config
ValConfig- Val configurationmodules
ValModules- Val modules definitionnextjs
NextJSIntegration- Next.js integration options
Returns:
{ fetchValStega, fetchValRouteStega, fetchValRouteUrl }
Example:
Client-Side Functions
initValClient(config, modules, nextjs)
Normally you do not need to use this function directly, it should be setup by the init script. Initialize Val for Client Components with Next.js integration.
Parameters:
config
ValConfig- Val configurationmodules
ValModules- Val modules definitionnextjs
NextJSIntegration- Next.js integration options (optional)
Returns:
{ useVal, useValRoute, useValRouteUrl }
Example:
Resources
For more detailed information and advanced usage, visit the Val Next.js README.