@rigxyz/tapd 0.1.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -65,15 +65,22 @@ type WalkResult = {
65
65
  };
66
66
  declare function walk(rootDir: string, opts: {
67
67
  ignore: Ignore;
68
+ /**
69
+ * Mount points (posix, relative to rootDir) to hard-exclude — import
70
+ * subdirectories materialized by mirror subscriptions. Never scanned,
71
+ * never uploaded into this binding. Non-overridable by .tapignore.
72
+ */
73
+ excludePaths?: ReadonlyArray<string>;
68
74
  }): WalkResult;
69
75
 
70
76
  /**
71
- * Thin fetch wrapper around the Phase 1 relay routes.
77
+ * Thin fetch wrapper around the relay routes.
72
78
  *
73
- * Module-level `createBinding` is unauthenticated (Phase 3 will Clerk-gate
74
- * it). Everything else binds to a (baseUrl, bindingId, token) triple via
75
- * the `RelayClient` class, since every binding-scoped route needs the
76
- * same three values on every call.
79
+ * Module-level `createBinding` and `acceptInvite` are user-authenticated
80
+ * via a relay-issued session bearer (Phase 3.5 replaced the
81
+ * X-Tap-User-Id placeholder). Binding-scoped routes use the
82
+ * `RelayClient` class which carries a (baseUrl, bindingId, capability
83
+ * token) triple.
77
84
  *
78
85
  * `RelayError` carries the route + status + parsed body so caller logic
79
86
  * can map specific 400s ("object_not_uploaded", "case_collision_with",
@@ -88,15 +95,14 @@ declare class RelayError extends Error {
88
95
  constructor(route: string, status: number, body: unknown);
89
96
  }
90
97
  /**
91
- * Create a new binding. User-authenticated via the X-Tap-User-Id header
92
- * (Phase 3 placeholder; Clerk JWT later). The response carries the
93
- * owner's first capability token, returned exactly once.
98
+ * Create a new binding. User-authenticated via a relay-issued session
99
+ * bearer. The response carries the owner's first capability token,
100
+ * returned exactly once.
94
101
  */
95
102
  declare function createBinding(opts: {
96
103
  baseUrl: string;
97
104
  request: CreateBindingRequest;
98
- userId: string;
99
- email?: string;
105
+ accessToken: string;
100
106
  fetch?: FetchLike$1;
101
107
  }): Promise<CreateBindingResponse>;
