func TestSimpleJSONDB_InitializesDataFile(t *testing.T) { firstDataBlock := make([]byte, 10) blocksBitMapBlock := make([]byte, dbio.DATABLOCK_SIZE) bTreeRootBlock := make([]byte, 2) fakeDataFile := utils.NewFakeDataFileWithBlocks([][]byte{ firstDataBlock, blocksBitMapBlock, nil, nil, bTreeRootBlock, }) jsondb.NewWithDataFile(fakeDataFile) if !utils.SlicesEqual(firstDataBlock[0:2], []byte{0x00, 0x03}) { t.Error("Did not set the next available data block pointer to 3") } if !utils.SlicesEqual(firstDataBlock[2:4], []byte{0x00, 0x03}) { t.Error("Did not set the first record block pointer to 3") } blocksBitMap := dbio.NewBitMapFromBytes(blocksBitMapBlock) for i := 0; i < 4; i++ { val, err := blocksBitMap.Get(i) if err != nil { t.Fatal(err) } if !val { t.Errorf("Expected block %d to be flagged as used", i) } } }
func TestSet(t *testing.T) { b := dbio.NewBitMap(16) b.Set(2) b.Set(15) if !utils.SlicesEqual(b.Bytes(), []byte{0x02, 0x40}) { t.Errorf("bytes do not match '%X'", b.Bytes()) } }
func TestFetchesBlockFromDataFile(t *testing.T) { fakeDataBlock := []byte{0x10, 0xF0} fakeDataFile := utils.NewFakeDataFileWithBlocks([][]byte{nil, fakeDataBlock}) dataBlock, err := dbio.NewDataBuffer(fakeDataFile, 1).FetchBlock(1) if err != nil { t.Fatal("Unexpected error", err) } if dataBlock.ID != 1 { t.Errorf("ID doesn't match (expected %d got %d)", 1, dataBlock.ID) } if !utils.SlicesEqual(dataBlock.Data[0:2], fakeDataBlock) { t.Errorf("Data blocks do not match (expected %x got %x)", fakeDataBlock, dataBlock.Data[0:2]) } }
func TestControlBlock_IndexRootBlockID(t *testing.T) { block := &dbio.DataBlock{Data: []byte{0, 0, 0, 0, 0, 0x09}} cb := &controlBlock{block} if blockID := cb.IndexRootBlockID(); blockID != 9 { t.Errorf("Root BTree datablock pointer was not read, got %d and expected %d", blockID, 9) } cb.SetIndexRootBlockID(901) if id := cb.IndexRootBlockID(); id != 901 { t.Errorf("Next id was not read, got %d and expected %d", id, 901) } if !utils.SlicesEqual(block.Data, []byte{0, 0, 0, 0, 0x03, 0x85}) { fmt.Printf("% x\n", block.Data) t.Errorf("Invalid data written to block (% x)", block.Data) } }
func TestControlBlock_NextAvailableRecordsDataBlock(t *testing.T) { block := &dbio.DataBlock{Data: []byte{0x10, 0x01}} cb := &controlBlock{block} if id := cb.NextAvailableRecordsDataBlockID(); id != 4097 { t.Errorf("Next id was not read, got %d and expected %d", id, 16) } cb.SetNextAvailableRecordsDataBlockID(900) if id := cb.NextAvailableRecordsDataBlockID(); id != 900 { t.Errorf("Next id was not read, got %d and expected %d", id, 900) } if !utils.SlicesEqual(block.Data, []byte{0x03, 0x84}) { fmt.Printf("% x\n", block.Data) t.Errorf("Invalid data written to block (% x)", block.Data) } }
func TestSavesDirtyFramesWhenEvicting(t *testing.T) { fakeDataBlock := []byte{0x00, 0x01, 0x02} fakeDataFile := utils.NewFakeDataFileWithBlocks([][]byte{ fakeDataBlock, []byte{}, []byte{}, []byte{}, }) blockThatWasWritten := uint16(999) bytesWritten := []byte{} fakeDataFile.WriteBlockFunc = func(id uint16, data []byte) error { blockThatWasWritten = id bytesWritten = data return nil } buffer := dbio.NewDataBuffer(fakeDataFile, 2) // Read the first 2 blocks and flag the first one as dirty buffer.FetchBlock(0) buffer.FetchBlock(1) buffer.MarkAsDirty(0) // Evict the frame 1 by loading a third frame buffer.FetchBlock(2) // Evict the frame 0 by loading a fourth frame buffer.FetchBlock(3) if blockThatWasWritten == 999 { t.Fatalf("Block was not saved to disk (%d)", blockThatWasWritten) } if blockThatWasWritten != 0 { t.Errorf("Unknown block saved to disk (%d)", blockThatWasWritten) } if !utils.SlicesEqual(bytesWritten[0:3], fakeDataBlock) { t.Errorf("Invalid data saved to disk %x", bytesWritten[0:3]) } }