@ricsam/r5dctl 0.0.27 → 0.0.28
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 +6 -0
- package/dist/cjs/cli.cjs +89 -4
- package/dist/cjs/package.json +1 -1
- package/dist/mjs/cli.mjs +86 -4
- package/dist/mjs/package.json +1 -1
- package/dist/types/cli.d.ts +4 -1
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -63,6 +63,10 @@ r5dctl -s <session-id> conversation --raw # raw JSON message/tool p
|
|
|
63
63
|
r5dctl -s <session-id> conversation --tools # include provider-shaped tool definitions
|
|
64
64
|
r5dctl -s <session-id> conversation --system # include system prompt messages
|
|
65
65
|
r5dctl -s <session-id> conversation --raw --tools --system # exact raw agent request transcript
|
|
66
|
+
r5dctl conversation overview <session-id> # dialogue/thinking with tool work omitted
|
|
67
|
+
r5dctl conversation inspect-work <session-id> <work-id> # compact call list for one omitted turn
|
|
68
|
+
r5dctl conversation inspect-work <session-id> <work-id> --summary
|
|
69
|
+
r5dctl conversation inspect-work <session-id> <work-id> --full
|
|
66
70
|
r5dctl -s <session-id> prompt --mode plan --model max "..."
|
|
67
71
|
r5dctl -s <session-id> answer-questions -a1 "Recipe Collection" -a2 "Both Manual & AI"
|
|
68
72
|
r5dctl -s <session-id> apply-required-envs -e KEY=value
|
|
@@ -86,6 +90,8 @@ Conversation output is human-readable by default and excludes both the system pr
|
|
|
86
90
|
|
|
87
91
|
When available, conversation rendering uses the newest complete persisted model-request snapshot on the active conversation branch, so its mode, tier, model, thinking mode, tools, and messages reflect the request that actually ran. Legacy or empty sessions without snapshots fall back to reconstruction from the latest conversation context.
|
|
88
92
|
|
|
93
|
+
`conversation overview` is a deterministic active-branch projection for continuing work in another session. It keeps user messages, injected context, assistant thinking/commentary/final responses, and user decisions, while replacing each turn's tool batches with a stable work ID and numbered call ranges. Use `conversation inspect-work` with that session and work ID to inspect the omitted calls. Inspection is compact by default; `--summary` adds bounded targets/outcomes and `--full` renders persisted inputs and results with the normal tool renderers. The explicit `--compact`, `--summary`, and `--full` flags are mutually exclusive. Compact and summary output are designed to be narrowed with `grep`, `head`, `tail`, `sed`, or `cat -n`.
|
|
94
|
+
|
|
89
95
|
Project mode is derived from the persisted `backwardsCompatible` project setting:
|
|
90
96
|
|
|
91
97
|
- `greenfield`: agent can make breaking/reset-style changes
|
package/dist/cjs/cli.cjs
CHANGED
|
@@ -34,6 +34,7 @@ __export(cli_exports, {
|
|
|
34
34
|
main: () => main,
|
|
35
35
|
parseAnswerFlags: () => parseAnswerFlags,
|
|
36
36
|
parseConversationRenderArgs: () => parseConversationRenderArgs,
|
|
37
|
+
parseConversationWorkDetailArgs: () => parseConversationWorkDetailArgs,
|
|
37
38
|
parseEnvFlags: () => parseEnvFlags,
|
|
38
39
|
parseGlobalArgs: () => parseGlobalArgs,
|
|
39
40
|
parsePromptArgs: () => parsePromptArgs,
|
|
@@ -41,7 +42,9 @@ __export(cli_exports, {
|
|
|
41
42
|
parseSetEnvArgs: () => parseSetEnvArgs,
|
|
42
43
|
parseShellArgs: () => parseShellArgs,
|
|
43
44
|
readDotenvFile: () => readDotenvFile,
|
|
45
|
+
renderConversationOverviewResponse: () => renderConversationOverviewResponse,
|
|
44
46
|
renderConversationResponse: () => renderConversationResponse,
|
|
47
|
+
renderConversationWorkResponse: () => renderConversationWorkResponse,
|
|
45
48
|
renderProcessList: () => renderProcessList,
|
|
46
49
|
resolveCommandExecution: () => resolveCommandExecution,
|
|
47
50
|
runR5dctlCli: () => runR5dctlCli,
|
|
@@ -163,6 +166,16 @@ const SHARED_HELP_ENTRIES = [
|
|
|
163
166
|
usage: "-s <session-id> conversation [--raw] [--tools] [--system]",
|
|
164
167
|
description: "Read the agent request transcript in human-readable form."
|
|
165
168
|
},
|
|
169
|
+
{
|
|
170
|
+
section: "sessions",
|
|
171
|
+
usage: "conversation overview <session-id>",
|
|
172
|
+
description: "Read dialogue and thinking while replacing tool work with inspectable ranges."
|
|
173
|
+
},
|
|
174
|
+
{
|
|
175
|
+
section: "sessions",
|
|
176
|
+
usage: "conversation inspect-work <session-id> <work-id> [--compact|--summary|--full]",
|
|
177
|
+
description: "Inspect one turn's omitted tool work at the selected detail."
|
|
178
|
+
},
|
|
166
179
|
{
|
|
167
180
|
section: "sessions",
|
|
168
181
|
usage: '-s <session-id> prompt --mode <mode> --model <tier> "<message>"',
|
|
@@ -316,10 +329,12 @@ function renderCliOnlyCommandHelp(entry) {
|
|
|
316
329
|
`;
|
|
317
330
|
}
|
|
318
331
|
function renderSharedCommandHelp(pathSegments) {
|
|
319
|
-
const entry = SHARED_HELP_ENTRIES.
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
})
|
|
332
|
+
const entry = SHARED_HELP_ENTRIES.map((candidate) => ({
|
|
333
|
+
candidate,
|
|
334
|
+
usageSegments: candidate.usage.split(" ").map((segment) => segment.replace(/^\[/, "").replace(/\]$/, "")).filter((segment) => !segment.startsWith("-") && !segment.startsWith("<") && !segment.startsWith("["))
|
|
335
|
+
})).filter(
|
|
336
|
+
({ usageSegments }) => usageSegments.length <= pathSegments.length && usageSegments.every((segment, index) => segment === pathSegments[index])
|
|
337
|
+
).sort((left, right) => right.usageSegments.length - left.usageSegments.length)[0]?.candidate;
|
|
323
338
|
if (!entry) {
|
|
324
339
|
return void 0;
|
|
325
340
|
}
|
|
@@ -1206,6 +1221,30 @@ function renderConversationResponse(read) {
|
|
|
1206
1221
|
return read.agentText.endsWith("\n") ? read.agentText : `${read.agentText}
|
|
1207
1222
|
`;
|
|
1208
1223
|
}
|
|
1224
|
+
function parseConversationWorkDetailArgs(args) {
|
|
1225
|
+
let detail = "compact";
|
|
1226
|
+
let selected = false;
|
|
1227
|
+
for (const arg of args) {
|
|
1228
|
+
const candidate = arg === "--compact" ? "compact" : arg === "--summary" ? "summary" : arg === "--full" ? "full" : void 0;
|
|
1229
|
+
if (!candidate) {
|
|
1230
|
+
throw new Error(`Unknown inspect-work argument: ${arg}`);
|
|
1231
|
+
}
|
|
1232
|
+
if (selected) {
|
|
1233
|
+
throw new Error("Use only one of --compact, --summary, or --full");
|
|
1234
|
+
}
|
|
1235
|
+
detail = candidate;
|
|
1236
|
+
selected = true;
|
|
1237
|
+
}
|
|
1238
|
+
return detail;
|
|
1239
|
+
}
|
|
1240
|
+
function renderConversationOverviewResponse(read) {
|
|
1241
|
+
return read.overviewText.endsWith("\n") ? read.overviewText : `${read.overviewText}
|
|
1242
|
+
`;
|
|
1243
|
+
}
|
|
1244
|
+
function renderConversationWorkResponse(read) {
|
|
1245
|
+
return read.workText.endsWith("\n") ? read.workText : `${read.workText}
|
|
1246
|
+
`;
|
|
1247
|
+
}
|
|
1209
1248
|
async function executeR5dctlCommand(client, json, args) {
|
|
1210
1249
|
const write = (data, human) => writeDataOutput(json, data, human);
|
|
1211
1250
|
const [first, second, third] = args;
|
|
@@ -1394,6 +1433,22 @@ ${result.message}
|
|
|
1394
1433
|
write(result, "Session deleted.\n");
|
|
1395
1434
|
return;
|
|
1396
1435
|
}
|
|
1436
|
+
if (first === "conversation" && second === "overview") {
|
|
1437
|
+
if (args.length > 3) {
|
|
1438
|
+
throw new Error(`Unexpected conversation overview argument: ${args[3]}`);
|
|
1439
|
+
}
|
|
1440
|
+
const read = await client.sessions.conversationOverview(requireValue(args[2], "Missing session id"));
|
|
1441
|
+
write(read, renderConversationOverviewResponse(read));
|
|
1442
|
+
return;
|
|
1443
|
+
}
|
|
1444
|
+
if (first === "conversation" && second === "inspect-work") {
|
|
1445
|
+
const sessionId = requireValue(args[2], "Missing session id");
|
|
1446
|
+
const workId = requireValue(args[3], "Missing work id");
|
|
1447
|
+
const detail = parseConversationWorkDetailArgs(args.slice(4));
|
|
1448
|
+
const read = await client.sessions.inspectConversationWork(sessionId, workId, { detail });
|
|
1449
|
+
write(read, renderConversationWorkResponse(read));
|
|
1450
|
+
return;
|
|
1451
|
+
}
|
|
1397
1452
|
if (first === "sessions" && second === "conversation" || first === "conversation") {
|
|
1398
1453
|
const offset = first === "conversation" ? 1 : 2;
|
|
1399
1454
|
const renderOptions = parseConversationRenderArgs(args.slice(offset + 1));
|
|
@@ -1716,6 +1771,33 @@ function resolveCommandExecution(options, rest) {
|
|
|
1716
1771
|
throw new Error("Unknown delete command");
|
|
1717
1772
|
}
|
|
1718
1773
|
if (command === "conversation") {
|
|
1774
|
+
const subcommand = commandArgs[0];
|
|
1775
|
+
if (subcommand === "overview") {
|
|
1776
|
+
const sessionId2 = options.session ?? commandArgs[1];
|
|
1777
|
+
if (!sessionId2) {
|
|
1778
|
+
throw new Error("Session id is required for `conversation overview`");
|
|
1779
|
+
}
|
|
1780
|
+
const remainingArgs = options.session ? commandArgs.slice(1) : commandArgs.slice(2);
|
|
1781
|
+
return {
|
|
1782
|
+
kind: "plugin",
|
|
1783
|
+
pluginArgs: ["conversation", "overview", sessionId2, ...remainingArgs]
|
|
1784
|
+
};
|
|
1785
|
+
}
|
|
1786
|
+
if (subcommand === "inspect-work") {
|
|
1787
|
+
const sessionId2 = options.session ?? commandArgs[1];
|
|
1788
|
+
if (!sessionId2) {
|
|
1789
|
+
throw new Error("Session id is required for `conversation inspect-work`");
|
|
1790
|
+
}
|
|
1791
|
+
const workId = options.session ? commandArgs[1] : commandArgs[2];
|
|
1792
|
+
if (!workId) {
|
|
1793
|
+
throw new Error("Work id is required for `conversation inspect-work`");
|
|
1794
|
+
}
|
|
1795
|
+
const remainingArgs = options.session ? commandArgs.slice(2) : commandArgs.slice(3);
|
|
1796
|
+
return {
|
|
1797
|
+
kind: "plugin",
|
|
1798
|
+
pluginArgs: ["conversation", "inspect-work", sessionId2, workId, ...remainingArgs]
|
|
1799
|
+
};
|
|
1800
|
+
}
|
|
1719
1801
|
const sessionId = options.session;
|
|
1720
1802
|
if (!sessionId) {
|
|
1721
1803
|
throw new Error("--session/-s is required for `conversation`");
|
|
@@ -1938,6 +2020,7 @@ async function main(argv = process.argv.slice(2)) {
|
|
|
1938
2020
|
main,
|
|
1939
2021
|
parseAnswerFlags,
|
|
1940
2022
|
parseConversationRenderArgs,
|
|
2023
|
+
parseConversationWorkDetailArgs,
|
|
1941
2024
|
parseEnvFlags,
|
|
1942
2025
|
parseGlobalArgs,
|
|
1943
2026
|
parsePromptArgs,
|
|
@@ -1945,7 +2028,9 @@ async function main(argv = process.argv.slice(2)) {
|
|
|
1945
2028
|
parseSetEnvArgs,
|
|
1946
2029
|
parseShellArgs,
|
|
1947
2030
|
readDotenvFile,
|
|
2031
|
+
renderConversationOverviewResponse,
|
|
1948
2032
|
renderConversationResponse,
|
|
2033
|
+
renderConversationWorkResponse,
|
|
1949
2034
|
renderProcessList,
|
|
1950
2035
|
resolveCommandExecution,
|
|
1951
2036
|
runR5dctlCli,
|
package/dist/cjs/package.json
CHANGED
package/dist/mjs/cli.mjs
CHANGED
|
@@ -116,6 +116,16 @@ const SHARED_HELP_ENTRIES = [
|
|
|
116
116
|
usage: "-s <session-id> conversation [--raw] [--tools] [--system]",
|
|
117
117
|
description: "Read the agent request transcript in human-readable form."
|
|
118
118
|
},
|
|
119
|
+
{
|
|
120
|
+
section: "sessions",
|
|
121
|
+
usage: "conversation overview <session-id>",
|
|
122
|
+
description: "Read dialogue and thinking while replacing tool work with inspectable ranges."
|
|
123
|
+
},
|
|
124
|
+
{
|
|
125
|
+
section: "sessions",
|
|
126
|
+
usage: "conversation inspect-work <session-id> <work-id> [--compact|--summary|--full]",
|
|
127
|
+
description: "Inspect one turn's omitted tool work at the selected detail."
|
|
128
|
+
},
|
|
119
129
|
{
|
|
120
130
|
section: "sessions",
|
|
121
131
|
usage: '-s <session-id> prompt --mode <mode> --model <tier> "<message>"',
|
|
@@ -269,10 +279,12 @@ function renderCliOnlyCommandHelp(entry) {
|
|
|
269
279
|
`;
|
|
270
280
|
}
|
|
271
281
|
function renderSharedCommandHelp(pathSegments) {
|
|
272
|
-
const entry = SHARED_HELP_ENTRIES.
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
})
|
|
282
|
+
const entry = SHARED_HELP_ENTRIES.map((candidate) => ({
|
|
283
|
+
candidate,
|
|
284
|
+
usageSegments: candidate.usage.split(" ").map((segment) => segment.replace(/^\[/, "").replace(/\]$/, "")).filter((segment) => !segment.startsWith("-") && !segment.startsWith("<") && !segment.startsWith("["))
|
|
285
|
+
})).filter(
|
|
286
|
+
({ usageSegments }) => usageSegments.length <= pathSegments.length && usageSegments.every((segment, index) => segment === pathSegments[index])
|
|
287
|
+
).sort((left, right) => right.usageSegments.length - left.usageSegments.length)[0]?.candidate;
|
|
276
288
|
if (!entry) {
|
|
277
289
|
return void 0;
|
|
278
290
|
}
|
|
@@ -1159,6 +1171,30 @@ function renderConversationResponse(read) {
|
|
|
1159
1171
|
return read.agentText.endsWith("\n") ? read.agentText : `${read.agentText}
|
|
1160
1172
|
`;
|
|
1161
1173
|
}
|
|
1174
|
+
function parseConversationWorkDetailArgs(args) {
|
|
1175
|
+
let detail = "compact";
|
|
1176
|
+
let selected = false;
|
|
1177
|
+
for (const arg of args) {
|
|
1178
|
+
const candidate = arg === "--compact" ? "compact" : arg === "--summary" ? "summary" : arg === "--full" ? "full" : void 0;
|
|
1179
|
+
if (!candidate) {
|
|
1180
|
+
throw new Error(`Unknown inspect-work argument: ${arg}`);
|
|
1181
|
+
}
|
|
1182
|
+
if (selected) {
|
|
1183
|
+
throw new Error("Use only one of --compact, --summary, or --full");
|
|
1184
|
+
}
|
|
1185
|
+
detail = candidate;
|
|
1186
|
+
selected = true;
|
|
1187
|
+
}
|
|
1188
|
+
return detail;
|
|
1189
|
+
}
|
|
1190
|
+
function renderConversationOverviewResponse(read) {
|
|
1191
|
+
return read.overviewText.endsWith("\n") ? read.overviewText : `${read.overviewText}
|
|
1192
|
+
`;
|
|
1193
|
+
}
|
|
1194
|
+
function renderConversationWorkResponse(read) {
|
|
1195
|
+
return read.workText.endsWith("\n") ? read.workText : `${read.workText}
|
|
1196
|
+
`;
|
|
1197
|
+
}
|
|
1162
1198
|
async function executeR5dctlCommand(client, json, args) {
|
|
1163
1199
|
const write = (data, human) => writeDataOutput(json, data, human);
|
|
1164
1200
|
const [first, second, third] = args;
|
|
@@ -1347,6 +1383,22 @@ ${result.message}
|
|
|
1347
1383
|
write(result, "Session deleted.\n");
|
|
1348
1384
|
return;
|
|
1349
1385
|
}
|
|
1386
|
+
if (first === "conversation" && second === "overview") {
|
|
1387
|
+
if (args.length > 3) {
|
|
1388
|
+
throw new Error(`Unexpected conversation overview argument: ${args[3]}`);
|
|
1389
|
+
}
|
|
1390
|
+
const read = await client.sessions.conversationOverview(requireValue(args[2], "Missing session id"));
|
|
1391
|
+
write(read, renderConversationOverviewResponse(read));
|
|
1392
|
+
return;
|
|
1393
|
+
}
|
|
1394
|
+
if (first === "conversation" && second === "inspect-work") {
|
|
1395
|
+
const sessionId = requireValue(args[2], "Missing session id");
|
|
1396
|
+
const workId = requireValue(args[3], "Missing work id");
|
|
1397
|
+
const detail = parseConversationWorkDetailArgs(args.slice(4));
|
|
1398
|
+
const read = await client.sessions.inspectConversationWork(sessionId, workId, { detail });
|
|
1399
|
+
write(read, renderConversationWorkResponse(read));
|
|
1400
|
+
return;
|
|
1401
|
+
}
|
|
1350
1402
|
if (first === "sessions" && second === "conversation" || first === "conversation") {
|
|
1351
1403
|
const offset = first === "conversation" ? 1 : 2;
|
|
1352
1404
|
const renderOptions = parseConversationRenderArgs(args.slice(offset + 1));
|
|
@@ -1669,6 +1721,33 @@ function resolveCommandExecution(options, rest) {
|
|
|
1669
1721
|
throw new Error("Unknown delete command");
|
|
1670
1722
|
}
|
|
1671
1723
|
if (command === "conversation") {
|
|
1724
|
+
const subcommand = commandArgs[0];
|
|
1725
|
+
if (subcommand === "overview") {
|
|
1726
|
+
const sessionId2 = options.session ?? commandArgs[1];
|
|
1727
|
+
if (!sessionId2) {
|
|
1728
|
+
throw new Error("Session id is required for `conversation overview`");
|
|
1729
|
+
}
|
|
1730
|
+
const remainingArgs = options.session ? commandArgs.slice(1) : commandArgs.slice(2);
|
|
1731
|
+
return {
|
|
1732
|
+
kind: "plugin",
|
|
1733
|
+
pluginArgs: ["conversation", "overview", sessionId2, ...remainingArgs]
|
|
1734
|
+
};
|
|
1735
|
+
}
|
|
1736
|
+
if (subcommand === "inspect-work") {
|
|
1737
|
+
const sessionId2 = options.session ?? commandArgs[1];
|
|
1738
|
+
if (!sessionId2) {
|
|
1739
|
+
throw new Error("Session id is required for `conversation inspect-work`");
|
|
1740
|
+
}
|
|
1741
|
+
const workId = options.session ? commandArgs[1] : commandArgs[2];
|
|
1742
|
+
if (!workId) {
|
|
1743
|
+
throw new Error("Work id is required for `conversation inspect-work`");
|
|
1744
|
+
}
|
|
1745
|
+
const remainingArgs = options.session ? commandArgs.slice(2) : commandArgs.slice(3);
|
|
1746
|
+
return {
|
|
1747
|
+
kind: "plugin",
|
|
1748
|
+
pluginArgs: ["conversation", "inspect-work", sessionId2, workId, ...remainingArgs]
|
|
1749
|
+
};
|
|
1750
|
+
}
|
|
1672
1751
|
const sessionId = options.session;
|
|
1673
1752
|
if (!sessionId) {
|
|
1674
1753
|
throw new Error("--session/-s is required for `conversation`");
|
|
@@ -1890,6 +1969,7 @@ export {
|
|
|
1890
1969
|
main,
|
|
1891
1970
|
parseAnswerFlags,
|
|
1892
1971
|
parseConversationRenderArgs,
|
|
1972
|
+
parseConversationWorkDetailArgs,
|
|
1893
1973
|
parseEnvFlags,
|
|
1894
1974
|
parseGlobalArgs,
|
|
1895
1975
|
parsePromptArgs,
|
|
@@ -1897,7 +1977,9 @@ export {
|
|
|
1897
1977
|
parseSetEnvArgs,
|
|
1898
1978
|
parseShellArgs,
|
|
1899
1979
|
readDotenvFile,
|
|
1980
|
+
renderConversationOverviewResponse,
|
|
1900
1981
|
renderConversationResponse,
|
|
1982
|
+
renderConversationWorkResponse,
|
|
1901
1983
|
renderProcessList,
|
|
1902
1984
|
resolveCommandExecution,
|
|
1903
1985
|
runR5dctlCli,
|
package/dist/mjs/package.json
CHANGED
package/dist/types/cli.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type R5dctlConversationRenderOptions, type R5dctlConversationResponse, type R5dctlEnvData, type R5dctlProcessListInput, type R5dctlProcessRun, type ChatMode, type ModelTier } from "@ricsam/r5d-api";
|
|
1
|
+
import { type R5dctlConversationRenderOptions, type R5dctlConversationResponse, type R5dctlConversationOverviewResponse, type R5dctlConversationWorkDetail, type R5dctlConversationWorkResponse, type R5dctlEnvData, type R5dctlProcessListInput, type R5dctlProcessRun, type ChatMode, type ModelTier } from "@ricsam/r5d-api";
|
|
2
2
|
export type GlobalOptions = {
|
|
3
3
|
baseUrl?: string;
|
|
4
4
|
json: boolean;
|
|
@@ -71,6 +71,9 @@ export type EnvSummaryData = Record<string, {
|
|
|
71
71
|
export declare function summarizeEnvData(data: R5dctlEnvData): EnvSummaryData;
|
|
72
72
|
export declare function parseConversationRenderArgs(args: string[]): ConversationRenderOptions;
|
|
73
73
|
export declare function renderConversationResponse(read: R5dctlConversationResponse): string;
|
|
74
|
+
export declare function parseConversationWorkDetailArgs(args: string[]): R5dctlConversationWorkDetail;
|
|
75
|
+
export declare function renderConversationOverviewResponse(read: R5dctlConversationOverviewResponse): string;
|
|
76
|
+
export declare function renderConversationWorkResponse(read: R5dctlConversationWorkResponse): string;
|
|
74
77
|
export declare function resolveCommandExecution(options: GlobalOptions, rest: string[]): CommandExecutionPlan;
|
|
75
78
|
export declare function runR5dctlCli(argv: string[]): Promise<number>;
|
|
76
79
|
export declare function main(argv?: string[]): Promise<void>;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ricsam/r5dctl",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.28",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "./dist/cjs/cli.cjs",
|
|
6
6
|
"module": "./dist/mjs/cli.mjs",
|
|
@@ -26,7 +26,7 @@
|
|
|
26
26
|
"r5dctl": "dist/cjs/main.cjs"
|
|
27
27
|
},
|
|
28
28
|
"dependencies": {
|
|
29
|
-
"@ricsam/r5d-api": "^0.0.
|
|
29
|
+
"@ricsam/r5d-api": "^0.0.28",
|
|
30
30
|
"dotenv": "^17",
|
|
31
31
|
"ws": "^8.18.3"
|
|
32
32
|
},
|