174 lines
25 KiB
Python
174 lines
25 KiB
Python
"""Update the existing executive report, backlog and evidence; retain earlier versions as history."""
|
||
import collections
|
||
import csv
|
||
import json
|
||
import re
|
||
import sys
|
||
from pathlib import Path
|
||
|
||
ROOT = Path(__file__).resolve().parent.parent
|
||
PRIVATE = ROOT / 'storage/app/private/investmoz-v2/portal-audit'
|
||
DOCS = ROOT / 'docs/investmoz/v2/auditoria-portal'
|
||
sys.stdout.reconfigure(encoding='utf-8')
|
||
csv.field_size_limit(16 * 1024 * 1024)
|
||
http = json.loads((PRIVATE / 'opportunity-semantic-http-qa.json').read_text(encoding='utf-8-sig'))
|
||
editorial = json.loads((PRIVATE / 'opportunity-semantic-publication-http-qa.json').read_text(encoding='utf-8-sig'))
|
||
verified = json.loads((PRIVATE / 'opportunity-semantic-verification-qa.json').read_text(encoding='utf-8-sig'))
|
||
environment = json.loads((PRIVATE / 'opportunity-semantic-environment-qa.json').read_text(encoding='utf-8-sig'))
|
||
active = json.loads((PRIVATE / 'dashboard-active-readonly.json').read_text(encoding='utf-8-sig'))
|
||
preserved = json.loads((PRIVATE / 'profiles-v1-preservation-qa.json').read_text(encoding='utf-8-sig'))
|
||
counts = json.loads((PRIVATE / 'contagens-requisitos.json').read_text(encoding='utf-8-sig'))
|
||
assert http['result'] == editorial['result'] == 'passed'
|
||
assert http['target'] == 'desk_restore_20261009_174726_test:55441'
|
||
assert all(p['active_writes'] == 0 for p in [http, editorial, verified, environment, active, preserved])
|
||
documents_path = PRIVATE / 'opportunity-semantic-documents-http-qa.json'
|
||
document = json.loads(documents_path.read_text(encoding='utf-8-sig')) if documents_path.exists() else {}
|
||
names = {'investment_project': 'Investimento', 'real_estate': 'Imobiliário', 'land_rights': 'Fundiário/DUAT',
|
||
'business_sale': 'Venda de negócio', 'business_partnership': 'Parceria de negócio', 'franchise': 'Franquia',
|
||
'concession': 'Concessão', 'financing': 'Financiamento', 'supply': 'Fornecimento', 'other': 'Outros'}
|
||
category_rows = []
|
||
for case in http['cases']:
|
||
category = case['category']
|
||
publication = ('Pública, só teaser; prova editorial posterior' if category == 'business_sale' else
|
||
'Bloqueada: autorização externa pendente' if category == 'land_rights' else
|
||
'Interna; sem exposição pública' if case['publication'] == 'published-internal' else 'Bloqueada')
|
||
ready = case['submission'] == 'passed'
|
||
category_rows.append(f"| {names[category]} — #{case['id']} | Incompleto guardado e recuperado | Edição gravada, nova sessão MFA | {'Aceite' if ready else '422: perfil modular por aprovar'} | {'Gates e aprovação interna' if ready else 'Não elegível'} | {publication} |")
|
||
category_table = '\n'.join(category_rows)
|
||
state_table = '\n'.join(f"| {state} | {v['requisitos']} | {v['linhas_origem']} |" for state, v in counts['por_estado'].items())
|
||
pdf_evidence = ('PDF válido de uma página, parser estrito, upload/scan ClamD real e SHA; download 21/24/25, negação 23(403); exclusão lógica→download404/opção removida; restauração→nova sessão→bytes/hash idênticos. Prova `opportunity-semantic-documents-http-qa.json`.'
|
||
if document.get('result') == 'passed' else 'Ensaio PDF web18097 ainda não encerrado; consultar a prova sanitizada da operação, sem extrapolar PNG a outros tipos.')
|
||
summary = f'''## Resultado atual por categoria — semântica e atribuições em QA, 10/10/2026
|
||
|
||
Este bloco é a evidência mais recente desta matriz; as secções anteriores abaixo permanecem como histórico. Estados antigos sobre objetos opacos, coordenação editorial e ausência de 190000 ficam confrontados com os resultados concretos deste bloco. **Código preparado e HTTP/persistência em QA não encerram interface nem funcionalidade ativa.** Não houve escrita na base ativa. C37 e aceitação visual permanecem pendentes.
|
||
|
||
Servidor **http://127.0.0.1:18097**, base **desk_restore_20261009_174726_test:55441**, Fortify e MFA normais. **Promotor QA 21** continua a conta de ensaio do dashboard. Não usar Auditor ou Superutilizador em seu lugar.
|
||
|
||
| Categoria / ID QA | Rascunho | Edição / recuperação | Submissão | Revisão | Publicação |
|
||
| --- | --- | --- | --- | --- | --- |
|
||
{category_table}
|
||
|
||
As dez categorias recuperaram dados noutra sessão autenticada. As seis com contrato definido aceitaram os cenários semânticos documentados; as quatro restantes conservaram rascunhos, sem inventar um perfil modular para as submeter. Fundiário #32 separa aprovação interna da decisão externa. Venda #33 passou depois pelo percurso editorial público, sem divulgar resumo/dados privados.
|
||
|
||
**Campos e regras preparados:** cronograma com início/fim/responsável e dependências acíclicas; maturidade com os oito códigos normativos; viabilidade com cenário/indicadores/modelo e estudo, sem score de sucesso; serviços/título/entidade emissora/ocupação/avaliação imobiliários; parcelas com editor de vértices/anéis MultiPolygon, benfeitorias e consulta comunitária; constituição/beneficiário efetivo, exercícios existentes, ativos/passivos, obrigações laborais, licenças, NDA, governação e franquia. O contrato é elaborado no servidor e consumido pelo editor, sem templates JSON divergentes no cliente. Objetos legados conservam chaves anteriores. O schema original de 110 definições mantém SHA `{verified['source_schema_sha256']}`.
|
||
|
||
**Falhas corrigidas com prova:** {len(http['negative_fields'])} recusas 422 identificaram o campo e conservaram o rascunho inválido: fim anterior ao início, ciclo, falta de cenário/modelo, serviços incompletos, título de outra oportunidade, comunidades sem consulta, financeiros insuficientes e contingências não declaradas. Erros `canonical.<campo>` são devolvidos pela API e ligados aos controlos; a posição/clareza visual ainda não foi observada. O formulário núcleo duplicado foi retirado do modo perfil; gestão legada mantém o seu acesso próprio.
|
||
|
||
**Filas e perfis:** revisão, preparação editorial, recurso e tarefas atribuídas reutilizam `tasks`, com ligação explícita ao bigint da oportunidade. #30 pediu parecer a 29: o destinatário errado recebeu403, a aprovação com parecer pendente422; a resposta foi guardada e concluiu a tarefa, sem aprovar o gate automaticamente. #33: coordenador editorial25 atribuiu a29; tarefa recuperada na fila; outro Publicador403; o designado publicou. Papéis/âmbitos/independência/responsabilidades são verificados no servidor; revogação após aprovação bloqueia publicação no teste específico. Responsabilidades atribuídas neste ensaio são sintéticas, sem competência institucional real inferida. SLA permanece `unconfigured` e `due_at=null`.
|
||
|
||
**Consumidores territoriais/documentais:** seis contratos recuperaram país MZ e uma localização com limite disponível; API retornou dois limites de contexto. O editor e os campos `location_id` consultam o território mais profundo e mantêm a parcela separada do limite administrativo. País FR do mercado do investimento foi gravado/recuperado; isto não encerra origem/filtros/estatísticas de todos os formulários. Originais dos seis casos permitiram21/24/25 e negaram organização estrangeira23(403). O download/prévia reutiliza `VerifiedDocumentBinary`, que verifica cifra/hash/scan e controla falhas; não altera os originais. #33 recuperou original da imagem e duas derivadas limpas pelo ClamD real. {pdf_evidence}
|
||
|
||
**Limites concretos:** correspondência entre titular/documento/cadastro e âmbito urbanístico exige evidência e decisão do gate, sem inferir autenticidade jurídica pela existência de um UUID. Limites urbanísticos e materialidade não são inventados. Unidades aplicáveis, Response integral e relações do §27 ainda precisam de reconciliação. O schema original exige pelo menos um exercício financeiro; casos com zero exercícios devem ter regra expressa reconciliada antes de serem declarados cobertos. A moeda obedece ao padrão do contrato; não existe aqui prova de catálogo completo ISO4217. DOCX/XLSX, partilhas e PDFs/exportações/derivadas sem prova específica continuam abertos. C37, A/B e todo o percurso visual por perfil permanecem pendentes.
|
||
|
||
**Preservação e compilação:** 18 conjuntos de linhas anteriores por ID/colunas originais preservados; MFA18 intacto. Manifesto ativo `{verified['active_manifest_sha256']}` preservado. Manifesto QA `{verified['qa_manifest_sha256']}`; bundle próprio `build-qa-opportunities`, sem recompilar o ativo. TypeScript, PHPStan e testes específicos passaram; as contagens de testes não são usadas como critério de conclusão.
|
||
|
||
Mesma matriz: **3.386 requisitos / 3.386 linhas**, **6.838 ocorrências de origem**. IDs, fontes, critérios, versões divergentes e referências anteriores conservados.
|
||
|
||
| Estado canónico | Requisitos | Ocorrências de origem |
|
||
| --- | ---: | ---: |
|
||
{state_table}
|
||
|
||
Linhas principais: **AUD-OP-02/03/04, AUD-GEO-03, AUD-PROFILE-11/12/19/25/28/31 e AUD-OPS-01**, em [matriz-requisitos.csv](matriz-requisitos.csv). Nenhum desses critérios visuais foi fechado por API.
|
||
'''
|
||
|
||
backlog = '''## Próximo trabalho executável e decisões separadas — lote semântico atual
|
||
|
||
| Prioridade / requisito | O que já tem prova QA | Falta / próxima ação e critério concreto |
|
||
| --- | --- | --- |
|
||
| P0 — UI-01/C37 | Diagnóstico/MFA preservados; ensaios HTTP21 não fecham18. | C37 e confirmação visual continuam pendentes conforme pedido. Quando retomados, dashboard→MFA→sessão→refresh→logout→novo login; rastreio sanitizado e primeiro ponto de perda. Nenhum novo teste visual solicitado agora. |
|
||
| P1 — OP-04 / PROFILE-28/25 | Seis editores/regras no contrato do servidor; dez drafts e doze rejeições por campo recuperadas. | Observar cada categoria na UI21, erro junto ao controlo e nova sessão; reconciliar unidades aplicáveis, entidade/título/cadastro e limites urbanísticos com gates; completar Response/§27 apenas reutilizando entidades. Não regredir source/enums/IDs ou tornar campos incompletos obrigatórios para guardar. |
|
||
| P1 — OP-03 / PROFILE-11/12/19 | Filas, parecer atribuído, resposta, revisão e coordenação editorial com task/hash/papéis; negações específicas. | Interface por24/25/29, reatribuição e revogação; incidentes, disponibilidade e revisão periódica. Parecer externo requer responsabilidade institucional concreta, não um ator fictício; aprovação interna não substitui decisão externa. |
|
||
| P1 — GEO-03 / COUNTRY/STATS | Seis contratos ligam localização/documentos por IDs e país MZ; investimento recupera mercadoFR; editores consultam geometrias no nível selecionado. | Verificar visual de todos os consumidores afetados, país/origem→recuperação→filtro→estatística por formulário. Resolver nomes pendentes do pacote:31distritos+157postos; localidades/parcelas não inferidas de limites administrativos. Reutilizar importação autenticada/idempotente; publicação de camada é separada. |
|
||
| P1 — OP-02 / LIB / PROFILE-23 | Originais por perfil, negação de organização23, cifragem/hash, PNG e duas derivadas ClamD; PDF do ensaio atual separado. | Continuar DOCX/XLSX, partilhas, PDFs/exportações/derivadas sem prova específica; preservar originals/versões. Consistência de erro404 recurso excluído versus423 scan pendente foi corrigida no consumidor de oportunidades. |
|
||
| P1 — PROFILE-23 | Dois avisos preexistentes de league/commonmark identificados no lote anterior. | Avaliar consumidores e corrigir compatibilidade emQA; não apagar o achado nem atribuir a Opis. |
|
||
| P2 — PROFILE-31 / OPS-01 | 190000confirmadaQA/ausenteativo;030/040QA;baseBalcãoativa instalada, hashes atualizados. | Construir instalação/bootstrap autenticados040 com duasidentidades reais explicitamente designadas; não mudar titulares nem retirar privilégio ativo automaticamente. Apósvisual, fixar candidata e renovarbackup/restauro dessa revisão; executar apenas migrações faltantes pelo mecanismo adequado. |
|
||
|
||
Decisões independentes, sem bloquear este lote:
|
||
|
||
1. **Concessão, financiamento, fornecimento e outros:** quais versões imutáveis de perfil modular, campos obrigatórios, documentos e gates são aprovadas para cada categoria? Sem esse contrato, guardar/editar funciona; submissão/revisão/publicação continuam bloqueadas.
|
||
2. **SLA:** qual política versionada fixa prazo por tipo de tarefa, tolerância, número de ciclos e escalamento? Quem assume formalmente cada competência de coordenação, parecer técnico/jurídico, publicação e recurso? Manter prazo nulo e atribuição explícita até existir decisão; não usar nomes/prazos de QA como norma.
|
||
3. **Condições sem regra inequívoca:** qual âmbito/citação estabelece a aplicabilidade de unidades/limites urbanísticos e materialidade? Como reconciliar o mínimo de um exercício do schema com entidades sem exercícios existentes? Não substituir valores ausentes por zero nem alterar silenciosamente a versão aceita.
|
||
|
||
Não iniciar jornadas educativas novas. Mantêm-se cinco fases/19 etapas e URLs, dossier privado, oportunidade publicada, fontes oficiais aceites e histórico.
|
||
'''
|
||
|
||
activation = f'''## Ativação reconciliada: 030000, 040000 e **09/190000** — nenhuma execução no ativo
|
||
|
||
A omissão de **2026_10_09_190000_prepare_investor_path** na sequência anterior foi um erro documental; a extensão **continua necessária e não foi substituída**. Não confundir com **2026_10_07_190000_create_internal_virtual_desk**, que já está instalada no ativo.
|
||
|
||
| Recurso | QA restaurada:55441 | Ativo investemoz:5432, READ ONLY | Evidência |
|
||
| --- | --- | --- | --- |
|
||
| Gestão020000 | Instalada | Instalada | Ledger/schema anteriores preservados |
|
||
| Balcão07/190000 e orientação08/120000 | Instalados | Ambos no ledger | Leitura efetiva das migrações, sem boot de sessão ativa |
|
||
| Recursos09/030000 | Instalada | Ausente | Tabelas e ledger; não repetirQA |
|
||
| Perfis10/040000 | Instalada | Ausente | Tabelas/verificaçãoQA; nunca instalada no ativo neste trabalho |
|
||
| Percurso09/190000 | **Ledger + duas colunas + definição publicada** | **Ledger ausente; duas colunas ausentes; nenhuma definição** | `dashboard-active-readonly.json`, `opportunity-semantic-environment-qa.json` |
|
||
|
||
DefiniçãoQA `61000919-0000-4000-8000-000000000001`, publicada, SHA256 **{environment['definitions'][0]['sha256']}**. Duas colunas: `investor_journeys.path_definition_id` e `journey_steps.path_detail`. Mantém cinco fases e rastreabilidade das19etapas; não renumera/reescreve os roteiros existentes. Recurso preparado/definição publicada não demonstra A/B na interface.
|
||
|
||
Dependências verificadas no código: **030000** usa oportunidades/documentos existentes e cria três coleções de recursos; **040000** acrescenta quatro tabelas de autorização/auditoria, uma coluna de revisão em users e três colunas em opportunities, preservando identidades/histórico; não usa as colunas de190000. **190000** usa investor_journeys/journey_steps/questionnaire_versions e depende da baseBalcão/orientação incluída no instalador. Não existe dependência DDL entre030/040 e190; disponibilizar o workflow requer020+030+040 e tasks/catalogue existentes; disponibilizar o percurso integrado requer190 e as capacidades instaladas/configuradas. Os fingerprints incluem código comum de perfis: alterar o código invalida provas antigas de readiness, sem converter isso numa dependência de schema.
|
||
|
||
| Ordem futura | Ação concreta e efeito / contagem esperada | Dependência e reversão |
|
||
| --- | --- | --- |
|
||
| 0 | Incorporar visualC37/Promotor21/A-B; corrigir falhas e fixar revisão/manifesta/configuração. Renovar dumpDB+ficheirosoriginaisprivados+chaveestável e restauroverificado numa novaQA. | Candidata ainda não fixada; provas antigas não são backup dessa revisão. Nunca key:generate indiscriminado. |
|
||
| 1 | Disponibilizar código/Composer/bundle após aprovação de ativação, flagsfalse. | Nesta análise só buildQA foi atualizado; manifestativo preservado. Reversão para código/build anteriores e flagsfalse; assegurar compatibilidade de leitura. |
|
||
| 2 | **030000**, se ledger/schema realmente ausentes: préviaGET e aplicaçãoPOST autenticada `/management/opportunity-resources-install` com hash/confirm. | Três coleções resource e metadado de cifra; **zero documentos/dados publicados/importados**. Base020/documentos existentes. Downgrade destructive recusado se originais cifrados usados. |
|
||
| 3 | **040000**, se ausente: instalar quatro tabelas/colunas através de mecanismo autenticado e bootstrap/recuperação da dupla, ainda por implementar paraativo. | Não substituir por migrateglobal/configmanual para contornar guarda. **Zero contas/grants QA** noativo. Titulares/reconciliação de permissões reais precisam de decisão explícita. Código independente de190. |
|
||
| 4 | **09/190000**, se ausente: préviaGET e aplicaçãoPOST autenticada `/management/balcao-install`; instalador seleciona só migrações faltantes. | BaseBalcão07/190000 e orientação08/120000 jáconstamdoativo: não repetir. **Duas colunas + uma definição publicada**, se não existir equivalente; **zero dossiers/journeys criados automaticamente**. Versões publicadas imutáveis. |
|
||
| 5 | Configurar catálogos/responsabilidades reais e instalar apenas contratos modulares aprovados; comparar IDs/citações/versões. | A autoridade sintética QA3e1ff315… e atores21–31 não são dados deativação. Sem alteração automática de valores legados. |
|
||
| 6 | Importação cartográfica autenticada privada `/management/territory-geometry-import`: prévia/correspondências/hash→aplicação idempotente→auditoria. | QA393=11províncias+128distritos+254postos; ativo0naúltimaleitura. **393 candidatas inequívocas**, sujeitas à prévia da revisão e aos mesmos IDs;188pendentes(31/157), sem criar geometrias falsas. Contagem final deve ser medida no alvo. Reversão por lote/metadados e histórico, sem apagar cadastros. |
|
||
| 7 | Ativar flags de perfis/oportunidades e percurso separadamente, testar navegação completa e permissões. | 030/040 antesdoscontratos/workflow;190antesdodisponibilizarpercurso; C37/visual/A-B não encerrados. Preparação paralela e acesso direto continuam. |
|
||
| 8 | **Publicar camadas, oportunidades ou documentos como ações separadas e explícitas**. | Nenhuma instalação/importação publica automaticamente; publicação não ativa cálculo fiscal. Usar decisões/evidências/hash atuais e autorização de divulgação. |
|
||
|
||
Reversão: desativarflags/voltarbundle compatível e conservar originais/auditoria. Migrações usadas não devem ser eliminadas por rollback genérico;190recusadownquandohápercurso,030recusacomcifrados,040preservaperfil/oportunidade. Quando necessária reversão de dados, usar o restauroverificado da candidata com reconciliação das escritas posteriores. **ready=true é preparação; não instalação, ativação nem aceitação funcional.**
|
||
'''
|
||
|
||
cases = '''## Reprodução e evidências adicionais — mesmo inventário
|
||
|
||
| Caso / requisito | Passos e esperado | Observado / causa | Correção e estado |
|
||
| --- | --- | --- | --- |
|
||
| C55 — OP-02 | QA21→PDF limpo→exclusão lógica→GETdownload. Esperado: recurso indisponível, sem atribuir falha de scan. Restaurar e recuperar original. | HTTP423/quarentena porque download juntava row inexistente à condição de scan. | Separa ausência/exclusão404 de quarentena423; teste específico e ensaioPDFweb18097. Originais/hash preservados; visualpendente. Prova da falha `opportunity-semantic-documents-http-qa-attempt1.json`. |
|
||
| C56 — OP-04/PROFILE-25 | Promotor21 abre editor de categoria; campos de núcleo devem ter um único valor/controlo e erros associados. | Revisão do código: formulário legado e contrato canónico duplicavam título/território/campos, com valores independentes. | Contrato canónico único no modo perfil; formulário legado continua na gestão própria. BuildQA/TS e payloadAPI; observação visualpendente. |
|
||
| C57 — OP-04/PROFILE-28 | Guardar fim anterior ao início/ciclo/serviços incompletos/documento estrangeiro/comunidade sem consulta/financeiros incompletos; recuperar noutra sessão; submeter. | Regras anteriores aceitavam objetos opacos sem semântica suficiente. | 12negativas422 com caminho de campo; rascunhos recuperados; seis cenários completos submetidos/revistos. Não extrapolar a regras jurídicas ainda sem âmbito/gate. |
|
||
| C58 — OP-03/PROFILE-19/12 | Parecer com destinatário técnico/jurídico; responder outro ator; aprovar pendente. Depois atribuir publicação e tentar outro Publicador. | Fluxo anterior não tinha destinatário/resposta/fila completa nem atribuição editorial. | #30destinatário29/resposta/tarefa;outro403/aprovação422; #33filaeditorial29/outro25publica403/designado29publica. Sem gateautoaprovado/prazofictício; visualpendente. |
|
||
| 190000 — OPS-01/PROFILE-31 | Comparar ledger/duascolunas/definição QA eativo, distinguir migraçãoBalcão07 depercurso09. | Plano anterior omitia recurso ainda ausenteativo. | 09/190000confirmadaQA e ausenteativo, necessária/nãosubstituída; seqüência autenticada recolocada. Nenhuma execuçãoativa. |
|
||
'''
|
||
|
||
manual = '''## Ensaio visual preparado — permanece pendente conforme pedido
|
||
|
||
URL QA **http://127.0.0.1:18097/dashboard**. Conta **Promotor QA21**, MFA normal, credenciais/código obtidos apenas localmente. Não incluir cookies, cabeçalhos X-XSRF-TOKEN, segredos ou corpo do código em capturas. C37/conta18 é um ensaio independente e continua pendente.
|
||
|
||
1. Entrar no dashboard como21. Esperado: **Minhas oportunidades** e **Nova oportunidade**, ambos funcionais, no contexto autorizado. URLlista `/minhas-oportunidades`; criação `/minhas-oportunidades/create`.
|
||
2. Abrir cada ID QA30–39 em `/minhas-oportunidades/<id>/view` e, nos estados editáveis, `/edit`. Esperado: estado privado e publicação distintos; núcleo único, categoria correta e permissões aplicadas. #36–39devem continuar drafts.
|
||
3. Criar rascunho incompleto, guardar; logout/nova sessãoMFA e recuperar. Não usar as fichas publicadas para substituir este passo. Esperado: mesmos dados/ID, sem mistura com outrosprojetos/oportunidades. Se ainda não houver localizações/documentos, guardar primeiro e abrir **Recursos**.
|
||
4. Nos recursos `/minhas-oportunidades/<id>/resources`, selecionar país e hierarquia; conferir mensagem de território cadastrado, geometria selecionada disponível/ausente e mapa. A parcela declarada em DUAT deve manter geometria própria, sem substituir por limiteadministrativo. Conferir original/prévia antes/depois de recuperar.
|
||
5. Num rascunho de ensaio das seis categorias, introduzir erro semântico e guardar; submeter. Esperado:422, mensagem junto ao campo, valores preservados; depois corrigir e resubmeter. Concessão/financiamento/fornecimento/outros devem informar perfilmodularpendente.
|
||
6. Como24, abrir mesma ficha/fila (`/minhas-oportunidades?queue=review`), atribuir/iniciar→solicitarcorreção→21corrige→nova revisão/gates. Registar motivo e documentos da própria versão. Ensaiar parecer por destinatário29: outra resposta negada e tarefa/parecer recuperados sem gateautoaprovado.
|
||
7. Como25, fila editorial (`?queue=publication`), designar Publicador independente; como29, fila `?queue=assigned`, comparar prévia/hash/teaser e publicar. OutroPublicadornãodesignado deve recebernegação; aprovarprópria/mesmaorganização/múltiplospapéis deve continuar negado. Não atribuirresponsabilidadesreais aos atoresQA.
|
||
8. Depois de publicar, solicitar revisão/materialalteração; esperado: publicação anterior preservada até nova revisão. Fundiário32não pode contornar autorizaçãoexternapendente. Conferir suspensão e recuperação dos motivos/tarefas.
|
||
|
||
Registar por ação URL/ator/ID/estado/API/persistência/resultado visível; associar a mesma matriz. A/B completos e cincofases/19etapas continuam no roteiro existente, sem renumerar. Não fechar critérios por leitura dos dados ou totaldetestes.
|
||
'''
|
||
|
||
marker = 'qa-semantic-20261010'
|
||
|
||
|
||
def prepend(path, text):
|
||
existing = path.read_text(encoding='utf-8')
|
||
existing = re.sub(r'\n?<!-- ' + marker + r':begin -->.*?<!-- ' + marker + r':end -->\n?', '', existing, flags=re.S)
|
||
parts = existing.split('\n', 1)
|
||
rest = parts[1].lstrip() if len(parts) > 1 else ''
|
||
path.write_text(parts[0] + '\n\n<!-- ' + marker + ':begin -->\n' + text.strip() + '\n<!-- ' + marker + ':end -->\n\n' + rest, encoding='utf-8')
|
||
|
||
|
||
for name, body in [('relatorio-executivo.md', summary), ('backlog.md', backlog), ('plano-ativacao.md', activation),
|
||
('casos-reproducao.md', cases), ('roteiro-manual-perfis-v1.md', manual),
|
||
('perfis-v1-reconciliacao.md', summary), ('cobertura-percursos-i0-i3.md', summary),
|
||
('execucao-percurso-i1-i3.md', summary), ('workflow-oportunidades-qa.md', summary + '\n\n' + backlog + '\n\n' + activation + '\n\n' + cases + '\n\n' + manual)]:
|
||
prepend(DOCS / name, body)
|
||
prepend(ROOT / 'docs/investmoz/v2/gestao-oportunidades-dashboard.md', manual + '\n\n' + summary)
|
||
print(json.dumps({'updated_documents': 10, 'requirements': 3386, 'sources': 6838, 'visual_pending': True, 'active_writes': 0}))
|
||
if (PRIVATE / 'profile-installation-http-qa.json').exists():
|
||
import subprocess
|
||
subprocess.run([sys.executable, str(ROOT / 'tools/portal-audit-installation-update.py')], check=True)
|