diff --git a/records/plugin-dev/KB-PLUGIN-037-redmine-plugin-api-contract.md b/records/plugin-dev/KB-PLUGIN-037-redmine-plugin-api-contract.md index 9e39c3f..8bacc98 100644 --- a/records/plugin-dev/KB-PLUGIN-037-redmine-plugin-api-contract.md +++ b/records/plugin-dev/KB-PLUGIN-037-redmine-plugin-api-contract.md @@ -54,8 +54,13 @@ andamento. Tarefas não concluídas ficam só no GLPI (gate no `state = Feito`). usuário for **membro do projeto** com papel que permita a ação → o plugin faz auto-membership (`POST /projects/:id/memberships.json`, papel = `default_role_id`). Falhou (403/412)? Refaz como admin e loga — nunca perde o lançamento. -- **Mapeamento de usuários:** cache `glpi_plugin_redmine_users` (sync) + auto-match por - **e-mail** + overrides manuais (`glpi_plugin_redmine_usermap`). +- **Mapeamento de usuários:** overrides manuais (`glpi_plugin_redmine_usermap`) → + auto-match por **e-mail** no cache `glpi_plugin_redmine_users` → **lookup ao vivo** + no Redmine (`/users.json?name=`) com upsert no cache (self-healing, 1.6.0). + Sem par: lança como admin **com log** ("Sem par Redmine para o usuário GLPI #N"). + Incidente real (2026-07-02): o cache ficou vazio em prod e os lançamentos saíram + como admin em silêncio — motivou o self-healing e o `syncUsers` por upsert + (nunca esvazia a tabela). - **Idempotência:** `glpi_plugin_redmine_tickets` (1 issue por chamado) e `glpi_plugin_redmine_tasks` (tempo 1× por task). Se a issue vinculada foi apagada no Redmine, o plugin detecta (GET 404) e **recria** removendo o vínculo órfão (1.5.5+).