UNPKG

io-reactive

Version:

Modern reactive UI framework with router, state management, and islands architecture

264 lines (202 loc) 6.68 kB
# IO-Reactive A lightweight and fast next-generation reactive UI library for the web. Supports directives, islands architecture, high performance, and minimal bundle size. --- ## Advantages - **Minimal size**: <100kB (gzip) - **High performance**: optimized rendering and updates - **Directives**: declarative binding, validation, masks, custom behaviors - **Islands architecture**: partial hydration, SSR, lazy component loading - **Compatibility**: easily integrates into existing projects - **TypeScript-first**: strict typing, JSDoc --- ## Installation ```bash npm install io-reactive ``` --- ## Quick Start ### Minimal Example ```typescript import { IO, tag } from 'io-reactive'; // Create a simple component function MyApp() { return new IO(tag.DIV, { text: 'Hello, world!', classList: ['app-container'], }); } // Initialize the app const root = document.getElementById('app'); if (root) { const app = MyApp(); root.appendChild(app.render()); } ``` ### Interactive Example with State ```typescript import { IO, tag } from 'io-reactive'; function CounterApp() { const io = new IO(tag.DIV); // Use built-in state const [count, setCount] = io.state<number>(0); io.components = [ () => new IO(tag.H1, { text: () => `Counter: ${count()}`, }), () => new IO(tag.BUTTON, { text: 'Increment', events: { click: () => setCount(count() + 1), }, }), ]; return io; } // Run the app document.addEventListener('DOMContentLoaded', () => { const root = document.getElementById('app'); if (root) { root.appendChild(CounterApp().render()); } }); ``` --- ## Core Features ### 1. Islands Architecture Revolutionary technology for web optimization. Static content is rendered on the server without JavaScript, and interactive "islands" are hydrated as needed. #### Static Components ```typescript // Static component (SSR, no JS on client) const header = IO.static('header', { classList: ['site-header'], text: 'My Site', }); const page = IO.static('main', {}, [() => header, () => IO.static('p', { text: 'Static content for SEO' })]); ``` #### Interactive Islands ```typescript // Interactive island with hydration const counterIsland = IO.island('div', { hydration: { 'client:visible': true }, // Lazy hydration fallback: () => IO.static('div', { text: 'Loading...' }), component: () => { const counter = new IO('div'); const [count, setCount] = counter.state(0); counter.components = [ () => new IO('span', { text: `Count: ${count()}` }), () => new IO('button', { text: '+', events: { click: () => setCount(count() + 1) }, }), ]; return counter; }, }); // Hybrid page const hybridPage = IO.static('main', {}, [ () => IO.static('h1', { text: 'Static page' }), () => counterIsland(), // Interactive island () => IO.static('footer', { text: 'Static footer' }), ]); ``` #### Hydration Strategies - **`client:load`** — immediate hydration - **`client:idle`** — hydration when browser is idle - **`client:visible`** — lazy hydration (on viewport) - **`client:media`** — conditional hydration (media queries) #### Data Bridge System ```typescript import { IslandDataBridge } from 'io-reactive'; // Set data between islands IslandDataBridge.setData('user', { name: 'John', theme: 'dark' }); // Subscribe to changes IslandDataBridge.subscribe('user', (userData) => { updateTheme(userData.theme); }); ``` **📖 [Detailed documentation on islands architecture](./docs/islands-architecture.md)** ### 2. Directives - **model** — two-way binding: ```ts <input :model="[() => state.value, v => state.value = v]" /> ``` - **validate** — validation: ```ts <input :model="..." :validate="v => v.length > 2 || 'At least 3 characters'" /> ``` - **onSubmit** — handle Enter: ```ts <input :model="..." :onSubmit="v => alert(v)" /> ``` - **debounce** — update delay: ```ts <input :model="..." :debounce="300" /> ``` - **custom** — your own directives: ```ts <input :custom="[{ name: 'my', init: (el, v) => ... }]" /> ``` ### 3. Reactivity - **Signals and state**: ```ts const count = IO.signal(0); count.value++; ``` - **Automatic effects**: ```ts IO.effect(() => console.log(count.value)); ``` ### 4. Validation and Forms - **Built-in validators**: ```ts import { required, minLength } from 'io-reactive/validators'; <input :validate="required" /> <input :validate="minLength(3)" /> ``` - **Input masks**: ```ts <input :mask="{ pattern: '+1 (###) ###-####' }" /> ``` ### 5. Integration and Extensibility - **Compatible with any framework** (can be used as standalone directives or islands) - **Extensible architecture**: write your own directives, plugins, islands --- ## Performance ### Islands architecture provides: - **Minimal JavaScript bundle** — only code for interactive islands is loaded - **Fast Time-to-Interactive** — critical content is static - **Core Web Vitals optimization** — lazy hydration does not block rendering - **SEO benefits** — static HTML is fully indexed --- ## Documentation and Examples - **[Islands architecture](./docs/islands-architecture.md)** — detailed guide on Islands - [Documentation and guides](./src/IO/docs/) - [Demos and examples](../demo-site/) - [Plans and architecture](./plans/) --- ## License MIT ## Публикация пакета и типы ### Как опубликовать новую версию 1. Увеличьте версию: ```bash npm version patch --no-git-tag-version --workspace=packages/io-reactive ``` 2. Соберите пакет: ```bash npm run build -w io-reactive ``` 3. Проверьте, что в dist/ есть .js и .d.ts: ```bash ls packages/io-reactive/dist/ ``` 4. Опубликуйте: ```bash npm publish --access public --workspace=packages/io-reactive ``` ### Как работают типы - Все типы автоматически подтягиваются через зависимость @oi-reactive/shared-types. - Пользователю не нужно явно устанавливать shared-types — типы доступны "из коробки" после установки io-reactive.