gpa

package module
v0.1.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 5, 2025 License: MIT Imports: 8 Imported by: 7

README

GPA (Go Persistence API)

Go Reference Go Report Card

A unified, type-safe persistence API for Go applications supporting both SQL and NoSQL databases through provider implementations with an advanced multi-provider registry system.

✨ Key Features

  • 🔒 Compile-time Type Safety - No interface{} or type assertions needed
  • 🚀 High Performance - Zero reflection overhead in runtime operations
  • 🔄 Unified API - Same interface for SQL, NoSQL, and key-value databases
  • 📦 Multiple Provider Support - GORM, Bun, MongoDB, Redis out of the box
  • 🎯 Advanced Provider Registry - Manage multiple database connections with type inference
  • 🧰 Rich Query Builder - Fluent, type-safe query construction
  • ⚡ Connection Pooling - Built-in connection management and health checks
  • 🔍 Generic Repositories - Type-safe repository pattern with Go generics

🚀 Quick Start

Installation
go get github.com/lemmego/gpa
Basic Usage
package main

import (
    "context"
    "log"
    
    "github.com/lemmego/gpa"
    "github.com/lemmego/gpagorm"
)

type User struct {
    ID   int    `gorm:"primaryKey" json:"id"`
    Name string `json:"name"`
    Email string `json:"email"`
}

func main() {
    // Configure your database
    config := gpa.Config{
        Driver:   "postgres",
        Host:     "localhost",
        Port:     5432,
        Database: "myapp",
        Username: "user",
        Password: "password",
    }
    
    // Create provider
    provider, err := gpagorm.NewProvider(config)
    if err != nil {
        log.Fatal(err)
    }
    defer provider.Close()
    
    // Register provider in global registry with type inference
    gpa.RegisterDefault[*gpagorm.Provider](provider)
    
    // Get type-safe repository
    userRepo := gpagorm.GetRepository[User](provider)
    
    ctx := context.Background()
    
    // Create user
    user := &User{Name: "John Doe", Email: "john@example.com"}
    err = userRepo.Create(ctx, user)
    if err != nil {
        log.Fatal(err)
    }
    
    // Find user - returns *User directly, no type assertions!
    foundUser, err := userRepo.FindByID(ctx, user.ID)
    if err != nil {
        log.Fatal(err)
    }
    
    // Query users with type-safe conditions
    users, err := userRepo.Query(ctx,
        gpa.Where("name", gpa.OpLike, "John%"),
        gpa.OrderBy("created_at", gpa.OrderDesc),
        gpa.Limit(10),
    )
    if err != nil {
        log.Fatal(err)
    }
    
    log.Printf("Found %d users", len(users))
}

🎯 Advanced Provider Registry

GPA features an advanced provider registry that allows you to manage multiple database connections with automatic type inference:

Register Providers
// Register multiple providers with full type safety
gpa.Register[*gpagorm.Provider]("primary", primaryDB)
gpa.Register[*gpagorm.Provider]("readonly", readonlyDB)
gpa.Register[*gparedis.Provider]("cache", redisCache)
gpa.Register[*gparedis.Provider]("sessions", sessionRedis)
gpa.Register[*gpamongo.Provider]("documents", mongoProvider)

// Register default providers
gpa.RegisterDefault[*gpagorm.Provider](primaryDB)
Retrieve Providers with Type Inference
// Get providers - type is automatically inferred, no strings needed!
primary, err := gpa.Get[*gpagorm.Provider]("primary")
cache := gpa.MustGet[*gparedis.Provider]("cache")
defaultDB, err := gpa.Get[*gpagorm.Provider]() // Gets default

// Get all providers of a specific type
allGormProviders, err := gpa.GetByType[*gpagorm.Provider]()
allRedisProviders, err := gpa.GetByType[*gparedis.Provider]()
Multi-Database Patterns
Primary/Replica Pattern
func setupPrimaryReplica() {
    primary, _ := gpagorm.NewProvider(primaryConfig)
    replica, _ := gpagorm.NewProvider(replicaConfig)
    
    gpa.Register[*gpagorm.Provider]("primary", primary)
    gpa.Register[*gpagorm.Provider]("replica", replica)
    gpa.RegisterDefault[*gpagorm.Provider](primary)
}

func useDatabase() {
    // Write operations use primary
    primary := gpa.MustGet[*gpagorm.Provider]("primary")
    userRepo := gpagorm.GetRepository[User](primary)
    userRepo.Create(ctx, &user)
    
    // Read operations can use replica
    replica := gpa.MustGet[*gpagorm.Provider]("replica")
    readRepo := gpagorm.GetRepository[User](replica)
    users := readRepo.FindAll(ctx)
}
Multi-Tenant Pattern
func setupMultiTenant() {
    tenants := []string{"tenant1", "tenant2", "tenant3"}
    
    for _, tenant := range tenants {
        config := gpa.Config{
            Database: fmt.Sprintf("app_%s", tenant),
            // ... other config
        }
        provider, _ := gpagorm.NewProvider(config)
        gpa.Register[*gpagorm.Provider](tenant, provider)
    }
}

func useTenant(tenantID string) {
    provider := gpa.MustGet[*gpagorm.Provider](tenantID)
    userRepo := gpagorm.GetRepository[User](provider)
    // Operations are scoped to this tenant's database
}
Hybrid Storage Pattern
func setupHybridStorage() {
    // SQL for transactional data
    sqlProvider, _ := gpagorm.NewProvider(sqlConfig)
    gpa.Register[*gpagorm.Provider]("sql", sqlProvider)
    
    // Redis for caching
    redisProvider, _ := gparedis.NewProvider(redisConfig)
    gpa.Register[*gparedis.Provider]("cache", redisProvider)
    
    // MongoDB for document storage
    mongoProvider, _ := gpamongo.NewProvider(mongoConfig)
    gpa.Register[*gpamongo.Provider]("documents", mongoProvider)
}

func useHybridStorage() {
    // User data in SQL
    sqlProvider := gpa.MustGet[*gpagorm.Provider]("sql")
    userRepo := gpagorm.GetRepository[User](sqlProvider)
    
    // Session data in Redis
    redisProvider := gpa.MustGet[*gparedis.Provider]("cache")
    sessionRepo := gparedis.GetRepository[Session](redisProvider)
    
    // Content in MongoDB
    mongoProvider := gpa.MustGet[*gpamongo.Provider]("documents")
    contentRepo := gpamongo.GetRepository[Content](mongoProvider)
}

🔧 Supported Providers

SQL Databases
GORM Provider (gpagorm)
import "github.com/lemmego/gpagorm"

provider, err := gpagorm.NewProvider(gpa.Config{
    Driver:   "postgres", // postgres, mysql, sqlite, sqlserver
    Host:     "localhost",
    Port:     5432,
    Database: "myapp",
    Username: "user",
    Password: "password",
})

userRepo := gpagorm.GetRepository[User](provider)
Bun Provider (gpabun)
import "github.com/lemmego/gpabun"

provider, err := gpabun.NewProvider(gpa.Config{
    Driver:   "postgres", // postgres, mysql, sqlite
    Host:     "localhost",
    Port:     5432,
    Database: "myapp",
    Username: "user",
    Password: "password",
})

userRepo := gpabun.GetRepository[User](provider)
NoSQL Databases
MongoDB Provider (gpamongo)
import "github.com/lemmego/gpamongo"

provider, err := gpamongo.NewProvider(gpa.Config{
    Host:     "localhost",
    Port:     27017,
    Database: "myapp",
    Username: "user",
    Password: "password",
})

userRepo := gpamongo.GetRepository[User](provider)
Redis Provider (gparedis)
import "github.com/lemmego/gparedis"

provider, err := gparedis.NewProvider(gpa.Config{
    Host:     "localhost",
    Port:     6379,
    Password: "password",
    Database: 0,
})

sessionRepo := gparedis.GetRepository[Session](provider)

📚 Repository Operations

Basic CRUD Operations
ctx := context.Background()

// Create
user := &User{Name: "John", Email: "john@example.com"}
err := userRepo.Create(ctx, user)

// Create multiple
users := []*User{{Name: "Alice"}, {Name: "Bob"}}
err := userRepo.CreateBatch(ctx, users)

// Find by ID
user, err := userRepo.FindByID(ctx, 123)

// Find all
users, err := userRepo.FindAll(ctx)

// Update
user.Name = "John Updated"
err := userRepo.Update(ctx, user)

// Partial update
err := userRepo.UpdatePartial(ctx, 123, map[string]interface{}{
    "name": "John Partial",
})

// Delete
err := userRepo.Delete(ctx, user)

// Delete by ID
err := userRepo.DeleteByID(ctx, 123)
Advanced Querying
// Complex queries with type-safe conditions
users, err := userRepo.Query(ctx,
    gpa.Where("age", gpa.OpGreaterThan, 18),
    gpa.Where("status", gpa.OpEqual, "active"),
    gpa.WhereLike("name", "John%"),
    gpa.WhereIn("role", []interface{}{"admin", "user"}),
    gpa.OrderBy("created_at", gpa.OrderDesc),
    gpa.Limit(50),
    gpa.Offset(0),
)

// Counting records
count, err := userRepo.Count(ctx, 
    gpa.Where("status", gpa.OpEqual, "active"),
)

// Check existence
exists, err := userRepo.Exists(ctx,
    gpa.Where("email", gpa.OpEqual, "john@example.com"),
)

