trainfabric 0.1.10 → 0.1.12

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/README.md CHANGED
@@ -29,7 +29,7 @@ trainfabric projects:list
29
29
  trainfabric datasets:upload ./train.jsonl --project <projectId>
30
30
  trainfabric runs:quote --summary --project <projectId> --dataset <datasetId> --model llama-3-8b
31
31
  trainfabric runs:create --yes --project <projectId> --dataset <datasetId> --model llama-3-8b
32
- trainfabric runs:watch <runId>
32
+ trainfabric runs:watch <runId> --timeout 30m
33
33
  trainfabric runs:cost-breakdown <runId> --summary
34
34
  ```
35
35
 
package/dist/index.cjs CHANGED
@@ -8204,6 +8204,9 @@ var DatasetsClient = class extends ResourceClient {
8204
8204
 
8205
8205
  // ../sdk/dist/client/deployments.js
8206
8206
  var DeploymentsClient = class extends ResourceClient {
8207
+ list() {
8208
+ return this.requestGet("/v1/deployments");
8209
+ }
8207
8210
  create(input) {
8208
8211
  return this.requestPost("/v1/deployments", input);
8209
8212
  }
@@ -8385,8 +8388,11 @@ var RunHandle = class {
8385
8388
  this.listeners.get(event)?.delete(listener);
8386
8389
  };
8387
8390
  }
8388
- async wait() {
8391
+ async wait(options) {
8389
8392
  this.ensureStreaming();
8393
+ const startedAt = Date.now();
8394
+ const pollMs = options?.pollMs ?? 1e3;
8395
+ const timeoutMs = options?.timeoutMs;
8390
8396
  for (; ; ) {
8391
8397
  const detail = await this.client.runs.get(this.snapshot.id);
8392
8398
  this.snapshot = detail.run;
@@ -8403,7 +8409,11 @@ var RunHandle = class {
8403
8409
  }
8404
8410
  return detail;
8405
8411
  }
8406
- await new Promise((resolve) => setTimeout(resolve, 1e3));
8412
+ if (timeoutMs !== void 0 && Date.now() - startedAt > timeoutMs) {
8413
+ this.close();
8414
+ throw new Error(`Timed out waiting for run ${this.snapshot.id}.`);
8415
+ }
8416
+ await new Promise((resolve) => setTimeout(resolve, pollMs));
8407
8417
  }
8408
8418
  }
8409
8419
  close() {
@@ -8621,9 +8631,9 @@ var RunsClient = class extends ResourceClient {
8621
8631
  explanation(runId) {
8622
8632
  return this.requestGet(`/v1/runs/${runId}/explanation`);
8623
8633
  }
8624
- async wait(runId) {
8634
+ async wait(runId, options) {
8625
8635
  const handle = await this.watch(runId);
8626
- return handle.wait();
8636
+ return handle.wait(options);
8627
8637
  }
8628
8638
  };
8629
8639
 
@@ -8911,7 +8921,7 @@ function buildComputeSpec(options) {
8911
8921
 
8912
8922
  // src/index.ts
8913
8923
  var DEFAULT_TRAINFABRIC_API_URL2 = "https://api.trainfabric.com";
8914
- var CLI_VERSION = "0.1.10";
8924
+ var CLI_VERSION = "0.1.12";
8915
8925
  var CONFIG_DIR = import_node_path3.default.join(import_node_os2.default.homedir(), ".trainfabric");
8916
8926
  var CONFIG_PATH = import_node_path3.default.join(CONFIG_DIR, "config.json");
8917
8927
  var FALLBACK_SECRET_PATH = import_node_path3.default.join(CONFIG_DIR, "session.enc");
@@ -9287,7 +9297,7 @@ function assertQuoteOptions(bundle, options) {
9287
9297
  )}). Omit --accelerator or increase --min-memory.`
9288
9298
  );
9289
9299
  }
9290
- async function watchRun(runId, json = false) {
9300
+ async function watchRun(runId, json = false, timeoutMs) {
9291
9301
  const handle = await createClient(loadConfig()).runs.watch(runId);
9292
9302
  if (json) {
9293
9303
  const emit = (type, payload) => printJson({ type, payload });
@@ -9324,9 +9334,26 @@ async function watchRun(runId, json = false) {
9324
9334
  console.log(`[failed] ${payload.reason ?? "Run failed."}`);
9325
9335
  });
9326
9336
  }
9327
- const detail = await handle.wait();
9337
+ const detail = await handle.wait({ timeoutMs });
9328
9338
  printJson(detail);
9329
9339
  }
