@clipform/mcp-server 1.8.0 → 1.9.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 +3 -2
- package/dist/auth-context.js +9 -0
- package/dist/auth-context.js.map +1 -0
- package/dist/chunk-BWCZX7XY.js +3824 -0
- package/dist/chunk-BWCZX7XY.js.map +1 -0
- package/dist/chunk-MYWOSQ66.js +15 -0
- package/dist/chunk-MYWOSQ66.js.map +1 -0
- package/dist/index.js +15 -10
- package/dist/index.js.map +1 -1
- package/dist/server.js +7 -72
- package/dist/server.js.map +1 -1
- package/package.json +5 -4
- package/dist/__tests__/api-parity.test.d.ts +0 -1
- package/dist/__tests__/api-parity.test.js +0 -157
- package/dist/__tests__/api-parity.test.js.map +0 -1
- package/dist/__tests__/config-sync.test.d.ts +0 -1
- package/dist/__tests__/config-sync.test.js +0 -16
- package/dist/__tests__/config-sync.test.js.map +0 -1
- package/dist/index.d.ts +0 -2
- package/dist/lib/api-client.d.ts +0 -36
- package/dist/lib/api-client.js +0 -129
- package/dist/lib/api-client.js.map +0 -1
- package/dist/lib/auth-context.d.ts +0 -17
- package/dist/lib/auth-context.js +0 -9
- package/dist/lib/auth-context.js.map +0 -1
- package/dist/lib/config.d.ts +0 -23
- package/dist/lib/config.js +0 -6
- package/dist/lib/config.js.map +0 -1
- package/dist/lib/format-form.d.ts +0 -2
- package/dist/lib/format-form.js +0 -32
- package/dist/lib/format-form.js.map +0 -1
- package/dist/lib/render-jobs.d.ts +0 -13
- package/dist/lib/render-jobs.js +0 -38
- package/dist/lib/render-jobs.js.map +0 -1
- package/dist/lib/schemas.d.ts +0 -64
- package/dist/lib/schemas.js +0 -140
- package/dist/lib/schemas.js.map +0 -1
- package/dist/lib/session-context.d.ts +0 -1
- package/dist/lib/session-context.js +0 -38
- package/dist/lib/session-context.js.map +0 -1
- package/dist/prompts.d.ts +0 -2
- package/dist/prompts.js +0 -272
- package/dist/prompts.js.map +0 -1
- package/dist/resources.d.ts +0 -2
- package/dist/resources.js +0 -336
- package/dist/resources.js.map +0 -1
- package/dist/server.d.ts +0 -2
- package/dist/tools/add-node.d.ts +0 -2
- package/dist/tools/add-node.js +0 -50
- package/dist/tools/add-node.js.map +0 -1
- package/dist/tools/attach-node-audio.d.ts +0 -2
- package/dist/tools/attach-node-audio.js +0 -37
- package/dist/tools/attach-node-audio.js.map +0 -1
- package/dist/tools/check-render.d.ts +0 -2
- package/dist/tools/check-render.js +0 -47
- package/dist/tools/check-render.js.map +0 -1
- package/dist/tools/create-form.d.ts +0 -2
- package/dist/tools/create-form.js +0 -217
- package/dist/tools/create-form.js.map +0 -1
- package/dist/tools/delete-form.d.ts +0 -2
- package/dist/tools/delete-form.js +0 -28
- package/dist/tools/delete-form.js.map +0 -1
- package/dist/tools/delete-node-media.d.ts +0 -2
- package/dist/tools/delete-node-media.js +0 -29
- package/dist/tools/delete-node-media.js.map +0 -1
- package/dist/tools/delete-node.d.ts +0 -2
- package/dist/tools/delete-node.js +0 -32
- package/dist/tools/delete-node.js.map +0 -1
- package/dist/tools/generate-slideshow.d.ts +0 -2
- package/dist/tools/generate-slideshow.js +0 -155
- package/dist/tools/generate-slideshow.js.map +0 -1
- package/dist/tools/generate-tts.d.ts +0 -2
- package/dist/tools/generate-tts.js +0 -73
- package/dist/tools/generate-tts.js.map +0 -1
- package/dist/tools/generate-video.d.ts +0 -2
- package/dist/tools/generate-video.js +0 -119
- package/dist/tools/generate-video.js.map +0 -1
- package/dist/tools/get-form.d.ts +0 -2
- package/dist/tools/get-form.js +0 -31
- package/dist/tools/get-form.js.map +0 -1
- package/dist/tools/get-node-media.d.ts +0 -2
- package/dist/tools/get-node-media.js +0 -39
- package/dist/tools/get-node-media.js.map +0 -1
- package/dist/tools/list-assets.d.ts +0 -2
- package/dist/tools/list-assets.js +0 -45
- package/dist/tools/list-assets.js.map +0 -1
- package/dist/tools/list-compositions.d.ts +0 -2
- package/dist/tools/list-compositions.js +0 -34
- package/dist/tools/list-compositions.js.map +0 -1
- package/dist/tools/log-generation.d.ts +0 -2
- package/dist/tools/log-generation.js +0 -34
- package/dist/tools/log-generation.js.map +0 -1
- package/dist/tools/render-composition.d.ts +0 -2
- package/dist/tools/render-composition.js +0 -50
- package/dist/tools/render-composition.js.map +0 -1
- package/dist/tools/search-media.d.ts +0 -2
- package/dist/tools/search-media.js +0 -40
- package/dist/tools/search-media.js.map +0 -1
- package/dist/tools/search-music.d.ts +0 -2
- package/dist/tools/search-music.js +0 -40
- package/dist/tools/search-music.js.map +0 -1
- package/dist/tools/search-news.d.ts +0 -2
- package/dist/tools/search-news.js +0 -47
- package/dist/tools/search-news.js.map +0 -1
- package/dist/tools/set-node-logic.d.ts +0 -2
- package/dist/tools/set-node-logic.js +0 -56
- package/dist/tools/set-node-logic.js.map +0 -1
- package/dist/tools/update-form.d.ts +0 -2
- package/dist/tools/update-form.js +0 -140
- package/dist/tools/update-form.js.map +0 -1
- package/dist/tools/update-node.d.ts +0 -2
- package/dist/tools/update-node.js +0 -71
- package/dist/tools/update-node.js.map +0 -1
- package/dist/tools/upload-node-media.d.ts +0 -2
- package/dist/tools/upload-node-media.js +0 -109
- package/dist/tools/upload-node-media.js.map +0 -1
package/dist/lib/format-form.js
DELETED
|
@@ -1,32 +0,0 @@
|
|
|
1
|
-
import { callApi } from "./api-client.js";
|
|
2
|
-
export function formatFormState(data) {
|
|
3
|
-
const questions = data.questions;
|
|
4
|
-
const lines = [
|
|
5
|
-
`Form: ${data.title}`,
|
|
6
|
-
`Form ID: ${data.form_id}`,
|
|
7
|
-
`Published: ${data.is_published}`,
|
|
8
|
-
``,
|
|
9
|
-
`Nodes (in order):`,
|
|
10
|
-
];
|
|
11
|
-
for (let i = 0; i < questions.length; i++) {
|
|
12
|
-
const q = questions[i];
|
|
13
|
-
lines.push(` ${i + 1}. [${q.type}] ${q.prompt || "(no prompt)"}`);
|
|
14
|
-
lines.push(` Node ID: ${q.id}`);
|
|
15
|
-
if (q.required)
|
|
16
|
-
lines.push(` Required: yes`);
|
|
17
|
-
if (q.config && Object.keys(q.config).length > 0) {
|
|
18
|
-
lines.push(` Config: ${JSON.stringify(q.config)}`);
|
|
19
|
-
}
|
|
20
|
-
if (q.options && q.options.length > 0) {
|
|
21
|
-
lines.push(` Options: ${q.options.map((o) => o.content).join(", ")}`);
|
|
22
|
-
}
|
|
23
|
-
}
|
|
24
|
-
return lines.join("\n");
|
|
25
|
-
}
|
|
26
|
-
export async function fetchAndFormatFormState(formId, editToken) {
|
|
27
|
-
const result = await callApi(`/forms/${formId}`, { token: editToken });
|
|
28
|
-
if (!result.ok)
|
|
29
|
-
return null;
|
|
30
|
-
return formatFormState(result.data);
|
|
31
|
-
}
|
|
32
|
-
//# sourceMappingURL=format-form.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"format-form.js","sourceRoot":"","sources":["../../src/lib/format-form.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAE1C,MAAM,UAAU,eAAe,CAAC,IAA6B;IAC3D,MAAM,SAAS,GAAG,IAAI,CAAC,SAQrB,CAAC;IAEH,MAAM,KAAK,GAAa;QACtB,SAAS,IAAI,CAAC,KAAK,EAAE;QACrB,YAAY,IAAI,CAAC,OAAO,EAAE;QAC1B,cAAc,IAAI,CAAC,YAAY,EAAE;QACjC,EAAE;QACF,mBAAmB;KACpB,CAAC;IAEF,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,SAAS,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QAC1C,MAAM,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC,CAAC;QACvB,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,MAAM,IAAI,aAAa,EAAE,CAAC,CAAC;QACnE,KAAK,CAAC,IAAI,CAAC,iBAAiB,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QACpC,IAAI,CAAC,CAAC,QAAQ;YAAE,KAAK,CAAC,IAAI,CAAC,oBAAoB,CAAC,CAAC;QACjD,IAAI,CAAC,CAAC,MAAM,IAAI,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACjD,KAAK,CAAC,IAAI,CAAC,gBAAgB,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;QACzD,CAAC;QACD,IAAI,CAAC,CAAC,OAAO,IAAI,CAAC,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACtC,KAAK,CAAC,IAAI,CACR,iBAAiB,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAC9D,CAAC;QACJ,CAAC;IACH,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAC3C,MAAc,EACd,SAAkB;IAElB,MAAM,MAAM,GAAG,MAAM,OAAO,CAAC,UAAU,MAAM,EAAE,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,CAAC;IACvE,IAAI,CAAC,MAAM,CAAC,EAAE;QAAE,OAAO,IAAI,CAAC;IAC5B,OAAO,eAAe,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;AACtC,CAAC"}
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
export interface RenderJob {
|
|
2
|
-
id: string;
|
|
3
|
-
status: "rendering" | "complete" | "failed";
|
|
4
|
-
tool: string;
|
|
5
|
-
createdAt: number;
|
|
6
|
-
result?: Record<string, unknown>;
|
|
7
|
-
error?: string;
|
|
8
|
-
}
|
|
9
|
-
export declare function createJob(tool: string): RenderJob;
|
|
10
|
-
export declare function completeJob(id: string, result: Record<string, unknown>): void;
|
|
11
|
-
export declare function failJob(id: string, error: string): void;
|
|
12
|
-
export declare function getJob(id: string): RenderJob | undefined;
|
|
13
|
-
export declare function pruneJobs(): void;
|
package/dist/lib/render-jobs.js
DELETED
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
import { v4 as uuidv4 } from "uuid";
|
|
2
|
-
const jobs = new Map();
|
|
3
|
-
const MAX_AGE_MS = 30 * 60 * 1000; // 30 minutes
|
|
4
|
-
export function createJob(tool) {
|
|
5
|
-
const job = {
|
|
6
|
-
id: uuidv4(),
|
|
7
|
-
status: "rendering",
|
|
8
|
-
tool,
|
|
9
|
-
createdAt: Date.now(),
|
|
10
|
-
};
|
|
11
|
-
jobs.set(job.id, job);
|
|
12
|
-
return job;
|
|
13
|
-
}
|
|
14
|
-
export function completeJob(id, result) {
|
|
15
|
-
const job = jobs.get(id);
|
|
16
|
-
if (job) {
|
|
17
|
-
job.status = "complete";
|
|
18
|
-
job.result = result;
|
|
19
|
-
}
|
|
20
|
-
}
|
|
21
|
-
export function failJob(id, error) {
|
|
22
|
-
const job = jobs.get(id);
|
|
23
|
-
if (job) {
|
|
24
|
-
job.status = "failed";
|
|
25
|
-
job.error = error;
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
|
-
export function getJob(id) {
|
|
29
|
-
return jobs.get(id);
|
|
30
|
-
}
|
|
31
|
-
export function pruneJobs() {
|
|
32
|
-
const cutoff = Date.now() - MAX_AGE_MS;
|
|
33
|
-
for (const [id, job] of jobs) {
|
|
34
|
-
if (job.createdAt < cutoff)
|
|
35
|
-
jobs.delete(id);
|
|
36
|
-
}
|
|
37
|
-
}
|
|
38
|
-
//# sourceMappingURL=render-jobs.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"render-jobs.js","sourceRoot":"","sources":["../../src/lib/render-jobs.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,EAAE,IAAI,MAAM,EAAE,MAAM,MAAM,CAAC;AAWpC,MAAM,IAAI,GAAG,IAAI,GAAG,EAAqB,CAAC;AAE1C,MAAM,UAAU,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC,CAAC,aAAa;AAEhD,MAAM,UAAU,SAAS,CAAC,IAAY;IACpC,MAAM,GAAG,GAAc;QACrB,EAAE,EAAE,MAAM,EAAE;QACZ,MAAM,EAAE,WAAW;QACnB,IAAI;QACJ,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;KACtB,CAAC;IACF,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,EAAE,GAAG,CAAC,CAAC;IACtB,OAAO,GAAG,CAAC;AACb,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,EAAU,EAAE,MAA+B;IACrE,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;IACzB,IAAI,GAAG,EAAE,CAAC;QACR,GAAG,CAAC,MAAM,GAAG,UAAU,CAAC;QACxB,GAAG,CAAC,MAAM,GAAG,MAAM,CAAC;IACtB,CAAC;AACH,CAAC;AAED,MAAM,UAAU,OAAO,CAAC,EAAU,EAAE,KAAa;IAC/C,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;IACzB,IAAI,GAAG,EAAE,CAAC;QACR,GAAG,CAAC,MAAM,GAAG,QAAQ,CAAC;QACtB,GAAG,CAAC,KAAK,GAAG,KAAK,CAAC;IACpB,CAAC;AACH,CAAC;AAED,MAAM,UAAU,MAAM,CAAC,EAAU;IAC/B,OAAO,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;AACtB,CAAC;AAED,MAAM,UAAU,SAAS;IACvB,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,UAAU,CAAC;IACvC,KAAK,MAAM,CAAC,EAAE,EAAE,GAAG,CAAC,IAAI,IAAI,EAAE,CAAC;QAC7B,IAAI,GAAG,CAAC,SAAS,GAAG,MAAM;YAAE,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;IAC9C,CAAC;AACH,CAAC"}
|
package/dist/lib/schemas.d.ts
DELETED
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
import { z } from "zod";
|
|
2
|
-
/** Active, non-system node types — the only types the MCP server exposes */
|
|
3
|
-
export declare const ACTIVE_NODE_TYPES: [string, ...string[]];
|
|
4
|
-
/** Contact field IDs derived from the config package */
|
|
5
|
-
export declare const CONTACT_FIELD_IDS: string[];
|
|
6
|
-
/** Per-type description including config hints, auto-generated from NODE_TYPES */
|
|
7
|
-
export declare const NODE_TYPES_DESCRIPTION: string;
|
|
8
|
-
/** Aggregate config description for Zod .describe() on the config field */
|
|
9
|
-
export declare const CONFIG_DESCRIPTION: string;
|
|
10
|
-
export declare const OptionSchema: z.ZodObject<{
|
|
11
|
-
content: z.ZodString;
|
|
12
|
-
score: z.ZodOptional<z.ZodNumber>;
|
|
13
|
-
scores: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodNumber>>;
|
|
14
|
-
}, "strip", z.ZodTypeAny, {
|
|
15
|
-
content: string;
|
|
16
|
-
score?: number | undefined;
|
|
17
|
-
scores?: Record<string, number> | undefined;
|
|
18
|
-
}, {
|
|
19
|
-
content: string;
|
|
20
|
-
score?: number | undefined;
|
|
21
|
-
scores?: Record<string, number> | undefined;
|
|
22
|
-
}>;
|
|
23
|
-
export declare const NodeSchema: z.ZodObject<{
|
|
24
|
-
type: z.ZodEnum<[string, ...string[]]>;
|
|
25
|
-
prompt: z.ZodString;
|
|
26
|
-
label: z.ZodOptional<z.ZodString>;
|
|
27
|
-
required: z.ZodDefault<z.ZodOptional<z.ZodBoolean>>;
|
|
28
|
-
config: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
29
|
-
options: z.ZodOptional<z.ZodArray<z.ZodObject<{
|
|
30
|
-
content: z.ZodString;
|
|
31
|
-
score: z.ZodOptional<z.ZodNumber>;
|
|
32
|
-
scores: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodNumber>>;
|
|
33
|
-
}, "strip", z.ZodTypeAny, {
|
|
34
|
-
content: string;
|
|
35
|
-
score?: number | undefined;
|
|
36
|
-
scores?: Record<string, number> | undefined;
|
|
37
|
-
}, {
|
|
38
|
-
content: string;
|
|
39
|
-
score?: number | undefined;
|
|
40
|
-
scores?: Record<string, number> | undefined;
|
|
41
|
-
}>, "many">>;
|
|
42
|
-
}, "strip", z.ZodTypeAny, {
|
|
43
|
-
type: string;
|
|
44
|
-
prompt: string;
|
|
45
|
-
required: boolean;
|
|
46
|
-
options?: {
|
|
47
|
-
content: string;
|
|
48
|
-
score?: number | undefined;
|
|
49
|
-
scores?: Record<string, number> | undefined;
|
|
50
|
-
}[] | undefined;
|
|
51
|
-
label?: string | undefined;
|
|
52
|
-
config?: Record<string, unknown> | undefined;
|
|
53
|
-
}, {
|
|
54
|
-
type: string;
|
|
55
|
-
prompt: string;
|
|
56
|
-
options?: {
|
|
57
|
-
content: string;
|
|
58
|
-
score?: number | undefined;
|
|
59
|
-
scores?: Record<string, number> | undefined;
|
|
60
|
-
}[] | undefined;
|
|
61
|
-
label?: string | undefined;
|
|
62
|
-
required?: boolean | undefined;
|
|
63
|
-
config?: Record<string, unknown> | undefined;
|
|
64
|
-
}>;
|
package/dist/lib/schemas.js
DELETED
|
@@ -1,140 +0,0 @@
|
|
|
1
|
-
import { z } from "zod";
|
|
2
|
-
import { NODE_TYPES, CONTACT_FIELDS } from "./config.js";
|
|
3
|
-
// --- Derived constants (zero hardcoded type lists) ---
|
|
4
|
-
/** Active, non-system node types — the only types the MCP server exposes */
|
|
5
|
-
export const ACTIVE_NODE_TYPES = Object.entries(NODE_TYPES)
|
|
6
|
-
.filter(([, def]) => def.is_active && !def.is_system)
|
|
7
|
-
.map(([type]) => type); // tuple for z.enum
|
|
8
|
-
/** Contact field IDs derived from the config package */
|
|
9
|
-
export const CONTACT_FIELD_IDS = CONTACT_FIELDS.map((f) => f.id);
|
|
10
|
-
// --- Auto-generated config descriptions ---
|
|
11
|
-
/**
|
|
12
|
-
* Walk a JSON-Schema-style config_schema and produce a concise one-line summary.
|
|
13
|
-
* Handles primitives, enums, nested objects (1 level), and arrays with item shapes.
|
|
14
|
-
*/
|
|
15
|
-
function generateConfigSummary(configSchema, typeKey) {
|
|
16
|
-
if (!configSchema?.properties)
|
|
17
|
-
return "";
|
|
18
|
-
const parts = [];
|
|
19
|
-
for (const [key, prop] of Object.entries(configSchema.properties)) {
|
|
20
|
-
// Skip internal-only fields the LLM shouldn't set
|
|
21
|
-
if (key === "content_media_type")
|
|
22
|
-
continue;
|
|
23
|
-
if (prop.enum) {
|
|
24
|
-
const vals = prop.enum.map((v) => `"${v}"`).join("|");
|
|
25
|
-
let s = `${key} (${vals}`;
|
|
26
|
-
if (prop.default !== undefined)
|
|
27
|
-
s += `, default: "${prop.default}"`;
|
|
28
|
-
s += ")";
|
|
29
|
-
parts.push(s);
|
|
30
|
-
}
|
|
31
|
-
else if (prop.type === "boolean") {
|
|
32
|
-
let s = `${key} (boolean`;
|
|
33
|
-
if (prop.default !== undefined)
|
|
34
|
-
s += `, default: ${prop.default}`;
|
|
35
|
-
s += ")";
|
|
36
|
-
parts.push(s);
|
|
37
|
-
}
|
|
38
|
-
else if (prop.type === "number") {
|
|
39
|
-
let s = `${key} (number`;
|
|
40
|
-
if (prop.default !== undefined)
|
|
41
|
-
s += `, default: ${prop.default}`;
|
|
42
|
-
s += ")";
|
|
43
|
-
parts.push(s);
|
|
44
|
-
}
|
|
45
|
-
else if (prop.type === "string") {
|
|
46
|
-
let s = `${key} (string`;
|
|
47
|
-
if (prop.default !== undefined)
|
|
48
|
-
s += `, default: "${prop.default}"`;
|
|
49
|
-
s += ")";
|
|
50
|
-
parts.push(s);
|
|
51
|
-
}
|
|
52
|
-
else if (prop.type === "array" && prop.items?.properties) {
|
|
53
|
-
// Array of objects — show item shape
|
|
54
|
-
const itemKeys = Object.keys(prop.items.properties).join(", ");
|
|
55
|
-
parts.push(`${key} (array of {${itemKeys}})`);
|
|
56
|
-
}
|
|
57
|
-
else if (prop.type === "array" && prop.items?.enum) {
|
|
58
|
-
const vals = prop.items.enum.map((v) => `"${v}"`).join("|");
|
|
59
|
-
parts.push(`${key} (array of ${vals})`);
|
|
60
|
-
}
|
|
61
|
-
else if (prop.type === "object" && prop.properties) {
|
|
62
|
-
// Nested object — summarize child keys
|
|
63
|
-
const childKeys = Object.keys(prop.properties).join(", ");
|
|
64
|
-
parts.push(`${key} ({${childKeys}})`);
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
// Special case: for contact type, append available field IDs
|
|
68
|
-
if (typeKey === "contact") {
|
|
69
|
-
parts.push(`Available field IDs: ${CONTACT_FIELD_IDS.join(", ")}`);
|
|
70
|
-
}
|
|
71
|
-
return parts.length > 0 ? `Config: ${parts.join(", ")}` : "";
|
|
72
|
-
}
|
|
73
|
-
/** Per-type description including config hints, auto-generated from NODE_TYPES */
|
|
74
|
-
export const NODE_TYPES_DESCRIPTION = (() => {
|
|
75
|
-
const lines = ["Node types:"];
|
|
76
|
-
for (const type of ACTIVE_NODE_TYPES) {
|
|
77
|
-
const def = NODE_TYPES[type];
|
|
78
|
-
let line = `- ${type}: ${def.description || def.label}`;
|
|
79
|
-
if (def.has_options) {
|
|
80
|
-
line += " (supports options array)";
|
|
81
|
-
}
|
|
82
|
-
const configHint = generateConfigSummary(def.config_schema, type);
|
|
83
|
-
if (configHint) {
|
|
84
|
-
line += `. ${configHint}`;
|
|
85
|
-
}
|
|
86
|
-
lines.push(line);
|
|
87
|
-
}
|
|
88
|
-
return lines.join("\n");
|
|
89
|
-
})();
|
|
90
|
-
/** Aggregate config description for Zod .describe() on the config field */
|
|
91
|
-
export const CONFIG_DESCRIPTION = (() => {
|
|
92
|
-
const lines = ["Type-specific configuration. Per-type keys:"];
|
|
93
|
-
for (const type of ACTIVE_NODE_TYPES) {
|
|
94
|
-
const def = NODE_TYPES[type];
|
|
95
|
-
const summary = generateConfigSummary(def.config_schema, type);
|
|
96
|
-
if (summary) {
|
|
97
|
-
lines.push(` ${type}: ${summary}`);
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
return lines.join("\n");
|
|
101
|
-
})();
|
|
102
|
-
// --- Zod schemas ---
|
|
103
|
-
export const OptionSchema = z.object({
|
|
104
|
-
content: z.string().describe("Option text"),
|
|
105
|
-
score: z.number().optional().describe("Score value for this option (for scored quizzes)"),
|
|
106
|
-
scores: z.record(z.number()).optional().describe("Category-based scores keyed by category name (for personality/category quizzes)"),
|
|
107
|
-
});
|
|
108
|
-
/** Build options description from config - which types need options, min counts, max lengths */
|
|
109
|
-
const OPTIONS_DESCRIPTION = (() => {
|
|
110
|
-
const hints = ["Answer options."];
|
|
111
|
-
for (const type of ACTIVE_NODE_TYPES) {
|
|
112
|
-
const def = NODE_TYPES[type];
|
|
113
|
-
if (!def.has_options)
|
|
114
|
-
continue;
|
|
115
|
-
const parts = [`${type}: required`];
|
|
116
|
-
if (def.min_options !== undefined)
|
|
117
|
-
parts.push(`min ${def.min_options}`);
|
|
118
|
-
if (def.max_options !== undefined)
|
|
119
|
-
parts.push(`max ${def.max_options}`);
|
|
120
|
-
if (def.max_option_length !== undefined)
|
|
121
|
-
parts.push(`content max ${def.max_option_length} chars`);
|
|
122
|
-
hints.push(parts.join(", "));
|
|
123
|
-
}
|
|
124
|
-
return hints.join(" ");
|
|
125
|
-
})();
|
|
126
|
-
export const NodeSchema = z.object({
|
|
127
|
-
type: z.enum(ACTIVE_NODE_TYPES),
|
|
128
|
-
prompt: z.string().describe("The text shown to the respondent"),
|
|
129
|
-
label: z.string().optional().describe("Short label for the node (used in logic builder). Defaults to the prompt text."),
|
|
130
|
-
required: z.boolean().optional().default(true),
|
|
131
|
-
config: z
|
|
132
|
-
.record(z.unknown())
|
|
133
|
-
.optional()
|
|
134
|
-
.describe(CONFIG_DESCRIPTION),
|
|
135
|
-
options: z
|
|
136
|
-
.array(OptionSchema)
|
|
137
|
-
.optional()
|
|
138
|
-
.describe(OPTIONS_DESCRIPTION),
|
|
139
|
-
});
|
|
140
|
-
//# sourceMappingURL=schemas.js.map
|
package/dist/lib/schemas.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"schemas.js","sourceRoot":"","sources":["../../src/lib/schemas.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,UAAU,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAEzD,wDAAwD;AAExD,4EAA4E;AAC5E,MAAM,CAAC,MAAM,iBAAiB,GAAG,MAAM,CAAC,OAAO,CAAC,UAAiC,CAAC;KAC/E,MAAM,CAAC,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,SAAS,IAAI,CAAC,GAAG,CAAC,SAAS,CAAC;KACpD,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,IAAI,CAA0B,CAAC,CAAC,mBAAmB;AAEtE,wDAAwD;AACxD,MAAM,CAAC,MAAM,iBAAiB,GAAG,cAAc,CAAC,GAAG,CACjD,CAAC,CAAiB,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAC5B,CAAC;AAEF,6CAA6C;AAE7C;;;GAGG;AACH,SAAS,qBAAqB,CAC5B,YAAiB,EACjB,OAAgB;IAEhB,IAAI,CAAC,YAAY,EAAE,UAAU;QAAE,OAAO,EAAE,CAAC;IAEzC,MAAM,KAAK,GAAa,EAAE,CAAC;IAE3B,KAAK,MAAM,CAAC,GAAG,EAAE,IAAI,CAAC,IAAI,MAAM,CAAC,OAAO,CAAM,YAAY,CAAC,UAAU,CAAC,EAAE,CAAC;QACvE,kDAAkD;QAClD,IAAI,GAAG,KAAK,oBAAoB;YAAE,SAAS;QAE3C,IAAI,IAAI,CAAC,IAAI,EAAE,CAAC;YACd,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAS,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;YAC9D,IAAI,CAAC,GAAG,GAAG,GAAG,KAAK,IAAI,EAAE,CAAC;YAC1B,IAAI,IAAI,CAAC,OAAO,KAAK,SAAS;gBAAE,CAAC,IAAI,eAAe,IAAI,CAAC,OAAO,GAAG,CAAC;YACpE,CAAC,IAAI,GAAG,CAAC;YACT,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChB,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,SAAS,EAAE,CAAC;YACnC,IAAI,CAAC,GAAG,GAAG,GAAG,WAAW,CAAC;YAC1B,IAAI,IAAI,CAAC,OAAO,KAAK,SAAS;gBAAE,CAAC,IAAI,cAAc,IAAI,CAAC,OAAO,EAAE,CAAC;YAClE,CAAC,IAAI,GAAG,CAAC;YACT,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChB,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YAClC,IAAI,CAAC,GAAG,GAAG,GAAG,UAAU,CAAC;YACzB,IAAI,IAAI,CAAC,OAAO,KAAK,SAAS;gBAAE,CAAC,IAAI,cAAc,IAAI,CAAC,OAAO,EAAE,CAAC;YAClE,CAAC,IAAI,GAAG,CAAC;YACT,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChB,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YAClC,IAAI,CAAC,GAAG,GAAG,GAAG,UAAU,CAAC;YACzB,IAAI,IAAI,CAAC,OAAO,KAAK,SAAS;gBAAE,CAAC,IAAI,eAAe,IAAI,CAAC,OAAO,GAAG,CAAC;YACpE,CAAC,IAAI,GAAG,CAAC;YACT,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChB,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,OAAO,IAAI,IAAI,CAAC,KAAK,EAAE,UAAU,EAAE,CAAC;YAC3D,qCAAqC;YACrC,MAAM,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAC/D,KAAK,CAAC,IAAI,CAAC,GAAG,GAAG,eAAe,QAAQ,IAAI,CAAC,CAAC;QAChD,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,OAAO,IAAI,IAAI,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC;YACrD,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAS,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;YACpE,KAAK,CAAC,IAAI,CAAC,GAAG,GAAG,cAAc,IAAI,GAAG,CAAC,CAAC;QAC1C,CAAC;aAAM,IAAI,IAAI,CAAC,IAAI,KAAK,QAAQ,IAAI,IAAI,CAAC,UAAU,EAAE,CAAC;YACrD,uCAAuC;YACvC,MAAM,SAAS,GAAG,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAC1D,KAAK,CAAC,IAAI,CAAC,GAAG,GAAG,MAAM,SAAS,IAAI,CAAC,CAAC;QACxC,CAAC;IACH,CAAC;IAED,6DAA6D;IAC7D,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;QAC1B,KAAK,CAAC,IAAI,CAAC,wBAAwB,iBAAiB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IACrE,CAAC;IAED,OAAO,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,WAAW,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;AAC/D,CAAC;AAED,kFAAkF;AAClF,MAAM,CAAC,MAAM,sBAAsB,GAAG,CAAC,GAAG,EAAE;IAC1C,MAAM,KAAK,GAAa,CAAC,aAAa,CAAC,CAAC;IAExC,KAAK,MAAM,IAAI,IAAI,iBAAiB,EAAE,CAAC;QACrC,MAAM,GAAG,GAAI,UAAkC,CAAC,IAAI,CAAC,CAAC;QACtD,IAAI,IAAI,GAAG,KAAK,IAAI,KAAK,GAAG,CAAC,WAAW,IAAI,GAAG,CAAC,KAAK,EAAE,CAAC;QAExD,IAAI,GAAG,CAAC,WAAW,EAAE,CAAC;YACpB,IAAI,IAAI,2BAA2B,CAAC;QACtC,CAAC;QAED,MAAM,UAAU,GAAG,qBAAqB,CAAC,GAAG,CAAC,aAAa,EAAE,IAAI,CAAC,CAAC;QAClE,IAAI,UAAU,EAAE,CAAC;YACf,IAAI,IAAI,KAAK,UAAU,EAAE,CAAC;QAC5B,CAAC;QAED,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACnB,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC,CAAC,EAAE,CAAC;AAEL,2EAA2E;AAC3E,MAAM,CAAC,MAAM,kBAAkB,GAAG,CAAC,GAAG,EAAE;IACtC,MAAM,KAAK,GAAa,CAAC,6CAA6C,CAAC,CAAC;IAExE,KAAK,MAAM,IAAI,IAAI,iBAAiB,EAAE,CAAC;QACrC,MAAM,GAAG,GAAI,UAAkC,CAAC,IAAI,CAAC,CAAC;QACtD,MAAM,OAAO,GAAG,qBAAqB,CAAC,GAAG,CAAC,aAAa,EAAE,IAAI,CAAC,CAAC;QAC/D,IAAI,OAAO,EAAE,CAAC;YACZ,KAAK,CAAC,IAAI,CAAC,KAAK,IAAI,KAAK,OAAO,EAAE,CAAC,CAAC;QACtC,CAAC;IACH,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC,CAAC,EAAE,CAAC;AAEL,sBAAsB;AAEtB,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,CAAC,MAAM,CAAC;IACnC,OAAO,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,aAAa,CAAC;IAC3C,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,kDAAkD,CAAC;IACzF,MAAM,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,iFAAiF,CAAC;CACpI,CAAC,CAAC;AAEH,gGAAgG;AAChG,MAAM,mBAAmB,GAAG,CAAC,GAAG,EAAE;IAChC,MAAM,KAAK,GAAa,CAAC,iBAAiB,CAAC,CAAC;IAC5C,KAAK,MAAM,IAAI,IAAI,iBAAiB,EAAE,CAAC;QACrC,MAAM,GAAG,GAAI,UAAkC,CAAC,IAAI,CAAC,CAAC;QACtD,IAAI,CAAC,GAAG,CAAC,WAAW;YAAE,SAAS;QAC/B,MAAM,KAAK,GAAa,CAAC,GAAG,IAAI,YAAY,CAAC,CAAC;QAC9C,IAAI,GAAG,CAAC,WAAW,KAAK,SAAS;YAAE,KAAK,CAAC,IAAI,CAAC,OAAO,GAAG,CAAC,WAAW,EAAE,CAAC,CAAC;QACxE,IAAI,GAAG,CAAC,WAAW,KAAK,SAAS;YAAE,KAAK,CAAC,IAAI,CAAC,OAAO,GAAG,CAAC,WAAW,EAAE,CAAC,CAAC;QACxE,IAAI,GAAG,CAAC,iBAAiB,KAAK,SAAS;YAAE,KAAK,CAAC,IAAI,CAAC,eAAe,GAAG,CAAC,iBAAiB,QAAQ,CAAC,CAAC;QAClG,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IAC/B,CAAC;IACD,OAAO,KAAK,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AACzB,CAAC,CAAC,EAAE,CAAC;AAEL,MAAM,CAAC,MAAM,UAAU,GAAG,CAAC,CAAC,MAAM,CAAC;IACjC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,iBAAiB,CAAC;IAC/B,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,kCAAkC,CAAC;IAC/D,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE,CAAC,QAAQ,CAAC,gFAAgF,CAAC;IACvH,QAAQ,EAAE,CAAC,CAAC,OAAO,EAAE,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC;IAC9C,MAAM,EAAE,CAAC;SACN,MAAM,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC;SACnB,QAAQ,EAAE;SACV,QAAQ,CAAC,kBAAkB,CAAC;IAC/B,OAAO,EAAE,CAAC;SACP,KAAK,CAAC,YAAY,CAAC;SACnB,QAAQ,EAAE;SACV,QAAQ,CAAC,mBAAmB,CAAC;CACjC,CAAC,CAAC"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export declare function getSessionContext(): Promise<string>;
|
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
import { BUSINESS } from "@vid-master/config";
|
|
2
|
-
import { callApi } from "./api-client.js";
|
|
3
|
-
export async function getSessionContext() {
|
|
4
|
-
const result = await callApi("/me", { method: "GET" });
|
|
5
|
-
if (!result.ok)
|
|
6
|
-
return "";
|
|
7
|
-
const me = result.data;
|
|
8
|
-
const plan = me.plan;
|
|
9
|
-
const lines = [];
|
|
10
|
-
lines.push("## Your Session");
|
|
11
|
-
if (me.auth_mode === "oauth") {
|
|
12
|
-
lines.push(`Auth: OAuth (connected)`);
|
|
13
|
-
lines.push(`Workspace: ${me.workspace?.name ?? "Unknown"} (${me.workspace?.id ?? "?"})`);
|
|
14
|
-
lines.push(`User: ${me.user_id ?? "?"}`);
|
|
15
|
-
lines.push(`Company: ${me.company_id ?? "none"}`);
|
|
16
|
-
}
|
|
17
|
-
else {
|
|
18
|
-
lines.push("Auth: anonymous (not connected to a Clipform account)");
|
|
19
|
-
if (me.workspace) {
|
|
20
|
-
lines.push(`Workspace: ${me.workspace.name} (${me.workspace.id})`);
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
lines.push(`Plan: ${plan.name} (tier ${plan.tier})`);
|
|
24
|
-
if (plan.node_limit !== null) {
|
|
25
|
-
lines.push(`Question limit: ${plan.node_limit} per form`);
|
|
26
|
-
}
|
|
27
|
-
else {
|
|
28
|
-
lines.push("Questions: unlimited");
|
|
29
|
-
}
|
|
30
|
-
if (plan.custom_theme === false) {
|
|
31
|
-
lines.push("Custom themes: not available on this plan");
|
|
32
|
-
}
|
|
33
|
-
if (me.auth_mode !== "oauth") {
|
|
34
|
-
lines.push(`\nTo unlock your full plan: connect your Clipform account in Settings > Connectors > ${BUSINESS.urls.mcp}`);
|
|
35
|
-
}
|
|
36
|
-
return lines.join("\n");
|
|
37
|
-
}
|
|
38
|
-
//# sourceMappingURL=session-context.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"session-context.js","sourceRoot":"","sources":["../../src/lib/session-context.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAE1C,MAAM,CAAC,KAAK,UAAU,iBAAiB;IACrC,MAAM,MAAM,GAAG,MAAM,OAAO,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;IACvD,IAAI,CAAC,MAAM,CAAC,EAAE;QAAE,OAAO,EAAE,CAAC;IAE1B,MAAM,EAAE,GAAG,MAAM,CAAC,IAAW,CAAC;IAC9B,MAAM,IAAI,GAAG,EAAE,CAAC,IAAI,CAAC;IACrB,MAAM,KAAK,GAAa,EAAE,CAAC;IAE3B,KAAK,CAAC,IAAI,CAAC,iBAAiB,CAAC,CAAC;IAC9B,IAAI,EAAE,CAAC,SAAS,KAAK,OAAO,EAAE,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,yBAAyB,CAAC,CAAC;QACtC,KAAK,CAAC,IAAI,CAAC,cAAc,EAAE,CAAC,SAAS,EAAE,IAAI,IAAI,SAAS,KAAK,EAAE,CAAC,SAAS,EAAE,EAAE,IAAI,GAAG,GAAG,CAAC,CAAC;QACzF,KAAK,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC,OAAO,IAAI,GAAG,EAAE,CAAC,CAAC;QACzC,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,CAAC,UAAU,IAAI,MAAM,EAAE,CAAC,CAAC;IACpD,CAAC;SAAM,CAAC;QACN,KAAK,CAAC,IAAI,CAAC,uDAAuD,CAAC,CAAC;QACpE,IAAI,EAAE,CAAC,SAAS,EAAE,CAAC;YACjB,KAAK,CAAC,IAAI,CAAC,cAAc,EAAE,CAAC,SAAS,CAAC,IAAI,KAAK,EAAE,CAAC,SAAS,CAAC,EAAE,GAAG,CAAC,CAAC;QACrE,CAAC;IACH,CAAC;IACD,KAAK,CAAC,IAAI,CAAC,SAAS,IAAI,CAAC,IAAI,UAAU,IAAI,CAAC,IAAI,GAAG,CAAC,CAAC;IACrD,IAAI,IAAI,CAAC,UAAU,KAAK,IAAI,EAAE,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,mBAAmB,IAAI,CAAC,UAAU,WAAW,CAAC,CAAC;IAC5D,CAAC;SAAM,CAAC;QACN,KAAK,CAAC,IAAI,CAAC,sBAAsB,CAAC,CAAC;IACrC,CAAC;IACD,IAAI,IAAI,CAAC,YAAY,KAAK,KAAK,EAAE,CAAC;QAChC,KAAK,CAAC,IAAI,CAAC,2CAA2C,CAAC,CAAC;IAC1D,CAAC;IACD,IAAI,EAAE,CAAC,SAAS,KAAK,OAAO,EAAE,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,wFAAwF,QAAQ,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC;IAC1H,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AAC1B,CAAC"}
|
package/dist/prompts.d.ts
DELETED
package/dist/prompts.js
DELETED
|
@@ -1,272 +0,0 @@
|
|
|
1
|
-
import { getSessionContext } from "./lib/session-context.js";
|
|
2
|
-
export function registerPrompts(server) {
|
|
3
|
-
server.registerPrompt("create-quiz", {
|
|
4
|
-
title: "Create a Quiz",
|
|
5
|
-
description: "Build a scored knowledge quiz with narrated video questions",
|
|
6
|
-
}, async () => {
|
|
7
|
-
const sessionContext = await getSessionContext();
|
|
8
|
-
return {
|
|
9
|
-
messages: [
|
|
10
|
-
{
|
|
11
|
-
role: "user",
|
|
12
|
-
content: {
|
|
13
|
-
type: "text",
|
|
14
|
-
text: "I want to create a quiz. What's the best approach?",
|
|
15
|
-
},
|
|
16
|
-
},
|
|
17
|
-
{
|
|
18
|
-
role: "assistant",
|
|
19
|
-
content: {
|
|
20
|
-
type: "text",
|
|
21
|
-
text: `${sessionContext ? sessionContext + "\n\n" : ""}Here's how to build a great quiz with Clipform. Read the quiz writing guide (clipform://guides/quiz) for detailed craft knowledge on question design, difficulty curves, and narration style.
|
|
22
|
-
|
|
23
|
-
## Workflow
|
|
24
|
-
|
|
25
|
-
1. **Research** the topic - find surprising facts, common misconceptions, myth-busters
|
|
26
|
-
2. **Write questions** - follow the difficulty curve (easy start, hard middle, satisfying end). Target 5-8 questions.
|
|
27
|
-
3. **Create the form** with clipform_create_form:
|
|
28
|
-
- show_step_counter: true
|
|
29
|
-
- disable_back_navigation: true
|
|
30
|
-
4. **Add questions** with clipform_add_node (type: "choice"):
|
|
31
|
-
- config: { choice: { show_answer_feedback: true } }
|
|
32
|
-
- randomise_options: true in config
|
|
33
|
-
- score: 1 on correct option, score: 0 on wrong
|
|
34
|
-
- 3-4 wrong answers per question
|
|
35
|
-
5. **Generate narration** with clipform_generate_tts for each question. Tease the question - do NOT reveal the answer or read options aloud. Keep each narration 5-15 seconds.
|
|
36
|
-
6. **Build video** for each question:
|
|
37
|
-
- clipform_search_media (kind: "image") - 3 images per question
|
|
38
|
-
- clipform_generate_video - creates Ken Burns video synced to audio
|
|
39
|
-
7. **Attach media** with clipform_upload_node_media. Include captions, set show_captions: true.
|
|
40
|
-
8. **Update end screen** with clipform_update_node - EVERY quiz must have:
|
|
41
|
-
- show_score: true, icon: "trophy"
|
|
42
|
-
- show_share_button: true (drives virality)
|
|
43
|
-
- cta_type: "restart", cta_text: a short challenge like "Beat your score?" or "Try again?"
|
|
44
|
-
- score_ranges with personalised title + message per tier. Write these in the quiz's voice - short, punchy, and specific to the topic (not generic "Good job!"). Example for a geography quiz:
|
|
45
|
-
\`\`\`json
|
|
46
|
-
{ "min": 0, "max": 2, "title": "Lost Tourist", "message": "You might need a map - and a compass." },
|
|
47
|
-
{ "min": 3, "max": 5, "title": "Frequent Flyer", "message": "Not bad! You know your way around." },
|
|
48
|
-
{ "min": 6, "max": 8, "title": "World Explorer", "message": "Impressive - you really know your stuff." }
|
|
49
|
-
\`\`\`
|
|
50
|
-
9. **Publish** with clipform_update_form
|
|
51
|
-
10. **Tag the form** - pass tags: one format (quiz/survey/interview/feedback/lead-gen), one genre (trivia/personality/nps/poll/testimonial), and 2-3 topic words
|
|
52
|
-
11. **Log** with clipform_log_generation (sources, images, attributions)
|
|
53
|
-
|
|
54
|
-
## Before building, ask
|
|
55
|
-
|
|
56
|
-
1. How many questions?
|
|
57
|
-
2. Media style: text only, still images, or slideshow video with narration?
|
|
58
|
-
3. Any topic or style preferences?`,
|
|
59
|
-
},
|
|
60
|
-
},
|
|
61
|
-
],
|
|
62
|
-
};
|
|
63
|
-
});
|
|
64
|
-
server.registerPrompt("create-personality-quiz", {
|
|
65
|
-
title: "Create a Personality Quiz",
|
|
66
|
-
description: "Build a 'Which X are you?' personality quiz with category-based scoring and outcome screens",
|
|
67
|
-
}, async () => {
|
|
68
|
-
const sessionContext = await getSessionContext();
|
|
69
|
-
return {
|
|
70
|
-
messages: [
|
|
71
|
-
{
|
|
72
|
-
role: "user",
|
|
73
|
-
content: {
|
|
74
|
-
type: "text",
|
|
75
|
-
text: "I want to create a personality quiz. What's the best approach?",
|
|
76
|
-
},
|
|
77
|
-
},
|
|
78
|
-
{
|
|
79
|
-
role: "assistant",
|
|
80
|
-
content: {
|
|
81
|
-
type: "text",
|
|
82
|
-
text: `${sessionContext ? sessionContext + "\n\n" : ""}Here's how to build a personality quiz with Clipform. Read the personality quiz guide (clipform://guides/personality-quiz) for craft knowledge on category design, option weighting, and outcome writing.
|
|
83
|
-
|
|
84
|
-
## How it differs from a knowledge quiz
|
|
85
|
-
|
|
86
|
-
There are NO correct answers. Each option maps to one or more outcome categories via \`scores\` (not \`score\`). The winning category at the end determines which result screen the respondent sees.
|
|
87
|
-
|
|
88
|
-
## Workflow
|
|
89
|
-
|
|
90
|
-
1. **Define 3-5 outcome categories** - these are the "personalities" (e.g. "Creative", "Analytical", "Leader", "Collaborator"). More than 5 gets muddy.
|
|
91
|
-
2. **Write questions** - each question should feel revealing but fun. Target 5-8 questions.
|
|
92
|
-
3. **Create the form** with clipform_create_form:
|
|
93
|
-
- show_step_counter: true
|
|
94
|
-
- disable_back_navigation: true
|
|
95
|
-
4. **Add questions** with clipform_add_node (type: "choice"):
|
|
96
|
-
- config: { choice: { show_answer_feedback: false } } (no right/wrong!)
|
|
97
|
-
- Do NOT set randomise_options (option order matters for personality quizzes - lead with the most appealing)
|
|
98
|
-
- Each option gets \`scores: { "CategoryA": 2, "CategoryB": 1 }\` - weight towards relevant categories
|
|
99
|
-
- Every option should score in at least one category (no dead options)
|
|
100
|
-
5. **Generate narration** with clipform_generate_tts - conversational, reflective tone. "What does this say about you?" not "Do you know the answer?"
|
|
101
|
-
6. **Build video** + **attach media** (same as knowledge quiz workflow)
|
|
102
|
-
7. **Update end screen** with clipform_update_node - EVERY personality quiz must have:
|
|
103
|
-
- show_score: false, icon: "star"
|
|
104
|
-
- show_share_button: true (personality results are inherently shareable - "I got X, what did you get?")
|
|
105
|
-
- cta_type: "restart", cta_text: "Find out again?" or "Take it again?"
|
|
106
|
-
- scoring_results (NOT score_ranges) with a result per category. Write the title as an identity reveal ("You're a Creative!") and the message as a short, flattering description that makes people want to share it. Be specific to the quiz theme, not generic. Example:
|
|
107
|
-
\`\`\`json
|
|
108
|
-
{
|
|
109
|
-
"show_score": false,
|
|
110
|
-
"icon": "star",
|
|
111
|
-
"show_share_button": true,
|
|
112
|
-
"cta_type": "restart",
|
|
113
|
-
"cta_text": "Retake quiz",
|
|
114
|
-
"scoring_results": [
|
|
115
|
-
{ "category": "Creative", "title": "You're a Creative!", "message": "You see the world through colour and possibility. Where others see problems, you see raw material." },
|
|
116
|
-
{ "category": "Analytical", "title": "You're an Analyst!", "message": "You don't guess - you figure it out. Your superpower is turning chaos into clarity." }
|
|
117
|
-
]
|
|
118
|
-
}
|
|
119
|
-
\`\`\`
|
|
120
|
-
8. **Publish** with clipform_update_form
|
|
121
|
-
9. **Tag the form** - pass tags: one format (quiz/survey/interview/feedback/lead-gen), one genre (trivia/personality/nps/poll/testimonial), and 2-3 topic words
|
|
122
|
-
10. **Log** with clipform_log_generation
|
|
123
|
-
|
|
124
|
-
## Before building, ask
|
|
125
|
-
|
|
126
|
-
1. What are the possible outcomes/personalities? (3-5 categories)
|
|
127
|
-
2. What's the theme? ("Which city are you?", "What's your work style?", "Which character are you?")
|
|
128
|
-
3. Media style: text only, still images, or slideshow video with narration?`,
|
|
129
|
-
},
|
|
130
|
-
},
|
|
131
|
-
],
|
|
132
|
-
};
|
|
133
|
-
});
|
|
134
|
-
server.registerPrompt("create-interview", {
|
|
135
|
-
title: "Create an Interview",
|
|
136
|
-
description: "Build a form to collect testimonials, case studies, async video interviews, or journalist responses",
|
|
137
|
-
}, async () => {
|
|
138
|
-
const sessionContext = await getSessionContext();
|
|
139
|
-
return {
|
|
140
|
-
messages: [
|
|
141
|
-
{
|
|
142
|
-
role: "user",
|
|
143
|
-
content: {
|
|
144
|
-
type: "text",
|
|
145
|
-
text: "I want to collect responses or testimonials from people. What's the best approach?",
|
|
146
|
-
},
|
|
147
|
-
},
|
|
148
|
-
{
|
|
149
|
-
role: "assistant",
|
|
150
|
-
content: {
|
|
151
|
-
type: "text",
|
|
152
|
-
text: `${sessionContext ? sessionContext + "\n\n" : ""}Here's how to build an interview or testimonial form with Clipform. Read the interview guide (clipform://guides/interview) for detailed craft knowledge on question design and pacing.
|
|
153
|
-
|
|
154
|
-
## Workflow
|
|
155
|
-
|
|
156
|
-
1. **Identify the ask** - what do you need from respondents? Testimonial, case study, expert comment, job application?
|
|
157
|
-
2. **Create the form** with clipform_create_form:
|
|
158
|
-
- show_step_counter: true
|
|
159
|
-
- disable_back_navigation: false
|
|
160
|
-
3. **Add a warm-up question** - something easy: "Tell us your name and role" (type: "open")
|
|
161
|
-
4. **Add core questions** (type: "open") - 2-3 max, one topic per question. Enable text + audio + video responses.
|
|
162
|
-
5. **Add contact collection** (type: "contact") - first name + email minimum
|
|
163
|
-
6. **Add consent** if needed - "I agree that my response may be used in [context]"
|
|
164
|
-
7. **Update end screen** - set expectations: "Thanks! We'll be in touch."
|
|
165
|
-
8. **Optional: add narration** - warm, inviting tone. "We'd love to hear your story..."
|
|
166
|
-
9. **Publish** with clipform_update_form
|
|
167
|
-
10. **Tag the form** - pass tags: one format (quiz/survey/interview/feedback/lead-gen), one genre (trivia/personality/nps/poll/testimonial), and 2-3 topic words
|
|
168
|
-
|
|
169
|
-
## Before building, ask
|
|
170
|
-
|
|
171
|
-
1. What are you collecting? (testimonial, case study, interview, application)
|
|
172
|
-
2. Should respondents reply with video, audio, text, or all three?
|
|
173
|
-
3. Do you need a consent statement?`,
|
|
174
|
-
},
|
|
175
|
-
},
|
|
176
|
-
],
|
|
177
|
-
};
|
|
178
|
-
});
|
|
179
|
-
server.registerPrompt("create-survey", {
|
|
180
|
-
title: "Create a Survey",
|
|
181
|
-
description: "Build a feedback survey, NPS form, or research questionnaire",
|
|
182
|
-
}, async () => {
|
|
183
|
-
const sessionContext = await getSessionContext();
|
|
184
|
-
return {
|
|
185
|
-
messages: [
|
|
186
|
-
{
|
|
187
|
-
role: "user",
|
|
188
|
-
content: {
|
|
189
|
-
type: "text",
|
|
190
|
-
text: "I want to collect feedback or run a survey. What's the best approach?",
|
|
191
|
-
},
|
|
192
|
-
},
|
|
193
|
-
{
|
|
194
|
-
role: "assistant",
|
|
195
|
-
content: {
|
|
196
|
-
type: "text",
|
|
197
|
-
text: `${sessionContext ? sessionContext + "\n\n" : ""}Here's how to build a survey with Clipform. Read the survey guide (clipform://guides/survey) for craft knowledge on question design and reducing respondent fatigue.
|
|
198
|
-
|
|
199
|
-
## Workflow
|
|
200
|
-
|
|
201
|
-
1. **Define the key metric** - what's the one number you care about? (NPS, satisfaction, likelihood to recommend)
|
|
202
|
-
2. **Create the form** with clipform_create_form:
|
|
203
|
-
- show_step_counter: true
|
|
204
|
-
- disable_back_navigation: false
|
|
205
|
-
3. **Add key metric question first** (type: "choice" or "rating") - put it first while attention is highest
|
|
206
|
-
4. **Add one "why?" follow-up** (type: "open") - "What's the main reason for your score?"
|
|
207
|
-
5. **Add 2-3 specific questions** (type: "choice") - only ask what you'll act on
|
|
208
|
-
6. **Contact** (optional) - only if you need to follow up. Many surveys work better anonymous.
|
|
209
|
-
7. **Update end screen** - "Thanks for your feedback!"
|
|
210
|
-
8. **Publish** with clipform_update_form
|
|
211
|
-
9. **Tag the form** - pass tags: one format (quiz/survey/interview/feedback/lead-gen), one genre (trivia/personality/nps/poll/testimonial), and 2-3 topic words
|
|
212
|
-
|
|
213
|
-
## Key rule: 5 questions max. Every extra question costs completions.
|
|
214
|
-
|
|
215
|
-
## Before building, ask
|
|
216
|
-
|
|
217
|
-
1. What feedback are you collecting? (NPS, satisfaction, event feedback, product research)
|
|
218
|
-
2. Anonymous or identified?
|
|
219
|
-
3. Any specific areas you want to ask about?`,
|
|
220
|
-
},
|
|
221
|
-
},
|
|
222
|
-
],
|
|
223
|
-
};
|
|
224
|
-
});
|
|
225
|
-
server.registerPrompt("create-funnel", {
|
|
226
|
-
title: "Create a Funnel",
|
|
227
|
-
description: "Build a lead qualification funnel or product recommendation quiz with branching logic",
|
|
228
|
-
}, async () => {
|
|
229
|
-
const sessionContext = await getSessionContext();
|
|
230
|
-
return {
|
|
231
|
-
messages: [
|
|
232
|
-
{
|
|
233
|
-
role: "user",
|
|
234
|
-
content: {
|
|
235
|
-
type: "text",
|
|
236
|
-
text: "I want to qualify leads or recommend products based on answers. What's the best approach?",
|
|
237
|
-
},
|
|
238
|
-
},
|
|
239
|
-
{
|
|
240
|
-
role: "assistant",
|
|
241
|
-
content: {
|
|
242
|
-
type: "text",
|
|
243
|
-
text: `${sessionContext ? sessionContext + "\n\n" : ""}Here's how to build a qualification funnel with Clipform. Read the funnel guide (clipform://guides/funnel) for craft knowledge on branching logic and conversion.
|
|
244
|
-
|
|
245
|
-
## Workflow
|
|
246
|
-
|
|
247
|
-
1. **Define outcomes** - what segments or recommendations exist? (e.g., Basic/Pro/Enterprise, or product categories)
|
|
248
|
-
2. **Create the form** with clipform_create_form:
|
|
249
|
-
- show_step_counter: false (funnels feel shorter without it)
|
|
250
|
-
- disable_back_navigation: true (prevents answer shopping that breaks scoring)
|
|
251
|
-
3. **Add hook question** (type: "choice") - "What best describes you?" or "What are you looking for?" This segments the user.
|
|
252
|
-
4. **Add qualifying questions** (type: "choice") - 2-3 questions that narrow down the need. Assign scores to each option.
|
|
253
|
-
5. **Set branching logic** with clipform_set_logic - route based on answers
|
|
254
|
-
6. **Add contact capture** (type: "contact") - name, email, phone. Place AFTER qualifying questions.
|
|
255
|
-
7. **Update end screen** with score_ranges for personalised outcomes: "Based on your answers, we recommend..."
|
|
256
|
-
8. **Publish** with clipform_update_form
|
|
257
|
-
9. **Tag the form** - pass tags: one format (quiz/survey/interview/feedback/lead-gen), one genre (trivia/personality/nps/poll/testimonial), and 2-3 topic words
|
|
258
|
-
|
|
259
|
-
## Key rule: 3-5 questions max. Every extra step loses leads.
|
|
260
|
-
|
|
261
|
-
## Before building, ask
|
|
262
|
-
|
|
263
|
-
1. What outcomes are you routing to? (products, plans, team members, messages)
|
|
264
|
-
2. What criteria determine the routing?
|
|
265
|
-
3. Do you need contact capture?`,
|
|
266
|
-
},
|
|
267
|
-
},
|
|
268
|
-
],
|
|
269
|
-
};
|
|
270
|
-
});
|
|
271
|
-
}
|
|
272
|
-
//# sourceMappingURL=prompts.js.map
|
package/dist/prompts.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"prompts.js","sourceRoot":"","sources":["../src/prompts.ts"],"names":[],"mappings":"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"}
|
package/dist/resources.d.ts
DELETED