// Aggregations (provider-specific)
if sqlRepo, ok := userRepo.(gpa.SQLRepository[User]); ok {
    // Raw SQL queries
    users, err := sqlRepo.FindBySQL(ctx,
        "SELECT * FROM users WHERE age > ? ORDER BY created_at DESC",
        []interface{}{18},
    )
    
    // Execute raw SQL
    result, err := sqlRepo.ExecSQL(ctx,
        "UPDATE users SET status = ? WHERE last_login < ?",
        "inactive", time.Now().AddDate(0, -6, 0),
    )
}
Transactions
err := userRepo.Transaction(ctx, func(tx gpa.Transaction[User]) error {
    // Create user
    user := &User{Name: "John", Email: "john@example.com"}
    if err := tx.Create(ctx, user); err != nil {
        return err
    }
    
    // Update related data
    if err := tx.UpdatePartial(ctx, relatedID, map[string]interface{}{
        "user_id": user.ID,
    }); err != nil {
        return err
    }
    
    return nil // Commit
})

🔍 Registry Management

Discovery and Health Checks
// List all provider types
types := gpa.Registry().ListTypes()
fmt.Printf("Available types: %v\n", types) // [GORM Redis MongoDB]

// List instances of a specific type
instances, _ := gpa.Registry().ListInstances("GORM")
fmt.Printf("GORM instances: %v\n", instances) // [primary readonly default]

// Health check all providers
healthResults := gpa.Registry().HealthCheck()
for providerType, instances := range healthResults {
    for instanceName, err := range instances {
        if err != nil {
            fmt.Printf("❌ %s:%s is unhealthy: %v\n", providerType, instanceName, err)
        } else {
            fmt.Printf("✅ %s:%s is healthy\n", providerType, instanceName)
        }
    }
}

// Remove providers
err := gpa.Registry().Remove("GORM", "readonly")
err := gpa.Registry().RemoveAll() // Remove all providers

⚙️ Configuration

config := gpa.Config{
    Driver:          "postgres",
    Host:            "localhost",
    Port:            5432,
    Database:        "myapp",
    Username:        "user",
    Password:        "password",
    ConnectionURL:   "", // Alternative to individual fields
    MaxOpenConns:    25,
    MaxIdleConns:    10,
    ConnMaxLifetime: time.Hour,
    ConnMaxIdleTime: time.Minute * 30,
    SSL: gpa.SSLConfig{
        Enabled:  true,
        Mode:     "require",
        CertFile: "/path/to/cert.pem",
        KeyFile:  "/path/to/key.pem",
        CAFile:   "/path/to/ca.pem",
    },
    Options: map[string]interface{}{
        "gorm": map[string]interface{}{
            "log_level":      "info",
            "singular_table": false,
        },
    },
}

🎯 Type Safety Benefits

Traditional approach with type assertions:

// ❌ Runtime type assertions and potential panics
provider, err := registry.Get("GORM", "primary")
gormProvider := provider.(*gpagorm.Provider) // Can fail at runtime!

result, err := repo.FindByID(ctx, 123)
user := result.(*User) // Another type assertion!

GPA approach with compile-time safety:

// ✅ Compile-time type safety, no type assertions
gormProvider, err := gpa.Get[*gpagorm.Provider]("primary")
user, err := userRepo.FindByID(ctx, 123) // Returns *User directly!

🚀 Performance

  • Zero reflection overhead in repository operations
  • Compile-time type checking eliminates runtime type assertion costs
  • Efficient connection pooling with health checks
  • Lazy provider initialization for better startup times
  • Concurrent-safe registry with optimized read-write locks

📖 Documentation

🤝 Contributing

We welcome contributions! Please see our Contributing Guide for details.

  1. Fork the repository
  2. Create your feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add some amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

📄 License

This project is licensed under the MIT License - see the LICENSE.md file for details.

🙏 Acknowledgments

  • Inspired by the repository pattern and clean architecture principles
  • Built with Go generics for maximum type safety
  • Supports multiple excellent Go database libraries (GORM, Bun, MongoDB driver, Redis)

📊 Project Status

  • ✅ Core API stable
  • ✅ Provider registry with type inference
  • ✅ GORM provider complete
  • ✅ Redis provider complete
  • 🚧 Bun provider (in development)
  • 🚧 MongoDB provider (in development)
  • 📋 Additional providers planned

Made with ❤️ by Tanmay Das

Documentation

Overview

Package gpa provides a unified persistence API for Go applications supporting both SQL and NoSQL databases through adapter implementations.

GPA provides compile-time type safety for all database operations using a unified provider pattern. This is the RECOMMENDED approach for all applications:

type User struct {
    ID   int    `json:"id"`
    Name string `json:"name"`
}

type Post struct {
    ID     int    `json:"id"`
    UserID int    `json:"user_id"`
    Title  string `json:"title"`
}

// Create a single provider for your database
provider, err := gpagorm.NewProvider(config)
if err != nil {
    log.Fatal(err)
}
defer provider.Close()

// Create multiple type-safe repositories from the same provider
userRepo := gpagorm.GetRepository[User](provider)
postRepo := gpagorm.GetRepository[Post](provider)

// All operations return strongly-typed results
user, err := userRepo.FindByID(ctx, 123)    // Returns *User directly
users, err := userRepo.FindAll(ctx)         // Returns []*User directly
posts, err := postRepo.FindAll(ctx)         // Returns []*Post directly

Benefits of Unified Provider API

• Single provider per database connection - efficient resource usage • Multiple type-safe repositories from one provider • Compile-time type safety - catch errors at build time • No interface{} conversions or type assertions • Better IDE support with autocompletion and refactoring • Improved performance - no runtime reflection for type checking • Cleaner, more readable code

Provider Support

All providers support the unified API: • GORM: gpagorm.NewProvider(config) + gpagorm.GetRepository[T](provider) • Bun: gpabun.NewProvider(config) + gpabun.GetRepository[T](provider) • MongoDB: gpamongo.NewProvider(config) + gpamongo.GetRepository[T](provider) • Redis: gparedis.NewProvider(config) + gparedis.GetRepository[T](provider)

Each provider supports their respective database drivers: • GORM: PostgreSQL, MySQL, SQLite, SQL Server • Bun: PostgreSQL, MySQL, SQLite • MongoDB: MongoDB • Redis: Redis

Use the unified provider API for all new development for the best developer experience and resource efficiency.

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrProviderNotFound = errors.New("provider not found")
)

Functions

func ExampleProviderUsage added in v0.1.1

func ExampleProviderUsage()

ExampleProviderUsage demonstrates how to use the provider interface hierarchy

func Get

func Get[T Provider](instanceName ...string) (T, error)

Get retrieves a provider by type using Go generics for compile-time type safety T must be a concrete provider type that implements Provider interface The provider type is automatically inferred from T Usage: provider, err := gpa.Get[*gpagorm.Provider]("instance")

func GetByType

func GetByType[T Provider]() (map[string]T, error)

GetByType returns all providers of a specific type using Go generics T must be a concrete provider type that implements Provider interface The provider type is automatically inferred from T Usage: providers, err := gpa.GetByType[*gpagorm.Provider]()

func IsConnection

func IsConnection(err error) bool

IsConnection checks if an error is a "connection" error

func IsDocumentProvider added in v0.1.1

func IsDocumentProvider(provider Provider) bool

IsDocumentProvider checks if a provider implements DocumentProvider interface

func IsDuplicate

func IsDuplicate(err error) bool

IsDuplicate checks if an error is a "duplicate" error

func IsErrorType

func IsErrorType(err error, errorType ErrorType) bool

IsErrorType checks if an error is of a specific type

func IsGraphProvider added in v0.1.1

func IsGraphProvider(provider Provider) bool

IsGraphProvider checks if a provider implements GraphProvider interface

func IsKeyValueProvider added in v0.1.1

func IsKeyValueProvider(provider Provider) bool

IsKeyValueProvider checks if a provider implements KeyValueProvider interface

func IsNotFound

func IsNotFound(err error) bool

IsNotFound checks if an error is a "not found" error

func IsSQLProvider added in v0.1.1

func IsSQLProvider(provider Provider) bool

IsSQLProvider checks if a provider implements SQLProvider interface

func IsTransaction

func IsTransaction(err error) bool

IsTransaction checks if an error is a "transaction" error

func IsValidation

func IsValidation(err error) bool

IsValidation checks if an error is a "validation" error

func IsWideColumnProvider added in v0.1.1

func IsWideColumnProvider(provider Provider) bool

IsWideColumnProvider checks if a provider implements WideColumnProvider interface

func MustGet

func MustGet[T Provider](instanceName ...string) T

MustGet retrieves a provider by type using Go generics, panics if not found T must be a concrete provider type that implements Provider interface The provider type is automatically inferred from T Usage: provider := gpa.MustGet[*gpagorm.Provider]("instance")

func RealWorldExample added in v0.1.1

func RealWorldExample()

RealWorldExample shows how to use this in a real application

func Register

func Register[T Provider](instanceName string, provider T)

Register registers a provider using Go generics for compile-time type safety T must be a concrete provider type that implements Provider interface Usage: gpa.Register[*gpagorm.Provider]("instance", provider)

func RegisterDefault

func RegisterDefault[T Provider](provider T)

RegisterDefault registers a provider as default using Go generics for compile-time type safety T must be a concrete provider type that implements Provider interface Usage: gpa.RegisterDefault[*gpagorm.Provider](provider)

Types

type AdvancedKeyValueRepository

AdvancedKeyValueRepository combines all key-value capabilities. Provides the full spectrum of key-value operations including batching, TTL, atomics, and patterns. Only the most advanced KV stores (Redis, Hazelcast) implement this complete interface.

type AfterCreateHook added in v0.1.1

type AfterCreateHook interface {
	AfterCreate(ctx context.Context) error
}

AfterCreateHook is called after successfully creating an entity

type AfterDeleteHook added in v0.1.1

type AfterDeleteHook interface {
	AfterDelete(ctx context.Context) error
}

AfterDeleteHook is called after successfully deleting an entity

