97 lines
16 KiB
Python
97 lines
16 KiB
Python
"""Reconcile consumer evidence into the existing executive report and backlog."""
|
||
from pathlib import Path
|
||
from datetime import datetime, timezone
|
||
import json, hashlib, sys
|
||
sys.stdout.reconfigure(encoding='utf-8')
|
||
root=Path(__file__).resolve().parent.parent
|
||
docs=root/'docs/investmoz/v2/auditoria-portal'
|
||
private=root/'storage/app/private/investmoz-v2/portal-audit'
|
||
packet=private/'consumer-completion-finalize-20261010'
|
||
evidence=json.loads((packet/'criterion-evidence.json').read_text(encoding='utf-8'))
|
||
verified=json.loads((packet/'preservation-verification.json').read_text(encoding='utf-8'))
|
||
assert verified['result']=='passed' and verified['changed']=={'matriz-requisitos.csv':15,'backlog-priorizado.csv':15}
|
||
stamp=datetime.now(timezone.utc).astimezone().isoformat()
|
||
report=f'''## Consumidores e workflow visual — {stamp}
|
||
|
||
**Lote demonstrado exclusivamente em QA18097, com seis correções C91–C96.** Interface → pedidos reais → gravação → recuperação noutra sessão → resultado apresentado ligados à leitura SQL QA. Base `desk_restore_20261009_174726_test:55441` conferida antes das escritas; não houve instalação, migration, tabela ou conta nova. A/B internos e C37 QA18 conservam a aceitação anterior; não foram repetidos para obter um novo fecho.
|
||
|
||
| Requisito/consumidor | Critério demonstrado | Limite e prova |
|
||
| --- | --- | --- |
|
||
| COUNTRY02 — Perfil e empresas | QA18 criou “QA entidade — país distinto”: constituição FR, residência PT. POST → v1 → nova sessão → FR/PT recuperados; QA23 não vê a declaração e recebe404 ao tentar alterá-la. | Declaração privada da empresa, não cadastro mestre da organização nem comprovação de representação. `consumer-entity-chromium-20261010.json` |
|
||
| COUNTRY03; STATS01; DESK01 — Balcão | Pedido sintético separado no dossierA, PT/ZA: interface submeteu → protocolo → v2 → nova sessão. Replay exato200 conserva protocolo/v2; estatística Pedidos do Balcão ZA0→1. SQL: uma revisão e um evento submitted. | Os pedidos A/B originais continuamDRAFT. Uma solicitação submetida não significa decisão externa. `consumer-stats-chromium-20261010.json` |
|
||
| COUNTRY06; STATS01 — Negócio | Oito passos do negócio QA18 existente, PT/FR → submissão200 → v5 → nova sessão → submitted. Replay409 por versão/estado não repetível, uma transição submitted; estatística Negócios FR0→1. | Replay409 é rejeição prevista, distinta do contrato idempotente200 do Balcão. Não conta como investidor único nem manifestação pública. `consumer-business-chromium-20261010.json` |
|
||
| GEO01/02/03 — Projetos, clusters e corredores | Cabo Delgado → Ancuabe → posto ANCUABE(01) → localidade ANCUABE - SEDE(01); guardar200 e nova sessão recuperam os quatro IDs nos três consumidores. Três limites de contexto renderizados e ausência de geometria própria da localidade explícita. | Sem nova importação; limite do pai não foi atribuído à localidade. Tiles externos bloqueados no ensaio, mapa base continua pendente. `consumer-structures-deep-chromium-20261010.json`; C96 rótulo do corredor corrigido em prova própria. |
|
||
| DOC01; COUNTRY07 — PDF fundiário | QA21: MZ/PT separados, texto legível, ação de impressão, PDF real de três páginas sem navegação; todas renderizadas e inspecionadas. Scan ClamAV clean da própria derivada, três originais com hashes preservados. Outra conta e gestor404 na rota privada. | PDF de preparação, não requerimento oficialmente recebido, DUAT ou decisão. PDF não etiquetado; acessibilidade documental integral pendente. `consumer-documents-chromium-20261010.json`, `consumer-pdf-presentation-qa.json`, `consumer-pdf-scan-qa.json` |
|
||
| OP01/02/03/04 — investment_project52 | Dashboard QA21 → Nova oportunidade → rascunho incompleto → guardar/recuperar → recursos próprios → contrato → submeter → QA24 solicita correção → QA21 corrige/resubmete → QA24 revê/aprova → QA25 publica no catálogo QA → recuperação pelo Promotor. SQL confirma atores distintos e hash aprovado=publicado. | Cobre esta categoria e ciclo de correção/aprovação/publicação. Não cobre todas as categorias, rejeição/suspensão/materialidade/múltiplos papéis, nem aprovação externa. `consumer-workflow-chromium-20261010.json` |
|
||
| DOC01; OP02 — originais/derivadas e permissões | Promotor21 descarrega o PDF com hash exato e vê WebP interna. Validador24 consulta PDF/miniatura, com gravação bloqueada. QA23 recebe403 no original e na URL assinada válida; anónimo401. Ficha pública abre sem login, sem UUIDs dos anexos ou metadados privados. Originais e cada WebP têm scan próprio clean. | A publicação da ficha não divulga os binários privados; permissões do servidor preservadas. `consumer-workflow-files-chromium-20261010.json`, `consumer-reviewer-files-chromium-20261010.json` |
|
||
|
||
**Falhas corrigidas:** C91 impressão com caracteres corrompidos e país/origem ausentes; C92 menus e paginação imprópria no PDF; C93 objeto ambiental sem campos apesar da definição canónica existente; C94 separadores de consulta bloqueados em leitura; C95 seletor de sector sem nome acessível próprio; C96 rótulo de descrição do corredor corrompido. Passos/causas/provas em [casos-reproducao.md](casos-reproducao.md). Nenhum significado de classificação ou dado anterior foi alterado silenciosamente.
|
||
|
||
Dados sintéticos novos são apenas fixtures QA: uma declaração privada de empresa, um pedido separado, uma estrutura de cada tipo e oportunidade52 com recursos próprios. Negócio e fundiário existentes foram reutilizados. A/B preservam resultados, rascunhos e tarefas originais; o novo pedido cria histórico próprio no dossierA, portanto não se afirma que o histórico completo desse dossier permaneceu idêntico. Não copiar fixtures ou identidades para ativo.
|
||
|
||
Prova transversal: `consumer-final-persistence-qa.json` é leitura SQL READ ONLY, com versões, estados, relações e hashes; `consumer-final-scope-qa.json` liga nove recibos Chromium, fontes e build QA. Regressões de contrato/workflow, escopo de publicação, fundiário e URL assinada válida passaram; TypeScript e compilação QA passaram. A contagem de testes não substitui os percursos da tabela. Capturas de mapas, países/estatísticas, workflow/miniaturas e as três páginas do PDF foram inspecionadas. Ensaios móveis dos novos consumidores, dispositivos reais e acessibilidade integral não foram declarados aceites. A falta de carregamento de tiles externos está explícita, separada dos limites oficiais apresentados.
|
||
|
||
Mesma matriz: **3393 requisitos/3393 linhas/6845 ocorrências**; **15 requisitos** receberam apenas provas/critério restante, preservando IDs, referências, versões e estado global. Estados:3235 parciais,145 não implementados,5 dependentes de decisão concreta,1 implementado mas não ativado,7 concluídos e demonstrados. Requisito parcial não reabre um subcritério agora demonstrado. Não foi criada outra matriz.
|
||
|
||
**Próximo lote executável:** consumidores de zonas e fundiário/Balcão com descendentes e filtros próprios; país nos registos mestres de organização/representação; conversão fundiária/estatísticas e manifestação pública ligada a negócio; PDFs/exportações/partilhas/revogação de outros consumidores; workflow visual de rejeição, suspensão e alterações materiais e demais contratos/Response§27. Correspondências cartográficas408 preservadas,173 pendentes (26 distritos/147 postos), Mandie/Guro ambíguo. SLA, perfis modulares e restauração continuam com decisões próprias. Mercado Financeiro permanece privado por ausência de conteúdo; nenhuma nova divulgação dessa frente.
|
||
|
||
**Código preparado e QA demonstrada; ativo não ativado por este lote.** Manifesto ativo SHA256 `75352185c2a85c34ab726613db864a598e301a5b342ebbc80ac8e678eed17a94` intacto. Não se fixou candidata global nem se declarou renovado o backup/restauro ativo. Preparação mantém030000→040000→2026_10_09_190000, somente instalações ausentes, separando correções, importação e publicação. Ver [plano-ativacao.md](plano-ativacao.md) e [backlog.md](backlog.md).
|
||
'''
|
||
remaining='\n'.join('| '+key+' | '+value.replace('|','\\|')+' |' for key,value in evidence['remaining'].items())
|
||
backlog=f'''## Critérios restantes após o lote de consumidores/workflow — {stamp}
|
||
|
||
**A/B internos e C37 QA18 conservam o fecho anterior.** Este lote acrescenta provas por consumidor, não um fecho da auditoria inteira. As pendências históricas abaixo são superadas somente nos subcritérios explicitamente demonstrados. Não repetir criação/recuperação A/B, autenticação, o ciclo investment_project52 ou os quatro níveis de projetos/clusters/corredores para justificar critérios diferentes.
|
||
|
||
| Requisito da matriz existente | Critério restante / próxima ação |
|
||
| --- | --- |
|
||
{remaining}
|
||
|
||
Ordem do próximo lote executável, sem aguardar decisões independentes:
|
||
|
||
1. **P1 — países/estatísticas:** país de constituição nos registos mestres existentes de organizações/representação; percurso fundiário convertido em manifestação e interesse ligado a negócio público. Demonstrar UI→gravação→nova sessão→filtros/estatísticas/repetição por cada consumidor, distinguindo os conjuntos.
|
||
2. **P1 — territórios:** zonas e fundiário/Balcão; seletores de descendentes, alteração de pai, persistência, mapa do consumidor e recusa de outros perfis. Três mapas estruturais e oportunidade51 já têm provas próprias. Não transformar limite administrativo de contexto em geometria da localidade ou parcela.
|
||
3. **P1 — documentos:** outros PDFs/exportações/partilhas e revogação; recuperação por perfil, hash/scan da própria derivada e preservação do original. C91/C92 e PDF fundiário ensaiado estão demonstrados; PDF etiquetado/leitor de ecrã e todos os formatos continuam separados. Consultas de Promotor/Validador e recusas QA23/anónimo na oportunidade52 estão demonstradas; completar os outros perfis/consumidores.
|
||
4. **P1 — workflow/contratos:** rejeição fundamentada, alterações materiais, suspensão e múltiplos papéis por interface, além das outras categorias e Response/§27. Ciclo de correção→aprovação independente→publicação de investment_project52 já demonstrado. Fila/pareceres/atribuições e critérios semânticos mantêm provas específicas; não usar esse ciclo como fecho automático.
|
||
5. **P2 — experiência:** apresentação móvel dos consumidores novos, acessibilidade integral e dispositivos reais. C95 corrige um nome acessível; não equivale à acessibilidade integral do wizard. Refinar rótulos de consulta e metadados técnicos em leitura sem remover rastreabilidade.
|
||
|
||
Decisões humanas não bloqueiam esses trabalhos: perfis modulares de concessão/financiamento/fornecimento/outros e distinção procura/oferta continuam separadas; calendário/responsáveis/suplentes para SLA interno; ator e estado de retorno da restauração de oportunidade. Não escolher titulares reais nem assumir prazos de entidades externas.
|
||
|
||
Provas e correçõesC91–C96 estão ligadas às15 linhas da matriz e do backlog priorizado. `consumer-completion-finalize-20261010/preservation-verification.json`:3393 requisitos/3393 linhas/6845 ocorrências, estados e versões preservados; `consumer-final-scope-qa.json`:código/build e nove recibos de interface. Imagens/PDFs inspecionados; falhas do harness guardadas nas tentativas não são atribuídas ao portal. Base ativa intacta; [plano-ativacao.md](plano-ativacao.md) continua preparação.
|
||
'''
|
||
activation=f'''## C91–C96 — revisão do incremento, sem ativação — {stamp}
|
||
|
||
**Código e build QA preparados; nove recibos visuais, leitura SQL e regressões ligadas em `consumer-final-scope-qa.json`. Candidata global ainda não fixada.** Zero migrations/tabelas/contas novas neste lote; QA já tem os recursos necessários e não recebeu reinstalação. Novas fixtures QA não entram numa futura instalação ativa. A/B e C37 permanecem aceites no seu âmbito, sem repetição.
|
||
|
||
| Alteração | Efeito | Instalação / reversão |
|
||
| --- | --- | --- |
|
||
| C91 controlador/componente de impressão | País/origem recuperados independentemente e caracteres reparados | Código, sem migration; revertê-lo não altera o pedido ou os originais |
|
||
| C92 layout/CSS de impressão | PDF sem menus, com quebra de secções; restantes páginas mantêm layout | Código/build; conservar ficheiros e hashes anteriores como histórico |
|
||
| C93 adaptador canónico | Campos ambientais passam a reutilizar definição existente no editor e validação | Contrato já existente; sem ativar cálculo ou aprovação externa. A versão nova de oportunidade52 é apenas QA |
|
||
| C94 recursos em leitura | Separadores consultáveis por quem tem autorização, mutações continuam bloqueadas | Código/build, políticas do servidor preservadas; não publica ficheiros |
|
||
| C95/C96 rótulos | Nome acessível próprio do sector e descrição legível no corredor | Código/build, sem alteração de significado ou dados |
|
||
|
||
Sequência futura, ainda sem execução ativa:
|
||
|
||
1. Completar os critérios restantes por consumidor/perfil; fixar revisão candidata global e hashes de fontes, builds/configuração e recibos. O snapshot deste incremento não substitui essa candidata global.
|
||
2. Consultar o ativo por leitura para instalação/schema/flags/configurações reais. O manifesto ativo permanece `75352185c2a85c34ab726613db864a598e301a5b342ebbc80ac8e678eed17a94`. Não transformar o retrato histórico de instalações em nova consulta nem em autorização de escrita.
|
||
3. Renovar backup e demonstrar restauro num clone QA fresco associado ao ativo e à candidata: base, ficheiros privados/originais, hashes, permissões, chave/configuração estável, compatibilidade e reversão. Backup/restauro anteriormente reportado conserva data e âmbito; não foi renovado neste lote.
|
||
4. Disponibilizar código/build compatíveis com flags controladas. Prévia/aplicação autenticadas **030000→040000→2026_10_09_190000_prepare_investor_path**, apenas instalações ausentes e após dependências. Recursos versionados→perfis/políticas→extensão do percurso; 09/190000 não é substituída por Balcão07/190000. Não repetir QA nem gerar identidades/grants/titulares reais. Contagens finais dependem da prévia da base candidata, não de `ready=true`.
|
||
5. Importação cartográfica separada: prévia, correspondências inequívocas, preservação de408 associações, hash, idempotência, auditoria e reversão por lote.173 pendentes e Mandie/Guro ambíguo não foram resolvidos pelo ensaio visual. Publicação de camadas/conteúdos/catálogo é outra ação; uma ficha publicada não divulga originais restritos. Scans ClamAV deste lote provam apenas os ficheiros/derivadas identificados; outros scans/operações mantêm pendência específica.
|
||
6. Disponibilizar percurso/consumidores após verificações correspondentes. Ação ativa e designação/recuperação dos dois titulares continuam fora da autorização QA atual.
|
||
|
||
Reversão do incremento por hunks e bundle de revisão conhecida, preservando alterações locais, revisões, protocolos, originais, consentimentos, recursos e auditoria. Não fazer reset do repositório, apagar fixtures/histórico para simular sucesso, regenerar a chave ou desfazer MFA. Compatibilidade/reversão global devem ser demonstradas no clone correspondente antes de corte futuro.
|
||
'''
|
||
updated=[]
|
||
for name,marker,body in [('relatorio-executivo.md','qa-consumers-results-20261010',report),('backlog.md','qa-consumers-remaining-20261010',backlog),('plano-ativacao.md','qa-consumers-activation-20261010',activation)]:
|
||
file=docs/name;original=file.read_text(encoding='utf-8-sig');start='<!-- '+marker+':begin -->';end='<!-- '+marker+':end -->'
|
||
history=original
|
||
if start in history:
|
||
assert history.startswith(start)
|
||
history=history.split(end,1)[1].lstrip('\r\n')
|
||
digest=hashlib.sha256(history.encode('utf-8')).hexdigest()
|
||
file.write_text(start+'\n'+body.strip()+'\n\n'+end+'\n\n'+history,encoding='utf-8')
|
||
assert file.read_text(encoding='utf-8').endswith(history)
|
||
updated.append({'file':name,'history_preserved_sha256':digest})
|
||
(packet/'documents-preservation.json').write_text(json.dumps(updated,ensure_ascii=False,indent=2),encoding='utf-8')
|
||
print(json.dumps({'updated':len(updated),'existing_documents':True,'historical_sections_preserved':True,'active_writes':0}))
|