### Install Enzyme and Preact Adapter
Source: https://preactjs.com/guide/v10/unit-testing-with-enzyme
Install the necessary Enzyme packages and the Preact adapter for testing.
```bash
npm install --save-dev enzyme enzyme-adapter-preact-pure
```
--------------------------------
### Install Preact X
Source: https://preactjs.com/guide/v10/upgrade-guide
Use this command to install the latest version of Preact X.
```bash
npm install preact
```
--------------------------------
### Install preact-render-to-string
Source: https://preactjs.com/guide/v10/server-side-rendering
Install the server-side renderer package for Preact using npm.
```bash
npm install -S preact-render-to-string
```
--------------------------------
### Start Vite Development Server
Source: https://preactjs.com/guide/v10/getting-started
After creating a new Preact project with Vite, navigate into the project directory and run this command to start a local development server.
```bash
# Go into the generated project folder
cd my-preact-app
# Start a development server
npm run dev
```
--------------------------------
### Install @preact/signals
Source: https://preactjs.com/guide/v10/signals
Command to install the Signals library for Preact projects using npm.
```bash
npm install @preact/signals
```
--------------------------------
### Install Preact Testing Library
Source: https://preactjs.com/guide/v10/preact-testing-library
Install the testing-library Preact adapter using npm. This library requires a DOM environment, which is typically included with Jest.
```bash
npm install --save-dev @testing-library/preact
```
--------------------------------
### setupRerender
Source: https://preactjs.com/guide/v10/api-reference
Setup a rerender function that will drain the queue of pending renders. This is a utility for testing.
```APIDOC
## setupRerender
### Description
Setup a rerender function that will drain the queue of pending renders. This is a utility for testing.
### Method Signature
`setupRerender()`
### Usage Example
```javascript
import { setupRerender } from 'preact/test-utils';
const rerender = setupRerender();
// ... trigger updates ...
rerender(); // Flush pending renders
```
```
--------------------------------
### Replace mobx-preact with mobx-react
Source: https://preactjs.com/guide/v10/upgrade-guide
Remove `mobx-preact` and install `mobx-react` as it's now the recommended package due to increased compatibility.
```bash
npm uninstall mobx-preact
npm install mobx-react
```
--------------------------------
### Pass global state as a prop
Source: https://preactjs.com/guide/v10/signals
Example of how to initialize and pass the global application state as a prop to a component.
```javascript
const state = createAppState();
// ...later:
;
```
--------------------------------
### Basic Preact Setup with Import Maps
Source: https://preactjs.com/guide/v10/no-build-workflows
Demonstrates a minimal Preact application using import maps to resolve module specifiers from a CDN. Ensure Preact is used as a singleton by specifying `?external=preact` for other modules that depend on it.
```html
```
--------------------------------
### Configure Enzyme with Preact Adapter
Source: https://preactjs.com/guide/v10/unit-testing-with-enzyme
Configure Enzyme in your test setup to use the Preact adapter.
```javascript
import { configure } from 'enzyme';
import Adapter from 'enzyme-adapter-preact-pure';
configure({ adapter: new Adapter() });
```
--------------------------------
### Legacy Context API Example
Source: https://preactjs.com/guide/v10/context
Demonstrates how to use the legacy Context API to pass theme information down to a child component. This API is not recommended for new development.
```javascript
function ThemedButton(_props, context) {
return ;
}
class App extends Component {
getChildContext() {
return {
theme: '#673ab8'
};
}
render() {
return (
);
}
}
```
--------------------------------
### Counter Component Example
Source: https://preactjs.com/guide/v10/preact-testing-library
A simple Preact Counter component with state management for displaying and incrementing a count.
```jsx
import { h } from 'preact';
import { useState } from 'preact/hooks';
export function Counter({ initialCount }) {
const [count, setCount] = useState(initialCount);
const increment = () => setCount(count + 1);
return (
Current value: {count}
);
}
```
--------------------------------
### Nested Routing Example
Source: https://preactjs.com/guide/v10/preact-iso
Demonstrates how to implement nested routers to break down routing logic into smaller, manageable components, useful for larger applications.
```APIDOC
## Nested Routing
Some applications would benefit from having routers of multiple levels, allowing to break down the routing logic into smaller components. This is especially useful for larger applications, and we solve this by allowing for multiple nested `` components.
Partially matched routes end with a wildcard (`/*`) and only the remaining value will be passed to descendant routers for further matching. This allows you to create a parent route that matches a base path, and then have child routes that match specific sub-paths.
```javascript
import {
lazy,
LocationProvider,
ErrorBoundary,
Router,
Route
} from 'preact-iso';
import AllMovies from './routes/movies/all.js';
const NotFound = lazy(() => import('./routes/_404.js'));
function App() {
return (
);
}
const TrendingMovies = lazy(() => import('./routes/movies/trending.js'));
const SearchMovies = lazy(() => import('./routes/movies/search.js'));
const MovieDetails = lazy(() => import('./routes/movies/details.js'));
function Movies() {
return (
);
}
```
The `` component will be used for the following routes:
* `/movies/trending`
* `/movies/search`
* `/movies/Inception`
* `/movies/...`
It will not be used for any of the following:
* `/movies`
* `/movies/`
```
--------------------------------
### Initialize Preact Debugging
Source: https://preactjs.com/guide/v10/debugging
Import `preact/debug` as the very first statement in your application's main entry file to enable Preact Devtools. This setup is automatically handled by `@preact/preset-vite`.
```javascript
// Must be the first import
import 'preact/debug';
import { render } from 'preact';
import App from './components/App';
render(, document.getElementById('root'));
```
--------------------------------
### Async Routing Setup with preact-iso
Source: https://preactjs.com/guide/v10/preact-iso
Configure a router with lazy-loaded asynchronous routes. The router handles suspended promises for incoming routes, preserving the outgoing route until the new one is ready. Use `default` for fallback routes.
```javascript
import {
lazy,
LocationProvider,
ErrorBoundary,
Router,
Route
} from 'preact-iso';
// Synchronous
import Home from './routes/home.js';
// Asynchronous (throws a promise)
const Profiles = lazy(() => import('./routes/profiles.js'));
const Profile = lazy(() => import('./routes/profile.js'));
const NotFound = lazy(() => import('./routes/_404.js'));
function App() {
return (
{/* Alternative dedicated route component for better TS support */}
{/* `default` prop indicates a fallback route. Useful for 404 pages */}
);
}
```
--------------------------------
### Creating a Reusable Counter Model
Source: https://preactjs.com/guide/v10/signals
Models encapsulate signals, computed values, and actions into reusable state containers. This example demonstrates creating a `CounterModel` with `increment` and `decrement` actions.
```javascript
import { signal, computed, createModel } from '@preact/signals';
const CounterModel = createModel((initialCount = 0) => {
const count = signal(initialCount);
const doubled = computed(() => count.value * 2);
return {
count,
doubled,
increment() {
count.value++;
},
decrement() {
count.value--;
}
};
});
const counter = new CounterModel(5);
counter.increment();
console.log(counter.count.value); // 6
```
--------------------------------
### Setup Rerender for Testing
Source: https://preactjs.com/guide/v10/api-reference
Configures a rerender function designed to drain the queue of pending renders, essential for testing component updates.
```javascript
import { setupRerender } from 'preact/test-utils';
setupRerender()
```
--------------------------------
### Full useErrorBoundary Implementation
Source: https://preactjs.com/guide/v10/hooks
A complete example demonstrating how to use `useErrorBoundary` to catch errors, display a user-friendly error message, and provide a 'Try again' button that resets the error.
```javascript
const App = props => {
const [error, resetError] = useErrorBoundary(error =>
callMyApi(error.message)
);
// Display a nice error message
if (error) {
return (
{error.message}
);
} else {
return
{props.children}
;
}
};
> If you've been using the class based component API in the past, then this hook is essentially an alternative to the componentDidCatch lifecycle method. This hook was introduced with Preact 10.2.0.
```
--------------------------------
### Basic Text Input with State Update (Class Component)
Source: https://preactjs.com/guide/v10/forms
Use the `onInput` event to capture keystrokes and update component state. This example shows how to bind input value to state and display it.
```jsx
class BasicInput extends Component {
state = { name: '' };
onInput = e => this.setState({ name: e.currentTarget.value });
render(_, { name }) {
return (
Hello {name}
);
}
}
```
--------------------------------
### Create a Class Component with State and Lifecycle Methods in Preact
Source: https://preactjs.com/guide/v10/components
Implement a class component that extends `Component` to manage internal state and respond to lifecycle events. This example creates a `` component that displays the current time and updates it every second using `setInterval` and `setState`.
```javascript
class Clock extends Component {
constructor() {
super();
this.state = { time: Date.now() };
}
// Lifecycle: Called whenever our component is created
componentDidMount() {
// update time every second
this.timer = setInterval(() => {
this.setState({ time: Date.now() });
}, 1000);
}
// Lifecycle: Called just before our component will be destroyed
componentWillUnmount() {
// stop when not renderable
clearInterval(this.timer);
}
render() {
let time = new Date(this.state.time).toLocaleTimeString();
return {time};
}
}
```
--------------------------------
### Render a Preact tree with multiple root elements
Source: https://preactjs.com/guide/v10/preact-root-fragment
When a Preact tree produces multiple root elements (like a Fragment or Array), `createRootFragment` can accept an array of children. This example renders only the last two child elements of the `document.body`.
```javascript
import { createRootFragment } from 'preact-root-fragment';
import { render } from 'preact';
function App() {
return (
<>
Example
Hello world!
>
);
}
// Use only the last two child elements within :
const children = [].slice.call(document.body.children, -2);
render(, createRootFragment(document.body, children));
```
--------------------------------
### Create a New Preact App with Vite
Source: https://preactjs.com/guide/v10/getting-started
Use the `create-preact` CLI to quickly scaffold a new Preact application powered by Vite. This is recommended for most new projects.
```bash
npm init preact
```
--------------------------------
### Get Current VNode in Preact
Source: https://preactjs.com/guide/v10/api-reference
Retrieves the current VNode being rendered. Logs the VNode object to the console.
```javascript
import { render } from 'preact';
import { getCurrentVNode } from 'preact/debug';
function MyComponent() {
const currentVNode = getCurrentVNode();
console.log(currentVNode); // Logs: Object { type: MyComponent(), props: {}, key: undefined, ref: undefined, ... }
return
Hello World!
}
render(, document.getElementById('app'));
```
--------------------------------
### Create Production Build with Vite
Source: https://preactjs.com/guide/v10/getting-started
Once your Preact application is ready, use this command to generate an optimized production build. The output will be placed in the `dist/` folder.
```bash
npm run build
```
--------------------------------
### Full Todo List State and Logic Simulation
Source: https://preactjs.com/guide/v10/signals
Combines signal initialization, the add todo function, and simulates adding a todo item to verify the logic.
```javascript
import { signal } from '@preact/signals';
const todos = signal([{ text: 'Buy groceries' }, { text: 'Walk the dog' }]);
const text = signal('');
function addTodo() {
todos.value = [...todos.value, { text: text.value }];
text.value = ''; // Reset input value on add
}
// Check if our logic works
console.log(todos.value);
// Logs: [{text: "Buy groceries"}, {text: "Walk the dog"}]
// Simulate adding a new todo
text.value = 'Tidy up';
addTodo();
// Check that it added the new item and cleared the `text` signal:
console.log(todos.value);
// Logs: [{text: "Buy groceries"}, {text: "Walk the dog"}, {text: "Tidy up"}]
console.log(text.value); // Logs: ""
```
--------------------------------
### Migrate preact-portal to preact/compat
Source: https://preactjs.com/guide/v10/upgrade-guide
Remove `preact-portal` and import `createPortal` directly from `preact/compat`.
```bash
npm uninstall preact-portal
```
--------------------------------
### getCurrentVNode
Source: https://preactjs.com/guide/v10/api-reference
Gets the current VNode being rendered. This is useful for inspecting the current component's virtual node during rendering.
```APIDOC
## getCurrentVNode
### Description
Gets the current VNode being rendered. This is useful for inspecting the current component's virtual node during rendering.
### Method Signature
`getCurrentVNode()`
### Usage Example
```javascript
import { getCurrentVNode } from 'preact/debug';
function MyComponent() {
const currentVNode = getCurrentVNode();
console.log(currentVNode);
return
Hello World!
;
}
```
```
--------------------------------
### Create Context with Initial State
Source: https://preactjs.com/guide/v10/context
Use `createContext` to create a new context. It accepts an initial state argument. This initial state is used when no Provider is present above the consumer.
```javascript
import { createContext } from 'preact';
export const Theme = createContext('light');
export const User = createContext({ name: 'Guest' });
export const Locale = createContext(null);
```
--------------------------------
### Get Owner Stack in Preact
Source: https://preactjs.com/guide/v10/api-reference
Returns the component stack captured up to the current point. Logs the stack to the console when an h1 element is diffed.
```javascript
import { render, options } from 'preact';
import { getOwnerStack } from 'preact/debug';
const oldVNode = options.diffed;
options.diffed = (vnode) => {
if (vnode.type === 'h1') {
console.log(getOwnerStack(vnode));
// Logs:
//
// in h1 (at /path/to/file.jsx:17)
// in MyComponent (at /path/to/file.jsx:20)
}
if (oldVNode) oldVNode(vnode);
};
function MyComponent() {
return
Hello World!
;
}
render(, document.getElementById('app'));
```
--------------------------------
### Create and Update a Signal
Source: https://preactjs.com/guide/v10/signals
Demonstrates how to create a signal with an initial value and how to read and update its value using the `.value` property.
```javascript
import { signal } from '@preact/signals';
const count = signal(0);
// Read a signal’s value by accessing .value:
console.log(count.value); // 0
// Update a signal’s value:
count.value += 1;
// The signal's value has changed:
console.log(count.value); // 1
```
--------------------------------
### Get Display Name of VNode
Source: https://preactjs.com/guide/v10/api-reference
Returns a string representation of a Virtual DOM Element's type. Useful for debugging and error messages.
```javascript
import { h } from 'preact';
import { getDisplayName } from 'preact/debug';
getDisplayName(h('div')); // "div"
getDisplayName(h(MyComponent)); // "MyComponent"
getDisplayName(h(() => )); // ""
```
--------------------------------
### resetPropWarnings
Source: https://preactjs.com/guide/v10/api-reference
Resets the internal history of which prop type warnings have already been logged. This is useful when running tests to ensure each test starts with a clean slate.
```APIDOC
## resetPropWarnings
### Description
Resets the internal history of which prop type warnings have already been logged. This is useful when running tests to ensure each test starts with a clean slate.
### Method Signature
`resetPropWarnings()`
### Usage Example
```javascript
import { resetPropWarnings } from 'preact/debug';
// ... after logging warnings ...
resetPropWarnings();
```
```
--------------------------------
### Basic Preact App in Browser (No Build Tools)
Source: https://preactjs.com/guide/v10/getting-started
Use this method for simple projects or when you want to avoid build tools. It requires importing Preact directly via an ES module URL.
```javascript
import { h, render } from 'https://esm.sh/preact';
// Create your app
const app = h('h1', null, 'Hello World!');
render(app, document.body);
```
--------------------------------
### Error Boundary with Error Notification
Source: https://preactjs.com/guide/v10/hooks
This example shows how to use `useErrorBoundary` with an optional callback to notify an external service (e.g., an API) when an error occurs.
```javascript
const [error] = useErrorBoundary(error => callMyApi(error.message));
```
--------------------------------
### Count Children with Children.count
Source: https://preactjs.com/guide/v10/api-reference
Get the total number of children in a collection. This utility is part of the compatibility layer and can be used to determine how many child elements are present.
```javascript
import { Children } from 'preact/compat';
function MyComponent(props) {
const children = Children.count(props.children);
return
I have {children.length} children
;
}
```
--------------------------------
### Define Routes with Router and Route Components
Source: https://preactjs.com/guide/v10/preact-iso
Use `Router` and `Route` components from `preact-iso` to define application routes. Both `` and `` are equivalent for defining routes.
```jsx
import { LocationProvider, Router, Route } from 'preact-iso';
function App() {
return (
{/* Both of these are equivalent */}
);
}
```
--------------------------------
### Enzyme Rendering Modes
Source: https://preactjs.com/guide/v10/unit-testing-with-enzyme
Demonstrates the three rendering modes provided by Enzyme: mount, shallow, and render.
```javascript
import { mount, shallow, render } from 'enzyme';
// Render the full component tree:
const wrapper = mount();
// Render only `MyComponent`'s direct output (ie. "mock" child components
// to render only as placeholders):
const wrapper = shallow();
// Render the full component tree to an HTML string, and parse the result:
const wrapper = render();
```
--------------------------------
### Get the Only Child with Children.only
Source: https://preactjs.com/guide/v10/api-reference
Retrieve the single child from a collection, throwing an error if the number of children is not exactly one. This ensures that a component receives precisely one child.
```javascript
import { Children } from 'preact/compat';
function List(props) {
const singleChild = Children.only(props.children);
return (
{singleChild}
);
}
```
--------------------------------
### Lazy computation of computed signals
Source: https://preactjs.com/guide/v10/signals
Computed signals are lazy by default and only re-compute when their value is accessed. This example shows how accessing `double.value` triggers its re-computation after `count` has been updated.
```javascript
const count = signal(0);
const double = computed(() => count.value * 2);
// Despite updating the `count` signal on which the `double` signal depends,
// `double` does not yet update because nothing has used its value.
count.value = 1;
// Reading the value of `double` triggers it to be re-computed:
console.log(double.value); // Logs: 2
```
--------------------------------
### Manage global state with Preact Context
Source: https://preactjs.com/guide/v10/signals
Demonstrates using Preact's Context API to provide and consume global application state across components, avoiding prop drilling.
```javascript
import { createContext } from 'preact';
import { useContext } from 'preact/hooks';
import { createAppState } from './my-app-state';
const AppState = createContext();
render(
);
// ...later when you need access to your app state
function App() {
const state = useContext(AppState);
return
{state.completed}
;
}
```
--------------------------------
### Access Custom Element Instance Methods with Refs
Source: https://preactjs.com/guide/v10/web-components
Use `useRef` to get a reference to a custom element instance, allowing you to call its methods or access its properties within `useEffect`.
```javascript
function Foo() {
const myRef = useRef(null);
useEffect(() => {
if (myRef.current) {
myRef.current.doSomething();
}
}, []);
return ;
}
```
--------------------------------
### Styling with CSS Custom Properties
Source: https://preactjs.com/guide/v10/whats-new
Apply CSS variables directly within the style prop for dynamic styling. This example sets a '--theme-color' CSS custom property.
```jsx
function Foo(props) {
return
{props.children}
;
}
```
--------------------------------
### Custom Render Function with Context Providers
Source: https://preactjs.com/guide/v10/preact-testing-library
Create a custom `render` function by wrapping the original from `@testing-library/preact`. This is useful for providing common context providers like routers or state management to all test cases.
```javascript
// helpers.js
import { render as originalRender } from '@testing-library/preact';
import { createMemoryHistory } from 'history';
import { FooContext } from './foo';
const history = createMemoryHistory();
export function render(vnode) {
return originalRender(
{vnode}
);
}
// Usage like usual. Look ma, no providers!
render();
```
--------------------------------
### Prerender with preact-iso
Source: https://preactjs.com/guide/v10/preact-iso
Use `prerender()` to render a VDOM tree to an HTML string using `preact-render-to-string`. It returns an object with `html` and `links` properties, useful for static site generation.
```javascript
import {
LocationProvider,
ErrorBoundary,
Router,
lazy,
prerender
} from 'preact-iso';
// Asynchronous (throws a promise)
const Foo = lazy(() => import('./foo.js'));
const Bar = lazy(() => import('./bar.js'));
function App() {
return (
);
}
const { html, links } = await prerender();
```
--------------------------------
### Importing from Preact Core
Source: https://preactjs.com/guide/v10/upgrade-guide
Demonstrates the shift from default exports to named exports in Preact X for improved tree-shaking. The named export approach is compatible with both Preact 8.x and Preact X.
```javascript
// Preact 8.x
import Preact from 'preact';
// Preact X
import * as preact from 'preact';
// Preferred: Named exports (works in 8.x and Preact X)
import { h, Component } from 'preact';
```
--------------------------------
### Initialize Todo List Signal
Source: https://preactjs.com/guide/v10/signals
Initializes a signal to hold the list of todo items. Each item is an object with a 'text' property.
```javascript
import { signal } from '@preact/signals';
const todos = signal([{ text: 'Buy groceries' }, { text: 'Walk the dog' }]);
```
--------------------------------
### Class Component: Limited Input (3 Characters)
Source: https://preactjs.com/guide/v10/forms
Example of a controlled component using a class component to limit input to 3 characters. It uses refs to manage cursor position when the input exceeds the limit.
```jsx
class LimitedInput extends Component {
state = { value: '' };
inputRef = createRef(null);
onInput = e => {
if (e.currentTarget.value.length <= 3) {
this.setState({ value: e.currentTarget.value });
} else {
const start = this.inputRef.current.selectionStart;
const end = this.inputRef.current.selectionEnd;
const diffLength = Math.abs(
e.currentTarget.value.length - this.state.value.length
);
this.inputRef.current.value = this.state.value;
// Restore selection
this.inputRef.current.setSelectionRange(
start - diffLength,
end - diffLength
);
}
};
render(_, { value }) {
return (
);
}
}
```
--------------------------------
### Switch from preact-redux to react-redux
Source: https://preactjs.com/guide/v10/upgrade-guide
Replace `preact-redux` with `react-redux` and alias `react` and `react-dom` to `preact/compat`.
```bash
npm uninstall preact-redux
npm install react-redux
```
--------------------------------
### Import Map for Preact with Hooks, Signals, and HTM
Source: https://preactjs.com/guide/v10/no-build-workflows
Configures import maps to include Preact, its hooks, signals, and HTM. Uses esm.sh CDN and specifies `?external=preact` to ensure Preact is treated as a singleton.
```json
{
"imports": {
"preact": "https://esm.sh/preact@10.23.1",
"preact/": "https://esm.sh/preact@10.23.1/",
"@preact/signals": "https://esm.sh/@preact/signals@1.3.0?external=preact",
"htm/preact": "https://esm.sh/htm@3.1.1/preact?external=preact"
}
}
```
--------------------------------
### Functional Component: Limited Input (3 Characters)
Source: https://preactjs.com/guide/v10/forms
Example of a controlled component using a functional component with hooks to limit input to 3 characters. It uses refs to manage cursor position when the input exceeds the limit.
```jsx
const LimitedInput = () => {
const [value, setValue] = useState('');
const inputRef = useRef();
const onInput = e => {
if (e.currentTarget.value.length <= 3) {
setValue(e.currentTarget.value);
} else {
const start = inputRef.current.selectionStart;
const end = inputRef.current.selectionEnd;
const diffLength = Math.abs(e.currentTarget.value.length - value.length);
inputRef.current.value = value;
// Restore selection
inputRef.current.setSelectionRange(start - diffLength, end - diffLength);
}
};
return (
);
};
```
--------------------------------
### Reading signal value without subscription using .peek()
Source: https://preactjs.com/guide/v10/signals
Use `.peek()` to get a signal's current value within an effect without creating a subscription to that signal. This prevents the effect from re-running when the peeked signal changes.
```javascript
const delta = signal(0);
const count = signal(0);
effect(() => {
// Update `count` without subscribing to `count`:
count.value = count.peek() + delta.value;
});
// Setting `delta` reruns the effect:
delta.value = 1;
// This won't rerun the effect because it didn't access `.value`:
count.value = 10;
```
--------------------------------
### Implement Nested Routing with Preact-ISO Router
Source: https://preactjs.com/guide/v10/preact-iso
Demonstrates how to set up nested routers to manage complex routing structures. Partially matched parent routes use a wildcard (/*) to pass remaining path segments to child routers for further matching.
```jsx
import {
lazy,
LocationProvider,
ErrorBoundary,
Router,
Route
} from 'preact-iso';
import AllMovies from './routes/movies/all.js';
const NotFound = lazy(() => import('./routes/_404.js'));
function App() {
return (
);
}
const TrendingMovies = lazy(() => import('./routes/movies/trending.js'));
const SearchMovies = lazy(() => import('./routes/movies/search.js'));
const MovieDetails = lazy(() => import('./routes/movies/details.js'));
function Movies() {
return (
);
}
```
--------------------------------
### Create a Functional Component in Preact
Source: https://preactjs.com/guide/v10/components
Define a functional component by creating a JavaScript function that accepts props. Ensure the function name starts with an uppercase letter for JSX compatibility. This component renders a div with dynamic content based on the 'name' prop.
```javascript
function MyComponent(props) {
return
My name is {props.name}.
;
}
// Usage
const App = ;
// Renders:
My name is John Doe.
render(App, document.body);
```
--------------------------------
### Set a Custom `vnode` Option Hook in Preact
Source: https://preactjs.com/guide/v10/options
This example demonstrates how to set a custom `vnode` hook. Always store the previous hook and call it within your new hook to avoid breaking existing functionality. This hook is invoked whenever a VNode object is created.
```javascript
import { options } from 'preact';
// Store previous hook
const oldHook = options.vnode;
// Set our own options hook
options.vnode = vnode => {
console.log("Hey I'm a vnode", vnode);
// Call previously defined hook if there was any
if (oldHook) {
oldHook(vnode);
}
};
```
--------------------------------
### Hydrate Preact Application from Server-Rendered HTML
Source: https://preactjs.com/guide/v10/api-reference
Use `hydrate()` instead of `render()` to attach event listeners and set up the component tree for pre-rendered or server-side-rendered applications, bypassing most diffing work.
```javascript
import { hydrate } from 'preact';
const Foo = () =>
foo
;
hyhydrate(, document.getElementById('container'));
```
--------------------------------
### Initialize Text Input Signal and Add Todo Function
Source: https://preactjs.com/guide/v10/signals
Creates a signal for input text and a function to add a new todo item to the list. Updates to the signal's .value property trigger changes.
```javascript
// We'll use this for our input later
const text = signal('');
function addTodo() {
todos.value = [...todos.value, { text: text.value }];
text.value = ''; // Clear input value on add
}
```
--------------------------------
### createModel(factory)
Source: https://preactjs.com/guide/v10/signals
Creates a model constructor from a factory function. The factory can accept initialization arguments and should return an object containing signals, computed values, and action methods. Models can be disposed of using `Symbol.dispose`.
```APIDOC
## createModel(factory)
### Description
The `createModel(factory)` function creates a model constructor from a factory function. The factory function can accept arguments for initialization and should return an object containing signals, computed values, and action methods.
### Example
```javascript
import { signal, computed, effect, createModel } from '@preact/signals';
const CounterModel = createModel((initialCount = 0) => {
const count = signal(initialCount);
const doubled = computed(() => count.value * 2);
effect(() => {
console.log('Count changed:', count.value);
});
return {
count,
doubled,
increment() {
count.value++;
},
decrement() {
count.value--;
}
};
});
// Create a new model instance using `new`
const counter = new CounterModel(5);
counter.increment(); // Updates are automatically batched
console.log(counter.count.value); // 6
console.log(counter.doubled.value); // 12
// Clean up all effects when done
counter[Symbol.dispose]();
```
> **TypeScript:** Calling `model[Symbol.dispose]()` requires `"ESNext.Disposable"` (or `"ESNext"`) in your `tsconfig.json` `lib` array.
```
--------------------------------
### Update preact-render-to-string
Source: https://preactjs.com/guide/v10/upgrade-guide
Update `preact-render-to-string` to version 5.x to ensure compatibility with Preact X.
```bash
npm install preact-render-to-string@5.x
```
--------------------------------
### Subscribe to External Stores with useSyncExternalStore
Source: https://preactjs.com/guide/v10/hooks
Use `useSyncExternalStore` from `preact/compat` to subscribe to external data sources like global state management libraries or browser APIs.
```jsx
import { useSyncExternalStore } from 'preact/compat';
function subscribe(cb) {
addEventListener('scroll', cb);
return () => removeEventListener('scroll', cb);
}
function App() {
const scrollY = useSyncExternalStore(subscribe, () => window.scrollY);
}
```
--------------------------------
### Preact with HTM for JSX-like Syntax (No Build Tools)
Source: https://preactjs.com/guide/v10/getting-started
This approach uses HTM with Preact to write JSX-like templates directly in the browser without a build step. Initialize HTM by binding it to Preact's `h` function.
```javascript
import { h, render } from 'https://esm.sh/preact';
import htm from 'https://esm.sh/htm';
// Initialize htm with Preact
const html = htm.bind(h);
function App(props) {
return html`
Hello ${props.name}!
`;
}
render(
html`<${App} name="World" />`,
document.body
);
```
--------------------------------
### Using Keys with Fragments in Loops
Source: https://preactjs.com/guide/v10/components
When creating Fragments within a loop, it's crucial to provide a `key` prop to each Fragment. This helps Preact efficiently update the list by identifying which elements have changed.
```jsx
function Glossary(props) {
return (
{props.items.map(item => (
{item.term}
{item.description}
))}
);
}
```
--------------------------------
### Importing preact/compat in Preact X
Source: https://preactjs.com/guide/v10/whats-new
In Preact X, the compatibility layer is imported directly from 'preact/compat' instead of the separate 'preact-compat' package.
```javascript
// Preact 8.x
import React from 'preact-compat';
// Preact X
import React from 'preact/compat';
```
--------------------------------
### Synchronous Rendering with renderToString
Source: https://preactjs.com/guide/v10/server-side-rendering
Use renderToString to synchronously transform a Preact component tree into an HTML string. This is the most basic rendering method.
```javascript
import { renderToString } from 'preact-render-to-string';
const name = 'Preact User!';
const App =
Hello {name}
;
const html = renderToString(App);
console.log(html);
//
Hello Preact User!
```
--------------------------------
### Preact Component with HTM
Source: https://preactjs.com/guide/v10/no-build-workflows
Demonstrates how to define Preact components and render them using HTM's tagged template literals. This approach avoids a build step.
```javascript
import { useState } from 'preact/hooks';
import { html } from 'htm/preact';
function Button({ action, children }) {
return html`
`;
}
function Counter() {
const [count, setCount] = useState(0);
return html`
`;
}
render(
html`<${Counter} />`,
document.getElementById('app')
);
```
--------------------------------
### Create a basic signal
Source: https://preactjs.com/guide/v10/signals
Creates a new signal with an initial value. The signal's value can be accessed and modified via its `.value` property.
```javascript
const count = signal(0);
```
--------------------------------
### Lazy Load Components with preact-iso
Source: https://preactjs.com/guide/v10/preact-iso
Use `lazy()` to create code-split components. It takes an async function that resolves to a component. The wrapper component loads the actual component on first render. Use `preload()` to load the component before it's needed.
```javascript
import { lazy, LocationProvider, Router } from 'preact-iso';
// Synchronous, not code-splitted:
import Home from './routes/home.js';
// Asynchronous, code-splitted:
const Profiles = lazy(() =>
import('./routes/profiles.js').then(m => m.Profiles)
); // Expects a named export called `Profiles`
const Profile = lazy(() => import('./routes/profile.js')); // Expects a default export
function App() {
return (
);
}
```
```javascript
const Profile = lazy(() => import('./routes/profile.js'));
function Home() {
return (
Profile.preload()}>
Profile Page -- Hover over me to preload the module!
);
}
```
--------------------------------
### action(fn)
Source: https://preactjs.com/guide/v10/signals
Wraps a function to execute it within a batched and untracked context. This is useful for creating standalone actions outside of models.
```APIDOC
## action(fn)
### Description
The `action(fn)` function wraps a function to run in a batched and untracked context. This is useful when you need to create standalone actions outside of a model:
### Example
```javascript
import { signal, action } from '@preact/signals';
const count = signal(0);
const incrementBy = action((amount) => {
count.value += amount;
});
incrementBy(5); // Batched update
```
```
--------------------------------
### Manage Transitions with useTransition
Source: https://preactjs.com/guide/v10/hooks
The `useTransition` hook from `preact/compat` is a stubbed-out implementation because Preact does not support concurrent rendering. `isPending` will always be `false`, and `startTransition` is a no-op.
```jsx
import { useTransition } from 'preact/compat';
function App() {
// `isPending` will always be `false`
const [isPending, startTransition] = useTransition();
const handleClick = () => {
// Immediately executes the callback, it's a no-op.
startTransition(() => {
// Transition code here
});
};
}
```
--------------------------------
### Using Hooks with useState and useCallback
Source: https://preactjs.com/guide/v10/whats-new
Leverage Hooks for state management and memoized callbacks. Import `useState` and `useCallback` from `preact/hooks`.
```jsx
function Counter() {
const [value, setValue] = useState(0);
const increment = useCallback(() => setValue(value + 1), [value]);
return (
Counter: {value}
);
}
```
--------------------------------
### Enable Preact Debugging
Source: https://preactjs.com/guide/v10/differences-to-react
Import 'preact/debug' at the top of your main entry file to enable helpful warnings and errors, and to attach the Preact Developer Tools browser extension.
```javascript
import 'preact/debug'; // <-- Add this line at the top of your main entry file
```
--------------------------------
### Update preact-jsx-chai
Source: https://preactjs.com/guide/v10/upgrade-guide
Update `preact-jsx-chai` to version 3.x to work with Preact X.
```bash
npm install preact-jsx-chai@3.x
```
--------------------------------
### Create a Context Object with createContext
Source: https://preactjs.com/guide/v10/api-reference
Use createContext to initialize a new Context object. This enables data to be passed down the component tree without explicit prop drilling.
```javascript
import { createContext } from 'preact';
const MyContext = createContext(defaultValue);
```
--------------------------------
### options
Source: https://preactjs.com/guide/v10/api-reference
Provides access to Preact's option hooks for customizing behavior.
```APIDOC
## options
### Description
See the Option Hooks documentation for more details.
```
--------------------------------
### useMemo for Memoizing Computations
Source: https://preactjs.com/guide/v10/hooks
Use useMemo to memoize the result of an expensive computation. The computation is only recalculated when its dependencies change.
```javascript
const memoized = useMemo(
() => expensive(a, b),
// Only re-run the expensive function when any of these
// dependencies change
[a, b]
);
```
--------------------------------
### Create global app state with signals
Source: https://preactjs.com/guide/v10/signals
Define a function to create and manage global application state using signals and computed signals. This approach helps in organizing state for testing and larger applications.
```javascript
function createAppState() {
const todos = signal([]);
const completed = computed(() => {
return todos.value.filter(todo => todo.completed).length;
});
return { todos, completed };
}
```
--------------------------------
### Hydrate Preact App with preact-iso
Source: https://preactjs.com/guide/v10/preact-iso
Use `hydrate()` as a wrapper around Preact's `hydrate` to switch between hydrating and rendering based on prerendering. It ensures rendering only happens in the browser.
```javascript
import { hydrate } from 'preact-iso';
function App() {
return (
Hello World
);
}
hydrate();
```
--------------------------------
### Context API with createContext and Consumer
Source: https://preactjs.com/guide/v10/whats-new
Utilize the createContext API for a robust pub/sub solution to deliver updates deep down the component tree, avoiding issues with shouldComponentUpdate.
```jsx
const Theme = createContext('light');
function ThemedButton(props) {
return (
{theme =>
Active theme: {theme}
}
);
}
function App() {
return (
);
}
```
--------------------------------
### Test Counter Component with Enzyme
Source: https://preactjs.com/guide/v10/unit-testing-with-enzyme
Write tests for the Counter component to verify its initial state and increment functionality.
```javascript
import { expect } from 'chai';
import { h } from 'preact';
import { mount } from 'enzyme';
import Counter from '../src/Counter';
describe('Counter', () => {
it('should display initial count', () => {
const wrapper = mount();
expect(wrapper.text()).to.include('Current value: 5');
});
it('should increment after "Increment" button is clicked', () => {
const wrapper = mount();
wrapper.find('button').simulate('click');
expect(wrapper.text()).to.include('Current value: 6');
});
});
```
--------------------------------
### render(virtualDom, containerNode, [replaceNode])
Source: https://preactjs.com/guide/v10/api-reference
Render a Virtual DOM Element into a parent DOM element containerNode. This function does not return anything.
```APIDOC
## render(virtualDom, containerNode, [replaceNode])
### Description
Render a Virtual DOM Element into a parent DOM element `containerNode`. Does not return anything.
### Parameters
* **virtualDom** - A valid Virtual DOM Element to render.
* **containerNode** - The parent DOM element where the virtualDom will be rendered.
* **[replaceNode]** - Optional. If provided, Preact will update or replace this element instead of inferring where to start rendering. Note: This argument will be removed in Preact v11.
```
--------------------------------
### Create reusable state models with createModel()
Source: https://preactjs.com/guide/v10/signals
The `createModel(factory)` function generates a constructor for state models. The factory function initializes signals, computed values, and actions. Models created with `createModel` can be instantiated using `new` and should be disposed of using `[Symbol.dispose]()` when no longer needed.
```javascript
import { signal, computed, effect, createModel } from '@preact/signals';
const CounterModel = createModel((initialCount = 0) => {
const count = signal(initialCount);
const doubled = computed(() => count.value * 2);
effect(() => {
console.log('Count changed:', count.value);
});
return {
count,
doubled,
increment() {
count.value++;
},
decrement() {
count.value--;
}
};
});
// Create a new model instance using `new`
const counter = new CounterModel(5);
counter.increment(); // Updates are automatically batched
console.log(counter.count.value); // 6
console.log(counter.doubled.value); // 12
// Clean up all effects when done
counter[Symbol.dispose]();
```
--------------------------------
### jsxTemplate
Source: https://preactjs.com/guide/v10/api-reference
Create a template vnode. Used by Deno's "precompile" transform.
```APIDOC
## jsxTemplate
### Description
Create a template vnode. Used by Deno's "precompile" transform.
### Method Signature
`jsxTemplate(templates, ...exprs)`
### Parameters
- **templates** (string[]) - An array of template string parts.
- **...exprs** (any[]) - Expressions to be interpolated into the template.
### Usage Example
```javascript
import { jsxTemplate } from 'preact/jsx-runtime';
const name = 'World';
jsxTemplate`Hello, ${name}!`;
```
```