type AfterFindHook added in v0.1.1

type AfterFindHook interface {
	AfterFind(ctx context.Context) error
}

AfterFindHook is called after successfully finding an entity

type AfterUpdateHook added in v0.1.1

type AfterUpdateHook interface {
	AfterUpdate(ctx context.Context) error
}

AfterUpdateHook is called after successfully updating an entity

type AssociationManager

type AssociationManager interface {
	// Count returns the number of associated records
	Count(ctx context.Context) (int64, error)

	// Find retrieves associated records
	Find(ctx context.Context, dest interface{}) error

	// Append adds one or more associations
	Append(ctx context.Context, values ...interface{}) error

	// Replace replaces all associations with the given values
	Replace(ctx context.Context, values ...interface{}) error

	// Delete removes associations (but not the records themselves)
	Delete(ctx context.Context, values ...interface{}) error

	// Clear removes all associations
	Clear(ctx context.Context) error
}

AssociationManager provides methods for managing entity associations in SQL databases

type BasicCondition

type BasicCondition struct {
	FieldName string
	Op        Operator
	Val       interface{}
}

BasicCondition implements Condition

func (BasicCondition) Field

func (c BasicCondition) Field() string

func (BasicCondition) Operator

func (c BasicCondition) Operator() Operator

func (BasicCondition) String

func (c BasicCondition) String() string

func (BasicCondition) Value

func (c BasicCondition) Value() interface{}

type BasicKeyValueRepository

type BasicKeyValueRepository[T any] interface {
	Repository[T]

	// Set stores a value with the given key.
	// Overwrites any existing value at that key.
	// Example: err := Set(ctx, "user:123", user)
	Set(ctx context.Context, key string, value *T) error

	// Get retrieves a value by key.
	// Returns the value with compile-time type safety.
	// Returns ErrorTypeNotFound if the key doesn't exist.
	// Example: user, err := Get(ctx, "user:123")
	Get(ctx context.Context, key string) (*T, error)

	// DeleteKey removes a key-value pair.
	// Returns ErrorTypeNotFound if the key doesn't exist.
	// Example: err := DeleteKey(ctx, "user:123")
	DeleteKey(ctx context.Context, key string) error

	// KeyExists checks if a key exists.
	// Returns true if the key exists, false otherwise.
	// Example: exists, err := KeyExists(ctx, "user:123")
	KeyExists(ctx context.Context, key string) (bool, error)
}

BasicKeyValueRepository provides basic key-value storage operations. Suitable for simple caching and key-value storage scenarios.

type BatchKeyValueRepository

type BatchKeyValueRepository[T any] interface {
	BasicKeyValueRepository[T]

	// MSet sets multiple key-value pairs in a single operation.
	// More efficient than multiple individual Set calls.
	// Example: err := MSet(ctx, map[string]*T{"user:1": user1, "user:2": user2})
	MSet(ctx context.Context, pairs map[string]*T) error

	// MGet retrieves multiple values by their keys.
	// Returns a map of key-value pairs with compile-time type safety.
	// Missing keys are omitted from the result map.
	// Example: users, err := MGet(ctx, []string{"user:1", "user:2", "user:3"})
	MGet(ctx context.Context, keys []string) (map[string]*T, error)

	// MDelete removes multiple keys in a single operation.
	// More efficient than multiple individual DeleteKey calls.
	// Returns the number of keys that were actually deleted.
	// Example: deleted, err := MDelete(ctx, []string{"user:1", "user:2"})
	MDelete(ctx context.Context, keys []string) (int64, error)
}

BatchKeyValueRepository extends BasicKeyValueRepository with batch operations. Provides efficient bulk operations for better performance.

type BeforeCreateHook added in v0.1.1

type BeforeCreateHook interface {
	BeforeCreate(ctx context.Context) error
}

BeforeCreateHook is called before creating an entity

type BeforeDeleteHook added in v0.1.1

type BeforeDeleteHook interface {
	BeforeDelete(ctx context.Context) error
}

BeforeDeleteHook is called before deleting an entity

type BeforeFindHook added in v0.1.1

type BeforeFindHook interface {
	BeforeFind(ctx context.Context) error
}

BeforeFindHook is called before finding an entity

type BeforeUpdateHook added in v0.1.1

type BeforeUpdateHook interface {
	BeforeUpdate(ctx context.Context) error
}

BeforeUpdateHook is called before updating an entity

type ColumnInfo

type ColumnInfo struct {
	Name         string
	Type         string
	IsNullable   bool
	DefaultValue interface{}
	IsPrimaryKey bool
	IsUnique     bool
	MaxLength    int
	Precision    int
	Scale        int
}

ColumnInfo represents information about a database column

type CompositeCondition

type CompositeCondition struct {
	Conditions []Condition
	Logic      LogicOperator
}

CompositeCondition for AND/OR operations

func (CompositeCondition) Field

func (c CompositeCondition) Field() string

func (CompositeCondition) Operator

func (c CompositeCondition) Operator() Operator

func (CompositeCondition) String

func (c CompositeCondition) String() string

func (CompositeCondition) Value

func (c CompositeCondition) Value() interface{}

type CompositeConditionOption

type CompositeConditionOption struct {
	Conditions []Condition
	Logic      LogicOperator
}

CompositeConditionOption implements QueryOption for composite conditions

func (CompositeConditionOption) Apply

func (o CompositeConditionOption) Apply(query *Query)

type Condition

type Condition interface {
	Field() string
	Operator() Operator
	Value() interface{}
	String() string
}

Condition represents a query condition

func WhereCondition

func WhereCondition(field string, operator Operator, value interface{}) Condition

WhereCondition creates a where condition from a basic condition

type ConditionOption

type ConditionOption struct {
	Condition Condition
}

ConditionOption implements QueryOption for basic conditions

func (ConditionOption) Apply

func (o ConditionOption) Apply(query *Query)

type Config

type Config struct {
	// Connection details
	Driver        string `json:"driver" yaml:"driver"`
	ConnectionURL string `json:"connection_url" yaml:"connection_url"`
	Host          string `json:"host" yaml:"host"`
	Port          int    `json:"port" yaml:"port"`
	Database      string `json:"database" yaml:"database"`
	Username      string `json:"username" yaml:"username"`
	Password      string `json:"password" yaml:"password"`

	// Connection pool settings
	MaxOpenConns    int           `json:"max_open_conns" yaml:"max_open_conns"`
	MaxIdleConns    int           `json:"max_idle_conns" yaml:"max_idle_conns"`
	ConnMaxLifetime time.Duration `json:"conn_max_lifetime" yaml:"conn_max_lifetime"`
	ConnMaxIdleTime time.Duration `json:"conn_max_idle_time" yaml:"conn_max_idle_time"`

	// Additional options
	Options map[string]interface{} `json:"options" yaml:"options"`

	// SSL/TLS configuration
	SSL SSLConfig `json:"ssl" yaml:"ssl"`
}

Config represents database connection configuration

type ConstraintInfo

type ConstraintInfo struct {
	Name       string
	Type       string
	Fields     []string
	References string
}

ConstraintInfo represents information about a database constraint

type DatabaseType

type DatabaseType string

DatabaseType represents the type of database

const (
	DatabaseTypeSQL      DatabaseType = "sql"
	DatabaseTypeDocument DatabaseType = "document"
	DatabaseTypeKV       DatabaseType = "key-value"
	DatabaseTypeGraph    DatabaseType = "graph"
	DatabaseTypeMemory   DatabaseType = "memory"
)

type DistinctOption

type DistinctOption struct{}

DistinctOption implements QueryOption for distinct results

func (DistinctOption) Apply

func (o DistinctOption) Apply(query *Query)

type DocumentProvider added in v0.1.1

type DocumentProvider interface {
	Provider

	// Database returns the underlying database instance
	Database() interface{}

	// Collection returns a collection instance
	Collection(name string) interface{}

	// CreateIndex creates an index on a collection
	CreateIndex(ctx context.Context, collection string, keys interface{}, options *IndexOptions) error

	// DropIndex drops an index from a collection
	DropIndex(ctx context.Context, collection string, name string) error

	// ListIndexes lists all indexes for a collection
	ListIndexes(ctx context.Context, collection string) ([]IndexInfo, error)

	// Aggregate runs an aggregation pipeline
	Aggregate(ctx context.Context, collection string, pipeline interface{}) (interface{}, error)

	// Watch starts a change stream
	Watch(ctx context.Context, collection string, pipeline interface{}) (interface{}, error)
}

DocumentProvider extends Provider with document database functionality Implemented by providers like MongoDB, CouchDB, etc.

func AsDocumentProvider added in v0.1.1

func AsDocumentProvider(provider Provider) (DocumentProvider, bool)

AsDocumentProvider safely casts a Provider to DocumentProvider Returns the DocumentProvider instance and true if successful, nil and false otherwise

type DocumentRepository

