Add Phase 1 foundation: Go module, core types, DB infrastructure, config
Establish the project foundation with three packages: - core: shared types (Header, Metadata, Value, ObjectType, UUID generation) - db: SQLite migration framework, connection management (WAL, FK, busy timeout), transaction helpers (StartTX/EndTX), time conversion - config: runtime configuration (DB path, blob store, Minio, gRPC addr) Includes initial schema migration (001_initial.sql) with 13 tables covering shared infrastructure, bibliographic data, and artifact repository. Full test coverage for all packages, strict linting (.golangci.yaml), and Makefile. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
106
core/core_test.go
Normal file
106
core/core_test.go
Normal file
@@ -0,0 +1,106 @@
|
||||
package core
|
||||
|
||||
import (
|
||||
"sort"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func TestNewUUID(t *testing.T) {
|
||||
id1 := NewUUID()
|
||||
id2 := NewUUID()
|
||||
if id1 == "" {
|
||||
t.Fatal("NewUUID returned empty string")
|
||||
}
|
||||
if id1 == id2 {
|
||||
t.Fatal("NewUUID returned duplicate UUIDs")
|
||||
}
|
||||
}
|
||||
|
||||
func TestVal(t *testing.T) {
|
||||
v := Val("hello")
|
||||
if v.Contents != "hello" {
|
||||
t.Fatalf("expected contents 'hello', got %q", v.Contents)
|
||||
}
|
||||
if v.Type != ValueTypeUnspecified {
|
||||
t.Fatalf("expected type %q, got %q", ValueTypeUnspecified, v.Type)
|
||||
}
|
||||
}
|
||||
|
||||
func TestVals(t *testing.T) {
|
||||
v := Vals("world")
|
||||
if v.Contents != "world" {
|
||||
t.Fatalf("expected contents 'world', got %q", v.Contents)
|
||||
}
|
||||
if v.Type != ValueTypeString {
|
||||
t.Fatalf("expected type %q, got %q", ValueTypeString, v.Type)
|
||||
}
|
||||
}
|
||||
|
||||
func TestNewHeader(t *testing.T) {
|
||||
before := time.Now().UTC().Unix()
|
||||
h := NewHeader(ObjectTypeArtifact)
|
||||
after := time.Now().UTC().Unix()
|
||||
|
||||
if h.ID == "" {
|
||||
t.Fatal("header ID is empty")
|
||||
}
|
||||
if h.Type != ObjectTypeArtifact {
|
||||
t.Fatalf("expected type %q, got %q", ObjectTypeArtifact, h.Type)
|
||||
}
|
||||
if h.Created < before || h.Created > after {
|
||||
t.Fatalf("Created timestamp %d not in range [%d, %d]", h.Created, before, after)
|
||||
}
|
||||
if h.Modified != h.Created {
|
||||
t.Fatalf("Modified (%d) should equal Created (%d)", h.Modified, h.Created)
|
||||
}
|
||||
if h.Meta == nil {
|
||||
t.Fatal("Meta should not be nil")
|
||||
}
|
||||
}
|
||||
|
||||
func TestHeaderTouch(t *testing.T) {
|
||||
h := NewHeader(ObjectTypeNode)
|
||||
original := h.Modified
|
||||
// Ensure at least 1 second passes for timestamp change.
|
||||
time.Sleep(10 * time.Millisecond)
|
||||
h.Touch()
|
||||
if h.Modified < original {
|
||||
t.Fatalf("Touch should not decrease Modified: was %d, now %d", original, h.Modified)
|
||||
}
|
||||
}
|
||||
|
||||
func TestMapFromList(t *testing.T) {
|
||||
list := []string{"alpha", "beta", "gamma"}
|
||||
m := MapFromList(list)
|
||||
if len(m) != 3 {
|
||||
t.Fatalf("expected 3 entries, got %d", len(m))
|
||||
}
|
||||
for _, s := range list {
|
||||
if !m[s] {
|
||||
t.Fatalf("expected %q in map", s)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestListFromMap(t *testing.T) {
|
||||
m := map[string]bool{"z": true, "a": true, "m": true}
|
||||
list := ListFromMap(m)
|
||||
if len(list) != 3 {
|
||||
t.Fatalf("expected 3 entries, got %d", len(list))
|
||||
}
|
||||
sort.Strings(list)
|
||||
expected := []string{"a", "m", "z"}
|
||||
for i, v := range list {
|
||||
if v != expected[i] {
|
||||
t.Fatalf("index %d: expected %q, got %q", i, expected[i], v)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestMapFromListEmpty(t *testing.T) {
|
||||
m := MapFromList(nil)
|
||||
if len(m) != 0 {
|
||||
t.Fatalf("expected empty map, got %d entries", len(m))
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user