"""Gera o relatório da Fase 2 (geração de hipóteses) em PT e EN: ../fase2/index.html e ../fase2/en/index.html. Uso: python gerar_fase2.py (depois de exposicoes.py e hipoteses.py; defina CLEDON_DOI para a versão depositada) """ import os import numpy as np import pandas as pd from config import RAIZ, RESULTADOS VERSAO = "1.7" DATAS = {"pt": "13 de novembro de 2026", "en": "November 13, 2026"} BASE = "https://cledon.org" ORCID = "0009-0008-5280-1869" PLANO_COMMIT = "0d88889" DOI = os.environ.get("CLEDON_DOI", "").strip() PT = True NOMES = { "fumo": ("Fumo: área colhida (% da área municipal)", "Tobacco: harvested area (% of municipal area)"), "mate_cultivo": ("Erva-mate cultivada: área colhida (% da área municipal)", "Cultivated yerba mate: harvested area (% of municipal area)"), "mate_extracao": ("Erva-mate extraída (t por mil hab.)", "Extracted yerba mate (t per 1,000 inhab.)"), "cafe": ("Café: área colhida (% da área municipal)", "Coffee: harvested area (% of municipal area)"), "lenha": ("Lenha: extração + silvicultura (m³ por hab.)", "Firewood: extraction + forestry (m³ per inhab.)"), "agua_poco": ("Água de poço, 2022 (% dos domicílios)", "Well water, 2022 (% of households)"), "agua_nascente": ("Água de fonte ou nascente, 2022 (% dos domicílios)", "Spring water, 2022 (% of households)"), "rural": ("População rural, 2022 (%)", "Rural population, 2022 (%)"), "pib_pc": ("PIB municipal per capita, 2010 (log)", "Municipal GDP per capita, 2010 (log)"), "altitude": ("Altitude do centroide (m)", "Centroid altitude (m)"), "mal_definidas": ("Causas mal definidas (%)", "Ill-defined causes (%)"), "lenha_extracao": ("Lenha: só extração (m³ por hab.)", "Firewood: extraction only (m³ per inhab.)"), "rural_2000": ("População rural, 2000 (%)", "Rural population, 2000 (%)"), "rural_2010": ("População rural, 2010 (%)", "Rural population, 2010 (%)"), "agua_poco_nascente_2010": ("Água de poço ou nascente, 2010 (% dos domicílios)", "Well or spring water, 2010 (% of households)"), } VARS = ["fumo", "mate_cultivo", "mate_extracao", "cafe", "lenha", "agua_poco", "agua_nascente", "rural", "pib_pc", "altitude"] AUDIT = {"fumo_area": ("Fumo (PAM 1612)", "Tobacco (PAM 1612)"), "mate_cultivo_area": ("Erva-mate cultivada (PAM 1613)", "Cultivated yerba mate (PAM 1613)"), "cafe_area": ("Café (PAM 1613)", "Coffee (PAM 1613)"), "mate_extracao_t": ("Erva-mate extraída (PEVS 289)", "Extracted yerba mate (PEVS 289)"), "lenha_extracao_m3": ("Lenha, extração (PEVS 289)", "Firewood, extraction (PEVS 289)"), "lenha_silvicultura_m3": ("Lenha, silvicultura (PEVS 291)", "Firewood, forestry (PEVS 291)")} def T(pt, en): return pt if PT else en def nome(v): return NOMES[v][0 if PT else 1] def n(x, c=2): s = f"{x:,.{c}f}" return s.replace(",", "X").replace(".", ",").replace("X", ".") if PT else s def i(x): s = f"{int(round(x)):,}" return s.replace(",", ".") if PT else s def pf(p): return ("< 0,001" if PT else "< 0.001") if p < 0.001 else n(p, 3) def tab(cab, linhas): th = "".join(f"
Geração de hipóteses — não são conclusões nem causas. Associações ecológicas entre características dos municípios e a mortalidade por câncer de esôfago. Valem para municípios, não para pessoas, e servem para escolher o que medir num estudo com pacientes. Não indicam causa, não permitem estimar o risco de uma pessoa e não mudam nenhuma recomendação médica. Versão {VERSAO} · {DATAS['pt']}.{doi}
As Fases 1 e 1b mostraram um excesso persistente de mortalidade por câncer de esôfago em áreas do interior de Minas Gerais, do Sul e da Bahia. A Fase 2 descreve que características municipais, em dados públicos, acompanham esse excesso, com plano de análise registrado no git antes dos dados (commit {PLANO_COMMIT}). Esta versão incorpora uma revisão técnica assistida por IA (não é revisão independente por pares): dados ausentes deixaram de ser tratados como zero, e as análises foram refeitas.
Desfecho. Óbitos por câncer de esôfago de 2015 a 2024 por município, com esperados calculados pelas taxas do próprio estado por sexo e faixa etária, usados como offset. Isso compara cada município com o padrão do seu estado, mas não equivale a incluir efeitos de estado na regressão: por isso há uma sensibilidade com efeitos fixos de estado.
Exposições e unidades. Fumo, erva-mate cultivada e café: área colhida da cultura como percentual da área territorial do município (PAM/IBGE). Erva-mate extraída: toneladas por mil habitantes; lenha: m³ por habitante, somando extração e silvicultura (PEVS/IBGE). Produção em média de 2005 a 2010. Água de poço e de fonte ou nascente: % dos domicílios, Censo 2022. População rural: %, Censo 2022. PIB municipal per capita de 2010 (não é renda domiciliar). Altitude do centroide (Copernicus DEM). As variáveis de produção entram como log(1 + x) e todas são padronizadas: a razão de taxas (RT) é por desvio-padrão da variável transformada, não por unidade original.
Dados ausentes. No IBGE, “-” é zero absoluto; “...” é dado não disponível. Na primeira versão, “...” e municípios ausentes viravam zero, o que confundia falta de informação com falta de produção. Agora: “-” = 0; “...”, “X” e ausência na resposta = ausente; a média usa só os anos com dado; sem nenhum ano, o município fica fora da análise daquela variável. A extração vegetal tem “...” no mesmo conjunto de municípios e anos para erva-mate e lenha, concentrado em SP, RJ, PR, SC e MG; a silvicultura omite muitos municípios da resposta, por isso a lenha (extração + silvicultura, como no plano) tem dado em poucos municípios e há uma sensibilidade só com a extração.
Tabela 1. Auditoria dos símbolos nas tabelas de produção (6 anos × 5.570 municípios).
{t_aud}Modelo. Regressão de Poisson com offset, erros-padrão sanduíche agrupados por região imediata do IBGE (para dependência espacial e sobredispersão), Benjamini–Hochberg entre as 10 variáveis.
RT de mortalidade por desvio-padrão de cada variável, com IC 95%: esôfago (azul) e os desfechos de comparação pulmão (laranja) e outros cânceres, exceto esôfago (verde).
Tabela 2. Esôfago: estimativa principal e sensibilidades.
{t_a}Pulmão e todos os cânceres exceto esôfago. Não são controles negativos no sentido formal: o pulmão compartilha exposições (tabaco), e vieses de registro ou diagnóstico podem afetar cânceres de formas diferentes. Servem para ver se o padrão é próprio do esôfago. A diferença foi testada formalmente num modelo conjunto, nos mesmos municípios.
{t_c}A razão das RT acima de 1 indica associação mais forte (ou mais positiva) para o esôfago que para o desfecho de comparação. Não houve evidência estatística de diferença para café e altitude.
Com as 10 variáveis, só entram os municípios com dado em todas (a lenha limita muito a amostra); por isso há também um modelo sem lenha e sem erva-mate extraída. Várias variáveis são correlacionadas (erva-mate cultivada e extraída, ρ = 0,81; ruralidade e PIB, ρ = −0,47).
{t_b}Média dentro de cada um dos 24 agrupamentos menos a média dos vizinhos do mesmo estado (até 100 km, fora dos agrupamentos), em desvios-padrão. O número de agrupamentos varia com a disponibilidade de dados (por exemplo, 21 para lenha e 23 para erva-mate extraída; 24 nas demais). Teste do sinal sem empates e correção de Benjamini–Hochberg entre as 10 variáveis. Os agrupamentos compartilham vizinhos, então as comparações não são independentes.
{t_d}Os agrupamentos tendem a ter PIB per capita menor que os vizinhos ({pib_neg} de 24), mas, após a correção, nenhuma variável fica com q < 0,05 (PIB: q = {pib_q}). Esta análise acrescenta pouca evidência às anteriores.
Modelos separados por região; variáveis com menos de 20 municípios com valor acima de zero na região foram omitidas (—), e a lenha ficou fora dos modelos conjuntos.
{t_f}Sul: erva-mate extraída e fumo seguem associados no modelo conjunto, com água de poço e menor PIB; a área de café tem associação inversa. Minas Gerais: ruralidade, menor PIB e menor altitude; a área de café também tem associação inversa; a água de poço, forte na análise univariada, perde força no modelo conjunto. Nenhuma das variáveis de produção medidas tem associação positiva estatisticamente clara com o excesso em Minas Gerais.
Água e ruralidade vêm do Censo 2022, depois do início dos óbitos (2015), e não documentam as condições anteriores ao adoecimento. Como comparação histórica (não pré-especificada), a população rural de 2000 e de 2010 e os domicílios com poço ou nascente em 2010 (o Censo 2010 não separa poço de nascente). A ruralidade é muito estável (correlação com 2022: {r2000} para 2000 e {r2010} para 2010); poço em 2022 e poço ou nascente em 2010 têm correlação {p10}.
{t_h}Maior presença de poços não demonstra contaminação da água. Nitrato e outros contaminantes são hipóteses a investigar, não achados desta análise.
Valor no município e, entre parênteses, a mediana do estado; “s/d” = sem dado. {poco_acima} dos 16 têm proporção de domicílios com água de poço acima da mediana do estado em 2022 ({poco10_acima} com poço ou nascente em 2010).
{t_e}Apoiadas, em nível municipal, por estes dados:
Motivadas pela literatura, não testadas aqui (sem dado municipal adequado): temperatura do chimarrão e de outras bebidas (a IARC classificou bebidas muito quentes, acima de 65 °C, como provavelmente carcinogênicas, grupo 2A); fumo de rolo, de corda ou de palha; cachaça e destilados caseiros; fogão a lenha dentro de casa; nitrato e outros contaminantes da água; dieta pobre em frutas e verduras. A Fase 2b ({BASE}/fase2b) aprofunda Minas Gerais.
Código em {BASE}/codigo. Plano: PLANO-fase2.md (commit {PLANO_COMMIT}).
Depois das Fases 1 e 1b: exposicoes.py, hipoteses.py, gerar_fase2.py. Resultados
em CSV na página do mapa e no depósito do Zenodo (fase2_*.csv).
Em memória de Francisco Cledio Capistrano (F.C.C.).
""" return f"""{ESTILO}Hypothesis generation — not conclusions or causes. Ecological associations between municipal characteristics and esophageal cancer mortality. They apply to municipalities, not to people, and serve to choose what to measure in a study with patients. They do not indicate causation, do not allow estimating any person's risk and do not change any medical recommendation. Version {VERSAO} · {DATAS['en']}.{doi} This is a translation of the Portuguese report; in case of discrepancy, the Portuguese version prevails.
Phases 1 and 1b showed a persistent excess of esophageal cancer mortality in inland areas of Minas Gerais, southern Brazil and Bahia. Phase 2 describes which municipal characteristics, in public data, go along with this excess, with an analysis plan recorded in git before the data (commit {PLANO_COMMIT}). This version incorporates an AI-assisted technical review (not independent peer review): missing data are no longer treated as zero, and the analyses were redone.
Outcome. Esophageal cancer deaths 2015–2024 by municipality, with expected deaths from the state's own rates by sex and age group, used as offset. This compares each municipality with its state's pattern, but is not equivalent to including state effects in the regression; hence a sensitivity analysis with state fixed effects.
Exposures and units. Tobacco, cultivated yerba mate and coffee: harvested area of the crop as a percentage of the municipality's territorial area (PAM/IBGE). Extracted yerba mate: tonnes per 1,000 inhabitants; firewood: m³ per inhabitant, adding extraction and forestry (PEVS/IBGE). Production averaged over 2005–2010. Well water and spring water: % of households, 2022 Census. Rural population: %, 2022 Census. Municipal GDP per capita in 2010 (not household income). Centroid altitude (Copernicus DEM). Production variables enter as log(1 + x) and all are standardized: the rate ratio (RR) is per standard deviation of the transformed variable, not per original unit.
Missing data. In IBGE tables, “-” is an absolute zero and “...” means data not available. In the first version, “...” and absent municipalities became zero, confusing missing information with no production. Now: “-” = 0; “...”, “X” and absence from the response = missing; the average uses only years with data; with no year, the municipality is left out of that variable's analysis. Plant extraction has “...” in the same municipalities and years for yerba mate and firewood, concentrated in SP, RJ, PR, SC and MG; the forestry table omits many municipalities, so firewood (extraction + forestry, as in the plan) has data for few municipalities and there is a sensitivity analysis with extraction only.
Table 1. Audit of symbols in the production tables (6 years × 5,570 municipalities).
{t_aud}Model. Poisson regression with offset, sandwich standard errors clustered by IBGE immediate region (for spatial dependence and overdispersion), Benjamini–Hochberg across the 10 variables.
Mortality RR per standard deviation of each variable, with 95% CI: esophagus (blue) and the comparison outcomes lung (orange) and other cancers except esophagus (green).
Table 2. Esophagus: main estimate and sensitivity analyses.
{t_a}Lung and all cancers except esophagus. They are not negative controls in the formal sense: lung shares exposures (tobacco), and recording or diagnostic biases may affect cancers differently. They show whether the pattern is specific to the esophagus. The difference was formally tested in a joint model, in the same municipalities.
{t_c}An RR ratio above 1 indicates a stronger (or more positive) association for the esophagus than for the comparison outcome. There was no statistical evidence of a difference for coffee and altitude.
With all 10 variables, only municipalities with data on all of them enter (firewood greatly limits the sample); hence also a model without firewood and extracted yerba mate. Several variables are correlated (cultivated and extracted yerba mate, ρ = 0.81; rurality and GDP, ρ = −0.47).
{t_b}Mean within each of the 24 clusters minus the mean of neighbours in the same state (up to 100 km, outside clusters), in standard deviations. The number of clusters varies with data availability (21 for firewood and 23 for extracted yerba mate; 24 for the others). Sign test excluding ties and Benjamini–Hochberg correction across the 10 variables. Clusters share neighbours, so the comparisons are not independent.
{t_d}Clusters tend to have lower GDP per capita than their neighbours ({pib_neg} of 24), but after correction no variable has q < 0.05 (GDP: q = {pib_q}). This analysis adds little evidence to the previous ones.
Separate models by region; variables with fewer than 20 municipalities with values above zero in the region were omitted (—), and firewood was left out of the joint models.
{t_f}South: extracted yerba mate and tobacco remain associated in the joint model, together with well water and lower GDP; coffee area is inversely associated. Minas Gerais: rurality, lower GDP and lower altitude; coffee area is also inversely associated; well water, strong in the single-variable analysis, weakens in the joint model. None of the measured production variables has a statistically clear positive association with the excess in Minas Gerais.
Water and rurality come from the 2022 Census, after deaths start (2015), and do not document conditions before disease onset. As a historical comparison (not pre-specified): rural population in 2000 and 2010 and households with well or spring water in 2010 (the 2010 Census does not separate wells from springs). Rurality is very stable (correlation with 2022: {r2000} for 2000 and {r2010} for 2010); well water in 2022 and well or spring water in 2010 have correlation {p10}.
{t_h}More wells do not demonstrate water contamination. Nitrate and other contaminants are hypotheses to investigate, not findings of this analysis.
Value in the municipality and, in parentheses, the state median; “n/a” = no data. {poco_acima} of the 16 have a share of households using well water above the state median in 2022 ({poco10_acima} for well or spring water in 2010).
{t_e}Supported, at the municipal level, by these data:
Motivated by the literature, not tested here (no suitable municipal data): temperature of chimarrão (mate) and other drinks (IARC classified very hot beverages, above 65 °C, as probably carcinogenic, group 2A); hand-rolled or rope tobacco; cachaça and home-distilled spirits; indoor wood stoves; nitrate and other water contaminants; diets poor in fruit and vegetables. Phase 2b ({BASE}/fase2b/en) looks further into Minas Gerais.
Code at {BASE}/codigo. Plan: PLANO-fase2.md (commit {PLANO_COMMIT}). After
Phases 1 and 1b: exposicoes.py, hipoteses.py, gerar_fase2.py. CSV results on the map
page and in the Zenodo deposit (fase2_*.csv).
In memory of Francisco Cledio Capistrano (F.C.C.).
""" SECOES = [("resumo", "Resumo", "Abstract"), ("metodo", "Método", "Methods"), ("univariada", "Associações", "Associations"), ("comparacao", "Comparação", "Comparison"), ("conjunto", "Conjuntos", "Joint models"), ("agrupamentos", "Vizinhos", "Neighbours"), ("regioes", "Sul e Minas", "South and Minas"), ("cronologia", "Cronologia", "Timing"), ("dezesseis", "Os 16", "The 16"), ("hipoteses", "Hipóteses", "Hypotheses"), ("limitacoes", "Limitações", "Limitations"), ("reproducao", "Reprodução", "Reproduction")] def casca(lang): autor = (f'Autor: Clériston Almeida Capistrano (ORCID {ORCID}) · ' f'pesquisador independente, sem formação na área da saúde · cledon.org') if lang == "pt" else \ (f'Author: Clériston Almeida Capistrano (ORCID {ORCID}) · ' f'independent researcher with no formal training in health sciences · cledon.org') toc = "".join(f'{b if lang == "pt" else c}' for a, b, c in SECOES) if lang == "pt": return {"HTML_LANG": "pt-BR", "TITLE": "Fase 2 · Câncer de esôfago — Cledon", "DESCRIPTION": "Câncer de esôfago no Brasil: características municipais associadas ao excesso de mortalidade. " "Geração de hipóteses.", "NAV_LABEL": "Navegação principal", "NAV": f'O mapaFase 1b' f'CódigoEnglish', "EYEBROW": "Relatório · Fase 2", "H1": "Câncer de esôfago: o que as áreas com excesso têm em comum", "LEAD": "Geração de hipóteses com dados públicos de produção agrícola, água, ruralidade, PIB e geografia, para " f'orientar um estudo com pacientes. English version.', "AUTHOR": autor, "TOC_LABEL": "Seções", "TOC": toc, "FOOTER": "Cledon · Find Cancer Clues · Iniciativa independente de pesquisa. Este estudo não oferece diagnóstico, " 'tratamento ou orientação médica. contato@cledon.org.', "PAGE": "Página", "OF": "de", "RUNNING": f"Cledon · Fase 2 · v{VERSAO}"} return {"HTML_LANG": "en", "TITLE": "Phase 2 · Esophageal cancer — Cledon", "DESCRIPTION": "Esophageal cancer in Brazil: municipal characteristics associated with excess mortality. " "Hypothesis generation.", "NAV_LABEL": "Main navigation", "NAV": f'The mapPhase 1b' f'CodePortuguês', "EYEBROW": "Report · Phase 2", "H1": "Esophageal cancer: what the areas with excess have in common", "LEAD": "Hypothesis generation with public data on agricultural production, water, rurality, GDP and geography, to " f'guide a study with patients. Versão em português.', "AUTHOR": autor, "TOC_LABEL": "Sections", "TOC": toc, "FOOTER": "Cledon · Find Cancer Clues · Independent research initiative. This study does not provide diagnosis, " 'treatment or medical advice. contato@cledon.org.', "PAGE": "Page", "OF": "of", "RUNNING": f"Cledon · Phase 2 · v{VERSAO}"} def main(): global PT d = dados() modelo = (RAIZ / "modelo_relatorio.html").read_text() for lang, saida in (("pt", RAIZ.parent / "fase2" / "index.html"), ("en", RAIZ.parent / "fase2" / "en" / "index.html")): PT = lang == "pt" pagina = modelo.replace("{{CORPO}}", corpo(d)) for k, v in casca(lang).items(): pagina = pagina.replace("{{" + k + "}}", v) assert "{{" not in pagina saida.parent.mkdir(parents=True, exist_ok=True) saida.write_text(pagina) print(f"Fase 2 ({lang}): {saida}") if __name__ == "__main__": main()