Skip to content

Commit

Permalink
multi traverse test
Browse files Browse the repository at this point in the history
  • Loading branch information
friendlymatthew committed Feb 15, 2024
1 parent 65ce3c3 commit 59e2a25
Show file tree
Hide file tree
Showing 6 changed files with 258 additions and 187 deletions.
13 changes: 9 additions & 4 deletions src/btree/bptree.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,16 +18,21 @@ type RootResponse = {
export class BPTree {
private readonly tree: RangeResolver;
private meta: MetaPage;
private readonly data: Uint8Array; // RangeResolver for the data-file
private readonly dataFileResolver: RangeResolver;

constructor(tree: RangeResolver, meta: MetaPage, data: Uint8Array) {
constructor(
tree: RangeResolver,
meta: MetaPage,
dataFileResolver: RangeResolver
) {
this.tree = tree;
this.meta = meta;
this.data = data;
this.dataFileResolver = dataFileResolver;
}

private async root(): Promise<RootResponse | null> {
const mp = await this.meta.root();

if (!mp || mp.length === 0) {
return null;
}
Expand All @@ -48,7 +53,7 @@ export class BPTree {
const { node, bytesRead } = await BPTreeNode.fromMemoryPointer(
ptr,
this.tree,
this.data
this.dataFileResolver
);

if (!bytesRead || bytesRead !== ptr.length) {
Expand Down
180 changes: 91 additions & 89 deletions src/btree/multi.ts
Original file line number Diff line number Diff line change
@@ -1,99 +1,101 @@
import { RangeResolver } from "../resolver";
import { MemoryPointer } from "./node";
import {PageFile} from "./pagefile";
import { PageFile } from "./pagefile";

const PAGE_SIZE_BYTES = 4096;

export class LinkedMetaPage {
private resolver: RangeResolver;
private offset: bigint;
private metaPageData: ArrayBuffer | null;

constructor(resolver: RangeResolver, offset: bigint) {
this.resolver = resolver;
this.offset = offset;
this.metaPageData = null;
}

async root(): Promise<MemoryPointer | null> {
const pageData = await this.getMetaPage();

// we seek by 12 bytes since offset is 8 bytes, length is 4 bytes
const data = pageData.slice(Number(this.offset), Number(this.offset) + 11);
const view = new DataView(data);

const pointerOffset = view.getBigUint64(0);
const lengthOffset = view.getUint32(8);

return {
offset: pointerOffset,
length: lengthOffset,
};
}

/**
* `metadata()` gets the page data. It does the following:
* (1) creates a slice from 24 to the end of the page
* (2) it reads the first four bytes of that slice which gives us the length to seek to
* (3) slices from [24, (24 + dataLength)] which contain metadata
*/
async metadata(): Promise<ArrayBuffer> {
console.log("metadata entered");
const pageData = await this.getMetaPage();
console.log("page data: ", pageData)
const lengthData = pageData.slice(
24,
PAGE_SIZE_BYTES
);

const lengthView = new DataView(lengthData);

// read the first four because that represents length
const metadataLength = lengthView.getUint32(0);

console.log("metadatalength: ", metadataLength);
return pageData.slice(
28,
28 + metadataLength
);
}

private async getMetaPage(): Promise<ArrayBuffer> {
if (this.metaPageData) {
return this.metaPageData;
}

const { data } = await this.resolver({
start: Number(this.offset),
end: Number(this.offset) + PAGE_SIZE_BYTES - 1,
});


this.metaPageData= data;

return data;
}

async next(): Promise<LinkedMetaPage | null> {
const pageData = await this.getMetaPage();
const data = pageData.slice(Number(this.offset) + 12, Number(this.offset) + 12 + 7);

const view = new DataView(data);

const nextOffset = view.getBigUint64(0);

const maxUint64 = BigInt(2) ** BigInt(64) - BigInt(1);
if (nextOffset === maxUint64) {
return null;
}

return new LinkedMetaPage(this.resolver, nextOffset);
}
private resolver: RangeResolver;
private offset: bigint;
private metaPageData: ArrayBuffer | null;

constructor(resolver: RangeResolver, offset: bigint) {
this.resolver = resolver;
this.offset = offset;
this.metaPageData = null;
}

async root(): Promise<MemoryPointer | null> {
const pageData = await this.getMetaPage();

// we seek by 12 bytes since offset is 8 bytes, length is 4 bytes
const data = pageData.slice(0, 12);
const view = new DataView(data);

const pointerOffset = view.getBigUint64(0);
const lengthOffset = view.getUint32(8);

return {
offset: pointerOffset,
length: lengthOffset,
};
}

/**
* `metadata()` gets the page data. It does the following:
* (1) creates a slice from 24 to the end of the page
* (2) it reads the first four bytes of that slice which gives us the length to seek to
* (3) slices from [24, (24 + dataLength)] which contain metadata
*/
async metadata(): Promise<ArrayBuffer> {
const pageData = await this.getMetaPage();
const lengthData = pageData.slice(24, PAGE_SIZE_BYTES);

const lengthView = new DataView(lengthData);

// read the first four because that represents length
const metadataLength = lengthView.getUint32(0);

return pageData.slice(28, 28 + metadataLength);
}

/**
* `getMetaPage()` seeks the index-file with the absolute bounds for a given page file.
* It caches the data in a pagefile. Note: all other methods that call this should be slicing with relative bounds.
*/
private async getMetaPage(): Promise<ArrayBuffer> {
if (this.metaPageData) {
return this.metaPageData;
}

const { data } = await this.resolver({
start: Number(this.offset),
end: Number(this.offset) + PAGE_SIZE_BYTES - 1,
});

this.metaPageData = data;

return data;
}

/**
* `next()` - returns a new LinkedMetaPage
*/
async next(): Promise<LinkedMetaPage | null> {
const pageData = await this.getMetaPage();
const data = pageData.slice(12, 12 + 8);

const view = new DataView(data);
const nextOffset = view.getBigUint64(0);
const maxUint64 = BigInt(2) ** BigInt(64) - BigInt(1);
console.log("next offset: ", nextOffset);
if (nextOffset === maxUint64) {
return null;
}

return new LinkedMetaPage(this.resolver, nextOffset);
}

getOffset(): bigint {
return this.offset;
}
}

export function ReadMultiBPTree(
resolver: RangeResolver,
pageFile: PageFile,
): LinkedMetaPage {
const offset = pageFile.page(0);

export function ReadMultiBPTree(resolver: RangeResolver, pageFile: PageFile): LinkedMetaPage {
const offset = pageFile.page(0);

return new LinkedMetaPage(resolver, offset);
return new LinkedMetaPage(resolver, offset);
}
21 changes: 11 additions & 10 deletions src/btree/node.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,18 +6,18 @@ export class BPTreeNode {
public keys: ReferencedValue[];
public leafPointers: MemoryPointer[];
public internalPointers: bigint[];
private data: Uint8Array;
private dataFileResolver: RangeResolver;

constructor(
keys: ReferencedValue[],
leafPointers: MemoryPointer[],
internalPointers: bigint[],
data: Uint8Array
dataFileResolver: RangeResolver
) {
this.keys = keys;
this.leafPointers = leafPointers;
this.internalPointers = internalPointers;
this.data = data;
this.dataFileResolver = dataFileResolver;
}

leaf(): boolean {
Expand Down Expand Up @@ -92,11 +92,12 @@ export class BPTreeNode {
this.keys[idx].dataPointer.length = dataView.getUint32(0);

const dp = this.keys[idx].dataPointer;
const dataSlice = this.data.slice(
Number(dp.offset),
Number(dp.offset + BigInt(dp.length)) - 1
);
this.keys[idx].value = new Uint8Array(dataSlice);
const { data } = await this.dataFileResolver({
start: Number(dp.offset),
end: Number(dp.offset + BigInt(dp.length)) - 1
});

this.keys[idx].value = data

m += 4 + 12;
} else {
Expand Down Expand Up @@ -129,13 +130,13 @@ export class BPTreeNode {
static async fromMemoryPointer(
mp: MemoryPointer,
resolver: RangeResolver,
data: Uint8Array
dataFilePointer : RangeResolver
): Promise<{ node: BPTreeNode; bytesRead: number }> {
const { data: bufferData } = await resolver({
start: Number(mp.offset),
end: Number(mp.offset) + 4096 - 1,
});
const node = new BPTreeNode([], [], [], data);
const node = new BPTreeNode([], [], [], dataFilePointer);
const bytesRead = await node.unmarshalBinary(bufferData);

return { node, bytesRead };
Expand Down
1 change: 0 additions & 1 deletion src/tests/bptree.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import { BPTree, MetaPage } from "../btree/bptree";
import { LinkedMetaPage } from "../btree/multi";
import { MemoryPointer } from "../btree/node";
import { RangeResolver } from "../resolver";

Expand Down
Loading

0 comments on commit 59e2a25

Please sign in to comment.