@semiont/react-ui
v0.5.1
Published
React components and hooks for Semiont
Readme
@semiont/react-ui
Framework-agnostic React component library for building Semiont knowledge management applications.
Overview
@semiont/react-ui provides reusable React components, hooks, and utilities for creating Semiont applications. The library is designed to be completely framework-agnostic, working seamlessly with Next.js, Create React App, Vite, Remix, or any other React framework.
Key Features
- Framework Independence - Zero dependencies on Next.js, next-auth, or next-intl
- Component Composition - Components accept framework-specific implementations (Link, routing) as props
- Provider Pattern - Consistent approach for session, translations, API client, and routing
- Type-Safe API Hooks - React Query wrappers for all Semiont API operations
- Authentication Components - Sign-in, sign-up, and error display components
- Navigation Components - Collapsible sidebar with drag & drop resource tabs
- Modal Components - Global search and resource selection modals
- Accessibility First - WCAG compliant with keyboard navigation, screen reader support
- Comprehensive Testing - 1250+ tests with extensive coverage
- Annotation System - Rich annotation and tagging capabilities
- Built-in Translations - English and Spanish included, with dynamic loading for optimal bundle size
- Flexible i18n - Three modes: default English, built-in locales, or custom translation system
- Favicon Assets - Complete set of Semiont branded favicons for all platforms
Installation
npm install @semiont/react-ui @semiont/api-client @tanstack/react-queryPeer Dependencies
{
"react": "^18.0.0",
"react-dom": "^18.0.0",
"@tanstack/react-query": "^5.0.0",
"@semiont/api-client": "*"
}CSS Setup
Import the styles in your app's main CSS file:
/* Your app's main CSS file (e.g., globals.css, app.css) */
@import '@semiont/react-ui/styles';Requirements:
- Your build system must support PostCSS with
postcss-importplugin - This is standard in Next.js, Vite, and most modern build tools
- The package exports source CSS files, which your build system will process
What this does:
- Imports all component styles, design tokens, and CSS variables
- Your build tool processes the
@importstatements and bundles the CSS - No additional configuration needed in most frameworks
Quick Start
1. Set Up Providers
import {
TranslationProvider,
ApiClientProvider,
KnowledgeBaseSessionProvider,
ProtectedErrorBoundary,
SessionExpiredModal,
PermissionDeniedModal,
} from '@semiont/react-ui';
import { QueryClientProvider } from '@tanstack/react-query';
function App({ children }) {
const translationManager = useTranslationManager(); // Your implementation
const queryClient = new QueryClient();
return (
<TranslationProvider translationManager={translationManager}>
<QueryClientProvider client={queryClient}>
<ApiClientProvider baseUrl="https://api.example.com">
{/* Mount KnowledgeBaseSessionProvider only on protected routes */}
<KnowledgeBaseSessionProvider>
<ProtectedErrorBoundary>
<SessionExpiredModal />
<PermissionDeniedModal />
{children}
</ProtectedErrorBoundary>
</KnowledgeBaseSessionProvider>
</ApiClientProvider>
</QueryClientProvider>
</TranslationProvider>
);
}2. Use Components
import { ResourceViewer, useResources } from '@semiont/react-ui';
function MyComponent() {
const resources = useResources();
const { data, isLoading } = resources.list.useQuery();
if (isLoading) return <div>Loading...</div>;
return <ResourceViewer resource={data[0]} />;
}3. Use Translations
import { useTranslations } from '@semiont/react-ui';
// Option 1: Default English (no provider needed)
function Toolbar() {
const t = useTranslations('Toolbar');
return <button>{t('save')}</button>;
}
// Option 2: Built-in locales
import { TranslationProvider } from '@semiont/react-ui';
function App() {
return (
<TranslationProvider locale="es">
<Toolbar />
</TranslationProvider>
);
}
// Option 3: Custom translation system
const myTranslationManager = {
t: (namespace, key, params) => myI18n.translate(`${namespace}.${key}`, params)
};
function App() {
return (
<TranslationProvider translationManager={myTranslationManager}>
<Toolbar />
</TranslationProvider>
);
}Favicon Assets
The package includes Semiont-branded favicons in multiple formats (SVG, PNG, ICO) and a React component for inline usage. See docs/FAVICON.md for complete usage instructions.
Architecture
The library follows strict architectural principles:
- No Aliasing or Wrappers - Direct API access, no compatibility layers
- Provider Pattern - Consistent dependency injection via React Context
- Framework Agnostic - Apps provide framework-specific implementations
- TypeScript First - Full type safety throughout
CSS Architecture
The styles are organized into a modular, maintainable structure:
- Design Tokens - Centralized variables for consistent theming
- Core UI Elements - Fundamental, reusable components (buttons, toggles, sliders, etc.)
- W3C Motivations - Dedicated styles for Web Annotation standard motivations
- Component/Panel Separation - Complex components vs. layout containers
- Dark Theme Support - Comprehensive dark mode using
[data-theme="dark"]
Key directories:
styles/core/- Fundamental UI elements (buttons, toggles, progress bars, sliders, badges, tags, indicators)styles/motivations/- W3C Web Annotation motivation styles (reference, highlight, assessment, comment, tag)styles/components/- Complex, composed componentsstyles/panels/- Panel layouts and containersstyles/features/- Feature-specific styling
See docs/STYLES.md for detailed CSS documentation.
Core Concepts
Providers
All cross-cutting concerns use the Provider Pattern:
- KnowledgeBaseSessionProvider - KB list, active KB, validated session, modal state — one merged provider that's the single source of truth for "which KB and what's the session against it"
- TranslationProvider - Internationalization
- ApiClientProvider - Authenticated API client
- OpenResourcesProvider - Recently opened resources
- RoutingContext - Framework-agnostic navigation
See docs/SESSION.md for details.
API Integration
React Query hooks for all API operations:
import { useResources, useAnnotations, useEntityTypes } from '@semiont/react-ui';
// List resources
const resources = useResources();
const { data } = resources.list.useQuery({ limit: 10 });
// Create annotation
const annotations = useAnnotations();
const { mutate } = annotations.create.useMutation();See docs/API-INTEGRATION.md for details.
Testing
Comprehensive test utilities included:
import { renderWithProviders } from '@semiont/react-ui/test-utils';
it('should render component', () => {
renderWithProviders(<MyComponent />);
expect(screen.getByText('Hello')).toBeInTheDocument();
});See docs/TESTING.md for details.
Documentation
- SESSION.md - Provider Pattern and manager interfaces
- INTERNATIONALIZATION.md - Translation approach
- TESTING.md - Testing utilities and patterns
- API-INTEGRATION.md - Working with the Semiont API
- COMPONENTS.md - Component library reference
- navigation-components.md - Navigation components (SidebarNavigation, CollapsibleResourceNavigation)
- modal-components.md - Modal components (SearchModal, ResourceSearchModal)
- ROUTING.md - Framework-agnostic routing
- ARCHITECTURE.md - Design principles and decisions
- STYLES.md - CSS architecture and styling guide
- FAVICON.md - Favicon assets and usage
- ANNOTATIONS.md - Annotation system (coming soon)
- ACCESSIBILITY.md - Accessibility architecture and WCAG compliance
Examples
Next.js Integration
// app/providers.tsx
'use client';
import { useSession } from 'next-auth/react';
import { useLocale } from 'next-intl';
import { SemiontApiClient } from '@semiont/api-client';
import { TranslationProvider, ApiClientProvider } from '@semiont/react-ui';
export function useTranslationManager() {
const locale = useLocale();
const messages = require(`@/messages/${locale}.json`);
return {
t: (namespace, key) => messages[namespace]?.[key] || key
};
}
export function useApiClientManager() {
const { data: session } = useSession();
const [token$] = useState(() => new BehaviorSubject<AccessToken | null>(null));
useEffect(() => {
token$.next(session?.backendToken ? accessToken(session.backendToken) : null);
}, [session?.backendToken, token$]);
return {
client: new SemiontApiClient({ baseUrl, eventBus, token$ }),
};
}Vite Integration
// src/App.tsx
import { useState } from 'react';
import { TranslationProvider } from '@semiont/react-ui';
function useTranslationManager() {
const [locale] = useState('en');
return {
t: (namespace, key) => `${namespace}.${key}` // Your i18n library
};
}
function App() {
const translationManager = useTranslationManager();
return (
<TranslationProvider translationManager={translationManager}>
{/* Your app */}
</TranslationProvider>
);
}Development
# Run tests
npm test
# Run tests in watch mode
npm run test:watch
# Run tests with coverage
npm run test:coverage
# Type checking
npm run typecheckContributing
This library follows strict quality standards:
- 100% TypeScript - All code must be properly typed
- No
anycasts - Without explicit permission - No cruft - Delete dead code immediately, no "legacy" patterns
- Direct fixes - If something is wrong, fix it directly (no aliases/wrappers)
See CLAUDE.md in the repository root for full guidelines.
License
[License information to be added]
Related Packages
- @semiont/api-client - TypeScript client for Semiont API
- semiont-frontend - Reference Next.js implementation
