sapiens-mcp 1.84.0 → 1.85.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/registry.js +1 -1
- package/dist/skills.js +7 -1
- package/dist/tools/carrossel.js +6 -1
- package/dist/tools/gallery.js +41 -2
- package/package.json +1 -1
package/dist/registry.js
CHANGED
|
@@ -89,7 +89,7 @@ export const TOOLS = {
|
|
|
89
89
|
handler: repertorio,
|
|
90
90
|
},
|
|
91
91
|
sapiens_gallery: {
|
|
92
|
-
description: "Browse, publicação e upload das imagens do user. Sub-actions: list (últimas N peças, com prompt/model/url + isPublic + acervoUrl; kind=image por default, kind=video traz os takes com posterUrl, a capa, e kind=all mistura. Depois de ingerir ou gerar vídeo, é o list kind=video que dá a capa pra mostrar miniatura + player em vez de link solto), get (1 imagem com metadados, opcionalmente base64), publish (torna a PRÓPRIA imagem pública: entra na galeria pública + feed Pinterest, e ganha página indexável /imagem/<id> se o modelo não for degen devolve publicPageUrl; publicado NÃO despublica, não existe unpublish), upload (traz pra galeria uma peça gerada FORA da casa, por sourceUrl https, filePath local ou base64; ADMIN por ora), ingest (A PONTE, qualquer conta logada: peça que a PESSOA dirigiu com a ficha do personagem daqui e um motor de fora renderizou, no crédito dela (Kie, fal, Magnific, Sogni, a própria placa): entra NATIVA na timeline e nasce PRIVADA (isPublic false), publicável DEPOIS por ela como qualquer geração da casa, nunca sozinha, com custo 0 em Sinapses e o custo real guardado em externalCost; carrega o prompt VERBATIM, as referências da casa (referenceImageIds), o personagem (characterId) e o motor (externalEngine 'provedor-motor'); a peça chega por filePath (local, só no MCP instalado), sourceUrl (o render, baixado pelo MCP na máquina da pessoa, nunca pelo servidor) ou base64; o carimbo +18 nasce na entrada pela CLASSE do provedor (peso aberto como Sogni, Replicate, HF, fal, WaveSpeed, Civitai e a própria placa entram carimbados, só a curadoria tira; serviço com moderação como Kie, Magnific, Freepik, Krea entra sem) ou por unfiltered=true dito pela pessoa (carimbo dela, ela tira depois); idempotente por sourceUrl ou pelo hash do arquivo, então re-ingerir corrige a ficha em vez de duplicar; tetos 12 MB imagem, 60 MB vídeo, 40 por dia. A chave do provedor NUNCA passa por aqui: quem gerou foi o harness da pessoa. Passo a passo na skill 'pontes'), refs (acopla peças da casa como REFERÊNCIA numa peça que já existe, de upload ou de ingest; ADMIN, e só na própria peça), processo (O COMO JUNTO DO QUE: anexa a uma peça as peças que mostram como ela foi dirigida, o mapa de rota desenhado sobre o still, a prancha de frames com o tempo de cada marco, o antes e depois de duas rodadas; elas viram a seção 'Como foi feito' na página pública da peça, na ordem que você mandar e com a sua legenda por peça; qualquer membro, só na própria peça, teto de 12. É IRMÃ do refs e a diferença importa: refs é o INSUMO que entrou na geração, processo é o REGISTRO de como ela foi dirigida, e uma lista não mexe na outra. Peça de processo privada não aparece pra quem está de fora nem em miniatura: pra aparecer, publique ela também), cast (QUEM ESTÁ EM CENA numa peça que já existe, quando é mais de uma criatura: characterIds em ordem, o protagonista primeiro, e a peça passa a contar na ficha de todos eles em vez de sumir da segunda; qualquer membro, na própria peça), parts (O INTEIRO E OS PEDAÇOS de um vídeo: o clipe de 30s que foi montado a partir de dois takes de 15s, a fita longa feita de partes. COM imageId devolve a ficha de parentesco daquela peça, quais são as partes dela e de qual inteiro ela é parte, com a url do arquivo completo pra baixar. SEM imageId devolve o que AINDA NÃO FOI MONTADO: varre os takes soltos da conta, agrupa os que têm cara de par (mesmo personagem, mesmo período, prompt de 'Part one/Part two' ou arquivo terminando em -a/-b) e diz o PORQUE de cada agrupamento, pra você saber o que falta juntar antes de o autor perguntar. É heurística e não monta nada sozinha: adianta a descoberta, quem decide é quem lê. characterId filtra por personagem. Sem custo), link_parts (LIGA o inteiro aos pedaços: imageId é o vídeo montado e partIds são os takes NA ORDEM em que aparecem nele. O juntador da casa e o ingest que traz referências de vídeo já gravam esse laço sozinhos; esta porta é pra montagem feita FORA (ffmpeg na máquina, ingest do arquivo já pronto) e pra corrigir ligação errada. Só na própria peça, teto de 16 partes, e a lista TROCA o que estava gravado antes. Sem custo). Use list/get pra reusar imagem como referência (passe o imageId em sapiens_image mode=edit ou mode=variation) ou pra mostrar pro user o que ele já tem; publish quando o user quer divulgar a imagem dele. IMPORTANTE sobre upload: a peça entra PRIVADA e continua privada: o servidor recusa publicar e recusa compartilhar na comunidade, porque ela é do usuário e a responsabilidade é dele. O caminho pra ela virar coisa pública é usar como referência numa geração daqui e publicar o resultado. O refs escreve só proveniência (de que ficha/folha a peça nasceu): não promove nada, e um upload continua sem publicar depois de ganhar referência. COMO A PEÇA FOI FEITA: list aceita skill=<slug> e devolve só o que saiu daquela skill (o mesmo slug que sapiens_image gravou em skills), com a busca varrendo as últimas 200 peças antes de cortar no limit; cada item volta com o campo skills, e null ali quer dizer que ninguém marcou, não que foi feita sem skill.",
|
|
92
|
+
description: "Browse, publicação e upload das imagens do user. Sub-actions: list (últimas N peças, com prompt/model/url + isPublic + acervoUrl; kind=image por default, kind=video traz os takes com posterUrl, a capa, e kind=all mistura. Depois de ingerir ou gerar vídeo, é o list kind=video que dá a capa pra mostrar miniatura + player em vez de link solto), get (1 imagem com metadados, opcionalmente base64), publish (torna a PRÓPRIA imagem pública: entra na galeria pública + feed Pinterest, e ganha página indexável /imagem/<id> se o modelo não for degen devolve publicPageUrl; publicado NÃO despublica, não existe unpublish), upload (traz pra galeria uma peça gerada FORA da casa, por sourceUrl https, filePath local ou base64; ADMIN por ora), ingest (A PONTE, qualquer conta logada: peça que a PESSOA dirigiu com a ficha do personagem daqui e um motor de fora renderizou, no crédito dela (Kie, fal, Magnific, Sogni, a própria placa): entra NATIVA na timeline e nasce PRIVADA (isPublic false), publicável DEPOIS por ela como qualquer geração da casa, nunca sozinha, com custo 0 em Sinapses e o custo real guardado em externalCost; carrega o prompt VERBATIM, as referências da casa (referenceImageIds), o personagem (characterId) e o motor (externalEngine 'provedor-motor'); a peça chega por filePath (local, só no MCP instalado), sourceUrl (o render, baixado pelo MCP na máquina da pessoa, nunca pelo servidor) ou base64; o carimbo +18 nasce na entrada pela CLASSE do provedor (peso aberto como Sogni, Replicate, HF, fal, WaveSpeed, Civitai e a própria placa entram carimbados, só a curadoria tira; serviço com moderação como Kie, Magnific, Freepik, Krea entra sem) ou por unfiltered=true dito pela pessoa (carimbo dela, ela tira depois); idempotente por sourceUrl ou pelo hash do arquivo, então re-ingerir corrige a ficha em vez de duplicar; tetos 12 MB imagem, 60 MB vídeo, 40 por dia. A chave do provedor NUNCA passa por aqui: quem gerou foi o harness da pessoa. Passo a passo na skill 'pontes'), refs (acopla peças da casa como REFERÊNCIA numa peça que já existe, de upload ou de ingest; ADMIN, e só na própria peça), processo (O COMO JUNTO DO QUE: anexa a uma peça as peças que mostram como ela foi dirigida, o mapa de rota desenhado sobre o still, a prancha de frames com o tempo de cada marco, o antes e depois de duas rodadas; elas viram a seção 'Como foi feito' na página pública da peça, na ordem que você mandar e com a sua legenda por peça; qualquer membro, só na própria peça, teto de 12. É IRMÃ do refs e a diferença importa: refs é o INSUMO que entrou na geração, processo é o REGISTRO de como ela foi dirigida, e uma lista não mexe na outra. Peça de processo privada não aparece pra quem está de fora nem em miniatura: pra aparecer, publique ela também), cast (QUEM ESTÁ EM CENA numa peça que já existe, quando é mais de uma criatura: characterIds em ordem, o protagonista primeiro, e a peça passa a contar na ficha de todos eles em vez de sumir da segunda; qualquer membro, na própria peça), parts (O INTEIRO E OS PEDAÇOS de um vídeo: o clipe de 30s que foi montado a partir de dois takes de 15s, a fita longa feita de partes. COM imageId devolve a ficha de parentesco daquela peça, quais são as partes dela e de qual inteiro ela é parte, com a url do arquivo completo pra baixar. SEM imageId devolve o que AINDA NÃO FOI MONTADO: varre os takes soltos da conta, agrupa os que têm cara de par (mesmo personagem, mesmo período, prompt de 'Part one/Part two' ou arquivo terminando em -a/-b) e diz o PORQUE de cada agrupamento, pra você saber o que falta juntar antes de o autor perguntar. É heurística e não monta nada sozinha: adianta a descoberta, quem decide é quem lê. characterId filtra por personagem. Sem custo), link_parts (LIGA o inteiro aos pedaços: imageId é o vídeo montado e partIds são os takes NA ORDEM em que aparecem nele. O juntador da casa e o ingest que traz referências de vídeo já gravam esse laço sozinhos; esta porta é pra montagem feita FORA (ffmpeg na máquina, ingest do arquivo já pronto) e pra corrigir ligação errada. Só na própria peça, teto de 16 partes, e a lista TROCA o que estava gravado antes. Sem custo), reprovar (O VETO do dono: imageId + motivo, o porquê numa frase concreta. A peça que errou (rosto do personagem trocado, mão quebrada, a referência errada) não sai mais por porta nenhuma, fila do Distribution, publicar, Telegram, e some das levas do garimpo; fica no acervo com o porquê, pra ensinar. Chame NO MESMO TURNO em que o dono condena uma peça: peça condenada e não marcada volta numa leva. desfazer=true tira o veto. Imagem e vídeo, só na própria peça, sem custo), reprovadas (as peças vetadas da conta com o prompt que as gerou e o motivo, a mais recente primeiro; characterId filtra por personagem. LEIA ANTES de gerar de novo um personagem que já teve peça reprovada: é a lista do que não repetir. Sem custo). Use list/get pra reusar imagem como referência (passe o imageId em sapiens_image mode=edit ou mode=variation) ou pra mostrar pro user o que ele já tem; publish quando o user quer divulgar a imagem dele. IMPORTANTE sobre upload: a peça entra PRIVADA e continua privada: o servidor recusa publicar e recusa compartilhar na comunidade, porque ela é do usuário e a responsabilidade é dele. O caminho pra ela virar coisa pública é usar como referência numa geração daqui e publicar o resultado. O refs escreve só proveniência (de que ficha/folha a peça nasceu): não promove nada, e um upload continua sem publicar depois de ganhar referência. COMO A PEÇA FOI FEITA: list aceita skill=<slug> e devolve só o que saiu daquela skill (o mesmo slug que sapiens_image gravou em skills), com a busca varrendo as últimas 200 peças antes de cortar no limit; cada item volta com o campo skills, e null ali quer dizer que ninguém marcou, não que foi feita sem skill.",
|
|
93
93
|
schema: gallerySchema,
|
|
94
94
|
handler: gallery,
|
|
95
95
|
},
|
package/dist/skills.js
CHANGED
|
@@ -348,6 +348,12 @@ Nas Krea 2 da WaveSpeed a referência é a imagem-base (uma só), e \`refStrengt
|
|
|
348
348
|
- \`generate\` é SÍNCRONA e cobra ao concluir. Modelo pesado (Pro, gpt-image-2-high, Grok quality, Seedream 5.0 Pro, 2K/4K) cai na regra do timeout: cheque \`sapiens_gallery action=list\` antes de repetir, senão cobra duas vezes. O \`seedream-5-0-pro\` foi medido em ~140s, ACIMA do teto de 120s do cliente, então o Timeout nele é o esperado e a imagem está lá.
|
|
349
349
|
- Uma imagem só vira pública (e ganha página indexável) com \`sapiens_gallery action=publish\`.
|
|
350
350
|
|
|
351
|
+
## Peça reprovada ensina a próxima
|
|
352
|
+
|
|
353
|
+
Quando a pessoa condena uma peça ("mudou o rosto dela", "a mão está quebrada", "não é ela"), marque NO MESMO TURNO: \`sapiens_gallery action=reprovar imageId=<id> motivo='<o porquê numa frase concreta>'\`. O motivo bom diz a CAUSA, não só o sintoma: "trocou o rosto: gerada só com o personagem, sem as fotos de rosto do passaporte" ensina mais que "ficou feia". A reprovada não sai mais por porta nenhuma (fila de distribuição, publicar, canal) e some das sugestões do que postar; ela fica no acervo pra ensinar. Peça condenada e não marcada volta numa leva semanas depois, porque nada nela diz que foi condenada.
|
|
354
|
+
|
|
355
|
+
Antes de gerar de novo um personagem, leia o que já deu errado com ele: \`sapiens_gallery action=reprovadas characterId=<id>\` devolve cada peça vetada com o prompt que a gerou e o motivo. Cada motivo vira cuidado nesta geração: a referência que faltou entra, a palavra que puxou o erro sai do prompt. O erro que se repete vira regra do personagem: grave no passaporte (\`sapiens_character action=set_passport\`, campo \`discarded\`, com o negativo junto).
|
|
356
|
+
|
|
351
357
|
## Quando a pessoa quer "do jeito dela", com o personagem dela
|
|
352
358
|
|
|
353
359
|
O design system dela é quem veste a peça (\`sapiens_brand\`), e o personagem dela pode virar a cara fixa desse design system. Depois de plugado, ele entra em toda imagem daquela marca sem ninguém anexar referência de novo:
|
|
@@ -827,7 +833,7 @@ Um carrossel é uma RECEITA: tema (paleta, folha e assinatura) mais slides, cada
|
|
|
827
833
|
|
|
828
834
|
1. \`sapiens_carrossel action=generate\` com \`brief\` (o tema e o ângulo, um parágrafo) OU \`articleId\` (artigo publicado) OU \`userArticleId\` (artigo dela). Custa 350 Sinapses, já com a escolha de fotos, e estorna se falhar. Devolve o \`id\` e a \`url\` do editor.
|
|
829
835
|
2. \`action=get\` traz o payload inteiro e o catálogo: os layouts com os slots de cada um, as paletas, as folhas e a assinatura. Leia antes de mexer.
|
|
830
|
-
3. \`action=update\` grava o payload INTEIRO de volta. Reescreva os textos com a voz da pessoa (puxe a skill \`voz-da-casa\`). Mande o \`theme\` inteiro e o \`image\` de todo slide que você não mexeu: o que faltar volta pro padrão e a foto do slide some.
|
|
836
|
+
3. \`action=update\` grava o payload INTEIRO de volta. Reescreva os textos com a voz da pessoa (puxe a skill \`voz-da-casa\`). Mande o \`theme\` inteiro e o \`image\` de todo slide que você não mexeu: o que faltar volta pro padrão e a foto do slide some. Mande também \`baseUpdatedAt\` com o \`updatedAt\` do get: se o carrossel mudou depois (uma foto gerada, uma edição dela no editor), o update recusa em vez de apagar isso, e aí você faz get de novo. Foto nova não entra por URL no update, só pelo passo 4.
|
|
831
837
|
4. Foto: \`action=auto_images\` (60) deixa a IA escolher do banco; \`action=set_image\` põe uma peça DA PESSOA pelo ID citável (\`img_…\`, de \`sapiens_reference\` ou \`sapiens_gallery\`), de graça; \`action=generate_image\` gera uma nova pra um slide, ~450 cada.
|
|
832
838
|
5. Mande a \`url\` do editor. É lá que ela confere, ajusta e baixa.
|
|
833
839
|
|
package/dist/tools/carrossel.js
CHANGED
|
@@ -66,8 +66,12 @@ export const carrosselSchema = z.object({
|
|
|
66
66
|
payload: z
|
|
67
67
|
.any()
|
|
68
68
|
.optional()
|
|
69
|
-
.describe("update: o payload INTEIRO, no shape do get: { theme: { palette, sheet, signature }, slides: [{ id, templateId, slots, image }], meta }. Preserve image dos slides que você não mexeu e o theme inteiro (folha e assinatura): o que faltar volta pro padrão."),
|
|
69
|
+
.describe("update: o payload INTEIRO, no shape do get: { theme: { palette, sheet, signature }, slides: [{ id, templateId, slots, image }], meta }. Preserve image dos slides que você não mexeu e o theme inteiro (folha e assinatura): o que faltar volta pro padrão. Foto NOVA não entra por URL aqui: use set_image (ID da peça) ou generate_image."),
|
|
70
70
|
title: z.string().optional().describe("update: novo título do carrossel (opcional)."),
|
|
71
|
+
baseUpdatedAt: z
|
|
72
|
+
.number()
|
|
73
|
+
.optional()
|
|
74
|
+
.describe("update: o updatedAt que o get devolveu. Mande sempre: se o carrossel mudou depois do get (uma foto gerada, uma edição no editor), o update recusa em vez de apagar isso com o payload velho. Aí faça get de novo e reaplique."),
|
|
71
75
|
force: z.boolean().optional().describe("auto_images: true troca também as fotos que já estão nos slides."),
|
|
72
76
|
makeVisual: z
|
|
73
77
|
.boolean()
|
|
@@ -144,6 +148,7 @@ export async function carrossel(args) {
|
|
|
144
148
|
carouselId: need(args.carouselId, "carouselId"),
|
|
145
149
|
payload: coercePayload(need(args.payload, "payload")),
|
|
146
150
|
...(args.title ? { title: args.title } : {}),
|
|
151
|
+
...(typeof args.baseUpdatedAt === "number" ? { baseUpdatedAt: args.baseUpdatedAt } : {}),
|
|
147
152
|
});
|
|
148
153
|
case "auto_images":
|
|
149
154
|
return await convexAction("carouselAutofill:mcpCarouselAutoImages", {
|
package/dist/tools/gallery.js
CHANGED
|
@@ -42,6 +42,8 @@ export const gallerySchema = z.object({
|
|
|
42
42
|
"cast",
|
|
43
43
|
"parts",
|
|
44
44
|
"link_parts",
|
|
45
|
+
"reprovar",
|
|
46
|
+
"reprovadas",
|
|
45
47
|
]),
|
|
46
48
|
processo: z
|
|
47
49
|
.array(z.object({
|
|
@@ -63,7 +65,7 @@ export const gallerySchema = z.object({
|
|
|
63
65
|
.positive()
|
|
64
66
|
.max(100)
|
|
65
67
|
.optional()
|
|
66
|
-
.describe("Default 20. Max 100.
|
|
68
|
+
.describe("Default 20. Max 100. Pra action=list (e action=reprovadas, teto 60). Sem offset: com filtro de model ou skill a busca varre só as últimas 200 peças. Pra achar o imageId de peça que não é de hoje, use sapiens_reference action=browse bucket=history term=<palavra> (paginado, devolve o imageId) ou sapiens_reference action=resolve handle=img_xxx."),
|
|
67
69
|
model: z
|
|
68
70
|
.string()
|
|
69
71
|
.optional()
|
|
@@ -137,7 +139,7 @@ export const gallerySchema = z.object({
|
|
|
137
139
|
characterId: z
|
|
138
140
|
.string()
|
|
139
141
|
.optional()
|
|
140
|
-
.describe("action=ingest: o personagem de quem é a peça (influencers:_id, ache com sapiens_character action=list_mine). A peça nasce ligada à ficha, igual ao que sai dos motores da casa: conta no personagem e resolve a miniatura dele. PODE OMITIR quando as referenceImageIds já são peças da casa feitas com aquele personagem (folha de storyboard, ficha): o servidor deduz o personagem da primeira ref que tem um. O que você diz aqui manda sobre o que ele deduz. Re-ingerir a mesma sourceUrl com characterId AMARRA uma peça que já entrou sem personagem, sem trocar o id. Aceita personagem seu ou público."),
|
|
142
|
+
.describe("action=ingest: o personagem de quem é a peça (influencers:_id, ache com sapiens_character action=list_mine). A peça nasce ligada à ficha, igual ao que sai dos motores da casa: conta no personagem e resolve a miniatura dele. PODE OMITIR quando as referenceImageIds já são peças da casa feitas com aquele personagem (folha de storyboard, ficha): o servidor deduz o personagem da primeira ref que tem um. O que você diz aqui manda sobre o que ele deduz. Re-ingerir a mesma sourceUrl com characterId AMARRA uma peça que já entrou sem personagem, sem trocar o id. Aceita personagem seu ou público. Em action=reprovadas, FILTRA as vetadas daquele personagem."),
|
|
141
143
|
characterIds: z
|
|
142
144
|
.union([z.array(z.string()), z.string()])
|
|
143
145
|
.optional()
|
|
@@ -163,6 +165,16 @@ export const gallerySchema = z.object({
|
|
|
163
165
|
.string()
|
|
164
166
|
.optional()
|
|
165
167
|
.describe("action=upload: de onde veio ('magnific', 'suno', 'camera'). Fica registrado na peça e no aviso do Discord."),
|
|
168
|
+
// --- action=reprovar: o veto do dono ---
|
|
169
|
+
motivo: z
|
|
170
|
+
.string()
|
|
171
|
+
.max(500)
|
|
172
|
+
.optional()
|
|
173
|
+
.describe("action=reprovar: O PORQUÊ do veto, numa frase concreta que a próxima geração consegue usar ('trocou o rosto da Helen: gerada só com influencerId, sem as refs do passaporte'; 'mão esquerda com seis dedos'). É a lição que fica na peça: sem ele, reprovar só esconde e não ensina. Até 500 caracteres. Reprovar de novo sem motivo mantém o que já estava escrito."),
|
|
174
|
+
desfazer: z
|
|
175
|
+
.boolean()
|
|
176
|
+
.optional()
|
|
177
|
+
.describe("action=reprovar: true TIRA o veto (a peça volta a poder sair e a entrar nas levas), e o motivo vai junto. Ausente/false reprova."),
|
|
166
178
|
});
|
|
167
179
|
// Teto igual ao do servidor (convex/galleryImport.ts): falha aqui é mais barata
|
|
168
180
|
// que falhar depois de trafegar o base64 inteiro.
|
|
@@ -661,6 +673,33 @@ export async function gallery(args) {
|
|
|
661
673
|
// uma peça nova, sem nenhum laço com os takes que a formaram. O juntador da
|
|
662
674
|
// casa (o "compilado") e o ingest com refs de vídeo já gravam o laço
|
|
663
675
|
// sozinhos; esta porta é pro resto, e pra corrigir ligação errada.
|
|
676
|
+
// reprovar: o VETO do dono. A peça errou (rosto trocado, mão quebrada) e
|
|
677
|
+
// não sai mais por porta nenhuma (fila do Distribution, publicar, Telegram,
|
|
678
|
+
// teia) nem volta numa leva do garimpo. Fica no acervo, com o porquê, pra
|
|
679
|
+
// ensinar: é o que action=reprovadas devolve antes da próxima geração.
|
|
680
|
+
if (args.action === "reprovar") {
|
|
681
|
+
if (!args.imageId) {
|
|
682
|
+
throw new Error("action=reprovar exige imageId: a peça vetada (imagem ou vídeo, o id da galeria).");
|
|
683
|
+
}
|
|
684
|
+
if (!args.desfazer && !args.motivo?.trim()) {
|
|
685
|
+
throw new Error("action=reprovar exige motivo: o porquê do veto numa frase concreta. É ele que ensina a próxima geração a não repetir o erro.");
|
|
686
|
+
}
|
|
687
|
+
return await convexAction("desktopMcp:galleryReprovar", {
|
|
688
|
+
sessionToken,
|
|
689
|
+
imageId: args.imageId,
|
|
690
|
+
reprovada: !args.desfazer,
|
|
691
|
+
motivo: args.desfazer ? undefined : args.motivo?.trim(),
|
|
692
|
+
});
|
|
693
|
+
}
|
|
694
|
+
// reprovadas: as peças vetadas da conta, com o prompt que gerou e o porquê,
|
|
695
|
+
// a mais recente primeiro. Leia ANTES de gerar de novo o mesmo personagem.
|
|
696
|
+
if (args.action === "reprovadas") {
|
|
697
|
+
return await convexAction("desktopMcp:galleryReprovadas", {
|
|
698
|
+
sessionToken,
|
|
699
|
+
characterId: args.characterId,
|
|
700
|
+
limit: args.limit,
|
|
701
|
+
});
|
|
702
|
+
}
|
|
664
703
|
if (args.action === "link_parts") {
|
|
665
704
|
if (!args.imageId) {
|
|
666
705
|
throw new Error("action=link_parts exige imageId: o vídeo INTEIRO, o clipe montado. Use action=parts SEM imageId pra ver os pares de take que ainda não viraram um inteiro.");
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "sapiens-mcp",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.85.0",
|
|
4
4
|
"mcpName": "com.sapiensinteticos/sapiens",
|
|
5
5
|
"description": "MCP server pra operar o Sapiens Sintéticos (sapiensinteticos.com) pelo Claude Code: gerar imagem, escrever artigo, voz, música e mais, na sua conta. Login pelo código de sapiensinteticos.com/conectar-claude.",
|
|
6
6
|
"type": "module",
|