type DocumentRepository[T any] interface {
	Repository[T]

	// FindByDocument retrieves entities matching a document-style query.
	// The query is a map representing the document structure to match.
	// Returns a slice of entity pointers with compile-time type safety.
	// Example: users, err := FindByDocument(ctx, map[string]interface{}{"status": "active", "age": map[string]interface{}{"$gte": 18}})
	FindByDocument(ctx context.Context, query map[string]interface{}) ([]*T, error)

	// UpdateDocument updates an entity using document-style operations.
	// The update parameter contains the update operations (e.g., $set, $unset, $inc).
	// Returns the number of documents modified.
	// Example: count, err := UpdateDocument(ctx, userID, map[string]interface{}{"$set": map[string]interface{}{"status": "inactive"}})
	UpdateDocument(ctx context.Context, id interface{}, update map[string]interface{}) (int64, error)

	// UpdateManyDocuments updates multiple entities using document-style operations.
	// Combines a query filter with update operations.
	// Returns the number of documents modified.
	// Example: count, err := UpdateManyDocuments(ctx, filter, update)
	UpdateManyDocuments(ctx context.Context, filter map[string]interface{}, update map[string]interface{}) (int64, error)

	// Aggregate performs aggregation operations using database-specific pipelines.
	// For MongoDB, this uses the aggregation pipeline. Other databases may use similar concepts.
	// Returns aggregated results as a slice of maps.
	// Example: results, err := Aggregate(ctx, []map[string]interface{}{{"$group": {"_id": "$status", "count": {"$sum": 1}}}})
	Aggregate(ctx context.Context, pipeline []map[string]interface{}) ([]map[string]interface{}, error)

	// CreateIndex creates an index on the specified fields.
	// The keys parameter maps field names to index direction (1 for ascending, -1 for descending).
	// For document databases, this might include text indexes, geospatial indexes, etc.
	// Example: err := CreateIndex(ctx, map[string]interface{}{"email": 1, "status": 1}, false)
	CreateIndex(ctx context.Context, keys map[string]interface{}, unique bool) error

	// DropIndex removes an index by name.
	// Example: err := DropIndex(ctx, "email_1_status_1")
	DropIndex(ctx context.Context, indexName string) error

	// TextSearch performs full-text search on indexed text fields.
	// The query string contains the search terms.
	// Returns entities matching the search criteria with compile-time type safety.
	// Example: users, err := TextSearch(ctx, "john developer", opts...)
	TextSearch(ctx context.Context, query string, opts ...QueryOption) ([]*T, error)

	// FindNear finds entities near a geographical point.
	// Requires geospatial indexes on the queried fields.
	// Returns entities sorted by distance with compile-time type safety.
	// Example: places, err := FindNear(ctx, "location", []float64{-73.9857, 40.7484}, 1000)
	FindNear(ctx context.Context, field string, point []float64, maxDistance float64) ([]*T, error)

	// FindWithinPolygon finds entities within a geographical polygon.
	// The polygon is defined by an array of coordinate points.
	// Returns matching entities with compile-time type safety.
	// Example: places, err := FindWithinPolygon(ctx, "location", polygon)
	FindWithinPolygon(ctx context.Context, field string, polygon [][]float64) ([]*T, error)
}

DocumentRepository extends Repository with document database-specific operations. Designed for NoSQL document stores like MongoDB, CouchDB, etc.

type EntityInfo

type EntityInfo struct {
	Name       string
	TableName  string
	Fields     []FieldInfo
	PrimaryKey []string
	Indexes    []IndexInfo
	Relations  []RelationInfo
}

EntityInfo contains metadata about an entity type

type ErrorType

type ErrorType string

ErrorType represents different types of errors that can occur

const (
	ErrorTypeValidation      ErrorType = "validation"
	ErrorTypeNotFound        ErrorType = "not_found"
	ErrorTypeDuplicate       ErrorType = "duplicate"
	ErrorTypeConnection      ErrorType = "connection"
	ErrorTypeTimeout         ErrorType = "timeout"
	ErrorTypePermission      ErrorType = "permission"
	ErrorTypeConstraint      ErrorType = "constraint"
	ErrorTypeTransaction     ErrorType = "transaction"
	ErrorTypeUnsupported     ErrorType = "unsupported"
	ErrorTypeInternal        ErrorType = "internal"
	ErrorTypeSerialization   ErrorType = "serialization"
	ErrorTypeInvalidArgument ErrorType = "invalid_argument"
	ErrorTypeDatabase        ErrorType = "database"
)

type EventHook

type EventHook interface {
	// BeforeCreate is called before creating an entity
	BeforeCreate(ctx interface{}, entity interface{}) error

	// AfterCreate is called after creating an entity
	AfterCreate(ctx interface{}, entity interface{}) error

	// BeforeUpdate is called before updating an entity
	BeforeUpdate(ctx interface{}, entity interface{}) error

	// AfterUpdate is called after updating an entity
	AfterUpdate(ctx interface{}, entity interface{}) error

	// BeforeDelete is called before deleting an entity
	BeforeDelete(ctx interface{}, id interface{}) error

	// AfterDelete is called after deleting an entity
	AfterDelete(ctx interface{}, id interface{}) error
}

EventHook represents a hook that can be called during repository operations

type Feature

type Feature string

Feature represents a database feature

const (
	FeatureTransactions   Feature = "transactions"
	FeatureIndexes        Feature = "indexes"
	FeatureTTL            Feature = "ttl"
	FeatureAtomicOps      Feature = "atomic_ops"
	FeatureFullText       Feature = "full_text_search"
	FeatureGeoSpatial     Feature = "geospatial"
	FeatureGeospatial     Feature = "geospatial"
	FeatureSubQueries     Feature = "subqueries"
	FeatureJoins          Feature = "joins"
	FeatureJSONQueries    Feature = "json_queries"
	FeatureIndexing       Feature = "indexing"
	FeatureAggregation    Feature = "aggregation"
	FeatureFullTextSearch Feature = "full_text_search"
	FeaturePubSub         Feature = "pub_sub"
	FeatureStreaming      Feature = "streaming"
	FeatureReplication    Feature = "replication"
	FeatureSharding       Feature = "sharding"
	FeatureMigration      Feature = "migration"
	FeatureRawSQL         Feature = "raw_sql"
)

type FieldInfo

type FieldInfo struct {
	Name            string
	Type            reflect.Type
	DatabaseType    string
	Tag             string
	IsPrimaryKey    bool
	IsNullable      bool
	IsAutoIncrement bool
	DefaultValue    interface{}
	MaxLength       int
	Precision       int
	Scale           int
}

FieldInfo contains metadata about a field

type FieldsOption

type FieldsOption struct {
	Fields []string
}

FieldsOption implements QueryOption for field selection

func (FieldsOption) Apply

func (o FieldsOption) Apply(query *Query)

type GPAError

type GPAError struct {
	Type    ErrorType
	Message string
	Cause   error
	Code    string
}

GPAError represents a GPA-specific error

func NewError

func NewError(errorType ErrorType, message string) GPAError

NewError creates a new GPAError

func NewErrorWithCause

func NewErrorWithCause(errorType ErrorType, message string, cause error) GPAError

NewErrorWithCause creates a new GPAError with a cause

func NewErrorWithCode

func NewErrorWithCode(errorType ErrorType, message string, code string) GPAError

NewErrorWithCode creates a new GPAError with a code

func (GPAError) Error

func (e GPAError) Error() string

Error implements the error interface

func (GPAError) Is

func (e GPAError) Is(target error) bool

Is checks if the error is of a specific type

func (GPAError) Unwrap

func (e GPAError) Unwrap() error

Unwrap returns the underlying error

type GraphProvider added in v0.1.1

type GraphProvider interface {
	Provider

	// Driver returns the underlying driver instance
	Driver() interface{}

	// Session returns a session for executing queries
	Session(ctx context.Context) (interface{}, error)

	// CypherQuery executes a Cypher query (for Neo4j-compatible databases)
	CypherQuery(ctx context.Context, query string, params map[string]interface{}) (interface{}, error)

	// CreateNode creates a node in the graph
	CreateNode(ctx context.Context, labels []string, properties map[string]interface{}) (interface{}, error)

	// CreateRelationship creates a relationship between two nodes
	CreateRelationship(ctx context.Context, fromNode, toNode interface{}, relType string, properties map[string]interface{}) (interface{}, error)

	// FindPath finds paths between nodes
	FindPath(ctx context.Context, from, to interface{}, maxDepth int) (interface{}, error)
}

GraphProvider extends Provider with graph database functionality Implemented by providers like Neo4j, ArangoDB, etc.

func AsGraphProvider added in v0.1.1

func AsGraphProvider(provider Provider) (GraphProvider, bool)

AsGraphProvider safely casts a Provider to GraphProvider Returns the GraphProvider instance and true if successful, nil and false otherwise

type GraphRepository

type GraphRepository[T any] interface {
	Repository[T]

	// FindConnected finds entities connected to the given entity.
	// Follows rel based on the specified relationship type and direction.
	// Returns connected entities with compile-time type safety.
	// Example: friends, err := FindConnected(ctx, userID, "FRIEND", "outgoing", 1)
	FindConnected(ctx context.Context, entityID interface{}, relationshipType string, direction string, depth int) ([]*T, error)

	// FindPath finds the shortest path between two entities.
	// Returns a list of entities representing the path with compile-time type safety.
	// Example: path, err := FindPath(ctx, startID, endID, "CONNECTED")
	FindPath(ctx context.Context, startID, endID interface{}, relationshipType string) ([]*T, error)

	// TraverseGraph performs a custom graph traversal.
	// Uses a traversal specification to define the traversal pattern.
	// Returns entities found during traversal with compile-time type safety.
	// Example: results, err := TraverseGraph(ctx, startID, traversal)
	TraverseGraph(ctx context.Context, startID interface{}, traversal GraphTraversal) ([]*T, error)
}

GraphRepository represents graph databases like Neo4j, ArangoDB. Optimized for relationship-heavy data and graph traversals.

type GraphTraversal

type GraphTraversal struct {
	StartingPoints []interface{}
	MaxDepth       int
	Relationships  []string
	Direction      string
	Filters        []Condition
}

GraphTraversal represents a graph traversal specification

type GroupByOption

type GroupByOption struct {
	Fields []string
}

GroupByOption implements QueryOption for grouping

func (GroupByOption) Apply

func (o GroupByOption) Apply(query *Query)

type HavingOption

type HavingOption struct {
	Condition Condition
}

HavingOption implements QueryOption for having conditions

func (HavingOption) Apply

