jldb/mdb/pfile/index_test.go
2023-10-13 11:43:27 +02:00

140 lines
2.5 KiB
Go

package pfile
import (
"testing"
)
type IndexState struct {
FreeList []uint64
AllocList map[[2]uint64][]uint64
}
func (idx *Index) Assert(t *testing.T, state IndexState) {
t.Helper()
idx.fList.Assert(t, state.FreeList...)
idx.aList.Assert(t, state.AllocList)
}
func TestIndex(t *testing.T) {
pf, idx := newForTesting(t)
defer pf.Close()
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{},
})
p0 := uint64(0)
l := (&changeListBuilder{}).
Store(1, 1, pageDataSize+1).
Build()
idx.StageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{},
})
// Unstage a change: free-list gets pages back.
idx.UnstageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{p0, p0 + 1},
AllocList: map[[2]uint64][]uint64{},
})
// Stage a change: free-list entries are used again.
l = (*changeListBuilder)(&l).
Clear().
Store(1, 1, pageDataSize+1).
Store(2, 2, pageDataSize-1).
Store(3, 3, pageDataSize).
Build()
idx.StageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{},
})
// Apply changes: alloc-list is updated.
idx.ApplyChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{
{1, 1}: {p0, p0 + 1},
{2, 2}: {p0 + 2},
{3, 3}: {p0 + 3},
},
})
// Clear some things.
l = (*changeListBuilder)(&l).
Clear().
Store(1, 1, pageDataSize).
Delete(2, 2).
Build()
idx.StageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{
{3, 3}: {p0 + 3},
},
})
// Ustaging will push the staged page p0+4 into the free list.
idx.UnstageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{p0 + 4},
AllocList: map[[2]uint64][]uint64{
{1, 1}: {p0, p0 + 1},
{2, 2}: {p0 + 2},
{3, 3}: {p0 + 3},
},
})
idx.StageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{},
AllocList: map[[2]uint64][]uint64{
{3, 3}: {p0 + 3},
},
})
idx.ApplyChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{p0, p0 + 1, p0 + 2},
AllocList: map[[2]uint64][]uint64{
{1, 1}: {p0 + 4},
{3, 3}: {p0 + 3},
},
})
// Duplicate updates.
l = (*changeListBuilder)(&l).
Clear().
Store(2, 2, pageDataSize).
Store(3, 3, pageDataSize+1).
Store(3, 3, pageDataSize).
Build()
idx.StageChanges(l)
idx.Assert(t, IndexState{
FreeList: []uint64{p0 + 2},
AllocList: map[[2]uint64][]uint64{
{1, 1}: {p0 + 4},
},
})
}