This commit is contained in:
Fabian Stamm
2023-07-03 18:06:48 +02:00
parent 1a7400e38c
commit 4943d8790d
5 changed files with 536 additions and 126 deletions

View File

@ -6,7 +6,7 @@ import { ServiceProvider as ServiceProviderClient } from "./com/service_client";
import { ServiceProvider as ServiceProviderServer } from "./com/service_server";
import { PullObjectRequest, PullObjectResponse, PushObjectRequest, PushObjectResponse, Sync as SyncClient, SyncInitRequest, SyncInitResponse } from "./com/sync_client";
import { Sync as SyncServer } from "./com/sync_server";
import Repository, { ObjectTypes } from "./repo";
import Repository, { Commit, ObjectTypes, TreeEntry } from "./repo";
if (typeof btoa === 'undefined') {
global.btoa = function (str) {
@ -189,10 +189,53 @@ export async function startSyncClient(stream: ISimpleStream, repo: Repository) {
let localHead = await repo.readHead()
if (localHead) { // If there is nothing to push, don't push
// Find matching point
let match = undefined;
let toCheck: Commit[] = [localHead];
if (!syncResponse.remoteCommit) { }
let commit: Commit;
while(toCheck.length > 0) {
commit = toCheck.shift() as Commit;
if(commit.id != syncResponse.remoteCommit) { //Not yet at remote commit. Wait
commitsToPush.add(commit.id);
if(commit.before && !commitsToPush.has(commit.before)) // A commit could already be checked by the other part of a merge
toCheck.push(await repo.readCommit(commit.before));
if(commit.merge && !commitsToPush.has(commit.merge))
toCheck.push(await repo.readCommit(commit.merge));
}
}
const traverseTree =async (current: TreeEntry[]) => {
for(const [type, hash, name] of current) {
objectsToPush.add(hash);
if(type =="tree") {
let tree = await repo.readTree(hash);
await traverseTree(tree);
}
}
}
for(const commitId of commitsToPush) {
let commit = await repo.readCommit(commitId);
let rootId = commit.root
objectsToPush.add(rootId);
if(objectsToPush.has(rootId)) {
objectsToPush.add(rootId);
let root = await repo.readTree(rootId);
await traverseTree(root);
}
}
}
for(const objId of objectsToPush) {
let obj = await repo.readObjectTyped(objId)
await service.PushObject({
id: objId,
data: obj?.data as Uint8Array,
type: obj?.type as string
});
}
}