@denpex/sdk 0.8.0 → 0.8.2
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 +50 -49
- package/dist/client.d.ts +59 -6
- package/dist/client.js +17 -10
- package/dist/evidence.d.ts +4 -0
- package/dist/evidence.js +54 -0
- package/package.json +48 -48
package/README.md
CHANGED
|
@@ -1,49 +1,50 @@
|
|
|
1
|
-
# @denpex/sdk
|
|
2
|
-
|
|
3
|
-
TypeScript/JavaScript client for the [Denpex](https://denpex.com) API — diagnose GPU training
|
|
4
|
-
failures from logs, report fix outcomes, and check your plan quota. Zero runtime dependencies,
|
|
5
|
-
Node ≥ 18.
|
|
6
|
-
|
|
7
|
-
## Install
|
|
8
|
-
|
|
9
|
-
```bash
|
|
10
|
-
npm install @denpex/sdk
|
|
11
|
-
```
|
|
12
|
-
|
|
13
|
-
## Quick start
|
|
14
|
-
|
|
15
|
-
```ts
|
|
16
|
-
import { DenpexClient } from "@denpex/sdk";
|
|
17
|
-
|
|
18
|
-
const denpex = new DenpexClient({ apiKey: process.env.DENPEX_API_KEY! });
|
|
19
|
-
|
|
20
|
-
// Diagnose a training log
|
|
21
|
-
const result = await denpex.diagnose(logText, { jobName: "llama3-405b-pretrain" });
|
|
22
|
-
console.log(result.meta?.failureType, result.meta?.confidence);
|
|
23
|
-
console.log(result.fix?.summary);
|
|
24
|
-
console.log(result.fix?.action);
|
|
25
|
-
|
|
26
|
-
// Close the accuracy flywheel by reporting whether the fix worked
|
|
27
|
-
await denpex.feedback(result.diagnosisId, "worked");
|
|
28
|
-
|
|
29
|
-
// Check remaining headroom for the key's plan
|
|
30
|
-
const quota = await denpex.quota();
|
|
31
|
-
console.log(quota.quota);
|
|
32
|
-
```
|
|
33
|
-
|
|
34
|
-
Create an API key at <https://denpex.com/dashboard>. It is sent as the `X-Denpex-Key` header.
|
|
35
|
-
|
|
36
|
-
## API
|
|
37
|
-
|
|
38
|
-
| Method | Description |
|
|
39
|
-
|---|---|
|
|
40
|
-
| `new DenpexClient({ apiKey, baseUrl?, timeoutMs? })` | Construct a client. `baseUrl` defaults to `https://api.denpex.com`; the default 320-second timeout covers the server's 290-second deep path. |
|
|
41
|
-
| `diagnose(logs, opts?)` | `POST /api/diagnose` — returns the diagnosis (failure type, confidence, root cause, fix, evidence). |
|
|
42
|
-
| `
|
|
43
|
-
| `
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
1
|
+
# @denpex/sdk
|
|
2
|
+
|
|
3
|
+
TypeScript/JavaScript client for the [Denpex](https://denpex.com) API — diagnose GPU training
|
|
4
|
+
failures from logs, report fix outcomes, and check your plan quota. Zero runtime dependencies,
|
|
5
|
+
Node ≥ 18.
|
|
6
|
+
|
|
7
|
+
## Install
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npm install @denpex/sdk
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
## Quick start
|
|
14
|
+
|
|
15
|
+
```ts
|
|
16
|
+
import { DenpexClient } from "@denpex/sdk";
|
|
17
|
+
|
|
18
|
+
const denpex = new DenpexClient({ apiKey: process.env.DENPEX_API_KEY! });
|
|
19
|
+
|
|
20
|
+
// Diagnose a training log
|
|
21
|
+
const result = await denpex.diagnose(logText, { jobName: "llama3-405b-pretrain" });
|
|
22
|
+
console.log(result.meta?.failureType, result.meta?.confidence);
|
|
23
|
+
console.log(result.fix?.summary);
|
|
24
|
+
console.log(result.fix?.action);
|
|
25
|
+
|
|
26
|
+
// Close the accuracy flywheel by reporting whether the fix worked
|
|
27
|
+
await denpex.feedback(result.diagnosisId, "worked");
|
|
28
|
+
|
|
29
|
+
// Check remaining headroom for the key's plan
|
|
30
|
+
const quota = await denpex.quota();
|
|
31
|
+
console.log(quota.quota);
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
Create an API key at <https://denpex.com/dashboard>. It is sent as the `X-Denpex-Key` header.
|
|
35
|
+
|
|
36
|
+
## API
|
|
37
|
+
|
|
38
|
+
| Method | Description |
|
|
39
|
+
|---|---|
|
|
40
|
+
| `new DenpexClient({ apiKey, baseUrl?, timeoutMs? })` | Construct a client. `baseUrl` defaults to `https://api.denpex.com`; the default 320-second timeout covers the server's 290-second deep path. |
|
|
41
|
+
| `diagnose(logs, opts?)` | `POST /api/diagnose` — returns the diagnosis (failure type, confidence, root cause, fix, evidence). |
|
|
42
|
+
| `refine(logs, operatorAnswers, opts?)` | Re-run the same canonical diagnosis with typed answers from `clarifyingChoices`. Send the full answer history; action selections become evidence requests, not evidence. |
|
|
43
|
+
| `feedback(diagnosisId, outcome, note?)` | `POST /api/diagnose/feedback` — `outcome` is `"worked"` or `"did_not_work"`. |
|
|
44
|
+
| `quota()` | `GET /api/diagnose/quota` — remaining diagnoses for the key's plan. |
|
|
45
|
+
|
|
46
|
+
Errors throw `DenpexError` with the HTTP status and server message.
|
|
47
|
+
|
|
48
|
+
## License
|
|
49
|
+
|
|
50
|
+
Proprietary. © Denpex. Use of this SDK is governed by your Denpex subscription agreement.
|
package/dist/client.d.ts
CHANGED
|
@@ -4,7 +4,7 @@ export interface DenpexClientOptions {
|
|
|
4
4
|
baseUrl?: string;
|
|
5
5
|
/** Override fetch (tests, custom agents). Defaults to globalThis.fetch. */
|
|
6
6
|
fetchImpl?: typeof fetch;
|
|
7
|
-
/** Per-request timeout in ms (AbortController). Default 320s
|
|
7
|
+
/** Per-request timeout in ms (AbortController). Default 320s. The server deep-path ceiling is 290s. */
|
|
8
8
|
timeoutMs?: number;
|
|
9
9
|
}
|
|
10
10
|
export interface DiagnoseOptions {
|
|
@@ -18,18 +18,27 @@ export interface DiagnoseOptions {
|
|
|
18
18
|
codeContext?: Record<string, unknown>;
|
|
19
19
|
/** Client-side signature matches (e.g. from denpex_lite) so Tier 0 starts from evidence. */
|
|
20
20
|
signatures?: unknown;
|
|
21
|
+
/** Prior clarification answers. Keep these typed and outside `logs`. */
|
|
22
|
+
operatorAnswers?: OperatorAnswerInput[];
|
|
23
|
+
}
|
|
24
|
+
export interface OperatorAnswerInput {
|
|
25
|
+
questionId?: string;
|
|
26
|
+
optionId?: string;
|
|
27
|
+
kind?: 'fact' | 'action';
|
|
28
|
+
question?: string;
|
|
29
|
+
answer: string;
|
|
21
30
|
}
|
|
22
31
|
export interface DiagnoseMeta {
|
|
23
32
|
failureType?: string;
|
|
24
33
|
confidence?: number;
|
|
25
34
|
source?: string;
|
|
26
35
|
tier?: number;
|
|
27
|
-
/** Engine build stamp
|
|
36
|
+
/** Engine build stamp. Compare across surfaces to detect a stale deploy. */
|
|
28
37
|
engineVersion?: string;
|
|
29
38
|
}
|
|
30
39
|
/**
|
|
31
40
|
* The known response fields. The engine attaches additional sections as it
|
|
32
|
-
* grows (forensics, advisories, execution plans)
|
|
41
|
+
* grows (forensics, advisories, execution plans). They pass through untyped
|
|
33
42
|
* rather than being silently dropped, so SDK users always receive everything
|
|
34
43
|
* the API returned.
|
|
35
44
|
*/
|
|
@@ -42,7 +51,7 @@ export interface DiagnoseMeta {
|
|
|
42
51
|
* few lines, so treat the node as the stronger signal of the two.
|
|
43
52
|
*
|
|
44
53
|
* `analyzedLines` < `totalLines` means the paste exceeded the window the engine
|
|
45
|
-
* reads
|
|
54
|
+
* reads. The verdict covers only what was analysed.
|
|
46
55
|
*/
|
|
47
56
|
export interface DiagnoseInitiator {
|
|
48
57
|
rank?: number | null;
|
|
@@ -52,11 +61,53 @@ export interface DiagnoseInitiator {
|
|
|
52
61
|
totalLines?: number | null;
|
|
53
62
|
analyzedLines?: number | null;
|
|
54
63
|
}
|
|
64
|
+
export interface ClarifyingOption {
|
|
65
|
+
id?: string;
|
|
66
|
+
label?: string;
|
|
67
|
+
detail?: string;
|
|
68
|
+
/**
|
|
69
|
+
* Present only on an `action` question. The engine never recommends an answer to a
|
|
70
|
+
* question of fact: a recommendation there returns the answer that was hinted at
|
|
71
|
+
* rather than the one that happened, and the next verdict is built on an
|
|
72
|
+
* observation nobody made. Render this marker only when `kind === 'action'`.
|
|
73
|
+
*/
|
|
74
|
+
recommended?: boolean;
|
|
75
|
+
/** Exact evidence command represented by this option on an action question. */
|
|
76
|
+
command?: string;
|
|
77
|
+
}
|
|
78
|
+
export interface ClarifyingQuestion {
|
|
79
|
+
id?: string;
|
|
80
|
+
/** `fact` = what the operator observed; `action` = what they could run next. */
|
|
81
|
+
kind?: 'fact' | 'action';
|
|
82
|
+
question?: string;
|
|
83
|
+
options?: ClarifyingOption[];
|
|
84
|
+
allowOther?: boolean;
|
|
85
|
+
/** The exact command behind the recommended option, on `action` questions. */
|
|
86
|
+
command?: string;
|
|
87
|
+
}
|
|
55
88
|
export interface DiagnoseResponse {
|
|
56
89
|
fix?: {
|
|
57
90
|
summary?: string;
|
|
58
91
|
action?: string;
|
|
59
92
|
evidence?: unknown[];
|
|
93
|
+
/**
|
|
94
|
+
* Set when the engine declined to name one cause and is asking for evidence
|
|
95
|
+
* instead. Answer with the option ids to get a sharper diagnosis. `inviteFollowup`
|
|
96
|
+
* is the flag that says this happened.
|
|
97
|
+
*/
|
|
98
|
+
clarifyingChoices?: ClarifyingQuestion[];
|
|
99
|
+
/** Plain-text form of the same questions, for older callers. */
|
|
100
|
+
clarifyingQuestions?: string[];
|
|
101
|
+
inviteFollowup?: boolean;
|
|
102
|
+
evidenceRequests?: Array<{
|
|
103
|
+
questionId: string;
|
|
104
|
+
optionId: string;
|
|
105
|
+
label: string;
|
|
106
|
+
command: string;
|
|
107
|
+
why?: string;
|
|
108
|
+
pasteBack?: string;
|
|
109
|
+
}>;
|
|
110
|
+
awaitingEvidence?: boolean;
|
|
60
111
|
[k: string]: unknown;
|
|
61
112
|
};
|
|
62
113
|
meta?: DiagnoseMeta;
|
|
@@ -88,9 +139,11 @@ export declare class DenpexClient {
|
|
|
88
139
|
private readonly fetchImpl;
|
|
89
140
|
private readonly timeoutMs;
|
|
90
141
|
constructor(options: DenpexClientOptions);
|
|
91
|
-
/** Diagnose a training failure from raw logs
|
|
142
|
+
/** Diagnose a training failure from raw logs. Oversized input is evidence-selected. */
|
|
92
143
|
diagnose(logs: string, opts?: DiagnoseOptions): Promise<DiagnoseResponse>;
|
|
93
|
-
/**
|
|
144
|
+
/** Re-run the canonical diagnosis with observed facts or a selected evidence check. */
|
|
145
|
+
refine(logs: string, operatorAnswers: OperatorAnswerInput[], opts?: Omit<DiagnoseOptions, 'operatorAnswers'>): Promise<DiagnoseResponse>;
|
|
146
|
+
/** Report whether a diagnosis worked. This feedback directly improves future priors. */
|
|
94
147
|
feedback(diagnosisId: string, outcome: FeedbackOutcome, note?: string): Promise<Record<string, unknown>>;
|
|
95
148
|
/** Remaining diagnosis headroom for this key's plan. */
|
|
96
149
|
quota(): Promise<QuotaResponse>;
|
package/dist/client.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
// @denpex/sdk
|
|
2
|
+
// @denpex/sdk: TypeScript client for the Denpex public API.
|
|
3
3
|
//
|
|
4
4
|
// Rewritten 2026-07-20: the previous file was a stub for /v1/{tenant}/incidents
|
|
5
5
|
// routes that do not exist in the api-worker. This client targets the REAL
|
|
@@ -15,6 +15,7 @@
|
|
|
15
15
|
// Zero dependencies. Requires global fetch (Node >= 18 or any browser/worker).
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
17
|
exports.default = exports.DenpexClient = exports.DenpexError = void 0;
|
|
18
|
+
const evidence_1 = require("./evidence");
|
|
18
19
|
class DenpexError extends Error {
|
|
19
20
|
constructor(message, status,
|
|
20
21
|
/** Machine-readable code when the API provides one (e.g. AUTH_REQUIRED, GPU_LIMIT_EXCEEDED). */
|
|
@@ -26,7 +27,7 @@ class DenpexError extends Error {
|
|
|
26
27
|
}
|
|
27
28
|
}
|
|
28
29
|
exports.DenpexError = DenpexError;
|
|
29
|
-
const MIN_LOG_CHARS =
|
|
30
|
+
const MIN_LOG_CHARS = 6;
|
|
30
31
|
const MAX_LOG_CHARS = 256000;
|
|
31
32
|
class DenpexClient {
|
|
32
33
|
constructor(options) {
|
|
@@ -37,19 +38,21 @@ class DenpexClient {
|
|
|
37
38
|
this.fetchImpl = options.fetchImpl ?? globalThis.fetch;
|
|
38
39
|
this.timeoutMs = options.timeoutMs ?? 320000;
|
|
39
40
|
if (!this.fetchImpl)
|
|
40
|
-
throw new Error('DenpexClient: global fetch not found
|
|
41
|
+
throw new Error('DenpexClient: global fetch not found. Node >= 18 required, or pass fetchImpl');
|
|
41
42
|
}
|
|
42
|
-
/** Diagnose a training failure from raw logs
|
|
43
|
+
/** Diagnose a training failure from raw logs. Oversized input is evidence-selected. */
|
|
43
44
|
async diagnose(logs, opts = {}) {
|
|
44
45
|
if (typeof logs !== 'string' || logs.length < MIN_LOG_CHARS) {
|
|
45
46
|
throw new DenpexError(`logs must be at least ${MIN_LOG_CHARS} characters`, 400);
|
|
46
47
|
}
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
48
|
+
const selected = (0, evidence_1.selectEvidence)(logs, MAX_LOG_CHARS);
|
|
49
|
+
return this.request('POST', '/api/diagnose', { logs: selected.text, ...opts });
|
|
50
|
+
}
|
|
51
|
+
/** Re-run the canonical diagnosis with observed facts or a selected evidence check. */
|
|
52
|
+
async refine(logs, operatorAnswers, opts = {}) {
|
|
53
|
+
return this.diagnose(logs, { ...opts, operatorAnswers });
|
|
51
54
|
}
|
|
52
|
-
/** Report whether a diagnosis worked
|
|
55
|
+
/** Report whether a diagnosis worked. This feedback directly improves future priors. */
|
|
53
56
|
async feedback(diagnosisId, outcome, note) {
|
|
54
57
|
if (!diagnosisId)
|
|
55
58
|
throw new DenpexError('diagnosisId required', 400);
|
|
@@ -79,7 +82,11 @@ class DenpexClient {
|
|
|
79
82
|
}
|
|
80
83
|
catch { /* non-JSON error body */ }
|
|
81
84
|
if (!res.ok) {
|
|
82
|
-
const message = typeof json.
|
|
85
|
+
const message = typeof json.guidance === 'string'
|
|
86
|
+
? json.guidance
|
|
87
|
+
: typeof json.error === 'string'
|
|
88
|
+
? json.error
|
|
89
|
+
: `Denpex API error (status ${res.status})`;
|
|
83
90
|
throw new DenpexError(message, res.status, typeof json.code === 'string' ? json.code : undefined);
|
|
84
91
|
}
|
|
85
92
|
return json;
|
package/dist/evidence.js
ADDED
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.selectEvidence = selectEvidence;
|
|
4
|
+
const EVIDENCE_RE = /error|fail|fatal|traceback|exception|assert|panic|segfault|xid|nvrm|ecc|fallen off the bus|nccl|cuda|oom|out of memory|timeout|nan\b|\binf\b|node_fail|killed|terminated|version|driver|kernel|container|slurm|kubernetes|rank|node|host|gpu|pci|topology|nvlink|nvswitch|infiniband|rdma|roce/i;
|
|
5
|
+
const CAUSAL_RE = /fatal|critical|traceback|exception|assert|panic|segfault|xid|uncorrectable|fallen off the bus|out of memory|watchdog timeout|crc mismatch|loss\s*=\s*(?:nan|inf)|insufficient|unhealthy|ibv_modify_qp|no space left|compil(?:e|ation) (?:error|failed)|no available memory|checksum mismatch|childfailederror|backendcompilerfailed|failedscheduling|input\/output error|nonfinite|divergence|first failure|initiator|caused by/i;
|
|
6
|
+
const MAX_LINE_CHARS = 2000;
|
|
7
|
+
function clipLine(line) {
|
|
8
|
+
if (line.length <= MAX_LINE_CHARS)
|
|
9
|
+
return line;
|
|
10
|
+
const marker = ' [line clipped by Denpex] ';
|
|
11
|
+
const side = Math.max(1, Math.floor((MAX_LINE_CHARS - marker.length) / 2));
|
|
12
|
+
return `${line.slice(0, side)}${marker}${line.slice(-side)}`.slice(0, MAX_LINE_CHARS);
|
|
13
|
+
}
|
|
14
|
+
function selectEvidence(logs, max) {
|
|
15
|
+
if (logs.length <= max)
|
|
16
|
+
return { text: logs, truncated: false };
|
|
17
|
+
const lines = logs.split(/\r?\n/);
|
|
18
|
+
const candidates = new Map();
|
|
19
|
+
const add = (index, radius, priority) => {
|
|
20
|
+
for (let i = Math.max(0, index - radius); i <= Math.min(lines.length - 1, index + radius); i++) {
|
|
21
|
+
candidates.set(i, Math.max(priority, candidates.get(i) ?? 0));
|
|
22
|
+
}
|
|
23
|
+
};
|
|
24
|
+
for (let i = 0; i < Math.min(48, lines.length); i++)
|
|
25
|
+
candidates.set(i, 300);
|
|
26
|
+
for (let i = Math.max(0, lines.length - 96); i < lines.length; i++)
|
|
27
|
+
candidates.set(i, 800);
|
|
28
|
+
let foundFirst = false;
|
|
29
|
+
for (let i = 0; i < lines.length; i++) {
|
|
30
|
+
const line = lines[i] ?? '';
|
|
31
|
+
if (!EVIDENCE_RE.test(line))
|
|
32
|
+
continue;
|
|
33
|
+
const causal = CAUSAL_RE.test(line);
|
|
34
|
+
add(i, causal ? 3 : 1, causal ? 1000 : 700);
|
|
35
|
+
if (!foundFirst) {
|
|
36
|
+
add(i, 6, 1100);
|
|
37
|
+
foundFirst = true;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
const warning = `[Denpex condensed input: input exceeded ${max.toLocaleString()} characters. Environment, causal, rank, topology, middle, and final-tail evidence were selected.]`;
|
|
41
|
+
let used = warning.length;
|
|
42
|
+
const selected = new Set();
|
|
43
|
+
for (const [index] of [...candidates].sort((a, b) => b[1] - a[1] || a[0] - b[0])) {
|
|
44
|
+
const line = clipLine(lines[index] ?? '');
|
|
45
|
+
if (used + line.length + 1 > max)
|
|
46
|
+
continue;
|
|
47
|
+
selected.add(index);
|
|
48
|
+
used += line.length + 1;
|
|
49
|
+
}
|
|
50
|
+
return {
|
|
51
|
+
text: [warning, ...[...selected].sort((a, b) => a - b).map((index) => clipLine(lines[index] ?? ''))].join('\n'),
|
|
52
|
+
truncated: true,
|
|
53
|
+
};
|
|
54
|
+
}
|
package/package.json
CHANGED
|
@@ -1,48 +1,48 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@denpex/sdk",
|
|
3
|
-
"version": "0.8.
|
|
4
|
-
"description": "TypeScript client for the Denpex API
|
|
5
|
-
"keywords": [
|
|
6
|
-
"denpex",
|
|
7
|
-
"gpu",
|
|
8
|
-
"ml-training",
|
|
9
|
-
"distributed-training",
|
|
10
|
-
"diagnosis",
|
|
11
|
-
"nccl",
|
|
12
|
-
"cuda",
|
|
13
|
-
"observability",
|
|
14
|
-
"sdk"
|
|
15
|
-
],
|
|
16
|
-
"homepage": "https://denpex.com",
|
|
17
|
-
"repository": {
|
|
18
|
-
"type": "git",
|
|
19
|
-
"url": "git+https://github.com/MisaMisaAI/Denpex.git",
|
|
20
|
-
"directory": "denpex-sdk-ts"
|
|
21
|
-
},
|
|
22
|
-
"bugs": {
|
|
23
|
-
"url": "https://denpex.com/contact"
|
|
24
|
-
},
|
|
25
|
-
"license": "Proprietary",
|
|
26
|
-
"main": "dist/client.js",
|
|
27
|
-
"types": "dist/client.d.ts",
|
|
28
|
-
"files": [
|
|
29
|
-
"dist",
|
|
30
|
-
"README.md"
|
|
31
|
-
],
|
|
32
|
-
"engines": {
|
|
33
|
-
"node": ">=18"
|
|
34
|
-
},
|
|
35
|
-
"publishConfig": {
|
|
36
|
-
"access": "public"
|
|
37
|
-
},
|
|
38
|
-
"scripts": {
|
|
39
|
-
"build": "tsc -p tsconfig.json",
|
|
40
|
-
"prepublishOnly": "npm run build",
|
|
41
|
-
"test": "tsx --test tests/client.test.ts"
|
|
42
|
-
},
|
|
43
|
-
"devDependencies": {
|
|
44
|
-
"typescript": "^5.0.0",
|
|
45
|
-
"@types/node": "^20.0.0",
|
|
46
|
-
"tsx": "^4.23.1"
|
|
47
|
-
}
|
|
48
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "@denpex/sdk",
|
|
3
|
+
"version": "0.8.2",
|
|
4
|
+
"description": "TypeScript client for the Denpex API : diagnose GPU training failures from logs (POST /api/diagnose), report fix outcomes, check quota. Zero dependencies, Node >= 18.",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"denpex",
|
|
7
|
+
"gpu",
|
|
8
|
+
"ml-training",
|
|
9
|
+
"distributed-training",
|
|
10
|
+
"diagnosis",
|
|
11
|
+
"nccl",
|
|
12
|
+
"cuda",
|
|
13
|
+
"observability",
|
|
14
|
+
"sdk"
|
|
15
|
+
],
|
|
16
|
+
"homepage": "https://denpex.com",
|
|
17
|
+
"repository": {
|
|
18
|
+
"type": "git",
|
|
19
|
+
"url": "git+https://github.com/MisaMisaAI/Denpex.git",
|
|
20
|
+
"directory": "denpex-sdk-ts"
|
|
21
|
+
},
|
|
22
|
+
"bugs": {
|
|
23
|
+
"url": "https://denpex.com/contact"
|
|
24
|
+
},
|
|
25
|
+
"license": "Proprietary",
|
|
26
|
+
"main": "dist/client.js",
|
|
27
|
+
"types": "dist/client.d.ts",
|
|
28
|
+
"files": [
|
|
29
|
+
"dist",
|
|
30
|
+
"README.md"
|
|
31
|
+
],
|
|
32
|
+
"engines": {
|
|
33
|
+
"node": ">=18"
|
|
34
|
+
},
|
|
35
|
+
"publishConfig": {
|
|
36
|
+
"access": "public"
|
|
37
|
+
},
|
|
38
|
+
"scripts": {
|
|
39
|
+
"build": "tsc -p tsconfig.json",
|
|
40
|
+
"prepublishOnly": "npm run build",
|
|
41
|
+
"test": "tsx --test tests/client.test.ts"
|
|
42
|
+
},
|
|
43
|
+
"devDependencies": {
|
|
44
|
+
"typescript": "^5.0.0",
|
|
45
|
+
"@types/node": "^20.0.0",
|
|
46
|
+
"tsx": "^4.23.1"
|
|
47
|
+
}
|
|
48
|
+
}
|