diff --git a/common/spaces/sync.test.ts b/common/spaces/sync.test.ts index 7385abe..ff44b1c 100644 --- a/common/spaces/sync.test.ts +++ b/common/spaces/sync.test.ts @@ -10,7 +10,7 @@ Deno.test("Test store", async () => { const primary = new DiskSpacePrimitives(primaryPath); const secondary = new DiskSpacePrimitives(secondaryPath); const statusMap = new Map(); - const sync = new SpaceSync(primary, secondary, statusMap); + const sync = new SpaceSync(primary, secondary, statusMap, {}); // Write one page to primary await primary.writeFile("index", "utf8", "Hello"); @@ -129,6 +129,7 @@ Deno.test("Test store", async () => { secondary, ternary, new Map(), + {}, ); console.log( "N ops", @@ -137,9 +138,25 @@ Deno.test("Test store", async () => { await sleep(2); assertEquals(await sync2.syncFiles(SpaceSync.primaryConflictResolver), 0); + // I had to look up what follows ternary (https://english.stackexchange.com/questions/25116/what-follows-next-in-the-sequence-unary-binary-ternary) + const quaternaryPath = await Deno.makeTempDir(); + const quaternary = new DiskSpacePrimitives(quaternaryPath); + const sync3 = new SpaceSync( + secondary, + quaternary, + new Map(), + { + excludePrefixes: ["index"], + }, + ); + const selectingOps = await sync3.syncFiles(SpaceSync.primaryConflictResolver); + + assertEquals(selectingOps, 1); + await Deno.remove(primaryPath, { recursive: true }); await Deno.remove(secondaryPath, { recursive: true }); await Deno.remove(ternaryPath, { recursive: true }); + await Deno.remove(quaternaryPath, { recursive: true }); async function doSync() { await sleep(); diff --git a/common/spaces/sync.ts b/common/spaces/sync.ts index d52c456..2e20f35 100644 --- a/common/spaces/sync.ts +++ b/common/spaces/sync.ts @@ -20,14 +20,25 @@ class ConsoleLogger implements Logger { } } +export type SyncOptions = { + logger?: Logger; + excludePrefixes?: string[]; +}; + // Implementation of this algorithm https://unterwaditzer.net/2016/sync-algorithm.html export class SpaceSync { + logger: ConsoleLogger; + excludePrefixes: string[]; + constructor( private primary: SpacePrimitives, private secondary: SpacePrimitives, readonly snapshot: Map, - readonly logger: Logger = new ConsoleLogger(), - ) {} + readonly options: SyncOptions, + ) { + this.logger = options.logger || new ConsoleLogger(); + this.excludePrefixes = options.excludePrefixes || []; + } async syncFiles( conflictResolver: ( @@ -100,6 +111,13 @@ export class SpaceSync { // console.log("Syncing", name, primaryHash, secondaryHash); let operations = 0; + // Check if not matching one of the excluded prefixes + for (const prefix of this.excludePrefixes) { + if (name.startsWith(prefix)) { + return operations; + } + } + if ( primaryHash !== undefined && secondaryHash === undefined && !this.snapshot.has(name) diff --git a/common/syscalls/sync.ts b/common/syscalls/sync.ts index 0536aee..1c09aef 100644 --- a/common/syscalls/sync.ts +++ b/common/syscalls/sync.ts @@ -3,7 +3,6 @@ import type { SyncEndpoint } from "../../plug-api/silverbullet-syscall/sync.ts"; import { SpaceSync, SyncStatusItem } from "../spaces/sync.ts"; import { HttpSpacePrimitives } from "../spaces/http_space_primitives.ts"; import { SpacePrimitives } from "../spaces/space_primitives.ts"; -import { race, timeout } from "../async_util.ts"; export function syncSyscalls( localSpace: SpacePrimitives, @@ -122,8 +121,11 @@ export function syncSyscalls( localSpace, remoteSpace, syncStatusMap, - // Log to the "sync" plug sandbox - system.loadedPlugs.get("sync")!.sandbox!, + { + excludePrefixes: endpoint.excludePrefixes, + // Log to the "sync" plug sandbox + logger: system.loadedPlugs.get("sync")!.sandbox!, + }, ); return { spaceSync, remoteSpace }; } diff --git a/plug-api/silverbullet-syscall/sync.ts b/plug-api/silverbullet-syscall/sync.ts index bcab068..94c7fe7 100644 --- a/plug-api/silverbullet-syscall/sync.ts +++ b/plug-api/silverbullet-syscall/sync.ts @@ -5,6 +5,7 @@ export type SyncEndpoint = { url: string; user?: string; password?: string; + excludePrefixes?: string[]; }; // Perform a sync with the server, based on the given status (to be persisted) diff --git a/plugs/sync/sync.ts b/plugs/sync/sync.ts index 2c161bc..f43c6e3 100644 --- a/plugs/sync/sync.ts +++ b/plugs/sync/sync.ts @@ -1,6 +1,7 @@ import { store } from "$sb/plugos-syscall/mod.ts"; import { editor, space, sync, system } from "$sb/silverbullet-syscall/mod.ts"; import type { SyncEndpoint } from "$sb/silverbullet-syscall/sync.ts"; +import { readSetting } from "$sb/lib/settings_page.ts"; export async function configureCommand() { const url = await editor.prompt( @@ -160,6 +161,8 @@ export async function performSync() { return; } + await augmentSettings(config); + // Check if sync not already in progress const ongoingSync: number | undefined = await store.get("sync.startTime"); if (ongoingSync) { @@ -196,12 +199,22 @@ export async function performSync() { } } +async function augmentSettings(endpoint: SyncEndpoint) { + const syncSettings = await readSetting("sync", {}); + if (syncSettings.excludePrefixes) { + endpoint.excludePrefixes = syncSettings.excludePrefixes; + } +} + export async function syncPage(page: string) { const config: SyncEndpoint = await store.get("sync.config"); if (!config) { // Sync not configured return; } + + await augmentSettings(config); + // Check if sync not already in progress const ongoingSync: number | undefined = await store.get("sync.startTime"); if (ongoingSync) {