func (o HavingOption) Apply(query *Query)

type IncrementKeyValueRepository

type IncrementKeyValueRepository interface {
	// Increment atomically increments a numeric value.
	// Creates the key with value 0 if it doesn't exist, then adds the delta.
	// Returns the new value after incrementing.
	// Example: newValue, err := Increment(ctx, "counter:visits", 1)
	Increment(ctx context.Context, key string, delta int64) (int64, error)

	// Decrement atomically decrements a numeric value.
	// Creates the key with value 0 if it doesn't exist, then subtracts the delta.
	// Returns the new value after decrementing.
	// Example: newValue, err := Decrement(ctx, "counter:items", 1)
	Decrement(ctx context.Context, key string, delta int64) (int64, error)
}

IncrementKeyValueRepository provides atomic increment/decrement operations. Useful for counters, statistics, and rate limiting.

type IndexInfo

type IndexInfo struct {
	Name     string
	Fields   []string
	IsUnique bool
	Type     IndexType
}

IndexInfo contains metadata about an index

type IndexOptions added in v0.1.1

type IndexOptions struct {
	Unique     bool
	Sparse     bool
	Background bool
	TTL        time.Duration
	Name       string
}

IndexOptions represents options for creating indexes

type IndexType

type IndexType string

IndexType represents different types of database indexes

const (
	IndexTypePrimary    IndexType = "primary"
	IndexTypeUnique     IndexType = "unique"
	IndexTypeStandard   IndexType = "standard"
	IndexTypeFullText   IndexType = "fulltext"
	IndexTypeGeoSpatial IndexType = "geospatial"
	IndexTypeComposite  IndexType = "composite"
)

type IsolationLevel added in v0.1.1

type IsolationLevel string

IsolationLevel represents transaction isolation levels

const (
	IsolationDefault         IsolationLevel = "DEFAULT"
	IsolationReadUncommitted IsolationLevel = "READ_UNCOMMITTED"
	IsolationReadCommitted   IsolationLevel = "READ_COMMITTED"
	IsolationRepeatableRead  IsolationLevel = "REPEATABLE_READ"
	IsolationSerializable    IsolationLevel = "SERIALIZABLE"
)

type JoinClause

type JoinClause struct {
	Type      JoinType
	Table     string
	Condition string
	Alias     string
}

JoinClause represents a table join

type JoinOption

type JoinOption struct {
	Join JoinClause
}

JoinOption implements QueryOption for joins

func (JoinOption) Apply

func (o JoinOption) Apply(query *Query)

type JoinType

type JoinType string

JoinType represents types of table joins

const (
	JoinInner JoinType = "INNER"
	JoinLeft  JoinType = "LEFT"
	JoinRight JoinType = "RIGHT"
	JoinFull  JoinType = "FULL"
)

type KeyValueProvider added in v0.1.1

type KeyValueProvider interface {
	Provider

	// Client returns the underlying client instance
	Client() interface{}

	// Set stores a key-value pair with optional TTL
	Set(ctx context.Context, key string, value interface{}, ttl time.Duration) error

	// Get retrieves a value by key
	Get(ctx context.Context, key string) (interface{}, error)

	// Delete removes a key
	Delete(ctx context.Context, key string) error

	// Exists checks if a key exists
	Exists(ctx context.Context, key string) (bool, error)

	// Keys returns all keys matching a pattern
	Keys(ctx context.Context, pattern string) ([]string, error)

	// Expire sets TTL for a key
	Expire(ctx context.Context, key string, ttl time.Duration) error

	// TTL returns the remaining TTL for a key
	TTL(ctx context.Context, key string) (time.Duration, error)
}

KeyValueProvider extends Provider with key-value store functionality Implemented by providers like Redis, memcached, etc.

func AsKeyValueProvider added in v0.1.1

func AsKeyValueProvider(provider Provider) (KeyValueProvider, bool)

AsKeyValueProvider safely casts a Provider to KeyValueProvider Returns the KeyValueProvider instance and true if successful, nil and false otherwise

type KeyspaceOptions added in v0.1.1

type KeyspaceOptions struct {
	ReplicationFactor int
	ReplicationClass  string
	DurableWrites     bool
}

KeyspaceOptions represents options for creating keyspaces

type LimitOption

type LimitOption struct {
	Count int
}

LimitOption implements QueryOption for limiting results

func (LimitOption) Apply

func (o LimitOption) Apply(query *Query)

type LockOption

type LockOption struct {
	Type LockType
}

LockOption implements QueryOption for row locking

func (LockOption) Apply

func (o LockOption) Apply(query *Query)

type LockType

type LockType string

LockType represents database lock types

const (
	LockNone         LockType = "NONE"
	LockShared       LockType = "SHARED"
	LockExclusive    LockType = "EXCLUSIVE"
	LockUpdateNoWait LockType = "UPDATE_NOWAIT"
	LockForUpdate    LockType = "FOR_UPDATE"
	LockForShare     LockType = "FOR_SHARE"
)

type LogicOperator

type LogicOperator string

LogicOperator represents logic operators for combining conditions

const (
	LogicAnd LogicOperator = "AND"
	LogicOr  LogicOperator = "OR"
	LogicNot LogicOperator = "NOT"
)

type MigratableRepository

type MigratableRepository[T any] interface {
	SQLRepository[T]

	// MigrateTable performs automatic schema migration for entity type T.
	// Analyzes the current entity structure and updates the database schema accordingly.
	// Can add new columns, indexes, and constraints but typically won't remove existing ones.
	// Example: err := MigrateTable(ctx)
	MigrateTable(ctx context.Context) error

	// GetMigrationStatus returns the current migration status for entity type T.
	// Indicates whether the table exists, what version it's at, and if migration is needed.
	// Example: status, err := GetMigrationStatus(ctx)
	GetMigrationStatus(ctx context.Context) (MigrationStatus, error)

	// GetTableInfo returns detailed information about the current table structure.
	// Includes columns, indexes, constraints, and other database-specific metadata.
	// Example: info, err := GetTableInfo(ctx)
	GetTableInfo(ctx context.Context) (TableInfo, error)
}

MigratableRepository extends SQLRepository with migration capabilities. Provides schema migration and evolution functionality.

type MigrationStatus

type MigrationStatus struct {
	TableExists     bool
	CurrentVersion  string
	RequiredVersion string
	NeedsMigration  bool
	PendingChanges  []string
}

MigrationStatus represents the migration status of a table

type OffsetOption

type OffsetOption struct {
	Count int
}

OffsetOption implements QueryOption for result offset

func (OffsetOption) Apply

func (o OffsetOption) Apply(query *Query)

type Operator

type Operator string

Operator represents query operators

const (
	OpEqual              Operator = "="
	OpNotEqual           Operator = "!="
	OpGreaterThan        Operator = ">"
	OpGreaterThanOrEqual Operator = ">="
	OpLessThan           Operator = "<"
	OpLessThanOrEqual    Operator = "<="
	OpLike               Operator = "LIKE"
	OpNotLike            Operator = "NOT LIKE"
	OpIn                 Operator = "IN"
	OpNotIn              Operator = "NOT IN"
	OpIsNull             Operator = "IS NULL"
	OpIsNotNull          Operator = "IS NOT NULL"
	OpBetween            Operator = "BETWEEN"
	OpNotBetween         Operator = "NOT BETWEEN"
	OpContains           Operator = "CONTAINS"
	OpStartsWith         Operator = "STARTS_WITH"
	OpEndsWith           Operator = "ENDS_WITH"
	OpRegex              Operator = "REGEX"
	OpExists             Operator = "EXISTS"
	OpNotExists          Operator = "NOT EXISTS"
	OpInSubQuery         Operator = "IN_SUBQUERY"
	OpNotInSubQuery      Operator = "NOT_IN_SUBQUERY"
)

type Order

type Order struct {
	Field     string
	Direction OrderDirection
}

Order represents sorting order

type OrderDirection

type OrderDirection string

OrderDirection represents sort direction

const (
	OrderAsc  OrderDirection = "ASC"
	OrderDesc OrderDirection = "DESC"
)

type OrderOption

type OrderOption struct {
	Order Order
}

OrderOption implements QueryOption for ordering

func (OrderOption) Apply

func (o OrderOption) Apply(query *Query)

type PatternKeyValueRepository

type PatternKeyValueRepository interface {
	// Keys returns all keys matching the given pattern.
	// Uses glob-style patterns (*, ?, [abc], etc.).
	// WARNING: Can be slow with large datasets - use with caution.
	// Example: keys, err := Keys(ctx, "user:*")
	Keys(ctx context.Context, pattern string) ([]string, error)

	// Scan iterates over keys matching a pattern using cursor-based pagination.
	// More efficient than Keys() for large datasets as it doesn't load all keys at once.
	// Returns matching keys and a cursor for the next iteration.
	// Example: keys, cursor, err := Scan(ctx, 0, "user:*", 10)
	Scan(ctx context.Context, cursor uint64, pattern string, count int64) ([]string, uint64, error)
}

PatternKeyValueRepository provides pattern-based key operations. Useful for finding keys that match certain patterns.

type PreloadOption

type PreloadOption struct {
	Relations []string
}

PreloadOption implements QueryOption for eager loading

func (PreloadOption) Apply

func (o PreloadOption) Apply(query *Query)

type Provider

