Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
c1706ca
feat(holograph): scaffold crate with SpaceConfig + CBOR envelope (Ste…
data-bot-coasys Jun 2, 2026
853e148
refactor(p-diff-sync): drop HDK trait bounds from PerspectiveDiffRetr…
data-bot-coasys Jun 2, 2026
79b1831
feat(perspective-diff-algorithm): extract substrate-agnostic algorith…
data-bot-coasys Jun 2, 2026
753dc0e
feat(holograph): sled-backed KvOpStore implementing kitsune2_api::OpS…
data-bot-coasys Jun 2, 2026
ad7cc23
feat(holograph): KitsuneRetreiver implementing PerspectiveDiffRetreiv…
data-bot-coasys Jun 2, 2026
605587d
test(holograph): p-diff-sync algorithm parity against KitsuneRetreive…
data-bot-coasys Jun 2, 2026
0d05d24
feat(holograph): HolographIntegrationQueue with cascade promotion and…
data-bot-coasys Jun 2, 2026
7eca8ff
feat(holograph): HolographSpace + K2 adapter glue + queue NotifyUp ti…
data-bot-coasys Jun 3, 2026
e8bdf8b
test(holograph): two-node end-to-end across real K2 mem transport (St…
data-bot-coasys Jun 3, 2026
8f71167
test(holograph): switch two-node test to manual peer cross-registration
data-bot-coasys Jun 3, 2026
e64b642
feat(holograph-link): scaffold AD4M LinkLanguage + holograph_wires st…
data-bot-coasys Jun 3, 2026
14cb703
feat(holograph): real HolographRuntime replaces NotImplemented stub (…
data-bot-coasys Jun 3, 2026
60cc974
feat(holograph): holograph_service deno extension + __holographDelega…
data-bot-coasys Jun 3, 2026
21716a2
feat(holograph): HOLOGRAPH_DEFAULT_NEIGHBORHOOD gated default switch …
data-bot-coasys Jun 3, 2026
56c88b8
feat(holograph-link): pass typed PerspectiveDiff across the wire (Ste…
data-bot-coasys Jun 3, 2026
84e1a23
test(holograph): two-node end-to-end via HolographRuntime wires (Step…
data-bot-coasys Jun 3, 2026
6365bcb
feat(holograph): print_holograph_address binary + snapshot ext (Step 7a)
data-bot-coasys Jun 3, 2026
b68e8e2
test(holograph-link): single-conductor JS end-to-end scaffold (Step 7b)
data-bot-coasys Jun 3, 2026
da16b70
fix(holograph): snapshot ext order + content-addressed install path (…
data-bot-coasys Jun 3, 2026
27e0ada
fix(holograph): align __holographDelegate__ method shapes with host.j…
data-bot-coasys Jun 3, 2026
570a3aa
feat(holograph): default-switch resolves to bundle content hash (Step…
data-bot-coasys Jun 3, 2026
8e51c35
feat(holograph): tx5 + CoreBootstrap + K2Gossip cross-process transpo…
data-bot-coasys Jun 3, 2026
3cd5264
test(holograph-link): two-conductor JS scaffold via Tx5/SBD (Step 9b)
data-bot-coasys Jun 3, 2026
7ca76bc
chore(holograph): diagnostic logs in publish_ops_to_peers (Step 10a)
data-bot-coasys Jun 3, 2026
9cf1ec4
fix(holograph): unique-per-process agent + Ed25519 verifier on Tx5 pa…
data-bot-coasys Jun 3, 2026
8cdc2f6
test(holograph-link): 15s deadlines + late-join Charlie (Step 10d)
data-bot-coasys Jun 3, 2026
824cfac
chore: cargo fmt --all
data-bot-coasys Jun 3, 2026
e3c3125
fix(holograph): commit holograph_service_extension.js (CI fix)
data-bot-coasys Jun 3, 2026
5cacd1c
refactor(holograph): swap transport_tx5 → transport_iroh on Tx5 path …
data-bot-coasys Jun 3, 2026
5e8ae2f
test(holograph-link): adapt multi-conductor test to iroh transport (S…
data-bot-coasys Jun 3, 2026
59eda07
test(holograph-link): 15s settle before first cross-process commit (S…
data-bot-coasys Jun 3, 2026
7d3f2cc
fix(ci): build holograph-link bundle on test via pretest hook
data-bot-coasys Jun 3, 2026
2fff2c1
refactor(p-diff-sync): extract ChunkedDiffs to algorithm crate (Step …
data-bot-coasys Jun 3, 2026
b226f85
feat(perspective-diff-algorithm): add Workspace + mirror types + retr…
data-bot-coasys Jun 3, 2026
8a7dc4f
refactor(p-diff-sync): consolidate Workspace into algorithm crate (St…
data-bot-coasys Jun 3, 2026
ca1c8bb
Merge branch 'dev' into feat/holograph-substrate
lucksus Jun 3, 2026
cc137fe
refactor(perspective-diff-algorithm): promote chunked-load to load_di…
data-bot-coasys Jun 3, 2026
c94f60b
Merge remote-tracking branch 'origin/feat/holograph-substrate' into f…
data-bot-coasys Jun 3, 2026
0d274f4
feat(perspective-diff-algorithm): substrate-agnostic snapshots module…
data-bot-coasys Jun 3, 2026
e39a34b
refactor(p-diff-sync): consolidate snapshots into algorithm crate (St…
data-bot-coasys Jun 3, 2026
cd3b174
refactor(p-diff-sync): extract revisions module to algorithm crate (S…
data-bot-coasys Jun 3, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
395 changes: 327 additions & 68 deletions Cargo.lock

Large diffs are not rendered by default.

2 changes: 2 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@
resolver = "2"
members = [
"cli",
"crates/perspective-diff-algorithm",
"rust-client",
"rust-executor",
"rust-executor/crates/holograph",
"ui/src-tauri"
]

Expand Down
46 changes: 46 additions & 0 deletions ad4m-ldk/js/src/host.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,4 +59,50 @@ declare module "ad4m:host" {
// language scope (e.g. test fixtures storing language bundles).
export function readStorageFile(path: string): string;
export function writeStorageFile(path: string, content: string): void;

// Holograph (Spec section 7.8 -- OPTIONAL EXTENSION, new in v1 of the
// holograph-link Language). Surface lives behind the
// __holographDelegate__ runtime global, populated by
// rust-executor's holograph_wires module (Step 5 stub /
// Step 6 real). Every call throws "[ad4m:host] holograph wire ..."
// if the runtime hasn't installed the delegate. See the holograph
// spike's SPIKE.md §2.2 Step 5 for the contract.
//
// WireDiff shape — what Languages hand to holographCommit and
// receive on emitted ops. The Rust substrate owns CBOR envelope
// wrap+unwrap (Step 6e), so JS deals with typed diff data on
// both ends.
export interface WireDiff {
additions: any[];
removals: any[];
}
// EmittedOp shape returned by holographNextEmitted.
export interface EmittedOpWire {
op_id_b64: string;
created_at_ms: number;
diff: WireDiff;
}
/** Open or create a neighborhood-scoped substrate, returning a
* numeric handle threaded through every other holograph call. */
export function holographCreateNeighborhood(spaceId: string, storageDir: string): Promise<number>;
/** Commit a locally-authored diff. The Rust side wraps it in an
* OpEnvelope (CBOR + timestamp + signature) before storing.
* Returns the op-id base64. */
export function holographCommit(handle: number, diff: WireDiff): Promise<string>;
/** Drive the algorithm-crate render entry point. Returns a JSON-
* shaped Perspective `{ links: [...] }`. */
export function holographRender(handle: number): Promise<{ links: any[] }>;
/** Pop the next-available EmittedOp for the handle. Awaits the
* underlying Rust-side mpsc receiver, so no JS-side polling is
* needed. Returns null only on channel close. */
export function holographNextEmitted(handle: number): Promise<EmittedOpWire | null>;
/** Register a local agent for the neighborhood (= `local_agent_join`
* on the K2 space). Returns the K2 URL this node is reachable at. */
export function holographJoinAgent(handle: number, agentKeyB64: string): Promise<string>;
/** Read the current revision pointer (op-id base64) or null. */
export function holographCurrentRevision(handle: number): Promise<string | null>;
/** Read the latest revision pointer (op-id base64) or null. */
export function holographLatestRevision(handle: number): Promise<string | null>;
/** Tear down the neighborhood. Idempotent. */
export function holographCloseNeighborhood(handle: number): Promise<void>;
}
17 changes: 17 additions & 0 deletions ad4m-ldk/js/src/imports.ts
Original file line number Diff line number Diff line change
Expand Up @@ -61,4 +61,21 @@ export {
// above unless you specifically need filesystem-like semantics.
readStorageFile,
writeStorageFile,

// Holograph (Spec section 7.8 -- OPTIONAL EXTENSION). v1 surface for
// the holograph-link Language module; backed by HolographSpace
// (sled + Kitsune2) once the runtime installs the delegate. See
// host.d.ts for full method docs.
holographCreateNeighborhood,
holographCommit,
holographRender,
holographNextEmitted,
holographJoinAgent,
holographCurrentRevision,
holographLatestRevision,
holographCloseNeighborhood,
} from "ad4m:host";

// Re-export the EmittedOp + WireDiff types so Language modules can
// name them without importing from "ad4m:host" twice.
export type { EmittedOpWire, WireDiff } from "ad4m:host";
3 changes: 3 additions & 0 deletions bootstrap-languages/holograph-link/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
build/
node_modules/
*.log
60 changes: 60 additions & 0 deletions bootstrap-languages/holograph-link/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
# holograph-link

AD4M `LinkLanguage` backed by the holograph substrate
(sled `KvOpStore` + Kitsune2 transport + the substrate-agnostic
`perspective-diff-algorithm`).

This Language is the JS-facing shape of the holograph v1 spike (see
`.spike-docs/SPIKE.md` for the design). It implements the AD4M
LinkLanguage capability surface (`commit`, `sync`, `peers`,
`telepresence`) by delegating to host functions registered in
`ad4m:host` (`holographCreateNeighborhood`, `holographCommit`,
`holographRender`, `holographNextEmitted`, …). Those host functions
land in `rust-executor/src/js_core/host.js` and are backed by the
`HolographDelegate` trait in `rust-executor/src/holograph_wires.rs`.

## Step 5 status

- **JS module**: complete (`index.ts`), bundles via
`pnpm run build` → `build/bundle.js`.
- **Host import surface**: exposed (the `holograph*` exports in
`ad4m:host`); type-correct against `ad4m-ldk`.
- **Runtime delegate**: stubbed. Every call throws
`[ad4m:host] holograph wire not yet implemented (Step 5 stub)`
until Step 6 wires the real `HolographSpace` instance into the
v8 isolate.

The Language address scheme uses the canonical content-address `hash()`
host function over `"@coasys/holograph-link@<version>"`. The version
string is part of `package.json`; bumping it produces a new address.

## Building

```sh
pnpm install # at workspace root
cd bootstrap-languages/holograph-link
pnpm run build
```

Output: `build/bundle.js`. The bundle is consumed by the AD4M executor
(or `test-runner`) as a standard ES module.

## Testing

Two layers (Step 5d):

1. `pnpm run test` — Deno smoke test, asserts the exported method
surface matches the AD4M LinkLanguage contract.
2. `pnpm run integration-test` — Step 7 territory; not exercised in
Step 5.

## Architectural notes

Zero polling. Zero `setInterval`. Zero peer-revision walks.

The Step-3 `HolographIntegrationQueue` owns the watcher loop that
re-issues stalled fetches; K2 gossip + publish_ops own the propagation;
the JS subscriber drains `holographNextEmitted` (which awaits the
underlying mpsc receiver inside Rust — no JS-side delay timer).
`peers.remote()` is read from `DynPeerStore` synchronously at call
time.
47 changes: 47 additions & 0 deletions bootstrap-languages/holograph-link/esbuild.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
/**
* Bundle the holograph-link Language module to build/bundle.js.
*
* Mirrors `p-diff-sync/esbuild.ts`'s plugin layout:
* - alias `@coasys/ad4m-ldk` to the workspace's compiled lib so deno
* doesn't try to resolve through `node_modules`,
* - mark `ad4m:host` as external (resolved at runtime by the executor's
* StringModuleLoader against `rust-executor/src/js_core/host.js`).
*/

import * as esbuild from "https://deno.land/x/esbuild@v0.17.18/mod.js";
import { denoPlugins } from "https://deno.land/x/esbuild_deno_loader@0.7.0/mod.ts";

const ad4mLdkEntry = new URL(
"../../ad4m-ldk/js/lib/index.js",
import.meta.url,
).pathname;

const ad4mLdkAliasPlugin = {
name: "ad4m-ldk-alias",
setup(build: any) {
build.onResolve({ filter: /^ad4m:host$/ }, () => ({
path: "ad4m:host",
external: true,
}));
build.onResolve({ filter: /^@coasys\/ad4m-ldk$/ }, () => ({
path: ad4mLdkEntry,
namespace: "file",
}));
},
};

const result = await esbuild.build({
plugins: [ad4mLdkAliasPlugin, ...denoPlugins()],
entryPoints: ["index.ts"],
outfile: "build/bundle.js",
bundle: true,
platform: "node",
target: "deno1.32.4",
format: "esm",
globalName: "holograph.link.language",
charset: "ascii",
legalComments: "inline",
});

console.log(result.outputFiles);
esbuild.stop();
Loading