Drizzle ServiceDrizzle Service

Drizzle Service Documentation

A comprehensive, type-safe service layer for Drizzle ORM with support for PostgreSQL and SQLite, featuring advanced query capabilities, mutations, and bulk operations

Drizzle Service

A powerful, type-safe service layer for Drizzle ORM that provides a comprehensive set of operations for building robust database applications.

Overview

Drizzle Service is a high-level abstraction layer built on top of Drizzle ORM that provides:

  • Universal Database Support - Works seamlessly with PostgreSQL and SQLite
  • Type-Safe Operations - Full TypeScript support with compile-time validation
  • Advanced Query Capabilities - Complex filtering, pagination, relations, and aggregations
  • Robust Mutation Operations - Create, update, delete with comprehensive error handling
  • High-Performance Bulk Operations - Efficient batch processing for large datasets
  • Soft Delete Support - Configurable soft delete functionality
  • Lifecycle Hooks - Before and after hooks for custom business logic

Key Features

Type Safety

Built with TypeScript from the ground up, providing compile-time validation and excellent IDE support.

Database Agnostic

Single API that works with both PostgreSQL and SQLite, allowing you to switch databases without changing your application code.

Performance Optimized

Efficient query building, automatic batching for bulk operations, and optimized SQL generation.

Flexible Configuration

Extensive configuration options for soft deletes, pagination limits, and custom business logic.

Quick Start

Installation

npm install drizzle-service drizzle-orm

Basic Usage

E-commerce Product Management
import { drizzleService } from 'drizzle-service/pg'
import { products, categories, orders, db } from './schema'

// Initialize the service with database instance
const service = drizzleService(db) 

// Product catalog service with soft delete
const productService = service(products, {
  defaultLimit: 50,
  maxLimit: 500,
  soft: {
    field: 'status',
    deletedValue: 'discontinued',
    notDeletedValue: 'active'
  }
})

// Category management service
const categoryService = service(categories) 

// Order processing service
const orderService = service(orders, {
  soft: {
    field: 'status', // [!code word:status
    deletedValue: 'canceled',
    notDeletedValue: 'pending'
  }
})

// Query product catalog
const activeProducts = await productService.findAll({
  orderBy: { updatedAt: 'desc' },
  limit: 20
})

const featuredProducts = await productService.findBy({ 
  featured: true,
  inStock: true
})

// Product search by category
const electronicsProducts = await productService.findByField(
  'categoryId', 
  'electronics-category-id'
)

// Create new product
const [error, newProduct] = await productService.create({
  name: 'Wireless Bluetooth Headphones',
  description: 'Premium noise-canceling wireless headphones',
  price: 149.99,
  categoryId: 'electronics-category-id',
  sku: 'WBH-001',
  inStock: true,
  featured: true
})

if (error) {
  console.error('Failed to create product:', error.message)
} else {
  console.log('Product created:', newProduct.id)
}

// Bulk import products from supplier
const supplierProducts = [
  {
    name: 'Gaming Mouse',
    price: 79.99,
    categoryId: 'electronics-category-id',
    sku: 'GM-001'
  },
  {
    name: 'Mechanical Keyboard',
    price: 129.99,
    categoryId: 'electronics-category-id', 
    sku: 'MK-001'
  }
]

const [bulkError, importedProducts] = await productService.bulkCreate(supplierProducts) 

Architecture

The service layer is built with a modular architecture that separates concerns:

Service Builder

The core service builder creates type-safe service instances with all necessary operations.

Operation Modules

  • Query Operations - Read operations with filtering and pagination
  • Mutation Operations - Write operations with validation and hooks
  • Bulk Operations - Batch operations for high-performance processing

Database Adapters

Specialized adapters for PostgreSQL and SQLite that handle database-specific optimizations.

Configuration Options

PropTypeDefault
override?
(baseMethods: ServiceMethods<T>) => Partial<ServiceMethods<T>>
-
id?
keyof T['$inferSelect']
-
soft?
SoftDeleteConfig<T>
-
maxLimit?
number
1000
defaultLimit?
number
100

Error Handling

The service uses a comprehensive error handling approach:

  • Handler Pattern - Mutations return [error, result] tuples for explicit error handling
  • Detailed Error Information - Rich error objects with context and suggestions
  • Validation Errors - Type-safe validation with detailed field-level errors
  • Database Constraint Handling - Automatic handling of unique constraints and foreign key violations

Best Practices

Service Configuration

Configure services once at application startup and reuse instances throughout your application.

Error Handling

Always check for errors in mutation operations and handle them appropriately.

Pagination

Use cursor-based pagination for large datasets and implement reasonable default limits.

Bulk Operations

Use bulk operations for processing multiple records to improve performance and maintain data consistency.

Next Steps