type Provider interface {
	// Configure applies new configuration to the provider.
	// Can be used to change connection settings, pool sizes, etc. at runtime.
	// May require reconnection depending on what settings changed.
	Configure(config Config) error

	// Health checks if the database connection is healthy and responsive.
	// Returns error if the database is unreachable or not functioning properly.
	// Useful for health check endpoints and monitoring.
	Health() error

	// Close shuts down the provider and releases all resources.
	// Closes database providers, stops background tasks, etc.
	// Should be called during application shutdown.
	Close() error

	// SupportedFeatures returns a list of features this provider supports.
	// Features include things like transactions, full-text search, pub/sub, etc.
	// Use this to check capabilities before using advanced features.
	SupportedFeatures() []Feature

	// ProviderInfo returns metadata about this provider.
	// Includes provider name, version, database type, and supported features.
	// Useful for debugging, logging, and feature detection.
	ProviderInfo() ProviderInfo
}

Provider is the main interface for database provider implementations. Provides unified access to database operations with type safety through repository creation functions.

This interface is implemented by all provider packages: • gpagorm.Provider (GORM SQL adapter) • gpabun.Provider (Bun SQL adapter) • gpamongo.Provider (MongoDB adapter) • gparedis.Provider (Redis adapter)

Usage:

provider, err := gpagorm.NewProvider(config)
if err != nil {
    log.Fatal(err)
}
defer provider.Close()

// Create type-safe repositories
userRepo := gpagorm.GetRepository[User](provider)
postRepo := gpagorm.GetRepository[Post](provider)

type ProviderFunc added in v0.1.1

type ProviderFunc func(...string) Provider

type ProviderInfo

type ProviderInfo struct {
	Name         string
	Version      string
	DatabaseType DatabaseType
	Features     []Feature
}

ProviderInfo contains information about the provider

type ProviderRegistry

type ProviderRegistry struct {
	// contains filtered or unexported fields
}

ProviderRegistry holds all registered providers organized by type and name

func Registry

func Registry() *ProviderRegistry

Registry returns the singleton instance of ProviderRegistry

func (*ProviderRegistry) Get

func (r *ProviderRegistry) Get(providerType string, instanceName ...string) (Provider, error)

Get retrieves a provider by type and instance name

func (*ProviderRegistry) GetByType

func (r *ProviderRegistry) GetByType(providerType string) (map[string]Provider, error)

GetByType returns all providers of a specific type

func (*ProviderRegistry) HealthCheck

func (r *ProviderRegistry) HealthCheck() map[string]map[string]error

HealthCheck checks the health of all registered providers

func (*ProviderRegistry) ListInstances

func (r *ProviderRegistry) ListInstances(providerType string) ([]string, error)

ListInstances returns all instance names for a given provider type

func (*ProviderRegistry) ListTypes

func (r *ProviderRegistry) ListTypes() []string

ListTypes returns all registered provider types

func (*ProviderRegistry) MustGet

func (r *ProviderRegistry) MustGet(providerType string, instanceName ...string) Provider

MustGet retrieves a provider by type and instance name, panics if not found

func (*ProviderRegistry) Register

func (r *ProviderRegistry) Register(instanceName string, provider Provider)

Register adds a provider to the registry

func (*ProviderRegistry) RegisterDefault

func (r *ProviderRegistry) RegisterDefault(provider Provider)

RegisterDefault registers a provider as the default instance for its type

func (*ProviderRegistry) Remove

func (r *ProviderRegistry) Remove(providerType, instanceName string) error

Remove closes and removes a provider from the registry

func (*ProviderRegistry) RemoveAll

func (r *ProviderRegistry) RemoveAll() error

RemoveAll closes and removes all providers from the registry

type Query

type Query struct {
	Conditions []Condition
	Orders     []Order
	Limit      *int
	Offset     *int
	Fields     []string
	Joins      []JoinClause
	Groups     []string
	Having     []Condition
	Distinct   bool
	Lock       LockType
	Preloads   []string
	SubQueries []SubQuery
}

Query represents a database query

func NewQuery

func NewQuery() *Query

NewQuery creates a new empty query

func (*Query) String

func (q *Query) String() string

String returns a string representation of the query

type QueryBuilder

type QueryBuilder[T any] struct {
	// contains filtered or unexported fields
}

QueryBuilder provides a fluent interface for building type-safe database queries. Supports method chaining for convenient query construction.

func NewQueryBuilder

func NewQueryBuilder[T any]() *QueryBuilder[T]

NewQueryBuilder creates a new type-safe query builder for entity type T. Example: qb := NewQueryBuilder[User]()

func (*QueryBuilder[T]) Build

func (qb *QueryBuilder[T]) Build() *Query

Build converts the QueryBuilder to a Query struct. Returns a Query that can be used with repository methods. Example: query := qb.Build()

func (*QueryBuilder[T]) Count

func (qb *QueryBuilder[T]) Count(ctx context.Context, repo Repository[T]) (int64, error)

Count executes the query and returns the count of matching entities. Returns the count as an int64. Example: count, err := qb.Count(ctx, repo)

func (*QueryBuilder[T]) Distinct

func (qb *QueryBuilder[T]) Distinct() *QueryBuilder[T]

Distinct adds a DISTINCT clause to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.Distinct()

func (*QueryBuilder[T]) Execute

func (qb *QueryBuilder[T]) Execute(ctx context.Context, repo Repository[T]) ([]*T, error)

Execute executes the query using the provided repository. Returns a slice of entity pointers with compile-time type safety. Example: users, err := qb.Execute(ctx, repo)

func (*QueryBuilder[T]) ExecuteOne

func (qb *QueryBuilder[T]) ExecuteOne(ctx context.Context, repo Repository[T]) (*T, error)

ExecuteOne executes the query and returns a single result. Returns the entity directly with compile-time type safety. Returns ErrorTypeNotFound if no entity matches the query. Example: user, err := qb.ExecuteOne(ctx, repo)

func (*QueryBuilder[T]) GroupBy

func (qb *QueryBuilder[T]) GroupBy(fields ...string) *QueryBuilder[T]

GroupBy adds a GROUP BY clause to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.GroupBy("status", "department")

func (*QueryBuilder[T]) Having

func (qb *QueryBuilder[T]) Having(field string, operator Operator, value interface{}) *QueryBuilder[T]

Having adds a HAVING condition to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.Having("COUNT(*)", ">", 5)

func (*QueryBuilder[T]) Join

func (qb *QueryBuilder[T]) Join(joinType JoinType, table string, condition string) *QueryBuilder[T]

Join adds a JOIN clause to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.Join(JoinLeft, "orders", "users.id = orders.user_id")

func (*QueryBuilder[T]) Limit

func (qb *QueryBuilder[T]) Limit(count int) *QueryBuilder[T]

Limit sets the maximum number of results to return. Returns the same QueryBuilder instance for method chaining. Example: qb.Limit(10)

func (*QueryBuilder[T]) Lock

func (qb *QueryBuilder[T]) Lock(lockType LockType) *QueryBuilder[T]

Lock adds a locking clause to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.Lock(LockExclusive)

func (*QueryBuilder[T]) Offset

func (qb *QueryBuilder[T]) Offset(count int) *QueryBuilder[T]

Offset sets the number of results to skip. Returns the same QueryBuilder instance for method chaining. Example: qb.Offset(20)

func (*QueryBuilder[T]) OrderBy

func (qb *QueryBuilder[T]) OrderBy(field string, direction OrderDirection) *QueryBuilder[T]

OrderBy adds an ORDER BY clause to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.OrderBy("name", OrderAsc).OrderBy("created_at", OrderDesc)

func (*QueryBuilder[T]) Preload

func (qb *QueryBuilder[T]) Preload(relations ...string) *QueryBuilder[T]

Preload specifies rel to eagerly load. Returns the same QueryBuilder instance for method chaining. Example: qb.Preload("Orders", "Profile")

func (*QueryBuilder[T]) Select

func (qb *QueryBuilder[T]) Select(fields ...string) *QueryBuilder[T]

Select specifies which fields to include in the results. Returns the same QueryBuilder instance for method chaining. Example: qb.Select("id", "name", "email")

func (*QueryBuilder[T]) Where

func (qb *QueryBuilder[T]) Where(field string, operator Operator, value interface{}) *QueryBuilder[T]

Where adds a WHERE condition to the query. Returns the same QueryBuilder instance for method chaining. Example: qb.Where("age", ">", 18).Where("status", "=", "active")

func (*QueryBuilder[T]) WhereCondition

func (qb *QueryBuilder[T]) WhereCondition(condition Condition) *QueryBuilder[T]

WhereCondition adds a custom condition to the query. Useful for complex conditions that can't be expressed with simple field/operator/value. Returns the same QueryBuilder instance for method chaining. Example: qb.WhereCondition(customCondition)

type QueryOption

type QueryOption interface {
	Apply(query *Query)
}

QueryOption interface for building database queries

func And

func And(conditions ...Condition) QueryOption

And creates an AND composite condition

func AndOption

func AndOption(conditions ...Condition) QueryOption

AndOption creates an AND composite condition

func CorrelatedSubQuery

func CorrelatedSubQuery(field string, operator Operator, subQuery *Query, correlationField string) QueryOption

CorrelatedSubQuery creates a correlated subquery

func Distinct

func Distinct() QueryOption

Distinct creates a distinct option

func ExistsSubQuery

func ExistsSubQuery(subQuery *Query) QueryOption

ExistsSubQuery creates an EXISTS subquery condition

func Fields

func Fields(fields ...string) QueryOption

Fields creates a field selection option

func GroupBy

func GroupBy(fields ...string) QueryOption

GroupBy creates a group by option

func Having

func Having(field string, operator Operator, value interface{}) QueryOption

Having creates a having condition option

func InSubQuery

func InSubQuery(field string, subQuery *Query) QueryOption

InSubQuery creates an IN subquery condition

func InnerJoin

func InnerJoin(table string, condition string) QueryOption

InnerJoin creates an INNER JOIN

func Join

func Join(joinType JoinType, table string, condition string, alias ...string) QueryOption

Join creates a join option

func LeftJoin

