@creativeproject/creative-plann-mcp 0.1.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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Creative Project
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,148 @@
1
+ # @creativeproject/creative-plann-mcp
2
+
3
+ Servidor [MCP](https://modelcontextprotocol.io) do **Creative Plann**. Conecta uma IA
4
+ (Claude Code, Codex, Cursor) ao seu planejamento de redes sociais: ela lê o
5
+ calendário, cria posts, escreve briefing e roteiro, e move os cards do fluxo.
6
+
7
+ ## Instalação
8
+
9
+ Não precisa instalar nada — o cliente baixa o pacote sob demanda.
10
+
11
+ ### Claude Code
12
+
13
+ ```bash
14
+ claude mcp add creative-plann \
15
+ -e CREATIVE_PLANN_TOKEN=seu_token \
16
+ -- npx -y @creativeproject/creative-plann-mcp
17
+ ```
18
+
19
+ ### Outros clientes
20
+
21
+ ```json
22
+ {
23
+ "mcpServers": {
24
+ "creative-plann": {
25
+ "command": "npx",
26
+ "args": ["-y", "@creativeproject/creative-plann-mcp"],
27
+ "env": { "CREATIVE_PLANN_TOKEN": "seu_token" }
28
+ }
29
+ }
30
+ }
31
+ ```
32
+
33
+ ## Token
34
+
35
+ Gere no menu da conta (avatar no topo) → **API e IA**. O token define:
36
+
37
+ - **papel** — de leitor a admin, nunca acima de quem o criou;
38
+ - **empresas** — todas, ou apenas as que você escolher;
39
+ - **permissão de publicar** — desligada por padrão.
40
+
41
+ O valor aparece uma única vez: guardamos apenas o hash. Se vazar, revogue e
42
+ gere outro — leva um clique, e revogar um token não afeta os demais.
43
+
44
+ ## Variáveis de ambiente
45
+
46
+ | Variável | Obrigatória | Descrição |
47
+ | --- | --- | --- |
48
+ | `CREATIVE_PLANN_TOKEN` | sim | Token gerado na aplicação. |
49
+ | `CREATIVE_PLANN_URL` | não | Base da instância. Padrão: `https://plann.creativeproject.com.br`. |
50
+
51
+ ## Publicar não é automático
52
+
53
+ Por padrão o token **não publica**. A IA planeja, escreve, organiza e agenda a
54
+ data — mas mover o post para publicação exige uma pessoa na interface.
55
+
56
+ Isso é deliberado: publicar não tem desfazer. Um horário ou um texto errado vai
57
+ ao ar no perfil do cliente, e nenhuma correção posterior desfaz quem já viu.
58
+ Quando quiser automação completa, marque *"pode publicar"* ao gerar o token.
59
+
60
+ ## Anotações de comportamento
61
+
62
+ Cada ferramenta declara ao cliente MCP se apenas lê, se altera, e se é
63
+ destrutiva. É o que permite ao cliente auto-aprovar `list_posts` e pedir
64
+ confirmação em `delete_post`, `set_stage` e `set_status` — as três que apagam
65
+ trabalho ou disparam publicação.
66
+
67
+ São hints de interface, não fronteira de segurança: a autorização real está no
68
+ servidor, ligada ao papel e ao escopo do token.
69
+
70
+ ## Ferramentas
71
+
72
+ **Contexto** — `whoami`, `list_companies`, `list_accounts`,
73
+ `describe_vocabulary`, `list_members`, `list_media`, `list_campaigns`,
74
+ `create_campaign`
75
+
76
+ **Visão do trabalho** — `get_board`, `get_calendar`, `list_posts`, `get_post`,
77
+ `get_post_history`
78
+
79
+ **Criação e edição** — `create_post`, `update_post`, `schedule_post`,
80
+ `set_stage`, `set_status`, `comment_on_post`, `delete_post`
81
+
82
+ Comece por `whoami`: ele diz quais empresas o token alcança e o que ele pode
83
+ fazer. Depois `list_accounts`, porque cada rede aceita formatos diferentes,
84
+ com limites próprios de texto e de mídia.
85
+
86
+ ## Dois eixos independentes
87
+
88
+ O mesmo post tem **etapa** e **status**, e eles não são a mesma coisa:
89
+
90
+ - **etapa** (`set_stage`) é o fluxo editorial no Kanban: `IDEA` → `BRIEFING` →
91
+ `SCRIPT` → `PRODUCTION` → `INTERNAL_REVIEW` → `CLIENT_REVIEW` →
92
+ `APPROVED_STAGE` → `READY`;
93
+ - **status** (`set_status`) é o ciclo de publicação: `DRAFT` → `IN_REVIEW` →
94
+ `APPROVED` → `SCHEDULED` → `PUBLISHED`.
95
+
96
+ `PUBLISHING`, `PUBLISHED` e `FAILED` são escritos pelo motor de publicação e
97
+ não podem ser definidos pela API — deixá-los editáveis faria o histórico mentir.
98
+
99
+ ## Horários
100
+
101
+ Datas de trabalho são sempre **locais à empresa**, no formato
102
+ `"2026-09-01T10:30"` — sem `Z`, sem offset. Cada empresa tem seu fuso, e a
103
+ conversão acontece no servidor.
104
+
105
+ As respostas trazem os dois: `{ "utc": "...", "local": "..." }`.
106
+
107
+ ## Um post, várias redes
108
+
109
+ Um post tem um conteúdo e vários destinos, cada um com seu formato. O mesmo
110
+ material pode sair como Reel no Instagram, vídeo no Facebook e artigo no
111
+ LinkedIn — com legenda própria por rede quando fizer sentido:
112
+
113
+ ```json
114
+ {
115
+ "company": "minha-empresa",
116
+ "contentKind": "VIDEO",
117
+ "caption": "Legenda base para todas as redes.",
118
+ "targets": [
119
+ { "socialAccountId": "...", "format": "REEL" },
120
+ { "socialAccountId": "...", "format": "VIDEO" },
121
+ {
122
+ "socialAccountId": "...",
123
+ "format": "LINKEDIN_ARTICLE",
124
+ "title": "Título do artigo",
125
+ "body": "<p>Corpo longo, só no LinkedIn.</p>"
126
+ }
127
+ ]
128
+ }
129
+ ```
130
+
131
+ ## Desenvolvimento
132
+
133
+ ```bash
134
+ npm install
135
+ npm run build # compila e marca o executável
136
+ npm test # testes do cliente e contrato das ferramentas
137
+ npm run typecheck # inclui os testes
138
+ ```
139
+
140
+ `CREATIVE_PLANN_URL` aponta para outra instância — é como se testa contra um
141
+ servidor local.
142
+
143
+ O executável (`cli.ts`) é separado da biblioteca (`index.ts`): importar o
144
+ pacote não inicia servidor nem toma o stdio do processo.
145
+
146
+ ## Licença
147
+
148
+ MIT — veja [LICENSE](./LICENSE).
package/dist/cli.d.ts ADDED
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env node
2
+ export {};
package/dist/cli.js ADDED
@@ -0,0 +1,33 @@
1
+ #!/usr/bin/env node
2
+ import { serveStdio } from "@modelcontextprotocol/server/stdio";
3
+ import { CreativePlannClient } from "./client.js";
4
+ import { createServer } from "./server.js";
5
+ import { VERSION } from "./version.js";
6
+ /**
7
+ * Executável do servidor MCP, sobre stdio.
8
+ *
9
+ * Em stdio o stdout é o canal JSON-RPC: qualquer `console.log` corromperia o
10
+ * protocolo. Diagnóstico vai sempre para stderr.
11
+ */
12
+ console.error(`creative-plann mcp ${VERSION} — stdio`);
13
+ const handle = serveStdio(() => createServer(new CreativePlannClient({
14
+ token: process.env.CREATIVE_PLANN_TOKEN ?? "",
15
+ baseUrl: process.env.CREATIVE_PLANN_URL,
16
+ })));
17
+ /**
18
+ * Encerra limpo em SIGINT/SIGTERM — é o que acontece quando o usuário fecha o
19
+ * cliente MCP. Sem isto, requisições em vôo são abortadas na marra.
20
+ */
21
+ async function shutdown(signal) {
22
+ console.error(`creative-plann mcp: recebido ${signal}, encerrando`);
23
+ try {
24
+ await handle.close();
25
+ }
26
+ catch (error) {
27
+ console.error("creative-plann mcp: falha ao encerrar:", error);
28
+ }
29
+ process.exit(0);
30
+ }
31
+ process.on("SIGINT", () => void shutdown("SIGINT"));
32
+ process.on("SIGTERM", () => void shutdown("SIGTERM"));
33
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA,OAAO,EAAE,UAAU,EAAE,MAAM,oCAAoC,CAAC;AAChE,OAAO,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AAClD,OAAO,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAC3C,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEvC;;;;;GAKG;AACH,OAAO,CAAC,KAAK,CAAC,sBAAsB,OAAO,UAAU,CAAC,CAAC;AAEvD,MAAM,MAAM,GAAG,UAAU,CAAC,GAAG,EAAE,CAC7B,YAAY,CACV,IAAI,mBAAmB,CAAC;IACtB,KAAK,EAAE,OAAO,CAAC,GAAG,CAAC,oBAAoB,IAAI,EAAE;IAC7C,OAAO,EAAE,OAAO,CAAC,GAAG,CAAC,kBAAkB;CACxC,CAAC,CACH,CACF,CAAC;AAEF;;;GAGG;AACH,KAAK,UAAU,QAAQ,CAAC,MAAc;IACpC,OAAO,CAAC,KAAK,CAAC,gCAAgC,MAAM,cAAc,CAAC,CAAC;IACpE,IAAI,CAAC;QACH,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC;IACvB,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,wCAAwC,EAAE,KAAK,CAAC,CAAC;IACjE,CAAC;IACD,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;AAClB,CAAC;AAED,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,GAAG,EAAE,CAAC,KAAK,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC;AACpD,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,GAAG,EAAE,CAAC,KAAK,QAAQ,CAAC,SAAS,CAAC,CAAC,CAAC"}
@@ -0,0 +1,40 @@
1
+ /**
2
+ * Cliente da API do Creative Plann. Fino de propósito: a regra de negócio vive
3
+ * no servidor, e duplicá-la aqui só criaria duas verdades que divergem a cada
4
+ * atualização da aplicação.
5
+ */
6
+ export type ApiErrorBody = {
7
+ error: {
8
+ code: string;
9
+ message: string;
10
+ hint?: string;
11
+ details?: unknown;
12
+ };
13
+ };
14
+ export declare class CreativePlannError extends Error {
15
+ readonly code: string;
16
+ readonly hint?: string;
17
+ readonly details?: unknown;
18
+ constructor(body: ApiErrorBody["error"], status: number);
19
+ /** Texto para o modelo: mensagem, o que fazer e o detalhe por campo. */
20
+ toModelText(): string;
21
+ }
22
+ export type ClientOptions = {
23
+ token: string;
24
+ baseUrl?: string;
25
+ };
26
+ export declare class CreativePlannClient {
27
+ private readonly token;
28
+ private readonly baseUrl;
29
+ constructor({ token, baseUrl }: ClientOptions);
30
+ /** Mensagem acionável em vez de um 401 cru quando falta configuração. */
31
+ private assertConfigured;
32
+ request<T = unknown>(method: "GET" | "POST" | "PATCH" | "DELETE", path: string, options?: {
33
+ body?: unknown;
34
+ query?: Record<string, string | number | undefined>;
35
+ }): Promise<T>;
36
+ get<T>(path: string, query?: Record<string, string | number | undefined>): Promise<T>;
37
+ post<T>(path: string, body?: unknown): Promise<T>;
38
+ patch<T>(path: string, body: unknown): Promise<T>;
39
+ delete<T>(path: string): Promise<T>;
40
+ }
package/dist/client.js ADDED
@@ -0,0 +1,99 @@
1
+ /**
2
+ * Cliente da API do Creative Plann. Fino de propósito: a regra de negócio vive
3
+ * no servidor, e duplicá-la aqui só criaria duas verdades que divergem a cada
4
+ * atualização da aplicação.
5
+ */
6
+ const DEFAULT_BASE_URL = "https://plann.creativeproject.com.br";
7
+ export class CreativePlannError extends Error {
8
+ code;
9
+ hint;
10
+ details;
11
+ constructor(body, status) {
12
+ super(body.message);
13
+ this.name = "CreativePlannError";
14
+ this.code = body.code || `http_${status}`;
15
+ this.hint = body.hint;
16
+ this.details = body.details;
17
+ }
18
+ /** Texto para o modelo: mensagem, o que fazer e o detalhe por campo. */
19
+ toModelText() {
20
+ const lines = [this.message];
21
+ if (this.hint)
22
+ lines.push(`Como resolver: ${this.hint}`);
23
+ if (this.details !== undefined) {
24
+ lines.push(`Detalhes: ${JSON.stringify(this.details, null, 2)}`);
25
+ }
26
+ return lines.join("\n");
27
+ }
28
+ }
29
+ export class CreativePlannClient {
30
+ token;
31
+ baseUrl;
32
+ constructor({ token, baseUrl }) {
33
+ // Token vazio não impede o servidor de subir. Se lançássemos aqui, o
34
+ // processo morreria antes do handshake e o cliente MCP mostraria apenas
35
+ // "desconectado" — a instrução de configuração ficaria enterrada no log.
36
+ // Assim ela chega como resultado da primeira ferramenta chamada.
37
+ this.token = token;
38
+ this.baseUrl = (baseUrl ?? DEFAULT_BASE_URL).replace(/\/+$/, "");
39
+ }
40
+ /** Mensagem acionável em vez de um 401 cru quando falta configuração. */
41
+ assertConfigured() {
42
+ if (!this.token) {
43
+ throw new CreativePlannError({
44
+ code: "missing_token",
45
+ message: "Token ausente: a variável CREATIVE_PLANN_TOKEN não está definida.",
46
+ hint: "Gere um token no menu da conta → API e IA e defina-o na configuração " +
47
+ "do servidor MCP (env CREATIVE_PLANN_TOKEN).",
48
+ }, 401);
49
+ }
50
+ }
51
+ async request(method, path, options = {}) {
52
+ this.assertConfigured();
53
+ const url = new URL(`${this.baseUrl}/api/v1${path}`);
54
+ for (const [key, value] of Object.entries(options.query ?? {})) {
55
+ if (value !== undefined && value !== "")
56
+ url.searchParams.set(key, String(value));
57
+ }
58
+ const response = await fetch(url, {
59
+ method,
60
+ headers: {
61
+ authorization: `Bearer ${this.token}`,
62
+ ...(options.body !== undefined ? { "content-type": "application/json" } : {}),
63
+ },
64
+ ...(options.body !== undefined ? { body: JSON.stringify(options.body) } : {}),
65
+ // Uma operação que trava é pior que uma que falha: o agente fica esperando.
66
+ signal: AbortSignal.timeout(30_000),
67
+ });
68
+ const text = await response.text();
69
+ const payload = text.trim() ? safeParse(text) : {};
70
+ if (!response.ok) {
71
+ const body = payload.error;
72
+ throw new CreativePlannError(body ?? { code: `http_${response.status}`, message: text.slice(0, 500) || response.statusText }, response.status);
73
+ }
74
+ return payload;
75
+ }
76
+ get(path, query) {
77
+ return this.request("GET", path, { query });
78
+ }
79
+ post(path, body) {
80
+ return this.request("POST", path, { body });
81
+ }
82
+ patch(path, body) {
83
+ return this.request("PATCH", path, { body });
84
+ }
85
+ delete(path) {
86
+ return this.request("DELETE", path);
87
+ }
88
+ }
89
+ function safeParse(text) {
90
+ try {
91
+ return JSON.parse(text);
92
+ }
93
+ catch {
94
+ // Resposta não-JSON costuma ser página de erro de proxy ou de login: o
95
+ // texto cru ajuda mais a diagnosticar que um "parse failed".
96
+ return { error: { code: "invalid_response", message: text.slice(0, 500) } };
97
+ }
98
+ }
99
+ //# sourceMappingURL=client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Entrada de biblioteca. Importar este módulo **não** inicia o servidor — quem
3
+ * faz isso é `cli.ts`, o executável. Manter os dois separados evita que um
4
+ * `import` do pacote tome o stdio do processo hospedeiro.
5
+ */
6
+ export { CreativePlannClient, CreativePlannError } from "./client.js";
7
+ export type { ApiErrorBody, ClientOptions } from "./client.js";
8
+ export { createServer } from "./server.js";
9
+ export { registerTools } from "./tools/index.js";
10
+ export { VERSION } from "./version.js";
package/dist/index.js ADDED
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Entrada de biblioteca. Importar este módulo **não** inicia o servidor — quem
3
+ * faz isso é `cli.ts`, o executável. Manter os dois separados evita que um
4
+ * `import` do pacote tome o stdio do processo hospedeiro.
5
+ */
6
+ export { CreativePlannClient, CreativePlannError } from "./client.js";
7
+ export { createServer } from "./server.js";
8
+ export { registerTools } from "./tools/index.js";
9
+ export { VERSION } from "./version.js";
10
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,OAAO,EAAE,mBAAmB,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AAEtE,OAAO,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAC3C,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AACjD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC"}
@@ -0,0 +1,7 @@
1
+ import { McpServer } from "@modelcontextprotocol/server";
2
+ import { CreativePlannClient } from "./client.js";
3
+ /**
4
+ * Monta o servidor. Separado do executável para poder ser instanciado em teste
5
+ * sem tomar o stdio do processo.
6
+ */
7
+ export declare function createServer(client: CreativePlannClient): McpServer;
package/dist/server.js ADDED
@@ -0,0 +1,38 @@
1
+ import { McpServer } from "@modelcontextprotocol/server";
2
+ import { registerTools } from "./tools/index.js";
3
+ import { VERSION } from "./version.js";
4
+ /**
5
+ * Monta o servidor. Separado do executável para poder ser instanciado em teste
6
+ * sem tomar o stdio do processo.
7
+ */
8
+ export function createServer(client) {
9
+ const server = new McpServer({ name: "creative-plann", version: VERSION }, {
10
+ capabilities: { tools: {} },
11
+ // O modelo lê isto antes de escolher ferramentas. Dizer o que a
12
+ // ferramenta NÃO faz evita que ele leia a recusa de publicar como bug e
13
+ // saia tentando caminhos alternativos.
14
+ //
15
+ // Não confiamos só nisto: clientes podem truncar ou ignorar
16
+ // `instructions`, então o que é crítico se repete na descrição de cada
17
+ // ferramenta.
18
+ instructions: [
19
+ "Creative Plann: planejamento e agendamento de posts em redes sociais,",
20
+ "organizado por empresa dentro de uma organização.",
21
+ "",
22
+ "Comece sempre por `whoami`: ele diz quais empresas você alcança e o que",
23
+ "este token pode fazer. Depois use `list_accounts` na empresa escolhida —",
24
+ "cada rede aceita formatos diferentes, com limites próprios de texto e mídia.",
25
+ "",
26
+ "Fluxo editorial (Kanban) e ciclo de publicação são eixos distintos:",
27
+ "`set_stage` move o card no fluxo (IDEA → BRIEFING → … → READY);",
28
+ "`set_status` controla a publicação (DRAFT → IN_REVIEW → APPROVED → SCHEDULED).",
29
+ "",
30
+ "Publicar é irreversível. Se o token não tiver permissão de publicar,",
31
+ "deixe o post pronto e agendado e informe que a liberação é humana —",
32
+ "não tente contornar a recusa por outro caminho.",
33
+ ].join("\n"),
34
+ });
35
+ registerTools(server, client);
36
+ return server;
37
+ }
38
+ //# sourceMappingURL=server.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,8BAA8B,CAAC;AAEzD,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AACjD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAEvC;;;GAGG;AACH,MAAM,UAAU,YAAY,CAAC,MAA2B;IACtD,MAAM,MAAM,GAAG,IAAI,SAAS,CAC1B,EAAE,IAAI,EAAE,gBAAgB,EAAE,OAAO,EAAE,OAAO,EAAE,EAC5C;QACE,YAAY,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE;QAC3B,gEAAgE;QAChE,wEAAwE;QACxE,uCAAuC;QACvC,EAAE;QACF,4DAA4D;QAC5D,uEAAuE;QACvE,cAAc;QACd,YAAY,EAAE;YACZ,uEAAuE;YACvE,mDAAmD;YACnD,EAAE;YACF,yEAAyE;YACzE,0EAA0E;YAC1E,8EAA8E;YAC9E,EAAE;YACF,qEAAqE;YACrE,iEAAiE;YACjE,gFAAgF;YAChF,EAAE;YACF,sEAAsE;YACtE,qEAAqE;YACrE,iDAAiD;SAClD,CAAC,IAAI,CAAC,IAAI,CAAC;KACb,CACF,CAAC;IAEF,aAAa,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC9B,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,81 @@
1
+ import * as z from "zod/v4";
2
+ /**
3
+ * Vocabulário e utilidades compartilhados pelos módulos de ferramentas.
4
+ *
5
+ * Duas convenções valem em tudo:
6
+ * - `company` aceita id **ou** slug, porque é o slug que aparece nas listagens
7
+ * e forçar a tradução para id só adicionaria uma chamada e uma chance de erro.
8
+ * - Horários são sempre locais à empresa. Fuso é a causa mais comum de post
9
+ * publicado na hora errada, e isso não tem desfazer.
10
+ */
11
+ export declare const COMPANY_ARG: z.ZodString;
12
+ export declare const LOCAL_DATETIME: z.ZodString;
13
+ export declare const STAGES: readonly ["IDEA", "BRIEFING", "SCRIPT", "PRODUCTION", "INTERNAL_REVIEW", "CLIENT_REVIEW", "APPROVED_STAGE", "READY", "ARCHIVED"];
14
+ export declare const FORMATS: readonly ["FEED", "CAROUSEL", "STORY", "REEL", "VIDEO", "SHORT", "LINKEDIN_POST", "LINKEDIN_ARTICLE", "BLOG_POST", "NEWSLETTER", "THREAD"];
15
+ export declare const CONTENT_KINDS: readonly ["IMAGE", "CAROUSEL", "VIDEO", "TEXT", "ARTICLE"];
16
+ export declare const OBJECTIVES: readonly ["AWARENESS", "ENGAGEMENT", "CONVERSION", "AUTHORITY", "RETENTION", "RECRUITING"];
17
+ export declare const PILLARS: readonly ["EDUCATIONAL", "SOCIAL_PROOF", "PRODUCT", "BEHIND_SCENES", "INSTITUTIONAL", "ENTERTAINMENT", "NEWS", "PROMOTION"];
18
+ export declare const PRIORITIES: readonly ["LOW", "NORMAL", "HIGH", "URGENT"];
19
+ export declare const SETTABLE_STATUSES: readonly ["DRAFT", "IN_REVIEW", "APPROVED", "SCHEDULED"];
20
+ export declare const ALL_STATUSES: readonly ["DRAFT", "IN_REVIEW", "APPROVED", "SCHEDULED", "PUBLISHING", "PUBLISHED", "FAILED"];
21
+ /**
22
+ * Anotações de comportamento. O cliente MCP usa estes hints para decidir o que
23
+ * auto-aprovar e o que confirmar com a pessoa: sem eles, `delete_post` parece
24
+ * igual a `whoami`.
25
+ *
26
+ * São hints de interface, não fronteira de segurança — a autorização real está
27
+ * no servidor, ligada ao papel e ao escopo do token.
28
+ */
29
+ export declare const READ_ONLY: {
30
+ readonly readOnlyHint: true;
31
+ readonly idempotentHint: true;
32
+ readonly openWorldHint: false;
33
+ };
34
+ /** Cria ou altera, sem apagar trabalho. */
35
+ export declare const MUTATING: {
36
+ readonly readOnlyHint: false;
37
+ readonly destructiveHint: false;
38
+ readonly idempotentHint: false;
39
+ readonly openWorldHint: false;
40
+ };
41
+ /** Mesma alteração repetida deixa o mesmo estado final. */
42
+ export declare const IDEMPOTENT_MUTATING: {
43
+ readonly readOnlyHint: false;
44
+ readonly destructiveHint: false;
45
+ readonly idempotentHint: true;
46
+ readonly openWorldHint: false;
47
+ };
48
+ /** Apaga trabalho, ou dispara efeito externo irreversível. */
49
+ export declare const DESTRUCTIVE: {
50
+ readonly readOnlyHint: false;
51
+ readonly destructiveHint: true;
52
+ readonly idempotentHint: false;
53
+ readonly openWorldHint: true;
54
+ };
55
+ /** Resposta em JSON — o modelo lida melhor com estrutura que com prosa. */
56
+ export declare function json(value: unknown): {
57
+ content: {
58
+ type: "text";
59
+ text: string;
60
+ }[];
61
+ };
62
+ /**
63
+ * Erro da API vira texto útil em vez de exceção de transporte: o modelo lê a
64
+ * mensagem e a dica, e pode se corrigir sozinho na tentativa seguinte.
65
+ */
66
+ export declare function failure(error: unknown): {
67
+ content: {
68
+ type: "text";
69
+ text: string;
70
+ }[];
71
+ isError: true;
72
+ };
73
+ /** Envolve o handler para nunca deixar exceção escapar como erro de protocolo. */
74
+ export declare function guard<T>(handler: (args: T) => Promise<unknown>): (args: T) => Promise<{
75
+ content: {
76
+ type: "text";
77
+ text: string;
78
+ }[];
79
+ }>;
80
+ /** Ids vão em path: escapar evita que uma barra vire outra rota. */
81
+ export declare const path: (value: string) => string;
package/dist/shared.js ADDED
@@ -0,0 +1,141 @@
1
+ import * as z from "zod/v4";
2
+ import { CreativePlannError } from "./client.js";
3
+ /**
4
+ * Vocabulário e utilidades compartilhados pelos módulos de ferramentas.
5
+ *
6
+ * Duas convenções valem em tudo:
7
+ * - `company` aceita id **ou** slug, porque é o slug que aparece nas listagens
8
+ * e forçar a tradução para id só adicionaria uma chamada e uma chance de erro.
9
+ * - Horários são sempre locais à empresa. Fuso é a causa mais comum de post
10
+ * publicado na hora errada, e isso não tem desfazer.
11
+ */
12
+ export const COMPANY_ARG = z
13
+ .string()
14
+ .describe("Empresa: id ou slug (veja `whoami` ou `list_companies`).");
15
+ export const LOCAL_DATETIME = z
16
+ .string()
17
+ .regex(/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}$/, 'Use "YYYY-MM-DDTHH:mm"')
18
+ .describe('Data e hora NO FUSO DA EMPRESA, formato "2026-09-01T10:30". Não envie UTC nem sufixo Z.');
19
+ export const STAGES = [
20
+ "IDEA",
21
+ "BRIEFING",
22
+ "SCRIPT",
23
+ "PRODUCTION",
24
+ "INTERNAL_REVIEW",
25
+ "CLIENT_REVIEW",
26
+ "APPROVED_STAGE",
27
+ "READY",
28
+ "ARCHIVED",
29
+ ];
30
+ export const FORMATS = [
31
+ "FEED",
32
+ "CAROUSEL",
33
+ "STORY",
34
+ "REEL",
35
+ "VIDEO",
36
+ "SHORT",
37
+ "LINKEDIN_POST",
38
+ "LINKEDIN_ARTICLE",
39
+ "BLOG_POST",
40
+ "NEWSLETTER",
41
+ "THREAD",
42
+ ];
43
+ export const CONTENT_KINDS = ["IMAGE", "CAROUSEL", "VIDEO", "TEXT", "ARTICLE"];
44
+ export const OBJECTIVES = [
45
+ "AWARENESS",
46
+ "ENGAGEMENT",
47
+ "CONVERSION",
48
+ "AUTHORITY",
49
+ "RETENTION",
50
+ "RECRUITING",
51
+ ];
52
+ export const PILLARS = [
53
+ "EDUCATIONAL",
54
+ "SOCIAL_PROOF",
55
+ "PRODUCT",
56
+ "BEHIND_SCENES",
57
+ "INSTITUTIONAL",
58
+ "ENTERTAINMENT",
59
+ "NEWS",
60
+ "PROMOTION",
61
+ ];
62
+ export const PRIORITIES = ["LOW", "NORMAL", "HIGH", "URGENT"];
63
+ export const SETTABLE_STATUSES = ["DRAFT", "IN_REVIEW", "APPROVED", "SCHEDULED"];
64
+ export const ALL_STATUSES = [
65
+ "DRAFT",
66
+ "IN_REVIEW",
67
+ "APPROVED",
68
+ "SCHEDULED",
69
+ "PUBLISHING",
70
+ "PUBLISHED",
71
+ "FAILED",
72
+ ];
73
+ /**
74
+ * Anotações de comportamento. O cliente MCP usa estes hints para decidir o que
75
+ * auto-aprovar e o que confirmar com a pessoa: sem eles, `delete_post` parece
76
+ * igual a `whoami`.
77
+ *
78
+ * São hints de interface, não fronteira de segurança — a autorização real está
79
+ * no servidor, ligada ao papel e ao escopo do token.
80
+ */
81
+ export const READ_ONLY = {
82
+ readOnlyHint: true,
83
+ idempotentHint: true,
84
+ openWorldHint: false,
85
+ };
86
+ /** Cria ou altera, sem apagar trabalho. */
87
+ export const MUTATING = {
88
+ readOnlyHint: false,
89
+ destructiveHint: false,
90
+ idempotentHint: false,
91
+ openWorldHint: false,
92
+ };
93
+ /** Mesma alteração repetida deixa o mesmo estado final. */
94
+ export const IDEMPOTENT_MUTATING = {
95
+ readOnlyHint: false,
96
+ destructiveHint: false,
97
+ idempotentHint: true,
98
+ openWorldHint: false,
99
+ };
100
+ /** Apaga trabalho, ou dispara efeito externo irreversível. */
101
+ export const DESTRUCTIVE = {
102
+ readOnlyHint: false,
103
+ destructiveHint: true,
104
+ idempotentHint: false,
105
+ openWorldHint: true,
106
+ };
107
+ /** Resposta em JSON — o modelo lida melhor com estrutura que com prosa. */
108
+ export function json(value) {
109
+ return { content: [{ type: "text", text: JSON.stringify(value, null, 2) }] };
110
+ }
111
+ /**
112
+ * Erro da API vira texto útil em vez de exceção de transporte: o modelo lê a
113
+ * mensagem e a dica, e pode se corrigir sozinho na tentativa seguinte.
114
+ */
115
+ export function failure(error) {
116
+ if (error instanceof CreativePlannError) {
117
+ return {
118
+ content: [{ type: "text", text: error.toModelText() }],
119
+ isError: true,
120
+ };
121
+ }
122
+ const message = error instanceof Error ? error.message : String(error);
123
+ return {
124
+ content: [{ type: "text", text: `Falha na chamada: ${message}` }],
125
+ isError: true,
126
+ };
127
+ }
128
+ /** Envolve o handler para nunca deixar exceção escapar como erro de protocolo. */
129
+ export function guard(handler) {
130
+ return async (args) => {
131
+ try {
132
+ return json(await handler(args));
133
+ }
134
+ catch (error) {
135
+ return failure(error);
136
+ }
137
+ };
138
+ }
139
+ /** Ids vão em path: escapar evita que uma barra vire outra rota. */
140
+ export const path = (value) => encodeURIComponent(value);
141
+ //# sourceMappingURL=shared.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"shared.js","sourceRoot":"","sources":["../src/shared.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import type { McpServer } from "@modelcontextprotocol/server";
2
+ import type { CreativePlannClient } from "../client.js";
3
+ /** Criação, edição e movimentação — tudo que altera o trabalho. */
4
+ export declare function registerAuthoringTools(server: McpServer, client: CreativePlannClient): void;
@@ -0,0 +1,173 @@
1
+ import * as z from "zod/v4";
2
+ import { CONTENT_KINDS, COMPANY_ARG, DESTRUCTIVE, FORMATS, guard, IDEMPOTENT_MUTATING, LOCAL_DATETIME, MUTATING, OBJECTIVES, path, PILLARS, PRIORITIES, SETTABLE_STATUSES, STAGES, } from "../shared.js";
3
+ /** Criação, edição e movimentação — tudo que altera o trabalho. */
4
+ export function registerAuthoringTools(server, client) {
5
+ server.registerTool("create_post", {
6
+ title: "Criar post",
7
+ description: "Cria um post. Um mesmo post pode sair em várias redes ao mesmo tempo, " +
8
+ "cada destino com seu formato — por exemplo Reel no Instagram e artigo " +
9
+ "no LinkedIn. Consulte `list_accounts` antes, para usar formatos válidos. " +
10
+ "O post nasce como rascunho na coluna de idealização: criar nunca publica.",
11
+ inputSchema: z.object({
12
+ company: COMPANY_ARG,
13
+ contentKind: z
14
+ .enum(CONTENT_KINDS)
15
+ .describe("Natureza do conteúdo; o formato por rede vai em cada destino."),
16
+ title: z.string().max(200).optional().describe("Título curto para o card do fluxo."),
17
+ caption: z.string().max(200_000).optional().describe("Legenda base, sem as hashtags."),
18
+ targets: z
19
+ .array(z.object({
20
+ socialAccountId: z.string().min(1),
21
+ format: z.enum(FORMATS),
22
+ captionOverride: z
23
+ .string()
24
+ .max(200_000)
25
+ .optional()
26
+ .describe("Legenda só desta rede."),
27
+ title: z
28
+ .string()
29
+ .max(300)
30
+ .optional()
31
+ .describe("Obrigatório em artigo/blog/newsletter."),
32
+ body: z
33
+ .string()
34
+ .max(200_000)
35
+ .optional()
36
+ .describe("Corpo do artigo/blog/newsletter."),
37
+ }))
38
+ .min(1)
39
+ .describe("Ao menos um destino. Cada um define em qual rede e formato o post sai."),
40
+ media: z
41
+ .array(z.object({
42
+ mediaAssetId: z.string().min(1),
43
+ altText: z
44
+ .string()
45
+ .max(1000)
46
+ .optional()
47
+ .describe("Descrição para leitores de tela."),
48
+ credit: z.string().max(200).optional(),
49
+ }))
50
+ .max(10)
51
+ .optional()
52
+ .describe("Da biblioteca (`list_media`), na ordem desejada."),
53
+ scheduledAtLocal: LOCAL_DATETIME.optional().describe("Data desejada de publicação (só marca; não publica)."),
54
+ dueAtLocal: LOCAL_DATETIME.optional().describe("Prazo interno da equipe."),
55
+ briefing: z
56
+ .string()
57
+ .max(200_000)
58
+ .optional()
59
+ .describe("Contexto e mensagem-chave (aceita HTML)."),
60
+ script: z
61
+ .string()
62
+ .max(200_000)
63
+ .optional()
64
+ .describe("Roteiro ou copy longa (aceita HTML)."),
65
+ visualElements: z
66
+ .string()
67
+ .max(200_000)
68
+ .optional()
69
+ .describe("O que aparece na peça: pessoas, produto, cenário, texto na tela."),
70
+ references: z
71
+ .string()
72
+ .max(200_000)
73
+ .optional()
74
+ .describe("Links de referência (aceita HTML)."),
75
+ audience: z.string().max(500).optional(),
76
+ objective: z.enum(OBJECTIVES).optional(),
77
+ pillar: z.enum(PILLARS).optional(),
78
+ campaignId: z.string().optional(),
79
+ tags: z.array(z.string()).max(20).optional(),
80
+ hashtags: z
81
+ .array(z.string())
82
+ .max(30)
83
+ .optional()
84
+ .describe("Sem o #. Ficam fora da legenda até a publicação."),
85
+ hashtagsInFirstComment: z
86
+ .boolean()
87
+ .optional()
88
+ .describe("Publica as hashtags no primeiro comentário, deixando a legenda limpa."),
89
+ callToAction: z.string().max(300).optional(),
90
+ linkUrl: z.string().optional(),
91
+ assigneeId: z.string().optional().describe("Responsável (veja `list_members`)."),
92
+ priority: z.enum(PRIORITIES).optional(),
93
+ }),
94
+ annotations: MUTATING,
95
+ }, guard((body) => client.post("/posts", body)));
96
+ server.registerTool("update_post", {
97
+ title: "Atualizar post",
98
+ description: "Atualiza campos de um post. Só o que você enviar muda — destinos e mídia " +
99
+ "ficam intactos, então é seguro preencher só o briefing.",
100
+ inputSchema: z.object({
101
+ postId: z.string().min(1),
102
+ title: z.string().max(200).optional(),
103
+ caption: z.string().max(200_000).optional(),
104
+ briefing: z.string().max(200_000).optional(),
105
+ script: z.string().max(200_000).optional(),
106
+ visualElements: z.string().max(200_000).optional(),
107
+ references: z.string().max(200_000).optional(),
108
+ audience: z.string().max(500).optional(),
109
+ callToAction: z.string().max(300).optional(),
110
+ priority: z.enum(PRIORITIES).optional(),
111
+ assigneeId: z.string().nullable().optional().describe("null remove o responsável."),
112
+ dueAtLocal: z.string().nullable().optional().describe("null remove o prazo."),
113
+ tags: z.array(z.string()).max(20).optional(),
114
+ hashtags: z.array(z.string()).max(30).optional(),
115
+ }),
116
+ // Reenviar o mesmo patch deixa o post no mesmo estado.
117
+ annotations: IDEMPOTENT_MUTATING,
118
+ }, guard(({ postId, ...body }) => client.patch(`/posts/${path(postId)}`, body)));
119
+ server.registerTool("schedule_post", {
120
+ title: "Definir data de publicação",
121
+ description: "Define a data e hora de publicação, no fuso da empresa. Só marca a data: " +
122
+ "o disparo acontece quando o post entra em SCHEDULED ou na coluna READY.",
123
+ inputSchema: z.object({
124
+ postId: z.string().min(1),
125
+ scheduledAtLocal: LOCAL_DATETIME,
126
+ }),
127
+ annotations: IDEMPOTENT_MUTATING,
128
+ }, guard(({ postId, scheduledAtLocal }) => client.post(`/posts/${path(postId)}/schedule`, { scheduledAtLocal })));
129
+ server.registerTool("set_stage", {
130
+ title: "Mover no fluxo",
131
+ description: "Move o card no fluxo editorial (Kanban). Mover para READY dispara a " +
132
+ "publicação real e exige token com permissão de publicar; se ela faltar, " +
133
+ "pare em APPROVED_STAGE e avise que a liberação é humana.",
134
+ inputSchema: z.object({
135
+ postId: z.string().min(1),
136
+ stage: z.enum(STAGES),
137
+ }),
138
+ // READY publica de verdade, num perfil público e sem desfazer: o cliente
139
+ // deve tratar esta chamada como irreversível, não auto-aprovar.
140
+ annotations: DESTRUCTIVE,
141
+ }, guard(({ postId, stage }) => client.post(`/posts/${path(postId)}/stage`, { stage })));
142
+ server.registerTool("set_status", {
143
+ title: "Mover no ciclo de publicação",
144
+ description: "Move o post no ciclo de publicação. SCHEDULED enfileira a publicação de " +
145
+ "verdade e exige permissão de publicar. PUBLISHED e FAILED não são " +
146
+ "definíveis aqui: quem os escreve é o motor de publicação.",
147
+ inputSchema: z.object({
148
+ postId: z.string().min(1),
149
+ status: z.enum(SETTABLE_STATUSES),
150
+ note: z.string().max(2000).optional().describe("Obrigatório ao reprovar."),
151
+ }),
152
+ annotations: DESTRUCTIVE,
153
+ }, guard(({ postId, ...body }) => client.post(`/posts/${path(postId)}/status`, body)));
154
+ server.registerTool("comment_on_post", {
155
+ title: "Comentar no post",
156
+ description: "Deixa um comentário interno no post — visível à equipe na interface. " +
157
+ "Não é o comentário publicado na rede social.",
158
+ inputSchema: z.object({
159
+ postId: z.string().min(1),
160
+ body: z.string().min(1).max(2000),
161
+ }),
162
+ annotations: MUTATING,
163
+ }, guard(({ postId, body }) => client.post(`/posts/${path(postId)}/comments`, { body })));
164
+ server.registerTool("delete_post", {
165
+ title: "Excluir post",
166
+ description: "Exclui um post e tudo nele: legenda, briefing, roteiro, comentários e " +
167
+ "histórico. Não afeta a mídia na biblioteca, e posts já publicados não " +
168
+ "podem ser excluídos. Confirme com a pessoa antes de usar.",
169
+ inputSchema: z.object({ postId: z.string().min(1) }),
170
+ annotations: DESTRUCTIVE,
171
+ }, guard(({ postId }) => client.delete(`/posts/${path(postId)}`)));
172
+ }
173
+ //# sourceMappingURL=authoring.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"authoring.js","sourceRoot":"","sources":["../../src/tools/authoring.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import type { McpServer } from "@modelcontextprotocol/server";
2
+ import type { CreativePlannClient } from "../client.js";
3
+ /** Descoberta: onde posso atuar, com quais contas e sob quais limites. */
4
+ export declare function registerContextTools(server: McpServer, client: CreativePlannClient): void;
@@ -0,0 +1,71 @@
1
+ import * as z from "zod/v4";
2
+ import { COMPANY_ARG, guard, MUTATING, path, READ_ONLY } from "../shared.js";
3
+ /** Descoberta: onde posso atuar, com quais contas e sob quais limites. */
4
+ export function registerContextTools(server, client) {
5
+ server.registerTool("whoami", {
6
+ title: "Quem sou eu",
7
+ description: "Primeira chamada de qualquer sessão: mostra a organização, as empresas " +
8
+ "que este token alcança e o que ele pode fazer (inclusive se pode publicar).",
9
+ inputSchema: z.object({}),
10
+ annotations: READ_ONLY,
11
+ }, guard(() => client.get("/me")));
12
+ server.registerTool("list_companies", {
13
+ title: "Listar empresas",
14
+ description: "Empresas da organização, com fuso horário, contas conectadas e total de posts.",
15
+ inputSchema: z.object({}),
16
+ annotations: READ_ONLY,
17
+ }, guard(() => client.get("/companies")));
18
+ server.registerTool("list_accounts", {
19
+ title: "Listar contas conectadas",
20
+ description: "Contas conectadas de uma empresa e, para cada uma, os formatos aceitos " +
21
+ "com limite de texto e de mídia. Consulte antes de criar um post: enviar " +
22
+ "um formato que a rede não aceita falha na validação.",
23
+ inputSchema: z.object({ company: COMPANY_ARG }),
24
+ annotations: READ_ONLY,
25
+ }, guard(({ company }) => client.get(`/companies/${path(company)}/accounts`)));
26
+ server.registerTool("describe_vocabulary", {
27
+ title: "Vocabulário da ferramenta",
28
+ description: "Catálogo da ferramenta: formatos e seus limites, estágios do fluxo, " +
29
+ "status de publicação, objetivos e pilares de conteúdo. Use para saber " +
30
+ "quais valores são aceitos, em vez de descobrir por tentativa e erro.",
31
+ inputSchema: z.object({}),
32
+ annotations: READ_ONLY,
33
+ }, guard(() => client.get("/formats")));
34
+ server.registerTool("list_members", {
35
+ title: "Listar membros",
36
+ description: "Membros da organização — necessário para atribuir responsável (assigneeId) a um post.",
37
+ inputSchema: z.object({ company: COMPANY_ARG }),
38
+ annotations: READ_ONLY,
39
+ }, guard(({ company }) => client.get(`/companies/${path(company)}/members`)));
40
+ server.registerTool("list_media", {
41
+ title: "Listar mídia",
42
+ description: "Biblioteca de mídia da empresa. Use o `id` retornado como `mediaAssetId` " +
43
+ "ao criar um post. Não é possível enviar arquivo novo por aqui: o upload " +
44
+ "é feito na interface.",
45
+ inputSchema: z.object({
46
+ company: COMPANY_ARG,
47
+ type: z.enum(["IMAGE", "VIDEO"]).optional(),
48
+ limit: z.number().int().min(1).max(100).optional(),
49
+ cursor: z.string().optional().describe("Cursor devolvido pela página anterior."),
50
+ }),
51
+ annotations: READ_ONLY,
52
+ }, guard(({ company, ...query }) => client.get(`/companies/${path(company)}/media`, query)));
53
+ server.registerTool("list_campaigns", {
54
+ title: "Listar campanhas",
55
+ description: "Campanhas da empresa, para agrupar posts sob uma mesma ação.",
56
+ inputSchema: z.object({ company: COMPANY_ARG }),
57
+ annotations: READ_ONLY,
58
+ }, guard(({ company }) => client.get(`/companies/${path(company)}/campaigns`)));
59
+ server.registerTool("create_campaign", {
60
+ title: "Criar campanha",
61
+ description: "Cria uma campanha na empresa.",
62
+ inputSchema: z.object({
63
+ company: COMPANY_ARG,
64
+ name: z.string().min(1).max(120),
65
+ startsAt: z.string().optional().describe("Data ISO de início."),
66
+ endsAt: z.string().optional().describe("Data ISO de término."),
67
+ }),
68
+ annotations: MUTATING,
69
+ }, guard(({ company, ...body }) => client.post(`/companies/${path(company)}/campaigns`, body)));
70
+ }
71
+ //# sourceMappingURL=context.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.js","sourceRoot":"","sources":["../../src/tools/context.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ import type { McpServer } from "@modelcontextprotocol/server";
2
+ import type { CreativePlannClient } from "../client.js";
3
+ /**
4
+ * Ferramentas agrupadas por domínio: descobrir onde atuar, ver o trabalho,
5
+ * alterá-lo. Separar por arquivo mantém cada módulo legível conforme a API
6
+ * cresce, e deixa claro onde entra uma ferramenta nova.
7
+ */
8
+ export declare function registerTools(server: McpServer, client: CreativePlannClient): void;
@@ -0,0 +1,14 @@
1
+ import { registerContextTools } from "./context.js";
2
+ import { registerPlanningTools } from "./planning.js";
3
+ import { registerAuthoringTools } from "./authoring.js";
4
+ /**
5
+ * Ferramentas agrupadas por domínio: descobrir onde atuar, ver o trabalho,
6
+ * alterá-lo. Separar por arquivo mantém cada módulo legível conforme a API
7
+ * cresce, e deixa claro onde entra uma ferramenta nova.
8
+ */
9
+ export function registerTools(server, client) {
10
+ registerContextTools(server, client);
11
+ registerPlanningTools(server, client);
12
+ registerAuthoringTools(server, client);
13
+ }
14
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/tools/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,oBAAoB,EAAE,MAAM,cAAc,CAAC;AACpD,OAAO,EAAE,qBAAqB,EAAE,MAAM,eAAe,CAAC;AACtD,OAAO,EAAE,sBAAsB,EAAE,MAAM,gBAAgB,CAAC;AAExD;;;;GAIG;AACH,MAAM,UAAU,aAAa,CAAC,MAAiB,EAAE,MAA2B;IAC1E,oBAAoB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACrC,qBAAqB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACtC,sBAAsB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AACzC,CAAC"}
@@ -0,0 +1,4 @@
1
+ import type { McpServer } from "@modelcontextprotocol/server";
2
+ import type { CreativePlannClient } from "../client.js";
3
+ /** Visão do trabalho: o que está agendado, parado ou atrasado. */
4
+ export declare function registerPlanningTools(server: McpServer, client: CreativePlannClient): void;
@@ -0,0 +1,61 @@
1
+ import * as z from "zod/v4";
2
+ import { ALL_STATUSES, COMPANY_ARG, guard, path, READ_ONLY, STAGES } from "../shared.js";
3
+ /** Visão do trabalho: o que está agendado, parado ou atrasado. */
4
+ export function registerPlanningTools(server, client) {
5
+ server.registerTool("get_board", {
6
+ title: "Ver o fluxo (Kanban)",
7
+ description: "O Kanban da empresa: colunas na ordem do fluxo com os cards de cada uma. " +
8
+ "Inclui colunas vazias, para você saber para onde é possível mover.",
9
+ inputSchema: z.object({ company: COMPANY_ARG }),
10
+ annotations: READ_ONLY,
11
+ }, guard(({ company }) => client.get(`/companies/${path(company)}/board`)));
12
+ server.registerTool("get_calendar", {
13
+ title: "Ver o calendário",
14
+ description: "Agenda de uma janela de datas, mais o que precisa de atenção: posts sem " +
15
+ "data marcada e posts com prazo interno vencido.",
16
+ inputSchema: z.object({
17
+ company: COMPANY_ARG,
18
+ from: z
19
+ .string()
20
+ .regex(/^\d{4}-\d{2}-\d{2}$/)
21
+ .describe("Início, YYYY-MM-DD (data local da empresa)."),
22
+ to: z
23
+ .string()
24
+ .regex(/^\d{4}-\d{2}-\d{2}$/)
25
+ .describe("Fim, YYYY-MM-DD (inclusive)."),
26
+ }),
27
+ annotations: READ_ONLY,
28
+ }, guard(({ company, ...query }) => client.get(`/companies/${path(company)}/calendar`, query)));
29
+ server.registerTool("list_posts", {
30
+ title: "Buscar posts",
31
+ description: "Busca posts com filtros. Use `unscheduled: true` para achar o que ainda " +
32
+ "não tem data, ou `stage`/`status` para ver o que está travado numa etapa.",
33
+ inputSchema: z.object({
34
+ company: COMPANY_ARG.optional().describe("Sem isto, busca em todas as empresas do token."),
35
+ stage: z.enum(STAGES).optional(),
36
+ status: z.enum(ALL_STATUSES).optional(),
37
+ from: z.string().optional().describe("Agendados a partir de YYYY-MM-DD."),
38
+ to: z.string().optional().describe("Agendados até YYYY-MM-DD."),
39
+ unscheduled: z.enum(["true", "false"]).optional(),
40
+ search: z.string().optional().describe("Texto no título ou na legenda."),
41
+ limit: z.number().int().min(1).max(100).optional(),
42
+ cursor: z.string().optional(),
43
+ }),
44
+ annotations: READ_ONLY,
45
+ }, guard((query) => client.get("/posts", query)));
46
+ server.registerTool("get_post", {
47
+ title: "Ver um post",
48
+ description: "Post completo: briefing, roteiro, mídia, destinos por rede e resultado " +
49
+ "de cada publicação (permalink ou erro).",
50
+ inputSchema: z.object({ postId: z.string().min(1) }),
51
+ annotations: READ_ONLY,
52
+ }, guard(({ postId }) => client.get(`/posts/${path(postId)}`)));
53
+ server.registerTool("get_post_history", {
54
+ title: "Ver histórico do post",
55
+ description: "Comentários e histórico do post: movimentações de etapa e eventos de " +
56
+ "aprovação, em ordem. Útil para entender por que um post está parado.",
57
+ inputSchema: z.object({ postId: z.string().min(1) }),
58
+ annotations: READ_ONLY,
59
+ }, guard(({ postId }) => client.get(`/posts/${path(postId)}/comments`)));
60
+ }
61
+ //# sourceMappingURL=planning.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"planning.js","sourceRoot":"","sources":["../../src/tools/planning.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1 @@
1
+ export declare const VERSION: string;
@@ -0,0 +1,10 @@
1
+ import { createRequire } from "node:module";
2
+ /**
3
+ * Versão lida do package.json, não duplicada aqui: duas fontes divergem na
4
+ * primeira release, e é justamente esta versão que o cliente MCP mostra no
5
+ * diagnóstico de problema.
6
+ */
7
+ const require = createRequire(import.meta.url);
8
+ const pkg = require("../package.json");
9
+ export const VERSION = pkg.version;
10
+ //# sourceMappingURL=version.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"version.js","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C;;;;GAIG;AACH,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAC/C,MAAM,GAAG,GAAG,OAAO,CAAC,iBAAiB,CAAwB,CAAC;AAE9D,MAAM,CAAC,MAAM,OAAO,GAAG,GAAG,CAAC,OAAO,CAAC"}
package/package.json ADDED
@@ -0,0 +1,62 @@
1
+ {
2
+ "name": "@creativeproject/creative-plann-mcp",
3
+ "version": "0.1.0",
4
+ "description": "Servidor MCP do Creative Plann — permite que uma IA planeje, escreva e organize posts nas redes sociais das empresas da sua organização.",
5
+ "license": "MIT",
6
+ "type": "module",
7
+ "bin": {
8
+ "creative-plann-mcp": "dist/cli.js"
9
+ },
10
+ "files": [
11
+ "dist",
12
+ "README.md",
13
+ "LICENSE"
14
+ ],
15
+ "engines": {
16
+ "node": ">=20"
17
+ },
18
+ "keywords": [
19
+ "mcp",
20
+ "model-context-protocol",
21
+ "social-media",
22
+ "instagram",
23
+ "scheduling",
24
+ "creative-plann"
25
+ ],
26
+ "scripts": {
27
+ "build": "rm -rf dist && tsc && chmod +x dist/cli.js",
28
+ "dev": "tsc --watch",
29
+ "prepublishOnly": "npm run build",
30
+ "test": "vitest run",
31
+ "test:watch": "vitest",
32
+ "typecheck": "tsc --noEmit -p tsconfig.test.json"
33
+ },
34
+ "dependencies": {
35
+ "@modelcontextprotocol/server": "^2.0.0",
36
+ "zod": "^4.2.0"
37
+ },
38
+ "devDependencies": {
39
+ "@types/node": "^22.0.0",
40
+ "typescript": "^5.7.0",
41
+ "vitest": "^4.0.0"
42
+ },
43
+ "author": "Creative Project",
44
+ "repository": {
45
+ "type": "git",
46
+ "url": "git+https://github.com/creativeproject/creative-plann-web.git",
47
+ "directory": "packages/mcp"
48
+ },
49
+ "homepage": "https://github.com/creativeproject/creative-plann-web/tree/main/packages/mcp#readme",
50
+ "bugs": "https://github.com/creativeproject/creative-plann-web/issues",
51
+ "publishConfig": {
52
+ "access": "public"
53
+ },
54
+ "main": "./dist/index.js",
55
+ "types": "./dist/index.d.ts",
56
+ "exports": {
57
+ ".": {
58
+ "types": "./dist/index.d.ts",
59
+ "default": "./dist/index.js"
60
+ }
61
+ }
62
+ }