@fastino-ai/pioneer-cli 0.2.9 → 0.2.10
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 +21 -12
- package/package.json +1 -1
- package/src/api.ts +108 -7
- package/src/index.tsx +1625 -711
package/README.md
CHANGED
|
@@ -59,26 +59,37 @@ pioneer agent --mode research # Research mode (Pro subscri
|
|
|
59
59
|
pioneer job list
|
|
60
60
|
pioneer job get <id>
|
|
61
61
|
pioneer job logs <id>
|
|
62
|
-
pioneer job
|
|
62
|
+
pioneer job delete <id>
|
|
63
|
+
# To create a training job, use the agent — it will help you pick a base model
|
|
64
|
+
# and datasets conversationally:
|
|
65
|
+
pioneer agent
|
|
63
66
|
|
|
64
67
|
# Models
|
|
65
|
-
pioneer model
|
|
68
|
+
pioneer model base-models # List available base models (tabular)
|
|
69
|
+
pioneer model endpoints list # List model catalog entries
|
|
66
70
|
pioneer model endpoints create # Create a model entry (interactive by default)
|
|
67
71
|
pioneer model endpoints create --model "qwen/Qwen3-8B-Instruct" --repo https://github.com/fastino-ai/Pioneer
|
|
68
|
-
pioneer model endpoints get <model-id>
|
|
72
|
+
pioneer model endpoints get <model-id> # Endpoint details (incl. attached dataset count)
|
|
69
73
|
pioneer model endpoints update <model-id> --description "Updated model metadata"
|
|
70
74
|
pioneer model endpoints delete <model-id>
|
|
71
|
-
pioneer model endpoints dataset-count <model-id>
|
|
72
75
|
pioneer model endpoints quality-metrics <model-id>
|
|
73
|
-
pioneer model endpoints deploy <model-id> --job <training-job-id> [--reason "..." ]
|
|
76
|
+
pioneer model endpoints deploy <model-id> [--job <training-job-id>] [--reason "..." ] [--all]
|
|
77
|
+
# If --job is omitted, pick from a list of deployable jobs interactively.
|
|
78
|
+
# The list is filtered to jobs whose base model matches the endpoint; pass --all to bypass that filter.
|
|
74
79
|
pioneer model endpoints rollback <model-id> <deployment-id>
|
|
75
80
|
|
|
76
81
|
pioneer model artifacts list # List trained and deployed artifacts
|
|
77
82
|
pioneer model artifacts trained # List trained artifacts
|
|
78
83
|
pioneer model artifacts deployed # List deployed artifacts
|
|
79
|
-
pioneer model artifacts download <job-id>
|
|
84
|
+
pioneer model artifacts download <job-id> # Get a signed download URL for the artifact
|
|
80
85
|
pioneer model artifacts upload <job-id> --to hf --repo username/model # Push trained artifact to HF
|
|
81
86
|
|
|
87
|
+
# Datasets
|
|
88
|
+
pioneer dataset list # List remote + local datasets (tabular)
|
|
89
|
+
pioneer dataset get <name[:version]> # Dataset details (key/value layout)
|
|
90
|
+
|
|
91
|
+
# Most read commands also accept --json for the raw JSON payload.
|
|
92
|
+
|
|
82
93
|
# Aliases
|
|
83
94
|
pioneer model_endpoints list
|
|
84
95
|
pioneer model_artifacts list
|
|
@@ -129,14 +140,12 @@ pioneer agent
|
|
|
129
140
|
|
|
130
141
|
### Step 3: Create a Training Job
|
|
131
142
|
|
|
132
|
-
|
|
143
|
+
Use `pioneer agent` to create a training job. The agent will guide you through
|
|
144
|
+
picking a base model, selecting datasets, and configuring hyperparameters
|
|
145
|
+
without needing to remember flags or dataset IDs:
|
|
133
146
|
|
|
134
147
|
```bash
|
|
135
|
-
pioneer
|
|
136
|
-
--model-name "Medical NER Model v1" \
|
|
137
|
-
--dataset-ids "<dataset-id>" \
|
|
138
|
-
--base-model "fastino/gliner2-base-v1" \
|
|
139
|
-
--epochs 10
|
|
148
|
+
pioneer agent
|
|
140
149
|
```
|
|
141
150
|
|
|
142
151
|
### Step 4: Monitor Training Progress
|
package/package.json
CHANGED
package/src/api.ts
CHANGED
|
@@ -1271,10 +1271,12 @@ export interface TrainingJobListResponse {
|
|
|
1271
1271
|
}
|
|
1272
1272
|
|
|
1273
1273
|
export async function listJobs(
|
|
1274
|
-
options: { status?: string } = {}
|
|
1274
|
+
options: { status?: string; project_id?: string; limit?: number } = {}
|
|
1275
1275
|
): Promise<ApiResult<TrainingJobListResponse>> {
|
|
1276
1276
|
const params = new URLSearchParams();
|
|
1277
1277
|
if (options.status) params.set("status", options.status);
|
|
1278
|
+
if (options.project_id) params.set("project_id", options.project_id);
|
|
1279
|
+
if (options.limit !== undefined) params.set("limit", String(options.limit));
|
|
1278
1280
|
const query = params.toString();
|
|
1279
1281
|
const url = query ? `/felix/training-jobs?${query}` : "/felix/training-jobs";
|
|
1280
1282
|
return request<TrainingJobListResponse>("GET", url);
|
|
@@ -1284,6 +1286,25 @@ export async function getJob(jobId: string): Promise<ApiResult<TrainingJob>> {
|
|
|
1284
1286
|
return request<TrainingJob>("GET", `/felix/training-jobs/${jobId}`);
|
|
1285
1287
|
}
|
|
1286
1288
|
|
|
1289
|
+
/**
|
|
1290
|
+
* Assign (or unassign) a training job to a project. The deploy endpoint
|
|
1291
|
+
* (`POST /projects/{id}/deployments`) requires the job's `project_id` to
|
|
1292
|
+
* match the target project, so callers typically PATCH this before deploy.
|
|
1293
|
+
*
|
|
1294
|
+
* @param jobId Training job UUID.
|
|
1295
|
+
* @param projectId Project UUID to attach to, or `null` to unassign.
|
|
1296
|
+
*/
|
|
1297
|
+
export async function updateTrainingJob(
|
|
1298
|
+
jobId: string,
|
|
1299
|
+
body: { project_id: string | null }
|
|
1300
|
+
): Promise<ApiResult<{ success?: boolean; message?: string }>> {
|
|
1301
|
+
return request<{ success?: boolean; message?: string }>(
|
|
1302
|
+
"PATCH",
|
|
1303
|
+
`/felix/training-jobs/${jobId}`,
|
|
1304
|
+
body
|
|
1305
|
+
);
|
|
1306
|
+
}
|
|
1307
|
+
|
|
1287
1308
|
export interface TrainingJobCreateRequest {
|
|
1288
1309
|
model_name: string;
|
|
1289
1310
|
datasets: DatasetRef[];
|
|
@@ -1457,6 +1478,24 @@ export interface DeployedModelsListResponse {
|
|
|
1457
1478
|
count: number;
|
|
1458
1479
|
}
|
|
1459
1480
|
|
|
1481
|
+
interface AnthropicCompatibleModelEntry {
|
|
1482
|
+
id?: string;
|
|
1483
|
+
display_name?: string;
|
|
1484
|
+
type?: string;
|
|
1485
|
+
created_at?: string | null;
|
|
1486
|
+
created?: number;
|
|
1487
|
+
owned_by?: string;
|
|
1488
|
+
}
|
|
1489
|
+
|
|
1490
|
+
interface AnthropicCompatibleModelsResponse {
|
|
1491
|
+
data?: AnthropicCompatibleModelEntry[];
|
|
1492
|
+
}
|
|
1493
|
+
|
|
1494
|
+
function isLikelyJobId(value: unknown): value is string {
|
|
1495
|
+
if (typeof value !== "string") return false;
|
|
1496
|
+
return /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(value);
|
|
1497
|
+
}
|
|
1498
|
+
|
|
1460
1499
|
export async function listModels(
|
|
1461
1500
|
options: { includeBase?: boolean } = {}
|
|
1462
1501
|
): Promise<ApiResult<DeployedModelsListResponse>> {
|
|
@@ -1465,8 +1504,49 @@ export async function listModels(
|
|
|
1465
1504
|
params.set("include_base", String(options.includeBase));
|
|
1466
1505
|
}
|
|
1467
1506
|
const query = params.toString();
|
|
1468
|
-
const
|
|
1469
|
-
|
|
1507
|
+
const legacyUrl = query ? `/felix/models?${query}` : "/felix/models";
|
|
1508
|
+
const legacy = await request<DeployedModelsListResponse>("GET", legacyUrl);
|
|
1509
|
+
if (legacy.ok || legacy.status !== 404) {
|
|
1510
|
+
return legacy;
|
|
1511
|
+
}
|
|
1512
|
+
|
|
1513
|
+
// Backend removed /felix/models. Fall back to the canonical
|
|
1514
|
+
// Anthropic/OpenAI-compatible catalog and adapt to DeployedModel.
|
|
1515
|
+
const fallback = await request<AnthropicCompatibleModelsResponse>("GET", "/v1/models");
|
|
1516
|
+
if (!fallback.ok) {
|
|
1517
|
+
return {
|
|
1518
|
+
ok: false,
|
|
1519
|
+
status: fallback.status,
|
|
1520
|
+
error: fallback.error ?? "Failed to list deployed models.",
|
|
1521
|
+
};
|
|
1522
|
+
}
|
|
1523
|
+
const entries = fallback.data?.data ?? [];
|
|
1524
|
+
const models: DeployedModel[] = entries
|
|
1525
|
+
.filter((entry) => entry && (options.includeBase || entry.owned_by !== "anthropic"))
|
|
1526
|
+
.map((entry) => {
|
|
1527
|
+
const id = typeof entry.id === "string" ? entry.id : "";
|
|
1528
|
+
return {
|
|
1529
|
+
id,
|
|
1530
|
+
job_id: isLikelyJobId(id) ? id : null,
|
|
1531
|
+
model_name: entry.display_name || id || undefined,
|
|
1532
|
+
is_base_model: entry.owned_by === "anthropic" || entry.owned_by === "openai",
|
|
1533
|
+
deployed_at: entry.created_at ?? null,
|
|
1534
|
+
last_used_at: null,
|
|
1535
|
+
invocation_count: 0,
|
|
1536
|
+
created_at: entry.created_at ?? null,
|
|
1537
|
+
updated_at: entry.created_at ?? null,
|
|
1538
|
+
};
|
|
1539
|
+
});
|
|
1540
|
+
|
|
1541
|
+
return {
|
|
1542
|
+
ok: true,
|
|
1543
|
+
status: fallback.status,
|
|
1544
|
+
data: {
|
|
1545
|
+
success: true,
|
|
1546
|
+
models,
|
|
1547
|
+
count: models.length,
|
|
1548
|
+
},
|
|
1549
|
+
};
|
|
1470
1550
|
}
|
|
1471
1551
|
|
|
1472
1552
|
export async function deleteModel(jobId: string): Promise<ApiResult> {
|
|
@@ -1678,12 +1758,20 @@ export interface BaseModelInfo {
|
|
|
1678
1758
|
id: string;
|
|
1679
1759
|
name?: string;
|
|
1680
1760
|
label?: string;
|
|
1681
|
-
|
|
1761
|
+
/**
|
|
1762
|
+
* One of "encoder" | "decoder" — the architectural family of the model.
|
|
1763
|
+
* Note: backend used to expose this as `type`; the field is now `task_type`.
|
|
1764
|
+
*/
|
|
1682
1765
|
task_type?: string;
|
|
1683
1766
|
supports_inference?: boolean;
|
|
1684
1767
|
supports_on_demand_inference?: boolean;
|
|
1685
1768
|
supports_training?: boolean;
|
|
1686
1769
|
description?: string;
|
|
1770
|
+
tier?: "enterprise" | "open" | string;
|
|
1771
|
+
context_window?: number;
|
|
1772
|
+
license?: string;
|
|
1773
|
+
input_price_per_million?: number;
|
|
1774
|
+
output_price_per_million?: number;
|
|
1687
1775
|
}
|
|
1688
1776
|
|
|
1689
1777
|
export interface BaseModelsResponse {
|
|
@@ -2820,10 +2908,23 @@ export interface ProjectDeploymentCreate {
|
|
|
2820
2908
|
}
|
|
2821
2909
|
|
|
2822
2910
|
export interface ProjectDeploymentResponse {
|
|
2823
|
-
|
|
2824
|
-
|
|
2911
|
+
/** Deployment record id. */
|
|
2912
|
+
id?: string;
|
|
2825
2913
|
project_id?: string;
|
|
2826
|
-
|
|
2914
|
+
/** Set when a fine-tuned checkpoint was deployed. */
|
|
2915
|
+
training_job_id?: string | null;
|
|
2916
|
+
/**
|
|
2917
|
+
* Set to the stock HuggingFace base model id when a base-model deploy was
|
|
2918
|
+
* performed. May also be populated for training-job deploys (post backend
|
|
2919
|
+
* enrichment) so the record always carries "what stock model is serving".
|
|
2920
|
+
*/
|
|
2921
|
+
base_model?: string | null;
|
|
2922
|
+
deployed_by?: string;
|
|
2923
|
+
reason?: string;
|
|
2924
|
+
deployed_at?: string;
|
|
2925
|
+
// Legacy/optional fields kept for older response shapes.
|
|
2926
|
+
success?: boolean;
|
|
2927
|
+
message?: string;
|
|
2827
2928
|
deployment_id?: string;
|
|
2828
2929
|
}
|
|
2829
2930
|
|