func LeftJoin(table string, condition string) QueryOption

LeftJoin creates a LEFT JOIN

func Limit

func Limit(count int) QueryOption

Limit creates a limit option

func Lock

func Lock(lockType LockType) QueryOption

Lock creates a lock option

func NotExistsSubQuery

func NotExistsSubQuery(subQuery *Query) QueryOption

NotExistsSubQuery creates a NOT EXISTS subquery condition

func NotInSubQuery

func NotInSubQuery(field string, subQuery *Query) QueryOption

NotInSubQuery creates a NOT IN subquery condition

func Offset

func Offset(count int) QueryOption

Offset creates an offset option

func Or

func Or(conditions ...Condition) QueryOption

Or creates an OR composite condition

func OrOption

func OrOption(conditions ...Condition) QueryOption

OrOption creates an OR composite condition

func OrderBy

func OrderBy(field string, direction OrderDirection) QueryOption

OrderBy creates an ordering option

func Preload

func Preload(relations ...string) QueryOption

Preload creates a preload option for eager loading

func ScalarSubQuery

func ScalarSubQuery(field string, operator Operator, subQuery *Query) QueryOption

ScalarSubQuery creates a scalar subquery condition

func Select

func Select(fields ...string) QueryOption

Select creates a field selection option (alias for Fields)

func Where

func Where(field string, operator Operator, value interface{}) QueryOption

Where creates a basic WHERE condition

func WhereIn

func WhereIn(field string, values []interface{}) QueryOption

WhereIn creates a WHERE IN condition

func WhereLike

func WhereLike(field string, value string) QueryOption

WhereLike creates a WHERE LIKE condition

func WhereNotNull

func WhereNotNull(field string) QueryOption

WhereNotNull creates a WHERE IS NOT NULL condition

func WhereNull

func WhereNull(field string) QueryOption

WhereNull creates a WHERE IS NULL condition

func WhereSubQuery

func WhereSubQuery(field string, operator Operator, subQuery *Query) QueryOption

WhereSubQuery creates a general subquery condition

type RelationInfo

type RelationInfo struct {
	Name         string
	Type         RelationType
	TargetEntity string
	ForeignKey   string
	References   string
}

RelationInfo contains metadata about rel

type RelationType

type RelationType string

RelationType represents different types of entity rel

const (
	RelationOneToOne   RelationType = "one_to_one"
	RelationOneToMany  RelationType = "one_to_many"
	RelationManyToOne  RelationType = "many_to_one"
	RelationManyToMany RelationType = "many_to_many"
)

type Repository

type Repository[T any] interface {

	// Create inserts a new entity into the database.
	// Returns error if the entity already exists or validation fails.
	// Example: err := Create(ctx, &user)
	Create(ctx context.Context, entity *T) error

	// CreateBatch inserts multiple entities in a single operation for better performance.
	// May not be atomic depending on the database implementation.
	// Example: err := CreateBatch(ctx, []*User{user1, user2, user3})
	CreateBatch(ctx context.Context, entities []*T) error

	// FindByID retrieves a single entity by its primary key.
	// Returns the entity directly with compile-time type safety.
	// Returns ErrorTypeNotFound if the entity doesn't exist.
	// Example: user, err := FindByID(ctx, 123)
	FindByID(ctx context.Context, id interface{}) (*T, error)

	// FindAll retrieves all entities of type T, optionally filtered by query options.
	// Returns a slice of entity pointers with compile-time type safety.
	// Use QueryOptions like Where(), Limit(), OrderBy() to filter and sort results.
	// Example: users, err := FindAll(ctx, Where("active", "=", true), Limit(10))
	FindAll(ctx context.Context, opts ...QueryOption) ([]*T, error)

	// Update modifies an existing entity. The entity must have an ID field.
	// Replaces the entire entity with the new values.
	// Returns ErrorTypeNotFound if the entity doesn't exist.
	// Example: err := Update(ctx, &user)
	Update(ctx context.Context, entity *T) error

	// UpdatePartial modifies specific fields of an entity without replacing the whole entity.
	// The updates map contains field names as keys and new values as values.
	// Returns ErrorTypeNotFound if the entity doesn't exist.
	// Example: err := UpdatePartial(ctx, 123, map[string]interface{}{"status": "inactive"})
	UpdatePartial(ctx context.Context, id interface{}, updates map[string]interface{}) error

	// Delete removes an entity by its primary key.
	// Returns ErrorTypeNotFound if the entity doesn't exist.
	// Example: err := Delete(ctx, 123)
	Delete(ctx context.Context, id interface{}) error

	// DeleteByCondition removes all entities matching the given condition.
	// Use Where() conditions to specify which entities to delete.
	// Example: err := DeleteByCondition(ctx, Where("status", "=", "inactive"))
	DeleteByCondition(ctx context.Context, condition Condition) error

	// Query retrieves entities based on the provided query options.
	// More flexible than FindAll, supports complex conditions, joins, subqueries.
	// Returns a slice of entity pointers with compile-time type safety.
	// Example: users, err := Query(ctx, Where("age", ">", 18), OrderBy("name", "ASC"))
	Query(ctx context.Context, opts ...QueryOption) ([]*T, error)

	// QueryOne retrieves a single entity based on query options.
	// Equivalent to Query() with Limit(1) but returns ErrorTypeNotFound if no match.
	// Returns the entity directly with compile-time type safety.
	// Example: user, err := QueryOne(ctx, Where("email", "=", "user@example.com"))
	QueryOne(ctx context.Context, opts ...QueryOption) (*T, error)

	// Count returns the number of entities matching the query options.
	// Does not retrieve the actual entities, just counts them.
	// Useful for pagination and analytics.
	// Example: count, err := Count(ctx, Where("active", "=", true))
	Count(ctx context.Context, opts ...QueryOption) (int64, error)

	// Exists checks if any entities match the query options.
	// More efficient than Count() when you only need to know if matches exist.
	// Returns true if at least one entity matches, false otherwise.
	// Example: exists, err := Exists(ctx, Where("email", "=", "user@example.com"))
	Exists(ctx context.Context, opts ...QueryOption) (bool, error)

	// Transaction executes a function within a database transaction.
	// If the function returns an error, the transaction is rolled back.
	// If the function completes successfully, the transaction is committed.
	// Not all databases support transactions (e.g., some NoSQL databases).
	// Example: err := Transaction(ctx, func(tx Transaction[T]) error { return tx.Create(ctx, &user) })
	Transaction(ctx context.Context, fn TransactionFunc[T]) error

	// RawQuery executes a database-specific query and returns results.
	// Returns a slice of entity pointers with compile-time type safety.
	// The query string and args format depend on the database type.
	// Example: users, err := RawQuery(ctx, "SELECT * FROM users WHERE age > ?", []interface{}{18})
	RawQuery(ctx context.Context, query string, args []interface{}) ([]*T, error)

	// RawExec executes a database-specific command that doesn't return data.
	// Used for database-specific operations like creating indexes, triggers, etc.
	// Returns a Result object with information about rows affected, etc.
	// Example: result, err := RawExec(ctx, "UPDATE users SET last_login = NOW()", nil)
	RawExec(ctx context.Context, query string, args []interface{}) (Result, error)

	// GetEntityInfo returns metadata about the entity type T.
	// Includes field information, primary keys, indexes, and rel.
	// Useful for reflection, validation, and building dynamic UIs.
	// Example: info, err := GetEntityInfo()
	GetEntityInfo() (*EntityInfo, error)

	// Close closes the repository and releases any resources.
	// Should be called when the repository is no longer needed.
	// May close database providers, file handles, etc.
	// Example: err := Close()
	Close() error
}

Repository is the main interface for database operations. Provides compile-time type safety for all CRUD operations. This is the PRIMARY interface - use this for all new code.

type Result

type Result interface {
	// LastInsertId returns the integer generated by the database
	// in response to a command. Typically this will be from an
	// "auto increment" column when inserting a new row.
	LastInsertId() (int64, error)

	// RowsAffected returns the number of rows affected by an
	// update, insert, or delete. Not every database or database
	// driver may support this.
	RowsAffected() (int64, error)
}

Result represents the result of a database operation

type SQLProvider added in v0.1.1

type SQLProvider interface {
	Provider

	// DB returns the underlying database/sql.DB instance
	// This allows direct access to the native SQL connection for advanced operations
	DB() interface{}

	// BeginTx starts a transaction with specific isolation level
	BeginTx(ctx context.Context, opts *TxOptions) (interface{}, error)

	// Migrate runs database migrations
	Migrate(models ...interface{}) error

	// RawQuery executes raw SQL and returns results
	RawQuery(ctx context.Context, query string, args ...interface{}) (interface{}, error)

	// RawExec executes raw SQL without returning results
	RawExec(ctx context.Context, query string, args ...interface{}) (Result, error)
}

SQLProvider extends Provider with SQL-specific functionality Implemented by providers that support SQL databases (GORM, Bun, etc.)

func AsSQLProvider added in v0.1.1

func AsSQLProvider(provider Provider) (SQLProvider, bool)

AsSQLProvider safely casts a Provider to SQLProvider Returns the SQLProvider instance and true if successful, nil and false otherwise

type SQLRepository

