fix(project-manager): remover Dify KB das descriptions, marcar nota TODO

Dify foi removido 06-03-2026. Skills brainstorm/discover ainda referenciam-no
no corpo. Bump v1.2 + nota top-of-file. Reescrita workflow para próxima sessão.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-04-07 04:52:03 +01:00
parent 6285be6c2e
commit faef9b47dc
185 changed files with 9238 additions and 589 deletions
+12
View File
@@ -173,3 +173,15 @@ mcp__ssh-unified__ssh_execute server:"server" command:"rm -f /home/USER/SITE/wp-
- `references/mapeamento-slugs.md` - Mapeamento completo slug -> seccao e tabela de Branda IDs
- `references/script-template.md` - Script PHP template + adaptacoes por tipo de site
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -223,3 +223,15 @@ Usar `references/automation.md` para detalhes sobre Formless Actions, JetSmartFi
---
**Versão**: 1.1.0 | **Autor**: Descomplicar® | **Data**: 18-02-2026
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -310,3 +310,15 @@ Para deploy automatizado, pipelines IA, migração em massa e manipulação prog
---
**Versão**: 1.2.0 | **Autor**: Descomplicar® | **Actualizado**: 18-02-2026
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -276,3 +276,15 @@ WP Admin > JetEngine > AI Command Center > Enable MCP Server
---
**Versão**: 1.1.0 | **Autor**: Descomplicar® | **Data**: 18-02-2026
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
File diff suppressed because it is too large Load Diff
+307
View File
@@ -0,0 +1,307 @@
---
name: seo-post
description: Optimizar posts WordPress com RankMath Pro via WP-CLI. Auditar, corrigir e aplicar SEO completo incluindo schema, OG, robots e links internos. Usar quando "seo post", "rankmath", "schema", "optimizar artigo", "seo wordpress".
context: fork
---
# /seo-post — Optimizar Posts WordPress com RankMath Pro
Modos: auditar (com ID), aplicar (com ID + dados), bulk (com lista IDs), novo (pipeline completo).
## Constantes
```
SERVIDOR: server (via mcp__ssh-unified__ssh_execute)
WP_PATH: cd /home/ealmeida/public_html
WP_CLI: wp --allow-root
WP_USER: --user=2 (para wp eval)
MANUAL: Hub/06-Operacoes/Documentacao/Manuais/WP-CLI/Rank-Math-WP-CLI-Manual-Definitivo.md
```
## Modo auditar (/seo-post ID)
Verifica estado SEO de um post e lista problemas.
```bash
cd /home/ealmeida/public_html
# 1. Dados do post
wp --allow-root post get POST_ID --fields=ID,post_title,post_name,post_status --format=table
# 2. Todos os meta RankMath
wp --allow-root post meta list POST_ID --format=table | grep rank_math
# 3. Thumbnail e alt text
THUMB_ID=$(wp --allow-root post meta get POST_ID _thumbnail_id)
wp --allow-root post meta get $THUMB_ID _wp_attachment_image_alt
# 4. Schema no HTML
curl -s "URL_DO_POST" | grep -o '"@type":"[^"]*"' | sort -u
```
**Checklist de auditoria:**
| Campo | Verificacao |
|-------|-----------|
| rank_math_title | Existe? 50-70 chars? Tem keyword? |
| rank_math_description | Existe? 150-160 chars? Tem keyword? |
| rank_math_focus_keyword | Existe? 1-3 keywords CSV? |
| rank_math_primary_category | Existe? ID valido? |
| rank_math_robots | Array? Tem ["index"]? |
| rank_math_advanced_robots | Array JSON? max-image-preview large? |
| rank_math_rich_snippet | "article"? |
| rank_math_snippet_article_type | "NewsArticle" ou "BlogPosting" ou "Article"? |
| rank_math_schema_* | Existe meta com schema? Tem isPrimary 1? |
| rank_math_facebook_title | Existe? |
| rank_math_facebook_image | Existe? URL valido? |
| rank_math_twitter_card_type | "summary_large_image"? |
| _thumbnail_id | Existe? Imagem real? |
| Alt text imagem | Tem keywords? |
| post_name (slug) | Curto? <40 chars? Tem keyword? |
| rank_math_seo_score | Existe? >0? Se N/A -> executar Passo 6 |
**Output:** tabela com campo, estado (OK/FALHA), valor actual, accao sugerida.
## Modo aplicar (/seo-post ID com dados)
Aplica SEO completo a um post. Pedir ao utilizador:
- Titulo SEO (ou gerar a partir do post_title)
- Meta description
- Focus keywords (CSV)
- Tipo schema: NewsArticle (noticias) ou Article (guias) ou BlogPosting (blog)
### Passo 1: Strings simples
```bash
wp --allow-root post meta update POST_ID rank_math_title 'TITULO SEO'
wp --allow-root post meta update POST_ID rank_math_description 'META DESC'
wp --allow-root post meta update POST_ID rank_math_focus_keyword 'kw1,kw2,kw3'
wp --allow-root post meta update POST_ID rank_math_primary_category 'CAT_ID'
```
### Passo 2: Arrays (OBRIGATORIO --format=json)
```bash
wp --allow-root post meta update POST_ID rank_math_robots '["index"]' --format=json
wp --allow-root post meta update POST_ID rank_math_advanced_robots '{"max-snippet":"-1","max-video-preview":"-1","max-image-preview":"large"}' --format=json
```
### Passo 3: Schema — DOIS formatos (AMBOS obrigatorios)
```bash
# Legacy (dashboard RankMath)
wp --allow-root post meta update POST_ID rank_math_rich_snippet 'article'
wp --allow-root post meta update POST_ID rank_math_snippet_article_type 'TIPO'
# TIPO: NewsArticle (noticias), Article (guias), BlogPosting (blog)
# Novo (schema real no HTML — via wp eval)
wp --allow-root eval '
$schema = [
"metadata" => ["title" => "TIPO", "type" => "custom", "shortcode" => "s-" . uniqid(), "isPrimary" => "1"],
"@type" => "TIPO",
"headline" => "%seo_title%",
"description" => "%seo_description%",
"keywords" => "%keywords%",
"image" => ["@type" => "ImageObject", "url" => "%post_thumbnail%"],
"author" => ["@type" => "Organization", "name" => "Descomplicar", "url" => "https://descomplicar.pt"],
"publisher" => ["@type" => "Organization", "name" => "Descomplicar", "url" => "https://descomplicar.pt"],
"datePublished" => "%date(Y-m-dTH:i:sP)%",
"dateModified" => "%modified(Y-m-dTH:i:sP)%",
"articleSection" => "%categories%"
];
update_post_meta(POST_ID, "rank_math_schema_TIPO", $schema);
echo "Schema OK\n";
' --user=2
```
### Passo 4: Social / OG
```bash
wp --allow-root post meta update POST_ID rank_math_facebook_title 'TITULO OG'
wp --allow-root post meta update POST_ID rank_math_facebook_description 'DESC OG'
wp --allow-root post meta update POST_ID rank_math_facebook_image 'IMAGE_URL'
wp --allow-root post meta update POST_ID rank_math_og_content_image 'IMAGE_URL'
wp --allow-root post meta update POST_ID rank_math_twitter_card_type 'summary_large_image'
```
### Passo 5: Slug (se necessario)
```bash
wp --allow-root post update POST_ID --post_name='slug-curto-keyword'
```
### Passo 6: SEO Score (OBRIGATORIO — posts via CLI nao calculam score automaticamente)
O RankMath calcula o SEO Score apenas no editor Gutenberg (JavaScript). Posts criados via WP-CLI ficam com score "N/A" no dashboard. Este passo calcula e grava o score server-side.
```bash
wp --allow-root eval '
$post_id = POST_ID;
$post = get_post($post_id);
$title = get_post_meta($post_id, "rank_math_title", true);
$desc = get_post_meta($post_id, "rank_math_description", true);
$kw_raw = get_post_meta($post_id, "rank_math_focus_keyword", true);
$keywords = array_map("trim", explode(",", $kw_raw));
$kw = strtolower($keywords[0] ?? "");
$content = $post->post_content;
$slug = $post->post_name;
$word_count = str_word_count(strip_tags($content));
$score = 0;
// Testes SEO (20 criterios, max 86 pontos brutos -> normalizado 0-100)
if ($kw) $score += 5;
if ($title) $score += 5;
if ($desc) $score += 5;
if ($title && stripos($title, $kw) !== false) $score += 5;
if ($desc && stripos($desc, $kw) !== false) $score += 5;
if (stripos($slug, str_replace(" ", "-", $kw)) !== false) $score += 5;
if ($title && stripos($title, $kw) === 0) $score += 3;
$tlen = strlen($title); if ($tlen >= 30 && $tlen <= 70) $score += 5;
$dlen = strlen($desc); if ($dlen >= 100 && $dlen <= 160) $score += 5;
if (has_post_thumbnail($post_id)) $score += 5;
if ($word_count >= 600) $score += 5;
if ($word_count >= 300) $score += 3;
if (stripos($content, $kw) !== false) $score += 5;
if (preg_match_all("/href=[\"\\x27]https?:\\/\\/descomplicar\\.pt/i", $content) >= 1) $score += 3;
if (preg_match_all("/href=[\"\\x27]https?:\\/\\/(?!descomplicar\\.pt)/i", $content) >= 1) $score += 3;
if (preg_match("/<h[23]/i", $content)) $score += 3;
if (preg_match("/<h[23][^>]*>.*" . preg_quote($kw, "/") . "/si", $content)) $score += 3;
if (preg_match("/alt=[\"\\x27][^\"\\x27]+[\"\\x27]/i", $content)) $score += 2;
if (get_post_meta($post_id, "rank_math_rich_snippet", true)) $score += 3;
if (get_post_meta($post_id, "rank_math_primary_category", true)) $score += 2;
$final = min(100, max(0, round(($score / 86) * 100)));
update_post_meta($post_id, "rank_math_seo_score", $final);
echo "SEO Score: $final/100\n";
' --user=2
```
### Passo 7: Verificar
```bash
curl -s "URL" | grep -o '"@type":"[^"]*"' | sort -u
wp --allow-root post meta list POST_ID --format=table | grep rank_math
```
## Modo bulk (/seo-post bulk)
Aplicar schema a multiplos posts. Util para corrigir posts antigos.
```bash
# Aplicar schema Article a todos os guias sem schema
wp --allow-root eval '
$schema = [
"metadata" => ["title" => "Article", "type" => "custom", "shortcode" => "s-" . uniqid(), "isPrimary" => "1"],
"@type" => "Article",
"headline" => "%seo_title%",
"description" => "%seo_description%",
"keywords" => "%keywords%",
"image" => ["@type" => "ImageObject", "url" => "%post_thumbnail%"],
"author" => ["@type" => "Organization", "name" => "Descomplicar", "url" => "https://descomplicar.pt"],
"publisher" => ["@type" => "Organization", "name" => "Descomplicar", "url" => "https://descomplicar.pt"],
"datePublished" => "%date(Y-m-dTH:i:sP)%",
"dateModified" => "%modified(Y-m-dTH:i:sP)%",
"articleSection" => "%categories%"
];
$posts = get_posts(["numberposts" => -1, "post_status" => "publish", "meta_query" => [["key" => "rank_math_rich_snippet", "compare" => "NOT EXISTS"]]]);
$count = 0;
foreach ($posts as $p) {
update_post_meta($p->ID, "rank_math_rich_snippet", "article");
update_post_meta($p->ID, "rank_math_snippet_article_type", "BlogPosting");
update_post_meta($p->ID, "rank_math_schema_Article", $schema);
$count++;
}
echo "$count posts actualizados com schema Article\n";
' --user=2
```
### Bulk: calcular SEO Score para todos os posts sem score
```bash
wp --allow-root eval '
$posts = get_posts(["numberposts" => -1, "post_status" => "publish", "meta_query" => [
["key" => "rank_math_focus_keyword", "compare" => "EXISTS"],
["relation" => "OR",
["key" => "rank_math_seo_score", "compare" => "NOT EXISTS"],
["key" => "rank_math_seo_score", "value" => "", "compare" => "="]
]
]]);
$count = 0;
foreach ($posts as $p) {
$title = get_post_meta($p->ID, "rank_math_title", true);
$desc = get_post_meta($p->ID, "rank_math_description", true);
$kw = strtolower(trim(explode(",", get_post_meta($p->ID, "rank_math_focus_keyword", true))[0] ?? ""));
$slug = $p->post_name;
$content = $p->post_content;
$wc = str_word_count(strip_tags($content));
$s = 0;
if ($kw) $s += 5;
if ($title) $s += 5;
if ($desc) $s += 5;
if ($title && stripos($title, $kw) !== false) $s += 5;
if ($desc && stripos($desc, $kw) !== false) $s += 5;
if (stripos($slug, str_replace(" ", "-", $kw)) !== false) $s += 5;
if ($title && stripos($title, $kw) === 0) $s += 3;
$tl = strlen($title); if ($tl >= 30 && $tl <= 70) $s += 5;
$dl = strlen($desc); if ($dl >= 100 && $dl <= 160) $s += 5;
if (has_post_thumbnail($p->ID)) $s += 5;
if ($wc >= 600) $s += 5;
if ($wc >= 300) $s += 3;
if (stripos($content, $kw) !== false) $s += 5;
if (preg_match_all("/href=[\"\\x27]https?:\\/\\/descomplicar\\.pt/i", $content) >= 1) $s += 3;
if (preg_match_all("/href=[\"\\x27]https?:\\/\\/(?!descomplicar\\.pt)/i", $content) >= 1) $s += 3;
if (preg_match("/<h[23]/i", $content)) $s += 3;
if (preg_match("/<h[23][^>]*>.*" . preg_quote($kw, "/") . "/si", $content)) $s += 3;
if (preg_match("/alt=[\"\\x27][^\"\\x27]+[\"\\x27]/i", $content)) $s += 2;
if (get_post_meta($p->ID, "rank_math_rich_snippet", true)) $s += 3;
if (get_post_meta($p->ID, "rank_math_primary_category", true)) $s += 2;
$final = min(100, max(0, round(($s / 86) * 100)));
update_post_meta($p->ID, "rank_math_seo_score", $final);
$count++;
}
echo "$count posts actualizados com SEO score\n";
' --user=2
```
## Categorias de noticias (referencia)
| Categoria | ID | Slug |
|-----------|-----|------|
| Noticias (pai) | 1188 | noticias |
| IA e Agentes | 1189 | ia-agentes |
| Automacao | 1190 | automacao |
| Marketing Digital | 1191 | marketing-digital |
| Tecnologia | 1192 | tecnologia |
| Regulacao e Europa | 1193 | regulacao-europa |
| Negocios e PMEs | 1194 | negocios-pmes |
## Erros comuns
| Erro | Causa | Solucao |
|------|-------|---------|
| Schema: Off no dashboard | Faltam campos legacy | Definir rank_math_rich_snippet + rank_math_snippet_article_type |
| Schema nao aparece no HTML | Falta rank_math_schema_* | Usar wp eval com array PHP |
| Robots corrompidos | Sem --format=json | SEMPRE --format=json para arrays |
| User ID invalido | --user=1 nao existe | Usar --user=2 (ealmeida) |
| Heredoc no conteudo | cat <<EOF | NUNCA heredoc, aspas simples directas |
| SEO Score N/A no dashboard | Post criado via CLI sem Gutenberg | Executar Passo 6 (calculo server-side) |
## Referencia
- **Skill relacionada:** `/rank-math` — gestao completa RankMath (audit, bulk, redirects, indexing, analytics, backup)
- Manual completo: `Hub/06-Operacoes/Documentacao/Manuais/WP-CLI/Rank-Math-WP-CLI-Manual-Definitivo.md`
- Pesquisa Claude: `Hub/06-Operacoes/Documentacao/Manuais/WP-CLI/Rank-Math-SEO-WP-CLI-Skils-Pesquisa-Claude.md`
- Pesquisa Gemini: `Hub/06-Operacoes/Documentacao/Manuais/WP-CLI/Rank-Math-SEO-WP-CLI-Skills-Pesquisa-Gemini.md`
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -257,3 +257,15 @@ Configurar cron real (`crontab -e` como root):
---
*WooCommerce CLI no CWP | Descomplicar® | v1.0.0 | 18-02-2026*
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -265,3 +265,15 @@ mcp__dify-kb__dify_kb_retrieve_segments({
---
**Versão**: 1.0.0 | **Autor**: Descomplicar®
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -320,3 +320,15 @@ wp user list --role=administrator --allow-root --path=$PATH
---
*WP-CLI no CWP | Descomplicar® | v1.0.0 | 18-02-2026*
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -408,3 +408,15 @@ INSERT INTO tblskill_agent_metrics (
---
**Versão**: 1.2.0 | **Data**: 2026-03-12 | **Instrumentação**: Activa
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -354,3 +354,15 @@ chown -R ${WP_USER}:${WP_USER} ${WP_PATH}
- Backup automatico antes de alteracoes
- Verificacao pos-hardening com rollback
- Tarefa Desk CRM #443 (Projecto #65, Discussao #33)
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -327,3 +327,15 @@ Skill:
3. Executar workflow integrado
Output: [resultado completo com referências]
```
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -253,3 +253,15 @@ wp --path=... cache flush --allow-root
---
*Skill v1.0.0 | 25-02-2026 | Descomplicar®*
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*
+12
View File
@@ -308,3 +308,15 @@ Skill:
3. Executar workflow integrado
Output: [resultado completo com referências]
```
---
## Healing Log
Registo de erros conhecidos e como evitá-los. Lido automaticamente antes de executar.
```jsonl
{"date":"","issue":"","fix":"","source":"user|auto"}
```
*Adicionar nova linha após cada erro corrigido.*