9340
+ function parseDurationMs(value) {
9341
+ if (!value) {
9342
+ return void 0;
9343
+ }
9344
+ const trimmed = value.trim().toLowerCase();
9345
+ const match = trimmed.match(/^(\d+(?:\.\d+)?)(ms|s|m|h)?$/);
9346
+ if (!match) {
9347
+ throw new Error(`Invalid duration "${value}". Use values like 30s, 10m, 1h, or 5000ms.`);
9348
+ }
9349
+ const amount = Number(match[1]);
9350
+ const unit = match[2] ?? "ms";
9351
+ const multiplier = unit === "h" ? 36e5 : unit === "m" ? 6e4 : unit === "s" ? 1e3 : 1;
9352
+ return Math.max(1, Math.round(amount * multiplier));
9353
+ }
9354
+ function parsePositiveMs(value, fallback) {
9355
+ return parseDurationMs(value) ?? fallback;
9356
+ }
9330
9357
  function createClient(config) {
9331
9358
  return new TrainingClient({
9332
9359
  accessToken: config.accessToken,
@@ -9495,11 +9522,16 @@ program2.command("runs:status").argument("<runId>").description("Fetch full run
9495
9522
  program2.command("runs:logs").argument("<runId>").description("Fetch run logs").action(async (runId) => {
9496
9523
  printJson(await createClient(loadConfig()).runs.logs(String(runId)));
9497
9524
  });
9498
- program2.command("runs:wait").argument("<runId>").description("Wait for a run to reach a terminal state").action(async (runId) => {
9499
- printJson(await createClient(loadConfig()).runs.wait(String(runId)));
9525
+ program2.command("runs:wait").argument("<runId>").option("--timeout <duration>", "maximum wait duration, for example 30s, 10m, or 1h").option("--poll <duration>", "poll interval, for example 1s or 500ms").description("Wait for a run to reach a terminal state").action(async (runId, options) => {
9526
+ printJson(
9527
+ await createClient(loadConfig()).runs.wait(String(runId), {
9528
+ timeoutMs: parseDurationMs(options.timeout),
9529
+ pollMs: parsePositiveMs(options.poll, 1e3)
9530
+ })
9531
+ );
9500
9532
  });
9501
- program2.command("runs:watch").argument("<runId>").option("--json", "emit event output as JSON").description("Stream a run until it completes").action(async (runId, options) => {
9502
- await watchRun(String(runId), Boolean(options.json));
9533
+ program2.command("runs:watch").argument("<runId>").option("--json", "emit event output as JSON").option("--timeout <duration>", "maximum watch duration, for example 30s, 10m, or 1h").description("Stream a run until it completes").action(async (runId, options) => {
9534
+ await watchRun(String(runId), Boolean(options.json), parseDurationMs(options.timeout));
9503
9535
  });
9504
9536
  program2.command("runs:usage").argument("<runId>").option("--summary", "print a human-readable cost summary instead of raw JSON").description("Fetch run usage summary").action(async (runId, options) => {
9505
9537
  const usage = await createClient(loadConfig()).runs.usage(String(runId));
@@ -9547,7 +9579,10 @@ program2.command("models:list").description("List exported models").action(async
9547
9579
  program2.command("models:export").argument("<modelId>").description("Fetch the export package path for a model").action(async (modelId) => {
9548
9580
  printJson(await createClient(loadConfig()).models.export(String(modelId)));
9549
9581
  });
9550
- program2.command("deployments:create").requiredOption("--model <modelId>").description("Create a deployment for a model").action(async (options) => {
9582
+ program2.command("deployments:list").description("List deployments").action(async () => {
9583
+ printJson(await createClient(loadConfig()).deployments.list());
9584
+ });
9585
+ program2.command("deployments:create").requiredOption("--model <modelId>").option("--project <projectId>", "accepted for consistency; deployment project is inferred from the model").description("Create a deployment for a model").action(async (options) => {
9551
9586
  printJson(await createClient(loadConfig()).deployments.create({ modelId: options.model }));
9552
9587
  });
9553
9588
  program2.command("deployments:get").argument("<deploymentId>").description("Fetch a deployment").action(async (deploymentId) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "trainfabric",
3
- "version": "0.1.10",
3
+ "version": "0.1.12",
4
4
  "description": "Trainfabric CLI for launching GPU training jobs on the hosted Trainfabric backend.",
5
5
  "type": "module",
6
6
  "main": "dist/index.cjs",