type SQLRepository[T any] interface {
	Repository[T]

	// FindBySQL executes a raw SQL SELECT query and returns typed results.
	// Returns a slice of entity pointers with compile-time type safety.
	// Example: users, err := FindBySQL(ctx, "SELECT * FROM users WHERE age > ?", []interface{}{18})
	FindBySQL(ctx context.Context, sql string, args []interface{}) ([]*T, error)

	// ExecSQL executes a raw SQL command that doesn't return entities (INSERT, UPDATE, DELETE, DDL).
	// Returns a Result with information about rows affected, last insert ID, etc.
	// Example: result, err := ExecSQL(ctx, "UPDATE users SET status = ? WHERE active = ?", "inactive", false)
	ExecSQL(ctx context.Context, sql string, args ...interface{}) (Result, error)

	// FindWithRelations retrieves entities with their related entities preloaded.
	// Returns a slice of entity pointers with compile-time type safety.
	// The relations slice specifies which rel to load.
	// Example: users, err := FindWithRelations(ctx, []string{"Posts", "Profile"}, Where("active", "=", true))
	FindWithRelations(ctx context.Context, relations []string, opts ...QueryOption) ([]*T, error)

	// FindByIDWithRelations retrieves a single entity by ID with rel preloaded.
	// Returns the entity directly with compile-time type safety.
	// Example: user, err := FindByIDWithRelations(ctx, userID, []string{"Posts", "Comments"})
	FindByIDWithRelations(ctx context.Context, id interface{}, relations []string) (*T, error)

	// CreateTable creates a new table based on the entity structure.
	// Analyzes the entity type T's fields, tags, and rel to generate appropriate SQL.
	// May create foreign key constraints, indexes, and other database objects.
	// Example: err := CreateTable(ctx)
	CreateTable(ctx context.Context) error

	// DropTable removes the table for entity type T from the database.
	// WARNING: This permanently deletes all data in the table.
	// May fail if there are foreign key constraints pointing to this table.
	// Example: err := DropTable(ctx)
	DropTable(ctx context.Context) error

	// CreateIndex creates a database index on the specified fields of entity type T.
	// Improves query performance for the specified field combinations.
	// The unique parameter determines if the index should enforce uniqueness.
	// Example: err := CreateIndex(ctx, []string{"email", "status"}, true)
	CreateIndex(ctx context.Context, fields []string, unique bool) error

	// DropIndex removes a database index.
	// The indexName should match an existing index on the table for entity type T.
	// Example: err := DropIndex(ctx, "idx_users_email_status")
	DropIndex(ctx context.Context, indexName string) error
}

SQLRepository extends Repository with SQL-specific operations. Provides additional functionality for SQL databases including raw SQL, rel, and schema management.

type SSLConfig

type SSLConfig struct {
	Enabled  bool   `json:"enabled" yaml:"enabled"`
	Mode     string `json:"mode" yaml:"mode"`
	CertFile string `json:"cert_file" yaml:"cert_file"`
	KeyFile  string `json:"key_file" yaml:"key_file"`
	CAFile   string `json:"ca_file" yaml:"ca_file"`
}

SSLConfig represents SSL/TLS configuration

type SubQuery

type SubQuery struct {
	Query    *Query
	Type     SubQueryType
	Field    string
	Operator Operator
	Args     []interface{}
}

SubQuery represents a subquery in a larger query

type SubQueryCondition

type SubQueryCondition struct {
	SubQuery  SubQuery
	FieldName string
}

SubQueryCondition implements Condition for subqueries

func (SubQueryCondition) Field

func (c SubQueryCondition) Field() string

func (SubQueryCondition) Operator

func (c SubQueryCondition) Operator() Operator

func (SubQueryCondition) String

func (c SubQueryCondition) String() string

func (SubQueryCondition) Value

func (c SubQueryCondition) Value() interface{}

type SubQueryOption

type SubQueryOption struct {
	SubQuery SubQuery
}

SubQueryOption implements QueryOption for subqueries

func (SubQueryOption) Apply

func (o SubQueryOption) Apply(query *Query)

type SubQueryType

type SubQueryType string

SubQueryType represents the type of subquery operation

const (
	SubQueryExists         SubQueryType = "EXISTS"
	SubQueryNotExists      SubQueryType = "NOT EXISTS"
	SubQueryIn             SubQueryType = "IN"
	SubQueryNotIn          SubQueryType = "NOT IN"
	SubQueryScalar         SubQueryType = "SCALAR"
	SubQueryAny            SubQueryType = "ANY"
	SubQueryAll            SubQueryType = "ALL"
	SubQueryTypeExists     SubQueryType = "EXISTS"
	SubQueryTypeIn         SubQueryType = "IN"
	SubQueryTypeScalar     SubQueryType = "SCALAR"
	SubQueryTypeCorrelated SubQueryType = "CORRELATED"
)

type TTLKeyValueRepository

type TTLKeyValueRepository[T any] interface {
	BasicKeyValueRepository[T]

	// SetWithTTL stores a value with an expiration time.
	// The value will be automatically deleted after the TTL expires.
	// Example: err := SetWithTTL(ctx, "session:abc123", session, 30*time.Minute)
	SetWithTTL(ctx context.Context, key string, value *T, ttl time.Duration) error

	// GetTTL returns the remaining time-to-live for a key.
	// Returns 0 if the key doesn't exist or has no TTL.
	// Example: ttl, err := GetTTL(ctx, "session:abc123")
	GetTTL(ctx context.Context, key string) (time.Duration, error)

	// SetTTL sets or updates the TTL for an existing key.
	// Returns ErrorTypeNotFound if the key doesn't exist.
	// Example: err := SetTTL(ctx, "session:abc123", 15*time.Minute)
	SetTTL(ctx context.Context, key string, ttl time.Duration) error

	// RemoveTTL removes the TTL from a key, making it persistent.
	// The key will no longer expire automatically.
	// Example: err := RemoveTTL(ctx, "permanent:key")
	RemoveTTL(ctx context.Context, key string) error
}

TTLKeyValueRepository extends BasicKeyValueRepository with TTL (Time To Live) support. Values automatically expire after a specified duration.

type TableInfo

type TableInfo struct {
	Name        string
	Columns     []ColumnInfo
	Indexes     []IndexInfo
	Constraints []ConstraintInfo
}

TableInfo represents detailed information about a database table

type Transaction

type Transaction[T any] interface {
	Repository[T]

	// Commit permanently saves all changes made within this transaction.
	// Once committed, changes cannot be rolled back.
	// Returns error if the commit fails (e.g., constraint violations).
	Commit() error

	// Rollback discards all changes made within this transaction.
	// Can be called manually or automatically when the transaction function returns an error.
	// Returns error if the rollback fails.
	Rollback() error

	// SetSavepoint creates a savepoint within the transaction.
	// Allows partial rollback to a specific point without rolling back the entire transaction.
	// Not supported by all databases.
	SetSavepoint(name string) error

	// RollbackToSavepoint rolls back to a previously created savepoint.
	// Only changes made after the savepoint are discarded.
	// Not supported by all databases.
	RollbackToSavepoint(name string) error
}

Transaction interface for transactional operations. This is the PRIMARY transaction interface - use this for all new code.

type TransactionFunc

type TransactionFunc[T any] func(tx Transaction[T]) error

TransactionFunc represents a function that runs within a transaction

type TxOptions added in v0.1.1

type TxOptions struct {
	IsolationLevel IsolationLevel
	ReadOnly       bool
	Timeout        time.Duration
}

TxOptions represents transaction options

type ValidationHook added in v0.1.1

type ValidationHook interface {
	Validate(ctx context.Context) error
}

ValidationHook is called to validate an entity before create/update

type WideColumnProvider added in v0.1.1

type WideColumnProvider interface {
	Provider

	// Session returns the underlying session instance
	Session() interface{}

	// CreateKeyspace creates a keyspace
	CreateKeyspace(ctx context.Context, name string, options *KeyspaceOptions) error

	// CreateTable creates a table in a keyspace
	CreateTable(ctx context.Context, keyspace string, table string, schema interface{}) error

	// PrepareStatement prepares a statement for execution
	PrepareStatement(ctx context.Context, query string) (interface{}, error)

	// BatchExecute executes multiple statements as a batch
	BatchExecute(ctx context.Context, statements []interface{}) error
}

WideColumnProvider extends Provider with wide-column store functionality Implemented by providers like Cassandra, HBase, etc.

func AsWideColumnProvider added in v0.1.1

func AsWideColumnProvider(provider Provider) (WideColumnProvider, bool)

AsWideColumnProvider safely casts a Provider to WideColumnProvider Returns the WideColumnProvider instance and true if successful, nil and false otherwise

type WideColumnRepository

type WideColumnRepository[T any] interface {
	Repository[T]

	// FindByPartitionKey retrieves entities by partition key.
	// Partition keys determine data distribution across nodes.
	// Returns entities within the same partition with compile-time type safety.
	// Example: events, err := FindByPartitionKey(ctx, partitionKey, opts...)
	FindByPartitionKey(ctx context.Context, partitionKey interface{}, opts ...QueryOption) ([]*T, error)

	// FindByRange retrieves entities within a clustering key range.
	// Clustering keys determine sort order within partitions.
	// Returns entities within the specified range with compile-time type safety.
	// Example: events, err := FindByRange(ctx, partitionKey, startKey, endKey)
	FindByRange(ctx context.Context, partitionKey, startKey, endKey interface{}) ([]*T, error)

	// FindByTimeRange retrieves entities within a time range.
	// Optimized for time-series data queries.
	// Returns time-ordered entities with compile-time type safety.
	// Example: metrics, err := FindByTimeRange(ctx, startTime, endTime, opts...)
	FindByTimeRange(ctx context.Context, startTime, endTime interface{}, opts ...QueryOption) ([]*T, error)

	// Compact triggers compaction of the underlying storage.
	// Improves read performance by merging and organizing data files.
	// Returns when compaction is complete or fails.
	// Example: err := Compact(ctx)
	Compact(ctx context.Context) error
}

WideColumnRepository represents wide column stores like Cassandra, HBase. Optimized for time-series data and large-scale analytics.

Directories

Path Synopsis
examples
gpabun command
gpagorm command
gpamongo command
gparedis command

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL