https://github.com/gabisonia/go-vectorstore
A lightweight Go vector-store library inspired by Microsoft.Extensions.VectorData
https://github.com/gabisonia/go-vectorstore
go-vector postgresql vectordb vectorstore
Last synced: 2 months ago
JSON representation
A lightweight Go vector-store library inspired by Microsoft.Extensions.VectorData
- Host: GitHub
- URL: https://github.com/gabisonia/go-vectorstore
- Owner: gabisonia
- License: mit
- Created: 2026-02-11T09:51:18.000Z (2 months ago)
- Default Branch: master
- Last Pushed: 2026-02-16T13:17:11.000Z (2 months ago)
- Last Synced: 2026-02-17T01:49:29.916Z (2 months ago)
- Topics: go-vector, postgresql, vectordb, vectorstore
- Language: Go
- Homepage:
- Size: 120 KB
- Stars: 5
- Watchers: 0
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# go-vectorstore
[](https://pkg.go.dev/github.com/gabisonia/go-vectorstore)
[](https://github.com/gabisonia/go-vectorstore/releases)
[](https://github.com/gabisonia/go-vectorstore/blob/master/go.mod)
[](LICENSE)
A lightweight Go vector-store library inspired by `Microsoft.Extensions.VectorData`.
MVP scope:
- Go 1.24.x
- Postgres + `pgvector`
- MSSQL connector
- Record-based core API with optional typed codec wrapper
This library can be used to build retrieval systems such as:
- semantic search
- RAG pipelines (retrieve from vector DB, then generate with an LLM)
- context-aware assistants grounded on your own data
## Requirements
- Go 1.24.x
- PostgreSQL 16+ with `pgvector` extension
- SQL Server 2022+ (for `stores/mssql`)
- Docker (optional, for integration tests and sample compose flows)
## Project layout
- `vectordata`: backend-agnostic core interfaces, record model, filters, typed wrapper
- `stores/postgres`: Postgres implementation with `pgxpool`
- `stores/mssql`: SQL Server implementation with `database/sql`
- `samples`: runnable demos (see `samples/README.md`)
- `docs`: architecture and implementation notes
## Install
```bash
go get github.com/gabisonia/go-vectorstore
```
## Quick Start (Local)
1. Start local Postgres + `pgvector` from the repository root:
```bash
docker compose up -d postgres
```
2. Export your OpenAI key and run the semantic sample:
```bash
export OPENAI_API_KEY=your_key_here
go get github.com/gabisonia/go-vectorstore/vectordata@latest
go run ./samples/semantic-search -q "how can I reduce cloud costs?"
```
3. Stop local services when done:
```bash
docker compose down
```
## Core API Walkthrough
```go
package main
import (
"context"
"fmt"
"github.com/gabisonia/go-vectorstore/stores/postgres"
"github.com/gabisonia/go-vectorstore/vectordata"
"github.com/jackc/pgx/v5/pgxpool"
)
func main() {
ctx := context.Background()
pool, err := pgxpool.New(ctx, "postgres://postgres:postgres@localhost:54329/vectorstore_test?sslmode=disable")
if err != nil {
panic(err)
}
defer pool.Close()
store, err := postgres.NewVectorStore(pool, postgres.DefaultStoreOptions())
if err != nil {
panic(err)
}
collection, err := store.EnsureCollection(ctx, vectordata.CollectionSpec{
Name: "docs",
Dimension: 3,
Metric: vectordata.DistanceCosine,
Mode: vectordata.EnsureStrict,
})
if err != nil {
panic(err)
}
records := []vectordata.Record{
{
ID: "doc-1",
Vector: []float32{0.1, 0.2, 0.3},
Metadata: map[string]any{"category": "news", "rank": 10},
},
{
ID: "doc-2",
Vector: []float32{0.2, 0.1, 0.2},
Metadata: map[string]any{"category": "blog", "rank": 5},
},
}
if err := collection.Upsert(ctx, records); err != nil {
panic(err)
}
if err := collection.EnsureIndexes(ctx, vectordata.IndexOptions{
Vector: &vectordata.VectorIndexOptions{
Method: vectordata.IndexMethodHNSW,
Metric: vectordata.DistanceCosine,
HNSW: vectordata.HNSWOptions{
M: 16,
EfConstruction: 64,
},
},
Metadata: &vectordata.MetadataIndexOptions{UsePathOps: true},
}); err != nil {
panic(err)
}
filter := vectordata.And(
vectordata.Eq(vectordata.Metadata("category"), "news"),
vectordata.Gt(vectordata.Metadata("rank"), 6),
)
results, err := collection.SearchByVector(
ctx,
[]float32{0.1, 0.2, 0.25},
5,
vectordata.SearchOptions{Filter: filter},
)
if err != nil {
panic(err)
}
for _, r := range results {
fmt.Printf("id=%s score=%.4f distance=%.4f\n", r.Record.ID, r.Score, r.Distance)
}
}
```
## Search Options
`SearchByVector` supports filtering, thresholding, and projection control.
```go
threshold := 0.35
projection := &vectordata.Projection{
IncludeMetadata: true,
IncludeContent: true,
IncludeVector: false,
}
results, err := collection.SearchByVector(ctx, queryVector, 10, vectordata.SearchOptions{
Filter: vectordata.Eq(vectordata.Metadata("category"), "backend"),
Threshold: &threshold,
Projection: projection,
})
```
If `Projection` is `nil`, the default projection includes `Metadata` and `Content`, but not `Vector`.
## Store Options
```go
store, err := postgres.NewVectorStore(pool, postgres.StoreOptions{
Schema: "public",
EnsureExtension: true,
StrictByDefault: true,
})
```
- `Schema`: SQL schema for collection tables
- `EnsureExtension`: auto-runs `CREATE EXTENSION IF NOT EXISTS vector`
- `StrictByDefault`: default ensure mode when `CollectionSpec.Mode` is not set
## Integration tests
```bash
go test -tags=integration ./...
```
Unit tests run with:
```bash
go test ./...
```
Notes:
- Integration tests start Postgres/pgvector and SQL Server automatically via Testcontainers
- Docker daemon must be available when running integration tests
- Optional override: set `PGVECTOR_TEST_DSN` to use an existing Postgres instance instead of starting a container
- Optional override: set `MSSQL_TEST_DSN` to use an existing SQL Server instance instead of starting a container
Run MSSQL integration tests against root compose service:
```bash
docker compose up -d mssql
MSSQL_TEST_DSN="sqlserver://sa:YourStrong%21Passw0rd@localhost:14339?database=master&encrypt=disable" \
go test -tags=integration ./stores/mssql
```
## Docker Compose (optional)
`docker-compose.yml` at the repository root is kept for manual local runs.
- Use root `docker-compose.yml` when you want a persistent local Postgres+pgvector instance outside tests
- Root compose also includes SQL Server (`mssql`) for local MSSQL connector validation
- Use Testcontainers (`go test -tags=integration ./...`) for integration tests
- Sample apps have their own compose files at `samples/semantic-search/docker-compose.yml` and `samples/ragrimosa/docker-compose.yml`
- Sample Dockerfiles use `golang:1.24-alpine` to match the repo Go version (`1.24.x`)
## Release Automation
GitHub Actions workflows are configured for:
- CI on pushes/PRs (`.github/workflows/ci.yml`)
- release publishing (`.github/workflows/release.yml`)
Release options:
1. Manual (recommended): run `Release` workflow via GitHub UI with `version` input (`0.2.2` or `v0.2.2`).
2. Tag-driven: push a semver tag and the workflow publishes release notes automatically:
```bash
git tag v0.2.2
git push origin v0.2.2
```
## Samples
- Overview and entry points: [`samples/README.md`](samples/README.md)
- Semantic search sample app: `samples/semantic-search`
- RAG sample app (`RAGrimosa`): `samples/ragrimosa`
## Documentation
- Docs index: [`docs/README.md`](docs/README.md)
- Internals and architecture: [`docs/architecture.md`](docs/architecture.md)
## License
This project is licensed under the MIT License.