kvx
kvx
kvx is a layered Redis / Valkey access package focused on strongly typed object access, repository-style persistence, and Redis-native capabilities.
What You Get
- Unified
Clientcapability interfaces forKV,Hash,JSON,PubSub,Stream,Search,Script, andLock - Metadata-driven mapping based on
kvxstruct tags HashRepositoryandJSONRepositoryfor strongly typed persistence- Secondary-index helper support through repository indexers
- Feature modules for
json,pubsub,stream,search, andlock - Thin adapters for Redis and Valkey drivers
Positioning
kvx is not trying to be a generic cache abstraction.
It is a Redis / Valkey-oriented object access layer for services that want typed repositories without giving up Redis-native data models.
Minimal Repository Example
type User struct {
ID string `kvx:"id"`
Name string `kvx:"name"`
Email string `kvx:"email,index=email"`
}
backend := shared.NewHashBackend()
repo := repository.NewHashRepository[User](backend, backend, "user")
_ = repo.Save(ctx, &User{
ID: "u-1",
Name: "Alice",
Email: "alice@example.com",
})
entity, _ := repo.FindByID(ctx, "u-1")
matches, _ := repo.FindByField(ctx, "email", "alice@example.com")
_, _ = entity, matchesCore Layers
Client Interfaces
KVHashJSONPubSubStreamSearchScriptLockClient
Mapping
kvx struct tags drive schema metadata:
type User struct {
ID string `kvx:"id"`
Name string `kvx:"name"`
Email string `kvx:"email,index=email"`
}Supported metadata concepts include:
- key field
- storage field name
- indexed field
- custom index alias
Repositories
repository.NewHashRepository[T](...)repository.NewJSONRepository[T](...)repository.NewPreset[T](...)repository.WithKeyBuilder(...)repository.WithIndexer(...)repository.WithHashCodec(...)repository.WithSerializer(...)
Feature Modules
module/json: higher-level JSON document helpersmodule/pubsub: channel subscription managementmodule/stream: stream and consumer-group helpersmodule/search: RediSearch-oriented query helpersmodule/lock: distributed lock helpers
Adapters
kvx/adapter/rediskvx/adapter/valkey
These adapters stay thin and primarily expose the kvx capability surface over the underlying driver.
Examples
go run ./examples/kvx/hash_repository- in-memory hash repository flow with indexing
go run ./examples/kvx/json_repository- in-memory JSON repository flow with field updates and scanning
go run ./examples/kvx/redis_adapter- real Redis-backed hash repository flow using
testcontainers-go
- real Redis-backed hash repository flow using
go run ./examples/kvx/redis_hash- real Redis hash example using
testcontainers-go
- real Redis hash example using
go run ./examples/kvx/redis_json- real Redis JSON example using
testcontainers-go
- real Redis JSON example using
go run ./examples/kvx/redis_stream- real Redis stream example using
testcontainers-go
- real Redis stream example using
go run ./examples/kvx/valkey_hash- real Valkey hash example using
testcontainers-go
- real Valkey hash example using
go run ./examples/kvx/valkey_json- real Valkey JSON example using
testcontainers-go
- real Valkey JSON example using
go run ./examples/kvx/valkey_stream- real Valkey stream example using
testcontainers-go
- real Valkey stream example using
Container Images
redis_hashandredis_streamdefault toredis:7-alpineredis_jsondefaults toredis/redis-stack-server:latestvalkey_hashandvalkey_streamdefault tovalkey/valkey:8-alpinevalkey_jsondefaults tovalkey/valkey:8-alpine; overrideKVX_VALKEY_JSON_IMAGEif your JSON commands require a different image
Notes
- The repository layer is currently the most mature part of
kvx. FindAll/Countnow scan the full keyspace cursor path instead of only a single page.- Workspace sibling modules like
collectionxresolve throughgo.work; no extra local dependency declaration is needed inkvx/go.mod.