A modular, type-safe foundation for building expressive, maintainable applications. This package provides core abstractions for domain modeling, HTTP integration, authentication, state management, and more — designed to be framework-agnostic and highly extensible.
npm install @schorts/shared-kernel --saveThe package ships agent docs in node_modules/@schorts/shared-kernel/ai/: an AGENTS.md overview, per-area rules, and step-by-step skills (add a command, create an aggregate, implement a DAO, and more) with type-checked examples. Point your agent at them, for example in CLAUDE.md:
Before writing code that uses @schorts/shared-kernel, read
node_modules/@schorts/shared-kernel/ai/AGENTS.md and follow its rules and skills.ai/README.md has setup for Claude Code (including linking the skills), Cursor, Copilot, and other tools.
The Shared Kernel is organized into several domains of functionality, providing robust primitives for your applications.
Primitives for expressing your business domain cleanly and enforcing invariants.
- Aggregates:
AggregateRoot: Base class for a cluster of domain objects that can be treated as a single unit. Inherits fromEntityand provides built-in domain event recording capabilities.
- Entities:
Entity: Base class for identity-based domain entities.EntityRegistry: Dynamic registry for entity constructors, enabling polymorphic instantiation.
- Value Objects: A vast collection of primitives that enforce domain constraints and immutability (e.g.,
CoordinatesValue,EmailValue,StringValue,UUIDValue,URLValue,DateValue, etc.). - Domain Events:
DomainEvent: Base class for domain-driven event dispatching.
- Result:
Result: Type-safe wrapper for success/failure outcomes. Enforces disciplined error handling without exceptions. Includes accessors (getValue,getError) and guards.
- Models:
BaseModel: Base class for serializable, type-safe models.
Abstractions for CQRS, Event Sourcing, and orchestrating complex distributed workflows.
- CQRS:
Command/CommandHandler: Encapsulate intent and state changes.Query/QueryHandler: Define read-side operations.CommandBus/QueryBus: Centralized dispatchers (includesInMemoryCommandBusandInMemoryQueryBus).
- Sagas:
Saga: Abstract base for defining long-running, stateful business processes.SagaManager: Orchestrates saga execution and event routing.SagaStateStore: Stores the ongoing state of a Saga to resume across restarts.
- Event Bus:
EventSubscriber: Clean, type-safe event handlers.InMemoryEventBus: Dispatcher with support for retries and requeueing.DomainEventRegistry: Centralized registry for hydrating polymorphic domain events.InMemoryEventStore: Tracks and replays events.DeadLetterStore: Captures events that failed after maximum retries.
Tools for managing identities and permissions across applications.
- Auth:
AuthProvider: Abstract interface for authentication strategies.IdentityProvider: Contract for external identity services (Firebase, Auth0, Cognito).
- RBAC (Role-Based Access Control):
RBACPolicy: Base class for defining role-based permission logic.Permission: Lightweight value object for action-resource pairs (e.g.,read:orders).
- ABAC (Attribute-Based Access Control): Extend RBAC with dynamic, contextual attributes using composable predicates.
Interfaces to decouple application logic from database engines.
- DAO (Data Access Object): Generic interface defining CRUD operations for entities.
- UnitOfWork: Enables transactional coordination across multiple persistence operations.
- Criteria: Fluent query builder for filtering, sorting, and pagination.
Infrastructure for offline persistence, replay, and durability.
- OfflineStore:
- Contract for queuing and replaying commands or service calls when offline.
- Methods:
enqueue,list,dequeue,clear. - Default payload type: { type: string; args: any[]; meta?: { userId, tenantId, timestamp, retries, correlationId, origin, version } }.
Integrate seamlessly with external services and clients.
- HTTP:
HTTPProvider: Abstract interface for HTTP transport.FetchHTTPProvider: Concrete implementation usingfetch.
- JSON:API:
JSONAPIConnector: Interact with JSON:API-compliant endpoints.URLCriteriaParser: Parses JSON:API-style URL parameters into a type-safeCriteriaobject.EntityJSONAPIMapper: ConvertsEntityinstances into JSON:API-compliant payloads.
- Pub-Sub:
Publisher: Dispatch real-time events to external transports (Pusher, Socket.IO).Subscription: Client-side abstraction for subscribing to real-time channels.
- Mail:
Mailer: Interface for sending email messages.Mail: Type-safe structure representing an email payload.
Framework-neutral helpers for managing application state.
- State Manager:
StateManager: Abstract reactive state manager with listener support.- Includes
InMemoryStateManagerfor in-memory state. - Extend
StateManagerin your application to provide custom persistence.
- i18n (Internationalization):
TranslationResolver: Infrastructure-agnostic interface for resolving localized strings within the domain.
Diagnostics, error handling, and structured logging.
- Logger:
Logger: Structured, context-aware logging (log,info,debug,warn,error).ConsoleLogger: Local development implementation.ScopedLogger: Composable logging scopes via.child().
- Error Tracking:
ErrorTracker: Coordinator class to track, store, and upload errors robustly with configurable ignore rules.ErrorStore&ErrorUploader: Interfaces to plug into telemetry systems (Sentry, Datadog).TrackedError: Generic model for a tracked error payload.
Essential helper functions and types used across bounded contexts.
- Types: Core utility types such as
Constructor,DeepPartial,Dictionary,JSON,MaybePromise,Nullable, andOptional. - Utils: Common functions for
assertion,asyncflows,objectmanipulation,stringhandling, andurlparsing. - Formatters: Utilities like
PascalCamelToSnakecase conversion. - Converters: Utilities like
RemoteFileToBase64.
This kernel is built around:
- Type safety: Every abstraction is strongly typed and composable.
- Domain expressiveness: Value objects, entities, and events encode business logic directly.
- Extensibility: Plug in your own HTTP, auth, or state strategies.
- Framework independence: Use it with Node.js, frontend apps, or serverless functions.
import { Criteria } from "@schorts/shared-kernel/criteria";
import { FetchHTTPProvider } from "@schorts/shared-kernel/http";
import { JSONAPIConnector } from "@schorts/shared-kernel/json-api";
type UserAttributes = { name: string; status: string; created_at: string };
const usersURL = new URL("https://api.example.com/users");
const criteria = Criteria.none()
.where("status", "EQUAL", "active")
.orderBy("created_at", "DESC")
.limitResults(10);
const connector = new JSONAPIConnector(new FetchHTTPProvider());
const users = await connector.findMany<UserAttributes>(usersURL, {
criteria,
include: ["organization"],
});
users.data.forEach(user => console.log(user.id, user.attributes.name));11.0 requires Node.js 20 or later. The CHANGELOG lists every change; the migrate-to-v11 skill walks through the upgrade step by step (and works as instructions for an AI agent).
Guided tours and browser-backed state managers have been removed from the kernel.
- Remove imports from
@schorts/shared-kernel/tour-guide.TourGuide,TourGuideOptions,BaseTourGuide,TourStep,TourSide, andTourAlignare no longer exported from the package root either. Keep tour integrations and their types in your application. LocalStorageStateManagerandSessionStorageStateManagerare no longer exported from the package root or@schorts/shared-kernel/state-manager. Implement browser persistence in your application by extendingStateManager;InMemoryStateManageris not a persistent replacement.StateManagerandInMemoryStateManagerremain available from the package root and@schorts/shared-kernel/state-manager.
No replacement UI package is provided.
execute is no longer part of the CommandHandler and QueryHandler interfaces, and it is protected on AbstractCommandHandler and AbstractQueryHandler.
- Handlers that extend the abstract classes keep working. Declaring
executeasprotectedis recommended but not required. - Hand-written handlers only need
handle; remove anyexecuteyou added just to satisfy the interface. - Replace direct
handler.execute(command)calls withhandler.handle(command)orbus.dispatch(command). Callingexecutedirectly skipped validation, authorization, idempotency, and timeouts.
Values the kernel hands back are now unknown instead of any, so mistakes that used to compile now surface as type errors. The CHANGELOG lists every affected type. Typical fixes:
HTTPException.body, exceptiondetails, JSON:APIattributes, identity claims, andcontextvalues: narrow with a type guard or cast to the shape you expect.Command,Query, andDomainEventwithout a type argument now have anunknownpayload. Pass the payload type (AbstractCommand<CreateUserPayload>) as usual.
- The snake_case validation rules (
greater_than,greater_than_or_equal,less_than,less_than_or_equal) are gone; usegreaterThan,greaterThanOrEqual,lessThan,lessThanOrEqual. Schemas that still use the old keys throw aTypeErrornaming the replacement. - A saga whose step failed is now final, and the event bus no longer retries saga deliveries. Retry transient work inside the step; delete the saga's state to run it again.
MailAttachment.contentisstring | Uint8Array. NodeBuffers still work.
Criteria.where checks value against the operator: IN, NOT_IN, and ARRAY_CONTAINS_ANY need an array, LIKE a string, range operators a number, string, boolean, bigint, or Date, BETWEEN two bounds, and GEO_RADIUS a center and radius. Custom DAOs can switch (filter.operator) to get a typed filter.value, and use readGeoRadius / readBetweenBounds to accept the same shapes as InMemoryDAO.
Tests use Jest and live in __tests__/, in folders that mirror src/ (for example __tests__/cqrs/), plus __tests__/integration/ for tests that span modules. CI runs them on every push and pull request, with minimum coverage levels set in jest.config.js.
npm testBefore publishing, npm run prepublishOnly also checks import paths, types, the build, and that every entry point loads with both import and require.
Licensed under LGPL-3.0-or-later. See LICENSE for the LGPLv3 text and COPYING for the GPLv3 terms it incorporates.