102
108
  type RelayClientOptions = {
@@ -129,6 +135,8 @@ declare class RelayClient {
129
135
  listChanges(opts?: {
130
136
  after?: string;
131
137
  limit?: number;
138
+ path?: string;
139
+ untilInclusive?: string;
132
140
  }): Promise<ChangesSinceResponse>;
133
141
  /**
134
142
  * Mint a new invite (owner-only). Returns the secret + a ready-to-share
@@ -144,6 +152,22 @@ declare class RelayClient {
144
152
  revoked: boolean;
145
153
  alreadyRevoked: boolean;
146
154
  }>;
155
+ listMembers(): Promise<{
156
+ members: Array<{
157
+ userId: string;
158
+ role: string;
159
+ email: string | null;
160
+ joinedAt: string;
161
+ }>;
162
+ }>;
163
+ removeMember(userId: string): Promise<{
164
+ removed: boolean;
165
+ tokensRevoked: number;
166
+ }>;
167
+ setMemberRole(userId: string, role: "owner" | "editor" | "viewer"): Promise<{
168
+ changed: boolean;
169
+ role: string;
170
+ }>;
147
171
  getManifest(opts?: {
148
172
  after?: string;
149
173
  limit?: number;
@@ -248,7 +272,8 @@ declare function hashFile(absPath: string): Promise<string>;
248
272
  type InitOptions = {
249
273
  rootDir: string;
250
274
  relayUrl: string;
251
- ownerUserId: string;
275
+ /** User access token (from credentials). */
276
+ accessToken: string;
252
277
  bindingName: string;
253
278
  deviceLabel?: string;
254
279
  /** Test seam: override fetch (used to drive the in-process relay). */
@@ -296,8 +321,11 @@ declare function init(opts: InitOptions): Promise<InitResult>;
296
321
  type JoinOptions = {
297
322
  rootDir: string;
298
323
  inviteUrl: string;
299
- userId: string;
300
- email?: string;
324
+ /**
325
+ * User access token from credentials. Required for member invites
326
+ * (role !== null), optional for pure-capability invites.
327
+ */
328
+ accessToken?: string | null;
301
329
  deviceLabel?: string;
302
330
  /** Test seam: override fetch. */
303
331
  fetch?: typeof fetch;
@@ -392,6 +420,19 @@ declare function conflictSidecarPath(path: string, ev: {
392
420
  id: string;
393
421
  actorDeviceId: string | null;
394
422
  }): string;
423
+ /**
424
+ * Apply mode.
425
+ *
426
+ * - `primary`: the local copy has write authority. Local-divergence
427
+ * guards protect unpushed edits (sidecars, keep-on-delete, refuse to
428
+ * clobber a dir) on the assumption scanAndPush carries them upstream.
429
+ * - `mirror`: a read-only import of another binding. The mount has no
430
+ * local authority, so **remote always wins** across every event type —
431
+ * every divergence guard flips to remote-authoritative. There is no
432
+ * scanAndPush to drain sidecars or re-submit kept files, so the primary
433
+ * guards would instead let edited imported content linger forever.
434
+ */
435
+ type ApplyMode = "primary" | "mirror";
395
436
  type ApplyEventError = {
396
437
  eventId: string;
397
438
  path: string;
@@ -421,6 +462,8 @@ declare function applyOnce(opts: {
421
462
  client: RelayClient;
422
463
  stateDb: StateDb;
423
464
  limit?: number;
465
+ /** Defaults to "primary". See ApplyMode. */
466
+ mode?: ApplyMode;
424
467
  }): Promise<ApplyResult>;
425
468
 
426
469
  /**
@@ -451,8 +494,260 @@ declare function scanAndPush(opts: {
451
494
  client: RelayClient;
452
495
  stateDb: StateDb;
453
496
  ignore: Ignore;
497
+ /** Import mount points to hard-exclude from the scan. See walk(). */
498
+ excludePaths?: ReadonlyArray<string>;
454
499
  }): Promise<ScanAndPushResult>;
455
500
 
501
+ /**
502
+ * Rig imports — read-only live mirrors of another binding into a
503
+ * subdirectory (see ~/Code/rig/docs/rig-imports.md).
504
+ *
505
+ * This module owns the *declaration* side: the ImportSpec shape, on-disk
506
+ * path helpers, and the security-critical validator. The daemon wiring
507
+ * (mirror subscriptions, orchestration) lives in start.ts; the
508
+ * apply-time behavior (remote-wins) lives in applier.ts (mode: "mirror").
509
+ *
510
+ * The validator is the single highest-risk part of the feature: a bad
511
+ * mount point is how an import could silently re-share — or, because
512
+ * mirror mode is remote-authoritative, destroy — primary content. Treat
513
+ * every rule here as security code, not input hygiene.
514
+ */
515
+ type ImportSpec = {
516
+ /** Boring slug — becomes the token filename + state-db dir name. */
517
+ name: string;
518
+ bindingId: string;
519
+ relayUrl: string;
520
+ /** Per-import capability token (read + subscribe). Machine-local. */
521
+ token: string;
522
+ /** Mount point: subdirectory relative to the rig root (posix). */
523
+ path: string;
524
+ };
525
+ /**
526
+ * On-disk shape of a per-import mount file
527
+ * (`.rig/tap/imports/<name>.local.json`). Machine-local, gitignored,
528
+ * never synced — mirrors `tap-binding.local.json`. Carries the capability
529
+ * secret plus enough to start a mirror subscription without parsing
530
+ * `rig.toml` (tapd has no TOML parser; the daemon reads JSON like it does
531
+ * for the primary binding). `ops` is persisted from the accept-invite
532
+ * response so the daemon can refuse a token that lacks read+subscribe.
533
+ */
534
+ type ImportMountFile = {
535
+ bindingId: string;
536
+ relayUrl: string;
537
+ token: string;
538
+ ops: ReadonlyArray<"read" | "write" | "subscribe">;
539
+ /** Mount point: subdirectory relative to the rig root (posix). */
540
+ path: string;
541
+ /** Import-edge id from the relay (inter-rig graph). Lets `rig import remove`
542
+ * tombstone the exact edge. Absent for anonymous imports / pre-edge mounts. */
543
+ edgeId?: string;
544
+ };
545
+ type ImportValidationError = {
546
+ name: string;
547
+ path: string;
548
+ reason: string;
549
+ };
550
+ declare function validateImportName(name: string): string | null;
551
+ /**
552
+ * Canonicalize a declared import path to a posix form with `.` and empty
553
+ * segments collapsed (`./sources/alex` and `sources/./alex` → `sources/alex`).
554
+ * `..` is deliberately preserved so validateImportPath can reject it. This
555
+ * canonical form is what the daemon uses for BOTH the mirror root and the
556
+ * primary writer's exclude set — they must be byte-identical or a mirror
557
+ * could materialize at `sources/alex` while the writer excludes
558
+ * `./sources/alex` (which never matches walker paths) and re-uploads it.
559
+ */
560
+ declare function normalizeImportPath(p: string): string;
561
+ /**
562
+ * Static + symlink validation of a single mount point. Returns a reason
563
+ * string on rejection, or null if the path is a legal mount.
564
+ *
565
+ * The mount may not exist on disk yet (first materialization hasn't
566
+ * run), so we can't realpath the full path. Instead we realpath the
567
+ * nearest existing ancestor and re-attach the not-yet-created remainder,
568
+ * then assert the result stays inside the (realpathed) rig root. This
569
+ * catches a symlinked ancestor that escapes the root even before the
570
+ * mount dir exists.
571
+ */
572
+ declare function validateImportPath(rootDir: string, importPath: string): string | null;
573
+ /**
574
+ * Validate a batch of imports against each other and against the
575
+ * primary's already-tracked content. Never throws — returns the imports
576
+ * that passed plus a structured error per rejection, so the orchestrator
577
+ * can degrade a bad mount without taking down the daemon.
578
+ */
579
+ declare function validateImports(opts: {
580
+ rootDir: string;
581
+ imports: ReadonlyArray<ImportSpec>;
582
+ /** Paths the primary binding already tracks (state-db listPaths). */
583
+ primaryTrackedPaths: ReadonlyArray<string>;
584
+ }): {
585
+ valid: ImportSpec[];
586
+ errors: ImportValidationError[];
587
+ };
588
+ /** `.rig/tap/state.local.db` — the primary binding's cursor/state. */
589
+ declare function primaryStateDbPath(rootDir: string): string;
590
+ /** `.rig/tap/imports/<name>/state.local.db` — per-import cursor/state. */
591
+ declare function importStateDbPath(rootDir: string, name: string): string;
592
+ /** `.rig/tap/imports` — holds `<name>.local.json` token files + `<name>/` state dirs. */
593
+ declare function importsDir(rootDir: string): string;
594
+ /** `.rig/tap/imports/<name>.local.json` — per-import token file. */
595
+ declare function importMountFile(rootDir: string, name: string): string;
596
+ declare function writeImportMount(rootDir: string, name: string, mount: ImportMountFile): void;
597
+ /**
598
+ * Read + validate a single mount file. Returns the spec on success or a
599
+ * structured reason on failure — never throws, so one broken mount can be
600
+ * degraded without taking down the daemon (gotcha #7).
601
+ */
602
+ declare function readImportMount(rootDir: string, name: string): {
603
+ ok: true;
604
+ spec: ImportSpec;
605
+ } | {
606
+ ok: false;
607
+ reason: string;
608
+ };
609
+ /**
610
+ * Enumerate `.rig/tap/imports/*.local.json` and resolve each to an
611
+ * ImportSpec. Broken mount files are reported, not thrown. This is the
612
+ * daemon's source of truth for which mirrors to run — read fresh at every
613
+ * `tapd start` (v1 "reload" = restart).
614
+ */
615
+ declare function loadImportMounts(rootDir: string): {
616
+ ready: ImportSpec[];
617
+ broken: ImportValidationError[];
618
+ };
619
+
620
+ /**
621
+ * A single binding's apply loop: SSE subscriber + poll fallback +
622
+ * apply-mutex → applyOnce. This is the "download direction" of the
623
+ * daemon, extracted from start.ts so it can run N times — once for the
624
+ * primary binding (mode "primary") and once per import (mode "mirror").
625
+ *
626
+ * It does NOT own the watcher or scanAndPush — that "upload direction"
627
+ * stays attached only to the primary binding, in start.ts. A mirror is a
628
+ * degenerate daemon: apply-only, no uploader.
629
+ *
630
+ * Each subscription owns its own state DB (separate cursor per binding)
631
+ * and its own RelayClient. stop() closes the state DB, so the caller
632
+ * must stop any writer that shares it FIRST.
633
+ */
634
+
635
+ /** Minimal connection config — the apply side never needs deviceId. */
636
+ type SubscriptionConfig = {
637
+ bindingId: string;
638
+ relayUrl: string;
639
+ token: string;
640
+ };
641
+ type SubscriptionHandle = {
642
+ /** Stop SSE + poll, drain the in-flight apply, then close the state DB. */
643
+ stop(): Promise<void>;
644
+ /** Force one apply cycle now (through the mutex). */
645
+ applyNow(): Promise<ApplyResult>;
646
+ /** Underlying state DB. Caller MUST NOT close it — stop() does. */
647
+ stateDb: StateDb;
648
+ };
649
+ type StartSubscriptionOptions = {
650
+ /** Directory this binding materializes into (primary root, or a mount subdir). */
651
+ rootDir: string;
652
+ config: SubscriptionConfig;
653
+ /** Separate db per binding → separate cursor. */
654
+ stateDbPath: string;
655
+ mode: ApplyMode;
656
+ fetch?: typeof fetch;
657
+ pollSeconds?: number;
658
+ /** Test seam — disable SSE (poll-only). */
659
+ noSse?: boolean;
660
+ sseHeartbeatTimeoutMs?: number;
661
+ };
662
+ declare function startSubscription(opts: StartSubscriptionOptions): Promise<SubscriptionHandle>;
663
+
664
+ /**
665
+ * `tapd import` — accept an invite to another binding and mount it
666
+ * read-only into a subdirectory of this rig (see rig-imports.md).
667
+ *
668
+ * Mirror of `join.ts`, but instead of making this folder a binding root
669
+ * it writes a per-import mount file (`.rig/tap/imports/<name>.local.json`)
670
+ * that the daemon picks up as a mirror subscription. Nothing about the
671
+ * primary binding (if any) changes.
672
+ *
673
+ * 1. Canonicalize + validate the mount (name slug, path, symlink/parent
674
+ * collisions, overlap with other mounts + primary content) BEFORE any
675
+ * network call — reusing validateImports so the rules can't drift.
676
+ * 2. Parse the invite URL → (baseUrl, secret).
677
+ * 3. acceptInvite → { bindingId, token: { secret, ops } }.
678
+ * 4. Refuse a token without read+subscribe (a mirror can't run on it).
679
+ * 5. Write the mount file (mode 0600). The daemon must be (re)started to
680
+ * pick it up — v1 "reload" = restart.
681
+ */
682
+ declare class ImportValidationFailed extends Error {
683
+ readonly reason: string;
684
+ constructor(reason: string);
685
+ }
686
+ declare class ImportTokenScopeError extends Error {
687
+ readonly ops?: ReadonlyArray<string> | undefined;
688
+ constructor(ops?: ReadonlyArray<string> | undefined);
689
+ }
690
+ type AddImportOptions = {
691
+ rootDir: string;
692
+ inviteUrl: string;
693
+ /** Mount point (subdir, relative to the rig root). */
694
+ path: string;
695
+ /** Slug; defaults to the last path segment. */
696
+ name?: string;
697
+ accessToken?: string | null;
698
+ deviceLabel?: string;
699
+ fetch?: typeof fetch;
700
+ };
701
+ type AddImportResult = {
702
+ name: string;
703
+ path: string;
704
+ bindingId: string;
705
+ ops: ReadonlyArray<"read" | "write" | "subscribe">;
706
+ /** Import-edge id recorded by the relay (absent for anonymous imports). */
707
+ edgeId?: string;
708
+ /** False when we sent our binding as the importer but the relay couldn't
709
+ * verify membership — the edge was recorded as a personal import (you → S),
710
+ * not rig → S. The CLI surfaces this as a warning. Undefined when we sent no
711
+ * binding (import-only) or no edge was recorded. */
712
+ importerBindingVerified?: boolean;
713
+ };
714
+ declare function addImport(opts: AddImportOptions): Promise<AddImportResult>;
715
+ /**
716
+ * Outcome of the best-effort server-side revoke half of a remove:
717
+ * - revoked — edge tombstoned + token revoked on the relay
718
+ * - not-creator — 403: the grant belongs to another user; left active
719
+ * - gone — 404: already revoked/removed server-side
720
+ * - no-edge — anonymous / pre-edge mount; nothing to revoke
721
+ * - no-token — not logged in; can't reach the user plane (local-only)
722
+ * - offline — relay unreachable / unexpected error
723
+ */
724
+ type RemoveImportRevoke = "revoked" | "not-creator" | "gone" | "no-edge" | "no-token" | "offline";
725
+ type RemoveImportResult = {
726
+ /** False if there was no mount file by that name. */
727
+ removed: boolean;
728
+ /** The mount point that was removed (for an optional purge), if known. */
729
+ path: string | null;
730
+ /** Whether the materialized subdir was deleted (--purge). */
731
+ purged: boolean;
732
+ /** What happened to the server-side grant. */
733
+ revoke: RemoveImportRevoke;
734
+ };
735
+ /**
736
+ * Remove a mount: relinquish the grant on the relay (best-effort), then delete
737
+ * the local token file + per-import state dir. With `purge`, also delete the
738
+ * materialized subdir. The local removal ALWAYS happens — even offline, even
739
+ * when the grant isn't ours — so the daemon stops mirroring locally. The
740
+ * caller restarts the daemon. See docs/inter-rig-graph.md §7.
741
+ */
742
+ declare function removeImport(opts: {
743
+ rootDir: string;
744
+ name: string;
745
+ purge?: boolean;
746
+ /** Hub token for the self-revoke. Omit → local-only ("no-token"). */
747
+ accessToken?: string | null;
748
+ fetch?: typeof fetch;
749
+ }): Promise<RemoveImportResult>;
750
+
456
751
  /**
457
752
  * SSE consumer for the relay's /stream endpoint.
458
753
  *
@@ -496,21 +791,24 @@ type SseSubscriber = {
496
791
  declare function subscribe(opts: SseSubscriberOptions): SseSubscriber;
497
792
 
498
793
  /**
499
- * `tapd start` — the daemon main loop.
794
+ * `tapd start` — the daemon orchestrator.
795
+ *
796
+ * A daemon = N subscriptions (apply loops) + 1 writer (watcher + scan).
797
+ * - The **primary** binding gets a subscription (mode "primary") AND
798
+ * the writer: chokidar → debounced `scanAndPush` pushes local diffs
799
+ * upstream.
800
+ * - Each **import** gets an apply-only subscription (mode "mirror")
801
+ * materializing another binding into a subdirectory, read-only. No
802
+ * writer — a mirror never pushes.
500
803
  *
501
- * Three concurrent jobs (Phase 4):
502
- * - SSE subscriber: opens /v1/bindings/:id/stream and triggers
503
- * applyOnce on every push. Fast path — latency is network +
504
- * download time, not pollSeconds.
505
- * - poll loop: every `pollSeconds`, runs applyOnce as a fallback
506
- * for SSE outages (and for multi-relay deployments where the SSE
507
- * bus is single-process; see relay's event-bus.ts).
508
- * - watcher: chokidar emits add / change / unlink / addDir / unlinkDir.
509
- * Debounced rescan calls `scanAndPush` so file diffs flow upstream.
804
+ * The subscription machinery (SSE + poll + apply-mutex) lives in
805
+ * subscription.ts; this file wires the pieces together and owns the
806
+ * primary writer.
510
807
  *
511
- * All three share the state DB and the same RelayClient. Echo
512
- * suppression in `applyEvent` prevents a self-write from being applied
513
- * back over the same bytes.
808
+ * Critical invariant: import mount points are HARD-excluded from the
809
+ * primary writer (watcher `ignored` + walker `excludePaths`), so a
810
+ * mirrored subtree is never re-uploaded into the primary's own binding
811
+ * — the "accidental re-share".
514
812
  */
515
813
 
516
814
  type StartOptions = {
@@ -518,6 +816,13 @@ type StartOptions = {
518
816
  pollSeconds?: number;
519
817
  /** Quiescence window before the watcher triggers a rescan. */
520
818
  debounceMs?: number;
819
+ /**
820
+ * Read-only imports to mount into subdirectories. When omitted, the
821
+ * daemon loads them from `.rig/tap/imports/*.local.json` (the normal
822
+ * path). Pass explicitly to bypass disk loading (tests / programmatic).
823
+ * Each carries its own binding + capability token.
824
+ */
825
+ imports?: ReadonlyArray<ImportSpec>;
521
826
  /** Test seam — override fetch (passed to RelayClient + SSE subscriber). */
522
827
  fetch?: typeof fetch;
523
828
  /** Test seam — disable the chokidar watcher (poll loop only). */
@@ -527,16 +832,25 @@ type StartOptions = {
527
832
  /** SSE watchdog window in ms. Default 45s. */
528
833
  sseHeartbeatTimeoutMs?: number;
529
834
  };
835
+ /** A live import mount — exposed for status + tests. */
836
+ type ImportHandle = {
837
+ name: string;
838
+ path: string;
839
+ applyNow(): Promise<ApplyResult>;
840
+ stateDb: StateDb;
841
+ };
530
842
  type DaemonHandle = {
531
- /** Cleanly shut down the watcher + poll loop + close the state DB. */
843
+ /** Cleanly shut down the writer + every subscription + close state DBs. */
532
844
  stop(): Promise<void>;
533
- /** Force one apply cycle now. Useful for tests + `tapd status`. */
845
+ /** Force one primary apply cycle now. No-op for an import-only daemon. */
534
846
  applyNow(): Promise<ApplyResult>;
535
- /** Force one upstream scan+push now. Useful for tests + `tapd status`. */
847
+ /** Force one upstream scan+push now. No-op for an import-only daemon. */
536
848
  scanNow(): Promise<ScanAndPushResult>;
537
- /** Underlying state DB. Caller MUST NOT close it — stop() does that. */
849
+ /** Primary state DB (or first mount's, if import-only). Do NOT close it. */
538
850
  stateDb: StateDb;
851
+ /** Live import mounts, in declaration order (valid ones only). */
852
+ imports: ImportHandle[];
539
853
  };
540
854
  declare function start(opts: StartOptions): Promise<DaemonHandle>;
541
855
 
542
- export { AlreadyInitializedError, AlreadyJoinedError, type ApplyResult, BINDING_CONFIG_PATH, BUILTIN_IGNORE_LINES, type BindingConfig, type DaemonHandle, type InitOptions, type InitResult, InvalidInviteUrlError, type JoinOptions, type JoinResult, type LocalPathState, type MintInviteOptions, NotInitializedError, RelayClient, type RelayClientOptions, RelayError, STATE_KEY_CONFLICT_COUNT, type ScanAndPushResult, type SseSubscriber, type SseSubscriberOptions, type StartOptions, type StateDb, type WalkFile, type WalkResult, type WalkWarning, applyOnce, bindingConfigFile, conflictSidecarPath, createBinding, hashFile, init, isAlwaysExcluded, join, list as listInvites, loadIgnore, mint as mintInvite, openStateDb, parseInviteUrl, readBindingConfig, revoke as revokeInvite, scanAndPush, subscribe as sseSubscribe, start, walk, writeBindingConfig };
856
+ export { type AddImportOptions, type AddImportResult, AlreadyInitializedError, AlreadyJoinedError, type ApplyMode, type ApplyResult, BINDING_CONFIG_PATH, BUILTIN_IGNORE_LINES, type BindingConfig, type DaemonHandle, type ImportHandle, type ImportMountFile, type ImportSpec, ImportTokenScopeError, type ImportValidationError, ImportValidationFailed, type InitOptions, type InitResult, InvalidInviteUrlError, type JoinOptions, type JoinResult, type LocalPathState, type MintInviteOptions, NotInitializedError, RelayClient, type RelayClientOptions, RelayError, type RemoveImportResult, STATE_KEY_CONFLICT_COUNT, type ScanAndPushResult, type SseSubscriber, type SseSubscriberOptions, type StartOptions, type StartSubscriptionOptions, type StateDb, type SubscriptionConfig, type SubscriptionHandle, type WalkFile, type WalkResult, type WalkWarning, addImport, applyOnce, bindingConfigFile, conflictSidecarPath, createBinding, hashFile, importMountFile, importStateDbPath, importsDir, init, isAlwaysExcluded, join, list as listInvites, loadIgnore, loadImportMounts, mint as mintInvite, normalizeImportPath, openStateDb, parseInviteUrl, primaryStateDbPath, readBindingConfig, readImportMount, removeImport, revoke as revokeInvite, scanAndPush, subscribe as sseSubscribe, start, startSubscription, validateImportName, validateImportPath, validateImports, walk, writeBindingConfig, writeImportMount };
package/dist/index.js CHANGED
@@ -4,61 +4,93 @@ import {
4
4
  AlreadyJoinedError,
5
5
  BINDING_CONFIG_PATH,
6
6
  BUILTIN_IGNORE_LINES,
7
+ ImportTokenScopeError,
8
+ ImportValidationFailed,
7
9
  InvalidInviteUrlError,
8
10
  NotInitializedError,
9
11
  RelayClient,
10
12
  RelayError,
11
13
  STATE_KEY_CONFLICT_COUNT,
14
+ addImport,
12
15
  applyOnce,
13
16
  bindingConfigFile,
14
17
  conflictSidecarPath,
15
18
  createBinding,
16
19
  hashFile,
20
+ importMountFile,
21
+ importStateDbPath,
22
+ importsDir,
17
23
  init,
18
24
  isAlwaysExcluded,
19
25
  join,
20
26
  list,
21
27
  loadIgnore,
28
+ loadImportMounts,
22
29
  mint,
30
+ normalizeImportPath,
23
31
  openStateDb,
24
32
  parseInviteUrl,
33
+ primaryStateDbPath,
25
34
  readBindingConfig,
35
+ readImportMount,
36
+ removeImport,
26
37
  revoke,
27
38
  scanAndPush,
28
39
  start,
40
+ startSubscription,
29
41
  subscribe,
42
+ validateImportName,
43
+ validateImportPath,
44
+ validateImports,
30
45
  walk,
31
- writeBindingConfig
32
- } from "./chunk-RQC73B5Y.js";
46
+ writeBindingConfig,
47
+ writeImportMount
48
+ } from "./chunk-YPZ2UNI5.js";
33
49
  export {
34
50
  AlreadyInitializedError,
35
51
  AlreadyJoinedError,
36
52
  BINDING_CONFIG_PATH,
37
53
  BUILTIN_IGNORE_LINES,
54
+ ImportTokenScopeError,
55
+ ImportValidationFailed,
38
56
  InvalidInviteUrlError,
39
57
  NotInitializedError,
40
58
  RelayClient,
41
59
  RelayError,
42
60
  STATE_KEY_CONFLICT_COUNT,
61
+ addImport,
43
62
  applyOnce,
44
63
  bindingConfigFile,
45
64
  conflictSidecarPath,
46
65
  createBinding,
47
66
  hashFile,
67
+ importMountFile,
68
+ importStateDbPath,
69
+ importsDir,
48
70
  init,
49
71
  isAlwaysExcluded,
50
72
  join,
51
73
  list as listInvites,
52
74
  loadIgnore,
75
+ loadImportMounts,
53
76
  mint as mintInvite,
77
+ normalizeImportPath,
54
78
  openStateDb,
55
79
  parseInviteUrl,
80
+ primaryStateDbPath,
56
81
  readBindingConfig,
82
+ readImportMount,
83
+ removeImport,
57
84
  revoke as revokeInvite,
58
85
  scanAndPush,
59
86
  subscribe as sseSubscribe,
60
87
  start,
88
+ startSubscription,
89
+ validateImportName,
90
+ validateImportPath,
91
+ validateImports,
61
92
  walk,
62
- writeBindingConfig
93
+ writeBindingConfig,
94
+ writeImportMount
63
95
  };
64
96
  //# sourceMappingURL=index.js.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rigxyz/tapd",
3
- "version": "0.1.0",
3
+ "version": "0.4.0",
4
4
  "description": "Local daemon for the hosted Tap relay — watches files, hashes content, uploads/downloads objects, applies remote changes. Pairs with @rigxyz/cli for shared-rig sync.",
5
5
  "license": "MIT",
6
6
  "author": "Dylan Bourgeois <dtsbourg@gmail.com>",