@pitcher/cli-scripts 3.1.1 → 3.3.0
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 +39 -2
- package/dist/index.js +2 -0
- package/dist/src/commands/analytics.d.ts +77 -0
- package/dist/src/commands/analytics.js +309 -1
- package/dist/src/commands/dsrLanding.js +1 -1
- package/dist/src/commands/roleplay.d.ts +236 -0
- package/dist/src/commands/roleplay.js +702 -0
- package/dist/src/core/dsr-engagement.d.ts +152 -0
- package/dist/src/core/dsr-engagement.js +301 -0
- package/dist/src/core/dsr-visits.d.ts +50 -0
- package/dist/src/core/dsr-visits.js +191 -0
- package/dist/src/core/envelope.d.ts +1 -0
- package/dist/src/core/envelope.js +6 -1
- package/dist/src/core/errors.d.ts +3 -1
- package/dist/src/core/errors.js +2 -2
- package/dist/src/core/http.js +7 -5
- package/dist/src/core/ld.js +2 -1
- package/dist/src/core/me.d.ts +3 -0
- package/dist/src/core/me.js +10 -0
- package/dist/src/core/roleplay-stats.d.ts +120 -0
- package/dist/src/core/roleplay-stats.js +171 -0
- package/dist/src/mcp/apps/confirm/define.d.ts +66 -0
- package/dist/src/mcp/apps/confirm/define.js +208 -0
- package/dist/src/mcp/apps/confirm/hash.d.ts +4 -0
- package/dist/src/mcp/apps/confirm/hash.js +23 -0
- package/dist/src/mcp/apps/confirm/types.d.ts +96 -0
- package/dist/src/mcp/apps/confirm/types.js +15 -0
- package/dist/src/mcp/apps/contentPicker.d.ts +104 -0
- package/dist/src/mcp/apps/contentPicker.js +268 -0
- package/dist/src/mcp/apps/dsrEngagement.d.ts +194 -0
- package/dist/src/mcp/apps/dsrEngagement.js +737 -0
- package/dist/src/mcp/apps/registry.d.ts +14 -0
- package/dist/src/mcp/apps/registry.js +25 -0
- package/dist/src/mcp/apps/roleplayManager.d.ts +228 -0
- package/dist/src/mcp/apps/roleplayManager.js +606 -0
- package/dist/src/mcp/apps/roleplayReps.d.ts +79 -0
- package/dist/src/mcp/apps/roleplayReps.js +328 -0
- package/dist/src/mcp/apps/roleplayWrites.d.ts +6 -0
- package/dist/src/mcp/apps/roleplayWrites.js +509 -0
- package/dist/src/mcp/apps/text.d.ts +41 -0
- package/dist/src/mcp/apps/text.js +58 -0
- package/dist/src/mcp/apps/types.d.ts +23 -0
- package/dist/src/mcp/apps/types.js +12 -0
- package/dist/src/mcp/apps/writeConfirm.d.ts +3 -0
- package/dist/src/mcp/apps/writeConfirm.js +8 -0
- package/dist/src/mcp/groups.d.ts +42 -0
- package/dist/src/mcp/groups.js +89 -0
- package/dist/src/mcp/hosted.d.ts +36 -0
- package/dist/src/mcp/hosted.js +47 -1
- package/dist/src/mcp/index.d.ts +9 -3
- package/dist/src/mcp/index.js +9 -2
- package/dist/src/mcp/prompts/registry.js +8 -7
- package/dist/src/mcp/prompts/types.d.ts +3 -0
- package/dist/src/mcp/registry.d.ts +4 -0
- package/dist/src/mcp/registry.js +30 -23
- package/dist/src/mcp/renderPolicy.d.ts +2 -1
- package/dist/src/mcp/renderPolicy.js +10 -3
- package/dist/src/mcp/resources/analyticsCatalog.d.ts +1 -1
- package/dist/src/mcp/resources/analyticsCatalog.js +23 -5
- package/dist/src/mcp/resources/registry.js +2 -2
- package/dist/src/mcp/resources/types.d.ts +3 -0
- package/dist/src/mcp/result.d.ts +2 -1
- package/dist/src/mcp/result.js +8 -6
- package/dist/src/mcp/server.d.ts +62 -0
- package/dist/src/mcp/server.js +161 -10
- package/dist/src/mcp/tools/analytics.js +88 -3
- package/dist/src/mcp/tools/roleplay.d.ts +2 -0
- package/dist/src/mcp/tools/roleplay.js +135 -0
- package/dist/src/mcp/tools/types.d.ts +35 -0
- package/package.json +7 -1
|
@@ -0,0 +1,236 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import type { AxiosInstance } from 'axios';
|
|
3
|
+
import { type CommonOpts } from '../core/http.js';
|
|
4
|
+
import { type Envelope } from '../core/envelope.js';
|
|
5
|
+
import { type AssignmentProgressLike, type RepStatus, type RoleplayAssignmentLike, type RoleplaySessionLike } from '../core/roleplay-stats.js';
|
|
6
|
+
/**
|
|
7
|
+
* AI Roleplay reads (PIT-9200, Phase 1: read-only). Two sources:
|
|
8
|
+
* - clickhouse-api `/analytics/roleplay/{kpis,sessions}` (the `roleplay_statements` replica,
|
|
9
|
+
* instance or org admins only): `kpis`, `sessions`, `rep-summary`;
|
|
10
|
+
* - next-core `/core/api/protected/roleplay/coach/*` and appsDB (`cch-*` rows in Postgres):
|
|
11
|
+
* `team`, `session`, `scenarios`.
|
|
12
|
+
* A session with no score is unscored, never 0. Practice Studio takes (`manager-video-practice`)
|
|
13
|
+
* never appear: the coach routes exclude them by default and `team` drops practice assignments.
|
|
14
|
+
*/
|
|
15
|
+
export interface RoleplayDeps {
|
|
16
|
+
client?: AxiosInstance;
|
|
17
|
+
}
|
|
18
|
+
export declare const ROLEPLAY_DIFFICULTIES: readonly ["easy", "medium", "hard"];
|
|
19
|
+
export declare const ROLEPLAY_SESSION_SORT: readonly ["session_at", "rep_name", "score", "duration_ms"];
|
|
20
|
+
export declare const ROLEPLAY_GROUP_BY: readonly ["rep", "scenario"];
|
|
21
|
+
export declare const REP_STATUSES: readonly RepStatus[];
|
|
22
|
+
/** rep-summary reads at most this many pages of this size (5000 sessions), newest first. */
|
|
23
|
+
export declare const REP_SUMMARY_PAGE_SIZE = 1000;
|
|
24
|
+
export declare const REP_SUMMARY_MAX_PAGES = 5;
|
|
25
|
+
export declare const REP_SUMMARY_MAX_GROUPS = 50;
|
|
26
|
+
/** next-core's coach/data returns at most this many sessions, newest first, and no total. */
|
|
27
|
+
export declare const COACH_DATA_SESSION_CAP = 1000;
|
|
28
|
+
export declare const TEAM_MAX_ASSIGNMENTS = 50;
|
|
29
|
+
export declare const TEAM_MAX_REPS_PER_ASSIGNMENT = 100;
|
|
30
|
+
/**
|
|
31
|
+
* Pass progress (PIT-9971) is read in pages of 2000 (assignment, rep) pairs. Above this many pages the
|
|
32
|
+
* tools use no progress at all (the manager app allows 100,000 pages; one tool call stays bounded).
|
|
33
|
+
*/
|
|
34
|
+
export declare const PROGRESS_MAX_PAGES = 10;
|
|
35
|
+
export interface RoleplayFilterOpts extends CommonOpts {
|
|
36
|
+
instanceId?: string;
|
|
37
|
+
startDate?: string;
|
|
38
|
+
endDate?: string;
|
|
39
|
+
rep?: string;
|
|
40
|
+
scenario?: string;
|
|
41
|
+
difficulty?: string;
|
|
42
|
+
}
|
|
43
|
+
export declare const finiteOrNull: (v: unknown) => number | null;
|
|
44
|
+
/** Totals for the window: sessions, scored/unscored, mean score over SCORED sessions only, active reps. */
|
|
45
|
+
export declare function runRoleplayKpis(opts: RoleplayFilterOpts, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
46
|
+
declare const SESSION_FIELDS: readonly ["entry_id", "session_at", "rep_name", "who", "scenario_name", "persona_name", "difficulty", "score", "evaluated", "rating", "duration_ms"];
|
|
47
|
+
export type RoleplaySessionRow = Record<(typeof SESSION_FIELDS)[number], unknown>;
|
|
48
|
+
/** The row allowlist: nothing else from the replica (provider, recording flags, rubric) leaves. */
|
|
49
|
+
export declare function pickSessionRow(row: Record<string, unknown>): RoleplaySessionRow;
|
|
50
|
+
export interface RoleplaySessionsOpts extends RoleplayFilterOpts {
|
|
51
|
+
sortBy?: string;
|
|
52
|
+
sortOrder?: string;
|
|
53
|
+
limit?: number;
|
|
54
|
+
page?: number;
|
|
55
|
+
}
|
|
56
|
+
export declare function runRoleplaySessions(opts: RoleplaySessionsOpts, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
57
|
+
export interface RoleplayRepSummaryOpts extends RoleplayFilterOpts {
|
|
58
|
+
groupBy?: string;
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Per-rep (keyed on the rep email `who`) or per-scenario (keyed on `scenario_id`) aggregates over
|
|
62
|
+
* the sessions list, read in pages of 1000 (newest first) up to 5000. `complete: false` when the
|
|
63
|
+
* window holds more than that; then the figures cover the newest 5000 only.
|
|
64
|
+
*/
|
|
65
|
+
export declare function runRoleplayRepSummary(opts: RoleplayRepSummaryOpts, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
66
|
+
export interface CoachAssignment extends RoleplayAssignmentLike {
|
|
67
|
+
id: string;
|
|
68
|
+
scenarioName?: string;
|
|
69
|
+
active?: boolean;
|
|
70
|
+
contentType?: string;
|
|
71
|
+
resolvedUserNames?: Record<string, string>;
|
|
72
|
+
}
|
|
73
|
+
/** A bundle session row: coach/data spreads the appsDB data and adds the entry `id` (transcript stripped). */
|
|
74
|
+
export type CoachSession = RoleplaySessionLike & {
|
|
75
|
+
id: string;
|
|
76
|
+
sessionType?: string;
|
|
77
|
+
evaluationStatus?: string;
|
|
78
|
+
};
|
|
79
|
+
type ProgressEntry = {
|
|
80
|
+
assignmentId?: unknown;
|
|
81
|
+
repUserId?: unknown;
|
|
82
|
+
} & Partial<Record<keyof AssignmentProgressLike, unknown>>;
|
|
83
|
+
interface ProgressPage {
|
|
84
|
+
page: number;
|
|
85
|
+
pageSize: number;
|
|
86
|
+
totalPairs: number;
|
|
87
|
+
hasMore: boolean;
|
|
88
|
+
}
|
|
89
|
+
/** A `cch-manager-comment` row as coach/data returns it: the appsDB data plus the entry `id` (soft-deleted rows excluded). */
|
|
90
|
+
export type CoachComment = Record<string, unknown> & {
|
|
91
|
+
id: string;
|
|
92
|
+
managerId?: string | number;
|
|
93
|
+
managerName?: string;
|
|
94
|
+
repUserId?: string | number;
|
|
95
|
+
assignmentId?: string;
|
|
96
|
+
sessionEntryId?: string | null;
|
|
97
|
+
comment?: string;
|
|
98
|
+
};
|
|
99
|
+
export interface CoachBundle {
|
|
100
|
+
scope?: 'instance' | 'coach';
|
|
101
|
+
assignments?: CoachAssignment[];
|
|
102
|
+
sessions?: CoachSession[];
|
|
103
|
+
comments?: CoachComment[];
|
|
104
|
+
assignmentProgress?: ProgressEntry[];
|
|
105
|
+
assignmentProgressPage?: ProgressPage;
|
|
106
|
+
}
|
|
107
|
+
export interface RoleplayTeamOpts extends CommonOpts {
|
|
108
|
+
instanceId?: string;
|
|
109
|
+
assignmentId?: string;
|
|
110
|
+
status?: string;
|
|
111
|
+
}
|
|
112
|
+
export type CoachScope = 'instance' | 'coach';
|
|
113
|
+
/** The caller's OWN coaching scope (coach/data without `scope`): what a coach may comment on (PIT-10113). */
|
|
114
|
+
export declare function getOwnCoachBundle(client: AxiosInstance, instanceId: string): Promise<CoachBundle>;
|
|
115
|
+
/** The manager app's progress map key (`useManagerData.ts`). */
|
|
116
|
+
export declare const progressKey: (assignmentId: string, repUserId: string) => string;
|
|
117
|
+
export interface Coverage {
|
|
118
|
+
sessionsCapped: boolean;
|
|
119
|
+
progress: 'full' | 'none';
|
|
120
|
+
/** (assignment, rep) pairs of the roleplay model with no progress entry when progress is full, else 0. */
|
|
121
|
+
pairsWithoutProgress: number;
|
|
122
|
+
}
|
|
123
|
+
export interface TeamModel {
|
|
124
|
+
/** The scope the server applied (an older next-core that ignores scope=instance answers 'coach'). */
|
|
125
|
+
scope: CoachScope;
|
|
126
|
+
/** The scope this load asked for first: 'coach' when the caller passed scopePref 'coach'. */
|
|
127
|
+
requested: CoachScope;
|
|
128
|
+
coverage: Coverage;
|
|
129
|
+
warnings: string[];
|
|
130
|
+
/** contentType !== 'practice', D18 order. */
|
|
131
|
+
assignments: CoachAssignment[];
|
|
132
|
+
/** sessionType !== 'manager-video-practice'. */
|
|
133
|
+
sessions: CoachSession[];
|
|
134
|
+
progress: ReadonlyMap<string, AssignmentProgressLike> | null;
|
|
135
|
+
}
|
|
136
|
+
/** D18 rep order: the reps who need the manager first. */
|
|
137
|
+
export declare const STATUS_RANK: Record<RepStatus, number>;
|
|
138
|
+
/** D18 assignment order: active first, then due date ascending (none last), then scenario name, then id. */
|
|
139
|
+
export declare function compareAssignments(a: CoachAssignment, b: CoachAssignment): number;
|
|
140
|
+
/** D18 rep order: status rank, then name (no name last), then user id. */
|
|
141
|
+
export declare function compareReps(a: {
|
|
142
|
+
status: RepStatus;
|
|
143
|
+
name: string | null;
|
|
144
|
+
user_id: string;
|
|
145
|
+
}, b: {
|
|
146
|
+
status: RepStatus;
|
|
147
|
+
name: string | null;
|
|
148
|
+
user_id: string;
|
|
149
|
+
}): number;
|
|
150
|
+
/**
|
|
151
|
+
* The one team derivation shared by `roleplay team` and the roleplay manager view (PIT-10068): the
|
|
152
|
+
* coach bundle, its pass progress, the roleplay filters and the D18 order, so the text tool and the
|
|
153
|
+
* view always cut the same 50 assignments.
|
|
154
|
+
*/
|
|
155
|
+
export declare function loadTeamModel(client: AxiosInstance, instanceId: string, scopePref?: CoachScope): Promise<TeamModel>;
|
|
156
|
+
/**
|
|
157
|
+
* Assignment completion per rep, ported from the manager app: an admin gets every roleplay
|
|
158
|
+
* assignment on the instance (`scope=instance`), anyone else the assignments they coach.
|
|
159
|
+
* Statuses, session counts and best scores follow `deriveStatus` / `repStats` with the server's
|
|
160
|
+
* pass progress when it loads (PIT-9971); assignments and reps in D18 order (`loadTeamModel`).
|
|
161
|
+
* Raw sessions, evaluations and comments never leave.
|
|
162
|
+
*/
|
|
163
|
+
export declare function runRoleplayTeam(opts: RoleplayTeamOpts, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
164
|
+
export interface RoleplaySessionGetOpts extends CommonOpts {
|
|
165
|
+
instanceId?: string;
|
|
166
|
+
entryId?: string;
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* The allowlist, shared by `roleplay session` and the manager view's scorecard. Never the transcript,
|
|
170
|
+
* messages, contact name, graded snapshot, voice session, recording or audio ids, or any
|
|
171
|
+
* video-evaluation field. The two scales (`grading_scale`, `max_score`) are numbers only (PIT-10068):
|
|
172
|
+
* legacy evaluations grade on 5, and a skill score is meaningless without its scale.
|
|
173
|
+
*/
|
|
174
|
+
export declare function pickSessionDetail(id: string, data: Record<string, unknown>): Record<string, unknown>;
|
|
175
|
+
export declare function runRoleplaySessionGet(opts: RoleplaySessionGetOpts, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
176
|
+
/** The trimmed catalog: never the persona prompt or the evaluation prompt. */
|
|
177
|
+
export declare function pickScenario(s: Record<string, unknown>): Record<string, unknown>;
|
|
178
|
+
export declare function runRoleplayScenariosList(opts: CommonOpts & {
|
|
179
|
+
instanceId?: string;
|
|
180
|
+
}, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
181
|
+
export declare const ROLEPLAY_PATH_STATUSES: readonly ["published", "draft", "all"];
|
|
182
|
+
export interface RoleplayPathRow {
|
|
183
|
+
id: string;
|
|
184
|
+
name: string;
|
|
185
|
+
status: string;
|
|
186
|
+
version: number;
|
|
187
|
+
stages: number;
|
|
188
|
+
steps: number;
|
|
189
|
+
default_passing_score: number | null;
|
|
190
|
+
updated_at: string | null;
|
|
191
|
+
}
|
|
192
|
+
/** The trimmed path: counts, never the stage/step bodies. */
|
|
193
|
+
export declare function pickPath(p: Record<string, unknown>): RoleplayPathRow;
|
|
194
|
+
/** next-core `GET roleplay/paths` (builder roles; 404 when paths are off or the caller is not a member). */
|
|
195
|
+
export declare function fetchPaths(client: AxiosInstance, instanceId: string, status?: (typeof ROLEPLAY_PATH_STATUSES)[number]): Promise<Record<string, unknown>[]>;
|
|
196
|
+
export declare function runRoleplayPathsList(opts: CommonOpts & {
|
|
197
|
+
instanceId?: string;
|
|
198
|
+
status?: string;
|
|
199
|
+
}, deps?: RoleplayDeps): Promise<Envelope<unknown>>;
|
|
200
|
+
/** next-core `GET roleplay/path-assignments`: the records in the caller's view (admins get the membership keys). */
|
|
201
|
+
export declare function fetchPathRecords(client: AxiosInstance, instanceId: string): Promise<Record<string, unknown>[]>;
|
|
202
|
+
export declare function postCoachComment(client: AxiosInstance, args: {
|
|
203
|
+
instanceId: string;
|
|
204
|
+
assignmentId: string;
|
|
205
|
+
repUserId: string;
|
|
206
|
+
sessionEntryId: string | null;
|
|
207
|
+
comment: string;
|
|
208
|
+
}, idempotencyKey: string): Promise<{
|
|
209
|
+
body: {
|
|
210
|
+
id?: string;
|
|
211
|
+
data?: Record<string, unknown>;
|
|
212
|
+
};
|
|
213
|
+
replayed: boolean;
|
|
214
|
+
}>;
|
|
215
|
+
export declare function deleteCoachComment(client: AxiosInstance, args: {
|
|
216
|
+
instanceId: string;
|
|
217
|
+
commentId: string;
|
|
218
|
+
}, idempotencyKey: string): Promise<{
|
|
219
|
+
replayed: boolean;
|
|
220
|
+
}>;
|
|
221
|
+
export declare function postPathAssignment(client: AxiosInstance, instanceId: string, body: {
|
|
222
|
+
pathId: string;
|
|
223
|
+
groupIds: string[];
|
|
224
|
+
recipientUserIds: string[];
|
|
225
|
+
managerIds: string[];
|
|
226
|
+
mandatory: boolean;
|
|
227
|
+
dueDate: string | null;
|
|
228
|
+
}, idempotencyKey: string): Promise<{
|
|
229
|
+
body: {
|
|
230
|
+
record?: Record<string, unknown>;
|
|
231
|
+
warnings?: unknown[];
|
|
232
|
+
};
|
|
233
|
+
replayed: boolean;
|
|
234
|
+
}>;
|
|
235
|
+
export declare function createRoleplayCommand(): Command;
|
|
236
|
+
export {};
|