conduyt-mcp 4.37.0 → 4.39.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/dist/tools/messaging.js +21 -0
- package/dist/tools/reports.js +51 -2
- package/package.json +1 -1
- package/scripts/coverage-matrix.json +14 -10
package/dist/tools/messaging.js
CHANGED
|
@@ -107,4 +107,25 @@ export function registerMessagingTools(server, client) {
|
|
|
107
107
|
const result = await client.get(`/api/v1/reports/sms-drip-conversion?${params}`);
|
|
108
108
|
return formatResult(result);
|
|
109
109
|
});
|
|
110
|
+
server.tool("conduyt_speed_to_lead_report", "Speed to lead: for every contact created in the window, the time to the FIRST HUMAN touch (a call placed by a person, a text or email a person sent through a connected provider, a note, or a completed task, inside the CRM): median and p90 seconds, leads reached within 5/15 min and 1/4/24 h, never reached, first-touch channel; overall, by assigned rep, by lead source and by who made the touch. Automation messages, campaign blasts and anything done outside the CRM are not touches (the response `definition` says so). Spans clamp to 90 days.", {
|
|
111
|
+
from: z.string().optional().describe("ISO start (omit both for the last 90 days; spans clamp to 90d)"),
|
|
112
|
+
to: z.string().optional().describe("ISO end"),
|
|
113
|
+
assignedTo: z.string().uuid().optional().describe("Only leads assigned to this user"),
|
|
114
|
+
sources: z.array(z.string()).max(50).optional().describe("Exact contact source values; '__none__' adds contacts with no source"),
|
|
115
|
+
smartListId: z.string().uuid().optional().describe("Only contacts in this smart list"),
|
|
116
|
+
}, async ({ from, to, assignedTo, sources, smartListId }) => {
|
|
117
|
+
const params = new URLSearchParams();
|
|
118
|
+
if (from)
|
|
119
|
+
params.set("from", from);
|
|
120
|
+
if (to)
|
|
121
|
+
params.set("to", to);
|
|
122
|
+
if (assignedTo)
|
|
123
|
+
params.set("assignedTo", assignedTo);
|
|
124
|
+
if (sources && sources.length > 0)
|
|
125
|
+
params.set("sources", sources.join(","));
|
|
126
|
+
if (smartListId)
|
|
127
|
+
params.set("smartListId", smartListId);
|
|
128
|
+
const result = await client.get(`/api/v1/reports/speed-to-lead?${params}`);
|
|
129
|
+
return formatResult(result);
|
|
130
|
+
});
|
|
110
131
|
}
|
package/dist/tools/reports.js
CHANGED
|
@@ -14,6 +14,14 @@ const filterSchema = z.object({
|
|
|
14
14
|
operator: z.string().describe("eq, neq, contains, gt, gte, lt, lte, between, in, isNull, isNotNull, or a relative-date operator (within_last_n, today, since_monday, this_calendar_month, previous_month, in_past, in_future…)"),
|
|
15
15
|
value: z.unknown().optional().describe("The value; [from, to] for between; a list for in; {n, unit} for within_last_n / within_next_n"),
|
|
16
16
|
});
|
|
17
|
+
const pivotSchema = z.object({
|
|
18
|
+
rows: z.array(z.string()).min(1).max(2).describe("One or two groupable fields down the side"),
|
|
19
|
+
columns: z.string().nullable().optional().describe("A groupable field across the top (omit for a single Total column)"),
|
|
20
|
+
measures: z.array(z.object({
|
|
21
|
+
aggregate: z.enum(["count", "sum", "avg", "min", "max"]),
|
|
22
|
+
field: z.string().nullable().optional().describe("A numeric field (rollup or cf:<key>); omit for count"),
|
|
23
|
+
})).min(1).max(5),
|
|
24
|
+
}).describe("Pivot table on the report (contacts / deals): every cell, row totals, column totals and the grand total come from the same filtered rows as the table; XLSX exports and deliveries add a Pivot sheet");
|
|
17
25
|
export function registerReportTools(server, client) {
|
|
18
26
|
server.tool("conduyt_report_fields", "The field catalogue a custom report may use on a base: the entity's own columns, its per-row rollups (contacts/deals) and the account's custom fields, with type, operators and whether each can group, sort or be measured. Read this before building a report.", { entity: z.enum(["contacts", "deals", "activities", "tasks", "messages", "invoices"]).describe("The report base") }, async ({ entity }) => formatResult(await client.get(`/api/v1/reports/custom/fields?entity=${encodeURIComponent(entity)}`)));
|
|
19
27
|
server.tool("conduyt_list_reports", "List the account's saved custom reports (shared ones and your own), with their definition and last-run status.", {}, async () => formatResult(await client.get("/api/v1/reports/custom")));
|
|
@@ -33,7 +41,8 @@ export function registerReportTools(server, client) {
|
|
|
33
41
|
chartType: z.enum(["bar", "line", "pie", "table", "funnel", "number"]).optional(),
|
|
34
42
|
population: z.object({ smartViewId: z.string().uuid().nullable().optional() }).optional().describe("contacts/deals only: { smartViewId } runs the report over the contacts in that Smart View"),
|
|
35
43
|
isShared: z.boolean().optional().describe("Visible to the whole account (default false = only you and admins)"),
|
|
36
|
-
|
|
44
|
+
pivot: pivotSchema.optional(),
|
|
45
|
+
}, async ({ name, description, entity, columns, filters, sortBy, sortDir, groupBy, groupBy2, timeGrain, aggregate, measureField, chartType, population, isShared, pivot }) => {
|
|
37
46
|
// Inline body (undefined fields drop out in JSON) — readable by the contract verifier's static parser.
|
|
38
47
|
const result = await client.post("/api/v1/reports/custom", {
|
|
39
48
|
name,
|
|
@@ -51,6 +60,7 @@ export function registerReportTools(server, client) {
|
|
|
51
60
|
chartType,
|
|
52
61
|
population,
|
|
53
62
|
isShared,
|
|
63
|
+
pivot,
|
|
54
64
|
});
|
|
55
65
|
return formatResult(result);
|
|
56
66
|
});
|
|
@@ -79,7 +89,8 @@ export function registerReportTools(server, client) {
|
|
|
79
89
|
aggregate: z.enum(["count", "sum", "avg", "min", "max"]).optional(),
|
|
80
90
|
measureField: z.string().optional(),
|
|
81
91
|
population: z.object({ smartViewId: z.string().uuid().nullable().optional() }).optional(),
|
|
82
|
-
|
|
92
|
+
pivot: pivotSchema.optional(),
|
|
93
|
+
}, async ({ entity, columns, filters, sortBy, sortDir, groupBy, groupBy2, timeGrain, aggregate, measureField, population, pivot }) => {
|
|
83
94
|
const result = await client.post("/api/v1/reports/custom/preview", {
|
|
84
95
|
entity,
|
|
85
96
|
columns,
|
|
@@ -92,6 +103,44 @@ export function registerReportTools(server, client) {
|
|
|
92
103
|
aggregate,
|
|
93
104
|
measureField,
|
|
94
105
|
population,
|
|
106
|
+
pivot,
|
|
107
|
+
});
|
|
108
|
+
return formatResult(result);
|
|
109
|
+
});
|
|
110
|
+
server.tool("conduyt_update_report", "Update a saved custom report: any create field, plus pivot (set a pivot grid, or null to remove it). Only the fields you pass change.", {
|
|
111
|
+
id: z.string().uuid().describe("Saved report id (from conduyt_list_reports)"),
|
|
112
|
+
name: z.string().min(1).max(120).optional(),
|
|
113
|
+
description: z.string().max(500).nullable().optional(),
|
|
114
|
+
columns: z.array(z.string()).min(1).max(60).optional(),
|
|
115
|
+
filters: z.array(filterSchema).max(30).optional(),
|
|
116
|
+
sortBy: z.string().nullable().optional(),
|
|
117
|
+
sortDir: z.enum(["asc", "desc"]).optional(),
|
|
118
|
+
groupBy: z.string().nullable().optional(),
|
|
119
|
+
groupBy2: z.string().nullable().optional(),
|
|
120
|
+
timeGrain: z.enum(["day", "week", "month"]).nullable().optional(),
|
|
121
|
+
aggregate: z.enum(["count", "sum", "avg", "min", "max"]).optional(),
|
|
122
|
+
measureField: z.string().nullable().optional(),
|
|
123
|
+
chartType: z.enum(["bar", "line", "pie", "table", "funnel", "number"]).optional(),
|
|
124
|
+
population: z.object({ smartViewId: z.string().uuid().nullable().optional() }).nullable().optional(),
|
|
125
|
+
isShared: z.boolean().optional(),
|
|
126
|
+
pivot: pivotSchema.nullable().optional().describe("A pivot definition, or null to remove the pivot"),
|
|
127
|
+
}, async ({ id, name, description, columns, filters, sortBy, sortDir, groupBy, groupBy2, timeGrain, aggregate, measureField, chartType, population, isShared, pivot }) => {
|
|
128
|
+
const result = await client.patch(`/api/v1/reports/custom/${encodeURIComponent(id)}`, {
|
|
129
|
+
name,
|
|
130
|
+
description,
|
|
131
|
+
columns,
|
|
132
|
+
filters,
|
|
133
|
+
sortBy,
|
|
134
|
+
sortDir,
|
|
135
|
+
groupBy,
|
|
136
|
+
groupBy2,
|
|
137
|
+
timeGrain,
|
|
138
|
+
aggregate,
|
|
139
|
+
measureField,
|
|
140
|
+
chartType,
|
|
141
|
+
population,
|
|
142
|
+
isShared,
|
|
143
|
+
pivot,
|
|
95
144
|
});
|
|
96
145
|
return formatResult(result);
|
|
97
146
|
});
|
package/package.json
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
{
|
|
2
|
-
"generatedAt": "2026-09-
|
|
3
|
-
"toolCount":
|
|
2
|
+
"generatedAt": "2026-09-11T01:28:31.871Z",
|
|
3
|
+
"toolCount": 234,
|
|
4
4
|
"totalEndpoints": 940,
|
|
5
5
|
"counts": {
|
|
6
|
-
"covered":
|
|
6
|
+
"covered": 216,
|
|
7
7
|
"excluded": 283,
|
|
8
|
-
"planned":
|
|
8
|
+
"planned": 441,
|
|
9
9
|
"uncategorized": 0
|
|
10
10
|
},
|
|
11
11
|
"matrix": {
|
|
@@ -2879,10 +2879,6 @@
|
|
|
2879
2879
|
"status": "planned",
|
|
2880
2880
|
"reason": "notification surfaces"
|
|
2881
2881
|
},
|
|
2882
|
-
"GET /api/v1/ops/capacity": {
|
|
2883
|
-
"status": "planned",
|
|
2884
|
-
"reason": "operator capacity dashboard (#51, shipped 2026-09) — read-only queue/park telemetry; a typed conduyt_capacity_snapshot tool is agent-relevant for throughput questions"
|
|
2885
|
-
},
|
|
2886
2882
|
"GET /api/v1/phone-numbers": {
|
|
2887
2883
|
"status": "planned",
|
|
2888
2884
|
"reason": "phone number inventory"
|
|
@@ -3186,8 +3182,10 @@
|
|
|
3186
3182
|
"reason": "additional report surfaces beyond ai/insights"
|
|
3187
3183
|
},
|
|
3188
3184
|
"PATCH /api/v1/reports/custom/:id": {
|
|
3189
|
-
"status": "
|
|
3190
|
-
"
|
|
3185
|
+
"status": "covered",
|
|
3186
|
+
"tools": [
|
|
3187
|
+
"conduyt_update_report"
|
|
3188
|
+
]
|
|
3191
3189
|
},
|
|
3192
3190
|
"DELETE /api/v1/reports/custom/:id": {
|
|
3193
3191
|
"status": "planned",
|
|
@@ -3279,6 +3277,12 @@
|
|
|
3279
3277
|
"status": "planned",
|
|
3280
3278
|
"reason": "additional report surfaces beyond ai/insights"
|
|
3281
3279
|
},
|
|
3280
|
+
"GET /api/v1/reports/speed-to-lead": {
|
|
3281
|
+
"status": "covered",
|
|
3282
|
+
"tools": [
|
|
3283
|
+
"conduyt_speed_to_lead_report"
|
|
3284
|
+
]
|
|
3285
|
+
},
|
|
3282
3286
|
"GET /api/v1/reports/subscriptions/:sid": {
|
|
3283
3287
|
"status": "planned",
|
|
3284
3288
|
"reason": "additional report surfaces beyond ai/insights"
|