tensorlake 0.5.76 → 0.5.85

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.cjs CHANGED
@@ -35,7 +35,7 @@ var SDK_VERSION, API_URL, API_KEY, NAMESPACE, SANDBOX_PROXY_URL, DEFAULT_HTTP_TI
35
35
  var init_defaults = __esm({
36
36
  "src/defaults.ts"() {
37
37
  "use strict";
38
- SDK_VERSION = "0.5.76";
38
+ SDK_VERSION = "0.5.85";
39
39
  API_URL = process.env.TENSORLAKE_API_URL ?? "https://api.tensorlake.ai";
40
40
  API_KEY = process.env.TENSORLAKE_API_KEY ?? void 0;
41
41
  NAMESPACE = process.env.INDEXIFY_NAMESPACE ?? "default";
@@ -6153,11 +6153,20 @@ var init_sandbox_image = __esm({
6153
6153
  var index_exports = {};
6154
6154
  __export(index_exports, {
6155
6155
  APIClient: () => APIClient,
6156
+ CliNotFoundError: () => CliNotFoundError,
6156
6157
  CloudClient: () => CloudClient,
6157
6158
  ContainerState: () => ContainerState,
6158
6159
  Desktop: () => Desktop,
6160
+ FileNotFoundInFilesystemError: () => FileNotFoundInFilesystemError,
6161
+ Filesystem: () => Filesystem,
6162
+ FilesystemAPIError: () => FilesystemAPIError,
6163
+ FilesystemClient: () => FilesystemClient,
6164
+ FilesystemError: () => FilesystemError,
6165
+ FilesystemMount: () => FilesystemMount,
6166
+ FilesystemNotFoundError: () => FilesystemNotFoundError,
6159
6167
  Image: () => Image,
6160
6168
  ImageBuildOperationType: () => ImageBuildOperationType,
6169
+ MountError: () => MountError,
6161
6170
  OutputMode: () => OutputMode,
6162
6171
  PoolInUseError: () => PoolInUseError,
6163
6172
  PoolNotFoundError: () => PoolNotFoundError,
@@ -6542,6 +6551,543 @@ async function deleteFileSystem(fileSystemId) {
6542
6551
  }
6543
6552
  }
6544
6553
 
6554
+ // src/filesystem.ts
6555
+ var import_node_child_process = require("child_process");
6556
+ var import_node_crypto2 = require("crypto");
6557
+ var import_node_fs2 = require("fs");
6558
+ var import_node_os2 = require("os");
6559
+ var import_node_path2 = require("path");
6560
+ var import_node_util2 = require("util");
6561
+ init_defaults();
6562
+
6563
+ // src/filesystem-models.ts
6564
+ var GIT_MODE_DIR = 16384;
6565
+ var GIT_MODE_SYMLINK = 40960;
6566
+ function trimSlashes(path2) {
6567
+ let start = 0;
6568
+ let end = path2.length;
6569
+ while (start < end && path2.charCodeAt(start) === 47) start += 1;
6570
+ while (end > start && path2.charCodeAt(end - 1) === 47) end -= 1;
6571
+ return path2.slice(start, end);
6572
+ }
6573
+ function fileEntryFromWire(entry, dirPath) {
6574
+ const mode = entry.mode ?? 33188;
6575
+ const prefix = trimSlashes(dirPath);
6576
+ return {
6577
+ name: entry.name,
6578
+ path: prefix ? `${prefix}/${entry.name}` : entry.name,
6579
+ oid: entry.oid ?? "",
6580
+ mode,
6581
+ size: entry.size ?? null,
6582
+ isDir: mode === GIT_MODE_DIR,
6583
+ isSymlink: mode === GIT_MODE_SYMLINK
6584
+ };
6585
+ }
6586
+ function mountStatusFromRaw(raw, localPath) {
6587
+ const mounted = "mounted" in raw ? Boolean(raw.mounted) : "active" in raw ? Boolean(raw.active) : true;
6588
+ const path2 = String(raw.path || raw.mount_path || localPath || "");
6589
+ const filesystem = raw.filesystem || raw.file_system || null;
6590
+ return { path: path2, filesystem, mounted, raw };
6591
+ }
6592
+ var FilesystemError = class extends Error {
6593
+ constructor(message) {
6594
+ super(message);
6595
+ this.name = "FilesystemError";
6596
+ }
6597
+ };
6598
+ var FilesystemNotFoundError = class extends FilesystemError {
6599
+ filesystemName;
6600
+ constructor(name) {
6601
+ super(`Filesystem not found: ${name}`);
6602
+ this.name = "FilesystemNotFoundError";
6603
+ this.filesystemName = name;
6604
+ }
6605
+ };
6606
+ var FileNotFoundInFilesystemError = class extends FilesystemError {
6607
+ filesystem;
6608
+ path;
6609
+ constructor(filesystem, path2) {
6610
+ super(`File not found in filesystem ${filesystem}: ${path2}`);
6611
+ this.name = "FileNotFoundInFilesystemError";
6612
+ this.filesystem = filesystem;
6613
+ this.path = path2;
6614
+ }
6615
+ };
6616
+ var FilesystemAPIError = class extends FilesystemError {
6617
+ statusCode;
6618
+ constructor(statusCode, message) {
6619
+ super(`API error (status ${statusCode}): ${message}`);
6620
+ this.name = "FilesystemAPIError";
6621
+ this.statusCode = statusCode;
6622
+ }
6623
+ };
6624
+ var MountError = class extends FilesystemError {
6625
+ constructor(message) {
6626
+ super(message);
6627
+ this.name = "MountError";
6628
+ }
6629
+ };
6630
+ var CliNotFoundError = class extends MountError {
6631
+ constructor(detail) {
6632
+ super(
6633
+ `Mount operations require the Tensorlake CLI (\`tl\`) with \`tl fs\` support: ${detail}. Install or upgrade it with: curl -fsSL https://tensorlake.ai/install.sh | sh`
6634
+ );
6635
+ this.name = "CliNotFoundError";
6636
+ }
6637
+ };
6638
+
6639
+ // src/filesystem.ts
6640
+ init_native_sandbox();
6641
+ init_sandbox_image();
6642
+ var execFileAsync = (0, import_node_util2.promisify)(import_node_child_process.execFile);
6643
+ var FILESYSTEM_REPO_KIND = "filesystem";
6644
+ function translateNativeError2(error, notFound) {
6645
+ const message = error instanceof Error ? error.message : String(error);
6646
+ let payload;
6647
+ try {
6648
+ payload = JSON.parse(message);
6649
+ } catch {
6650
+ return error instanceof Error ? error : new FilesystemError(message);
6651
+ }
6652
+ if (!payload || typeof payload.category !== "string") {
6653
+ return error instanceof Error ? error : new FilesystemError(message);
6654
+ }
6655
+ const detail = typeof payload.message === "string" ? payload.message : message;
6656
+ if (payload.category === "connection") {
6657
+ return new FilesystemError(detail);
6658
+ }
6659
+ if (payload.status === 404 && notFound !== void 0) {
6660
+ return notFound;
6661
+ }
6662
+ if (typeof payload.status === "number") {
6663
+ return new FilesystemAPIError(payload.status, detail);
6664
+ }
6665
+ return new FilesystemError(detail);
6666
+ }
6667
+ async function callNative2(fn, notFound) {
6668
+ try {
6669
+ return await fn();
6670
+ } catch (error) {
6671
+ throw translateNativeError2(error, notFound);
6672
+ }
6673
+ }
6674
+ var FsCli = class {
6675
+ binary = null;
6676
+ envOverrides;
6677
+ constructor(envOverrides) {
6678
+ this.envOverrides = envOverrides;
6679
+ }
6680
+ async findCli() {
6681
+ const candidates = [];
6682
+ if (process.env.TENSORLAKE_CLI) {
6683
+ candidates.push(process.env.TENSORLAKE_CLI);
6684
+ }
6685
+ candidates.push("tl");
6686
+ const installed = (0, import_node_path2.join)((0, import_node_os2.homedir)(), ".tensorlake", "bin", "tl");
6687
+ try {
6688
+ (0, import_node_fs2.accessSync)(installed, import_node_fs2.constants.F_OK);
6689
+ candidates.push(installed);
6690
+ } catch {
6691
+ }
6692
+ let unsupported = null;
6693
+ for (const candidate of candidates) {
6694
+ try {
6695
+ await execFileAsync(candidate, ["fs", "--help"], { timeout: 15e3 });
6696
+ return candidate;
6697
+ } catch (error) {
6698
+ if (error.code !== "ENOENT") {
6699
+ unsupported = candidate;
6700
+ }
6701
+ }
6702
+ }
6703
+ throw new CliNotFoundError(
6704
+ unsupported ? `\`tl\` at ${unsupported} does not support \`tl fs\` (upgrade required)` : "`tl` was not found on PATH"
6705
+ );
6706
+ }
6707
+ async run(args, timeoutMs = 3e5) {
6708
+ if (this.binary === null) {
6709
+ this.binary = await this.findCli();
6710
+ }
6711
+ try {
6712
+ const { stdout } = await execFileAsync(this.binary, ["fs", ...args], {
6713
+ timeout: timeoutMs,
6714
+ env: { ...process.env, ...this.envOverrides },
6715
+ maxBuffer: 16 * 1024 * 1024
6716
+ });
6717
+ return stdout;
6718
+ } catch (error) {
6719
+ const failure = error;
6720
+ if (failure.killed) {
6721
+ throw new MountError(`\`tl fs ${args[0]}\` timed out after ${timeoutMs}ms`);
6722
+ }
6723
+ const detail = (failure.stderr || failure.stdout || String(error)).trim();
6724
+ throw new MountError(`\`tl fs ${args.join(" ")}\` failed: ${detail}`);
6725
+ }
6726
+ }
6727
+ // Flags always precede a `--` end-of-options separator so caller-supplied
6728
+ // names/paths can never be parsed as CLI flags (e.g. a path literally
6729
+ // named "--discard" must stay a path, not become the destructive flag).
6730
+ async mount(filesystem, localPath, readonly) {
6731
+ const args = ["mount"];
6732
+ if (readonly) args.push("--ro");
6733
+ args.push("--", filesystem, localPath);
6734
+ await this.run(args);
6735
+ }
6736
+ async unmount(localPath, discard) {
6737
+ const args = ["unmount"];
6738
+ if (discard) args.push("--discard");
6739
+ args.push("--", localPath);
6740
+ await this.run(args);
6741
+ }
6742
+ async snapshot(localPath, message) {
6743
+ const args = ["snapshot"];
6744
+ if (message) args.push(`--message=${message}`);
6745
+ args.push("--", localPath);
6746
+ await this.run(args);
6747
+ }
6748
+ async status(localPath) {
6749
+ const args = ["status", "--json"];
6750
+ if (localPath) args.push("--", localPath);
6751
+ const output = await this.run(args, 6e4);
6752
+ try {
6753
+ const payload = JSON.parse(output);
6754
+ return typeof payload === "object" && payload !== null ? payload : { status: payload };
6755
+ } catch {
6756
+ throw new MountError(
6757
+ `\`tl fs status --json\` returned invalid JSON: ${output.slice(0, 200)}`
6758
+ );
6759
+ }
6760
+ }
6761
+ };
6762
+ var FilesystemClient = class {
6763
+ native;
6764
+ cli;
6765
+ /**
6766
+ * Any option left unset is resolved from the environment
6767
+ * (`TENSORLAKE_API_KEY` / `TENSORLAKE_PAT`, `TENSORLAKE_API_URL`,
6768
+ * `TENSORLAKE_ORGANIZATION_ID`, `TENSORLAKE_PROJECT_ID`).
6769
+ */
6770
+ constructor(options = {}) {
6771
+ const context = buildContextFromEnv();
6772
+ const token = options.apiKey ?? context.apiKey ?? context.personalAccessToken;
6773
+ if (!token) {
6774
+ throw new FilesystemError(
6775
+ "Missing TENSORLAKE_API_KEY or TENSORLAKE_PAT credentials."
6776
+ );
6777
+ }
6778
+ const organizationId = options.organizationId ?? context.organizationId;
6779
+ const projectId = options.projectId ?? context.projectId;
6780
+ if (!organizationId || !projectId) {
6781
+ throw new FilesystemError(
6782
+ "Filesystem operations require organization and project context (TENSORLAKE_ORGANIZATION_ID and TENSORLAKE_PROJECT_ID)."
6783
+ );
6784
+ }
6785
+ if (options.nativeClient) {
6786
+ this.native = options.nativeClient;
6787
+ } else {
6788
+ const binding = loadNativeSandboxBinding();
6789
+ if (typeof binding.NativeRepositoryClient !== "function") {
6790
+ throw new FilesystemError(
6791
+ "native binding does not export the repository client; rebuild with 'npm run build:native'"
6792
+ );
6793
+ }
6794
+ this.native = new binding.NativeRepositoryClient(
6795
+ options.apiUrl ?? context.apiUrl,
6796
+ token,
6797
+ organizationId,
6798
+ projectId,
6799
+ `tensorlake-typescript-sdk/${SDK_VERSION}`,
6800
+ null
6801
+ );
6802
+ }
6803
+ const envOverrides = {
6804
+ TENSORLAKE_ORGANIZATION_ID: organizationId,
6805
+ TENSORLAKE_PROJECT_ID: projectId,
6806
+ // The CLI must target the same deployment the data plane does, or a
6807
+ // mount could resolve a same-named filesystem in the wrong environment.
6808
+ TENSORLAKE_API_URL: options.apiUrl ?? context.apiUrl
6809
+ };
6810
+ if (options.apiKey) {
6811
+ envOverrides.TENSORLAKE_API_KEY = options.apiKey;
6812
+ }
6813
+ this.cli = new FsCli(envOverrides);
6814
+ }
6815
+ // -- lifecycle --------------------------------------------------------------
6816
+ /** Create a new filesystem and return a handle to it. */
6817
+ async create(name) {
6818
+ if (typeof name !== "string") {
6819
+ throw new TypeError("name must be a string");
6820
+ }
6821
+ if (name.length === 0) {
6822
+ throw new FilesystemError("filesystem name must not be empty");
6823
+ }
6824
+ const raw = await callNative2(() => this.native.createFilesystem(name));
6825
+ const created = JSON.parse(raw);
6826
+ return new Filesystem(
6827
+ this,
6828
+ this.native,
6829
+ this.cli,
6830
+ name,
6831
+ created.default_branch || "main"
6832
+ );
6833
+ }
6834
+ /** Return a handle to an existing filesystem (verifies it exists). */
6835
+ async get(name) {
6836
+ const traced = await callNative2(
6837
+ () => this.native.filesystemMeta(name),
6838
+ new FilesystemNotFoundError(name)
6839
+ );
6840
+ const meta = JSON.parse(traced.json);
6841
+ if ((meta.kind ?? FILESYSTEM_REPO_KIND) !== FILESYSTEM_REPO_KIND) {
6842
+ throw new FilesystemNotFoundError(name);
6843
+ }
6844
+ return new Filesystem(
6845
+ this,
6846
+ this.native,
6847
+ this.cli,
6848
+ name,
6849
+ meta.default_branch || "main"
6850
+ );
6851
+ }
6852
+ /** List all filesystems in the project. */
6853
+ async list() {
6854
+ const traced = await callNative2(() => this.native.listFilesystems());
6855
+ const page = JSON.parse(traced.json);
6856
+ return (page.repos ?? []).map((repo) => ({
6857
+ name: String(repo.name ?? ""),
6858
+ fullName: String(repo.full_name ?? ""),
6859
+ defaultBranch: String(repo.default_branch ?? "main"),
6860
+ status: String(repo.status ?? ""),
6861
+ kind: String(repo.kind ?? FILESYSTEM_REPO_KIND)
6862
+ }));
6863
+ }
6864
+ /** Permanently delete a filesystem and all its snapshots. */
6865
+ async delete(name) {
6866
+ await callNative2(
6867
+ () => this.native.deleteFilesystem(name),
6868
+ new FilesystemNotFoundError(name)
6869
+ );
6870
+ }
6871
+ // -- local mounts -------------------------------------------------------------
6872
+ /** Mount a filesystem to a local path (requires the `tl` CLI). */
6873
+ async mount(name, localPath, readonly = false) {
6874
+ await this.cli.mount(name, localPath, readonly);
6875
+ return new FilesystemMount(this, this.cli, name, localPath, readonly);
6876
+ }
6877
+ /**
6878
+ * Unmount a locally mounted filesystem.
6879
+ *
6880
+ * `discard: true` drops local changes that were not yet uploaded.
6881
+ */
6882
+ async unmount(localPath, discard = false) {
6883
+ await this.cli.unmount(localPath, discard);
6884
+ }
6885
+ /** Status of a local mount (defaults to the mount containing CWD). */
6886
+ async mountStatus(localPath) {
6887
+ return mountStatusFromRaw(await this.cli.status(localPath), localPath);
6888
+ }
6889
+ };
6890
+ function toBuffer(data) {
6891
+ return typeof data === "string" ? Buffer.from(data, "utf-8") : Buffer.from(data);
6892
+ }
6893
+ var Filesystem = class {
6894
+ client;
6895
+ native;
6896
+ cli;
6897
+ name;
6898
+ defaultBranch;
6899
+ /** @internal — obtain instances via `FilesystemClient.create()` / `.get()`. */
6900
+ constructor(client, native, cli, name, defaultBranch = null) {
6901
+ this.client = client;
6902
+ this.native = native;
6903
+ this.cli = cli;
6904
+ this.name = name;
6905
+ this.defaultBranch = defaultBranch;
6906
+ }
6907
+ /**
6908
+ * The filesystem's default branch — the target of every write and the
6909
+ * default version of every read, so writes and `status()` can never
6910
+ * silently disagree on a non-"main" filesystem.
6911
+ */
6912
+ async branch() {
6913
+ if (!this.defaultBranch) {
6914
+ const traced = await callNative2(
6915
+ () => this.native.filesystemMeta(this.name),
6916
+ new FilesystemNotFoundError(this.name)
6917
+ );
6918
+ const meta = JSON.parse(traced.json);
6919
+ this.defaultBranch = meta.default_branch || "main";
6920
+ }
6921
+ return this.defaultBranch;
6922
+ }
6923
+ // -- writes -------------------------------------------------------------------
6924
+ /** Write one file. Returns the snapshot (version) the write produced. */
6925
+ async writeFile(path2, data, message) {
6926
+ return await this.writeFiles(/* @__PURE__ */ new Map([[path2, data]]), message);
6927
+ }
6928
+ /** Write several files (and/or delete paths) in one atomic snapshot. */
6929
+ async writeFiles(files, message, deletes = []) {
6930
+ const entries = files instanceof Map ? [...files.entries()] : Object.entries(files);
6931
+ if (entries.length === 0 && deletes.length === 0) {
6932
+ throw new FilesystemError("nothing to write: no files or deletions given");
6933
+ }
6934
+ const writes = entries.map(([path2, data]) => ({
6935
+ path: path2,
6936
+ content: toBuffer(data)
6937
+ }));
6938
+ const resolvedMessage = message || `write ${writes.length} file(s) via SDK`;
6939
+ const branch = await this.branch();
6940
+ const traced = await callNative2(
6941
+ () => this.native.pushFilesystemFiles(
6942
+ this.name,
6943
+ writes,
6944
+ deletes,
6945
+ resolvedMessage,
6946
+ branch,
6947
+ // One key per logical write: a retried submit reattaches to the
6948
+ // same durable commit job instead of double-committing.
6949
+ (0, import_node_crypto2.randomBytes)(16).toString("hex")
6950
+ ),
6951
+ new FilesystemNotFoundError(this.name)
6952
+ );
6953
+ const report = JSON.parse(traced.json);
6954
+ return {
6955
+ commit: String(report.commit ?? ""),
6956
+ tree: String(report.tree ?? ""),
6957
+ refName: String(report.ref_name ?? ""),
6958
+ parent: null,
6959
+ created: report.created === void 0 ? true : Boolean(report.created),
6960
+ message: resolvedMessage
6961
+ };
6962
+ }
6963
+ /** Delete one file. Returns the snapshot the deletion produced. */
6964
+ async deleteFile(path2, message) {
6965
+ return await this.writeFiles(
6966
+ /* @__PURE__ */ new Map(),
6967
+ message || `delete ${path2} via SDK`,
6968
+ [path2]
6969
+ );
6970
+ }
6971
+ /**
6972
+ * Return the filesystem's current version as a snapshot.
6973
+ *
6974
+ * Writes already create snapshots implicitly; this pins the current head
6975
+ * without changing any content.
6976
+ */
6977
+ async snapshot(message = "") {
6978
+ const status = await this.status();
6979
+ if (!status.headCommit) {
6980
+ throw new FilesystemError(
6981
+ `filesystem ${this.name} is empty: write files first`
6982
+ );
6983
+ }
6984
+ return {
6985
+ commit: status.headCommit,
6986
+ tree: "",
6987
+ refName: `refs/heads/${status.defaultBranch}`,
6988
+ parent: null,
6989
+ created: false,
6990
+ message
6991
+ };
6992
+ }
6993
+ // -- reads --------------------------------------------------------------------
6994
+ /**
6995
+ * Read a file's bytes at `version` (branch, ref, or snapshot commit;
6996
+ * defaults to the filesystem's default branch).
6997
+ */
6998
+ async readFile(path2, version) {
6999
+ if (trimSlashes(path2) === "") {
7000
+ throw new FilesystemError("file path must not be empty");
7001
+ }
7002
+ const resolvedVersion = version || await this.branch();
7003
+ const traced = await callNative2(
7004
+ () => this.native.readFilesystemFile(this.name, path2, resolvedVersion),
7005
+ new FileNotFoundInFilesystemError(this.name, path2)
7006
+ );
7007
+ return new Uint8Array(traced.data);
7008
+ }
7009
+ /** Read a file as UTF-8 text at `version`. Throws on non-UTF-8 content. */
7010
+ async readText(path2, version) {
7011
+ return new TextDecoder("utf-8", { fatal: true, ignoreBOM: true }).decode(
7012
+ await this.readFile(path2, version)
7013
+ );
7014
+ }
7015
+ /** List one directory (non-recursive) at `version`. */
7016
+ async listFiles(dirPath = "", version) {
7017
+ const resolvedVersion = version || await this.branch();
7018
+ const traced = await callNative2(
7019
+ () => this.native.listFilesystemTree(this.name, dirPath, resolvedVersion),
7020
+ new FileNotFoundInFilesystemError(this.name, dirPath || "/")
7021
+ );
7022
+ const page = JSON.parse(traced.json);
7023
+ return (page.entries ?? []).map((entry) => fileEntryFromWire(entry, dirPath));
7024
+ }
7025
+ // -- status -------------------------------------------------------------------
7026
+ /** Remote status: identity plus the current head snapshot. */
7027
+ async status() {
7028
+ const metaTraced = await callNative2(
7029
+ () => this.native.filesystemMeta(this.name),
7030
+ new FilesystemNotFoundError(this.name)
7031
+ );
7032
+ const meta = JSON.parse(metaTraced.json);
7033
+ const defaultBranch = String(meta.default_branch || "main");
7034
+ this.defaultBranch = defaultBranch;
7035
+ let headCommit = null;
7036
+ let generation = null;
7037
+ try {
7038
+ const refTraced = await callNative2(
7039
+ () => this.native.filesystemRefStatus(this.name, defaultBranch)
7040
+ );
7041
+ const ref = JSON.parse(refTraced.json);
7042
+ headCommit = ref.resolved_commit || ref.oid || null;
7043
+ generation = typeof ref.generation === "number" ? ref.generation : null;
7044
+ } catch (error) {
7045
+ if (!(error instanceof FilesystemAPIError) || error.statusCode !== 404) {
7046
+ throw error;
7047
+ }
7048
+ }
7049
+ return {
7050
+ name: this.name,
7051
+ status: String(meta.status ?? ""),
7052
+ defaultBranch,
7053
+ headCommit,
7054
+ generation
7055
+ };
7056
+ }
7057
+ // -- mounts -------------------------------------------------------------------
7058
+ /** Mount this filesystem to a local path (requires the `tl` CLI). */
7059
+ async mount(localPath, readonly = false) {
7060
+ return await this.client.mount(this.name, localPath, readonly);
7061
+ }
7062
+ };
7063
+ var FilesystemMount = class {
7064
+ client;
7065
+ cli;
7066
+ filesystem;
7067
+ path;
7068
+ readonly;
7069
+ /** @internal — obtain instances via `FilesystemClient.mount()`. */
7070
+ constructor(client, cli, filesystem, path2, readonly) {
7071
+ this.client = client;
7072
+ this.cli = cli;
7073
+ this.filesystem = filesystem;
7074
+ this.path = path2;
7075
+ this.readonly = readonly;
7076
+ }
7077
+ /** Flush pending local changes into a durable snapshot. */
7078
+ async snapshot(message) {
7079
+ await this.cli.snapshot(this.path, message);
7080
+ }
7081
+ /** Local mount status as reported by the mount daemon. */
7082
+ async status() {
7083
+ return await this.client.mountStatus(this.path);
7084
+ }
7085
+ /** Unmount; `discard: true` drops changes not yet uploaded. */
7086
+ async unmount(discard = false) {
7087
+ await this.client.unmount(this.path, discard);
7088
+ }
7089
+ };
7090
+
6545
7091
  // src/index.ts
6546
7092
  init_image();
6547
7093
  init_url();
@@ -6550,11 +7096,20 @@ init_models();
6550
7096
  // Annotate the CommonJS export names for ESM import in node:
6551
7097
  0 && (module.exports = {
6552
7098
  APIClient,
7099
+ CliNotFoundError,
6553
7100
  CloudClient,
6554
7101
  ContainerState,
6555
7102
  Desktop,
7103
+ FileNotFoundInFilesystemError,
7104
+ Filesystem,
7105
+ FilesystemAPIError,
7106
+ FilesystemClient,
7107
+ FilesystemError,
7108
+ FilesystemMount,
7109
+ FilesystemNotFoundError,
6556
7110
  Image,
6557
7111
  ImageBuildOperationType,
7112
+ MountError,
6558
7113
  OutputMode,
6559
7114
  PoolInUseError,
6560
7115
  PoolNotFoundError,