FJFrigo · Relatórios · menu 3-8 Indicadores — 381

Demonstrativo de Faturamento por Unidade

O faturamento por filial e mercado (interno e exportação) em três visões, com o painel em tela, a página da diretoria e o resumo das 7h. De onde vem cada número, as duas visões (fiscal e gerencial), as recusas e como conferir no banco.

Tela: Demonstrativo de Faturamento por Unidade (381)Origem: desenho novo, sem legadoSaída: XLS, PDF, painel em tela e e-mailGrava: só o resultado do último envio

Bloqueia

Recusa e não gera. HTTP 200 com statuscode 400 e a frase indicada.

Aviso

Comportamento que surpreende sem ser erro — origem da maioria dos chamados de "o número não bate". Parte sai como painel de avisos na tela.

Uma apuração, cinco saídas

XLS, PDF, painel, página da diretoria e e-mail usam a mesma apuração (RelatorioDemonstrativoFaturamentoService).

A natureza decide

Venda, devolução e estorno saem de tipo_faturamento.tipo_natop; o que a empresa não conta fica nas chaves da Config. Globais.

A

O que a tela mostra

Janela, painel em tela, página da diretoria e e-mail

O 381 substitui a planilha semanal de faturamento fiscal que a contabilidade da BMG monta à mão (abas mensal e semanal). Desenho novo, sem legado: o que é venda sai da natureza do tipo de faturamento (tipo_faturamento.tipo_natop), não de uma lista digitada. Uma mesma apuração alimenta o XLS, o PDF, o painel "Ver em tela", a página da diretoria e o e-mail das 7h — por isso eles nunca divergem entre si.

Linhas e colunas do arquivo (XLS/PDF)

VisãoColunasLinhas
MensalUm mês por coluna (o mês inicial e o final podem ser parciais), Total e Média/mês.Uma linha por filial × mercado (Mercado interno / Exportação), depois TOTAL MERCADO INTERNO, TOTAL EXPORTAÇÃO, FATURAMENTO TOTAL e Variação s/ mês anterior (%).
SemanalUma coluna Semana dd/MM a dd/MM e uma Acum. até dd/MM por semana, com Var. sem. %. Semana fecha no domingo; a última fecha na data final.As mesmas linhas e totais da mensal.
ComparativoSó vale a data final: mês, mesmo mês do ano anterior, Var. %, acumulado do ano, acumulado do ano anterior, Var. %, mês anterior, Var. % mês.As mesmas linhas e totais. A data inicial é ignorada (a tela avisa).

Composição (opção Detalhar)

Acrescenta uma seção Componente por filial × mercado: Venda: <id> <tipo>, (-) Descontos na nota, Frete e Seguro (só exportação), (-) Devolução: <tipo>, (-) Estorno de venda: <tipo> e (+) Estorno de devolução: <tipo>. É o primeiro lugar para olhar quando um número não bate.

Excel

Gerado por DemonstrativoFaturamentoXls com o visual da planilha original: logo e título em vermelho, cabeçalho dourado (colunas Var. em salmão), autofiltro e painéis congelados, barras verdes por formatação condicional (mínimo fixo em 0), setas ▲/▼ na variação, A4 paisagem. O PDF usa o impresso padrão de grade.

Painel "Ver em tela" (BI)

Janela própria (PainelDemonstrativoFaturamento.vue) com os mesmos filtros: indicadores (mês × mesmo mês do ano anterior e × mês anterior, acumulado × ano anterior, % exportação, unidades faturando), evolução empilhada interno × exportação com a linha tracejada do ano anterior, ranking (top 12; clique abre a composição), grade com barras e setas. Seletor Fiscal | Gerencial e botão Atualizar; mostra atualizado em quando os números vêm dos totais guardados.

Página da diretoria e e-mail das 7h

/painel/faturamento (login próprio, feita para celular; recarrega sozinha a cada 15 min; ?base= no link preenche o banco no login). Abre na visão gerencial. O e-mail das 7h (e o botão Enviar agora da janela) leva indicadores até ontem, as 10 maiores unidades do mês, o botão "Abrir o painel" e o semanal em PDF e Excel, também no critério gerencial.

B

Filtros e opções

Com o valor que a tela abre
CampoPadrão ao abrirEfeito
Período de / atéDia 1 do mês corrente até hojeCorta por data_emissao (faixa meio-aberta: >= de e < até + 1 dia). Obrigatório.
VisãoSemanal (a API assume Mensal se vier vazio)Mensal, Semanal ou Comparativo (tabela da seção A).
CritérioFiscalFiscal = todas as notas, como a contabilidade. Gerencial = sem os tipos de DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOS_GERENCIAL. O painel da diretoria e o e-mail abrem em Gerencial.
Filial (multi)Vazio = todas as filiais do usuárioSó filiais do alcance do usuário (FiliaisDoUsuario).
Excluir Tipo de Faturamento (multi)VazioSoma-se ao que a Config. Globais já exclui. Tira o tipo da venda/devolução e os estornos cuja nota estornada era desse tipo.
Moeda conversãoMoeda localConverte cada dia pela cotação do dia (última cotação até o dia). Ver regras da seção D.
Esconder unidades sem movimentoLigadoDesligado lista todas as filiais do alcance, mesmo zeradas.
Detalhar composiçãoDesligadoAcrescenta a seção Composição.
Paisagem (PDF)LigadoSó PDF.
Filtros salvos / folha "Filtros utilizados"—Barra de filtros salvos por usuário (código 381); o PDF leva a folha de filtros (desligável nas Opções).
C

De onde vem cada número

Tabelas, colunas e filtros

Regras comuns a todos os componentes: documento não excluído (IFNULL(excluido,'F') <> 'T', também nos itens); data pela emissão em faixa meio-aberta; valor na moeda local da filial (valor × valor_cambio quando idmoeda ≠ filial.idmoeda_local; câmbio vazio ou zero vale 1); só as filiais do alcance; tipos fora: DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOS (+ _GERENCIAL no critério gerencial) + filtro da tela.

Componente (linha da composição)Tabela / colunasRegra
Venda: <tipo>faturamento_venda × faturamento_venda_produtos.valor_totalTipos com tipo_natop LIKE 'venda%' e entrada_saida = 'S' (hoje na BMG entram 113, 114, 11109, 11175, 1194, 11179, 11151 etc. — qualquer tipo novo com natureza venda* entra sozinho). Só itens tipo_produto = '1' (o '2' duplica o item). Mercado = Exportação se tipo_faturamento.venda_exportacao = 1, senão interno.
(-) Descontos na notafaturamento_venda.valor_outros_descontos (arredondado por nota)Mesmas notas da venda. Na BMG só as lojas usam. Entra negativo.
Frete e Seguro (só exportação)valor_frete_liquido_terrestre, valor_frete_liquido_maritimo, valor_seguro, tipo_freteComo a NF-e os declara (vFrete/vSeg): terrestre só em CPT, CIP, FOB; marítimo em CPT, CIP, CFR, FOB; arredondado por nota. Se as colunas não existem no tenant, frete = 0.
(-) Devolução: <tipo>faturamento_compra_carne × faturamento_compra_carne_produtos.valor_totalTipos de natureza devolucao_venda. Mercado = Exportação quando o emitente (emitente → cidade → estado) tem UF EX; senão interno.
(-) Estorno de venda / (+) Estorno de devoluçãofaturamento_compra_carne (tipos cancelamento_venda: 1189, 11168, 11186 na BMG) + faturamento_nfeA nota estornada é achada pela chave <refNFe> do XML do estorno (faturamento_nfe.nfe_conteudo_xml) e localizada em faturamento_nfe pelo número (documento, posições 26–34 da chave) e pelo nome <chave>-nfe.xml. Se a estornada era venda: abate (mercado da venda). Se era devolução: soma de volta (mercado do emitente). Qualquer outro tipo (transferência, devolução de compra, retorno de industrialização) fica fora.

Cálculo das colunas. Total = soma dos períodos; Variação % = atual ÷ base − 1, em branco quando a base é zero ou negativa; Participação = parte ÷ total. Mês incompleto: o rótulo diz até que dia vai (Mês 10/2026 até dia 1, Acum. 2025 até 01/10).

Totais guardados da base (FatosDaBase). Quando o período cabe entre 1º/1 do ano passado e hoje, a tela e o arquivo não consultam as notas: recortam em memória os totais por dia de toda a base, guardados por 20 min (a rotina do painel os refaz a cada 15 min nos bancos com PAINEL_FATURAMENTO = 1; nos outros, a primeira tela depois disso refaz; o botão Atualizar do painel refaz na hora). Pedido fora dessa janela (antes de 1º/1 do ano passado, ou data final no futuro) consulta direto. O JSON memória × consulta direta foi conferido idêntico em 5 recortes.

Fiscal × Gerencial (BMG, conferido em 03/10/2026, milhões, jan–set/2026)

CritérioJanFevMarAbrMaiJunJulAgoSet
Fiscal401,3262,6203,2145,757,0−44,721,6−2,747,6
Gerencial322,5188,2187,3143,964,835,921,620,147,6

A diferença é a operação financeira 11195 (venda "MI Financeiro") × 11196 (devolução) que volta meses depois: as 231 devoluções de junho (−80,6 mi) devolvem vendas de 11/2025 a 05/2026. Valores de referência — notas lançadas depois (NFC-e atrasada, retroativos) mudam os meses antigos.

D

Regras, travas e avisos

O que recusa e o que surpreende

O 381 não grava nada no faturamento. A única escrita é a de PAINEL_FATURAMENTO_ULTIMO_ENVIO (system_config) a cada tentativa de e-mail. Não há regra de acesso nomeada: o alcance é pelas filiais do usuário.

Bloqueia

Informe a data inicial.

QuandoPeríodo vazio (também Informe a data final.). Data torta: Data inicial inválida: <valor> (confira o ano).

TambémA data final não pode ser anterior à inicial.

Todos
Bloqueia

A visão mensal vai até 24 meses - o período escolhido tem N.

TesteMensal de 01/01/2024 a 30/09/2026 (33 meses).

Todos
Bloqueia

A visão semanal vai até 10 semanas - o período escolhido tem N. Escolha um mês.

TesteSemanal de 01/07/2026 a 30/09/2026 dá 14 semanas.

Todos
Bloqueia

A filial N não está entre as filiais do usuário.

QuandoFilial pedida (API ou filtro salvo antigo) fora do alcance do usuário.

Todos
Bloqueia

Não foram encontrados dados nessas condições.

QuandoTodas as linhas zeradas no recorte (período sem venda, filial sem movimento, tudo excluído).

PainelNo "Ver em tela" só recusa se a visão e os indicadores do comparativo estiverem zerados.

Todos
Bloqueia

Nenhum tipo de faturamento com natureza de venda - confira o cadastro de tipos (natureza) e os tipos excluídos.

QuandoTodos os tipos de venda foram excluídos (filtro + Config. Globais), ou o cadastro não tem natureza venda*.

VarianteO cadastro de tipos de faturamento desta base não tem a natureza (tipo_natop) - o demonstrativo não sabe o que é venda. — tenant sem a coluna tipo_natop.

Todos
Bloqueia

A moeda X não tem cotação lançada (21) até <data> - não há como converter.

TambémAs filiais escolhidas têm moedas locais diferentes [..] - escolha uma filial para converter a moeda. e Moeda de conversão N não cadastrada.

ConversãoDivide o valor pelo último valor de moeda_valores até o dia (se não há anterior, o dia fica fora da conversão, com aviso — nunca cotação futura). Escolher a própria moeda local não converte.

Todos
Bloqueia

Cadastre os e-mails do resumo na Config. Globais (PAINEL_FATURAMENTO_EMAILS) antes de enviar.

QuandoEnviar agora sem destinatário (precisa de pelo menos um valor com @).

Sem SMTPCom destinatário e sem servidor (filial 1, aba NF-e, nem spring.mail), não é erro: grava ERRO|...|sem servidor de e-mail (filial 1, aba NF-e) em PAINEL_FATURAMENTO_ULTIMO_ENVIO e a janela mostra "falhou".

Todos
Aviso

N dia(s) convertido(s) para <moeda> com cotação de mais de 7 dias antes (de <data> a <data>) - confira a cotação de moedas (21).

EfeitoConverte mesmo assim, com a última cotação disponível. No central não há cotação de dólar desde 2022: converter para dólar sai (com este aviso) pela cotação de 2022.

Todos
Aviso

N estorno(s) de NF-e (cancelamento de venda) sem a nota referenciada no XML ficaram fora do demonstrativo.

QuandoEstorno sem <refNFe> no XML, ou cuja nota estornada não está em faturamento_nfe.

Sem avisoEstorno cuja nota estornada existe mas é de tipo que não é venda nem devolução (ex.: o 1189 de Iporã de 01/09/2026, R$ 333.938,02, estorna uma transferência 1151) também fica fora — sem aviso. É a regra decidida, não bug.

Todos
Aviso

Lojas: o valor de hoje é maior que o da planilha.

MotivoAs NFC-e das lojas chegam ao central com dias de atraso (data_inclusao). A planilha guardava o que havia na hora da extração (01–13/09 = notas incluídas até 14/09 0h, conferido ao centavo). O relatório sempre mostra o valor de hoje.

Todos
Aviso

Mensal de meses antigos muda depois de fechado.

MotivoLançamento retroativo (ex.: devoluções 11196 lançadas depois) altera meses passados. O relatório é "vivo"; não há fotografia de fechamento.

Todos
Aviso

Venda nova não aparece de imediato.

MotivoOs totais por dia ficam em memória por até 20 min (XLS, PDF e painel). Só o botão Atualizar do painel refaz na hora; o XLS/PDF não tem esse botão.

Todos
Aviso

Comparativo: a data inicial é ignorada e a Var. % pode vir em branco.

RegraMês e acumulado vão até a data final; quando ela é o último dia do mês, os períodos de comparação vão ao fim do mês deles (29/02, 30 × 31). Base ≤ 0 → variação em branco (ex.: junho de 2025 negativo).

Todos
Aviso

1121 Venda Funcionários não entra, mas tem natureza de venda.

RegraEstá na chave DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOS (fora do fiscal e do gerencial). Parametrização definitiva "depois vemos" (usuário, 02/10).

Todos
Aviso

Vila Bela (filial 14) não aparece.

MotivoNão há nenhuma nota dela no central; o faturamento deve estar em outra base (a conferir). Não é filtro.

Todos
E

Configuração e permissões

Config. Globais (grupo faturamento) e application.yml
ChavePadrãoEfeito
DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOSvazio (BMG: 1121)Ids de tipo_faturamento fora em todas as apurações (relatório, tela, painel, e-mail e também 384, 38A e 38F). Separador vírgula, ponto e vírgula ou espaço; valor torto é ignorado.
DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOS_GERENCIALvazio (BMG: 11195,11196,11203)Fora só do critério Gerencial. 384, 38A e 38F sempre aplicam as duas (a visão deles é a gerencial).
PAINEL_FATURAMENTO0 (desligado)Liga a rotina (recálculo a cada 15 min e e-mail das 7h) no banco. Desligada, o painel da diretoria ainda abre (recalcula na hora) e o Enviar agora funciona. No central de homologação não há linha = desligado.
PAINEL_FATURAMENTO_EMAILSvazioDestinatários do resumo (só valores com @).
PAINEL_FATURAMENTO_ULTIMO_ENVIOsomente leituraaaaa-mm-dd hh:mm|OK ou ERRO|destinatários|mensagem. A rotina só considera "já enviado hoje" um envio OK gravado aqui (sobrevive a reinício); se falhar às 7h00 tenta 7h15, 7h30, 7h45.
app.painel-faturamento.* (variáveis PAINEL_FATURAMENTO_*)automatico=true, intervalo-minutos=15, hora-email=7, bases, url-web, remetentebases garante a rotina depois de reiniciar (sem ela, só bancos em que alguém já entrou); url-web é o endereço do front no link do e-mail.
SMTP da filial 1filial_trib.nfe_servidor_smtp, _porta_smtp, _usuario_smtp, _senha_smtp, nfe_email_sslO e-mail sai por aqui (SSL direto na 465, STARTTLS nas outras). Sem ele, cai no spring.mail do backend. Envio real não testado.

Permissão. Item de menu sem idOpcao (sem linha em opcao_sistema): qualquer usuário logado abre. O que ele vê depende só das filiais do usuário; a página da diretoria, para quem não alcança todas as filiais, devolve o painel só com as dele (parcial: true).

Sessão da página da diretoria: ela não manda heartbeat de "atividade de gente"; ao fim de app.jwt.expiration-minutes / max-session-hours o diretor entra de novo (o link volta ao painel).

F

Casos de teste sugeridos

Com o resultado esperado e como conferir no banco

Banco de referência: central (BMG, codicfj 004). Valores de 03–04/10/2026; nota nova ou retroativa muda meses antigos, então confira sempre contra a mesma consulta, no mesmo momento.

#PassoEsperadoComo conferir
1Mensal, 01/09 a 30/09/2026, Fiscal, todas as filiais, Detalhar ligado.Linhas por filial × mercado, totais, e a seção Composição. Venda: 114 Venda Mercado Interno é a maior linha do interno.Componente Venda por filial (consulta abaixo). Em 04/10/2026, todas as filiais sem o 1121: 48.757.117,71 — o FATURAMENTO TOTAL fica abaixo (descontos e devoluções).
SELECT ROUND(SUM(fvp.valor_total * IF(fv.idmoeda = f.idmoeda_local OR IFNULL(fv.valor_cambio,0) = 0, 1, fv.valor_cambio)), 2) AS venda_itens
FROM faturamento_venda fv
JOIN filial f ON f.id_filial = fv.idfilial
JOIN tipo_faturamento t ON t.id = fv.idtipo_faturamento
JOIN faturamento_venda_produtos fvp ON fvp.idfaturamento_venda = fv.id
     AND fvp.tipo_produto = '1' AND IFNULL(fvp.excluido,'F') <> 'T'
WHERE IFNULL(fv.excluido,'F') <> 'T' AND t.tipo_natop LIKE 'venda%' AND t.entrada_saida = 'S'
  AND fv.idtipo_faturamento NOT IN (1121)            -- tipos da Config. Globais + filtro da tela
  AND fv.idfilial IN (5)                             -- filial(is) pedida(s)
  AND fv.data_emissao >= '2026-09-01' AND fv.data_emissao < '2026-10-01'
2Mesmo recorte, soma de Devolução e Estorno.As linhas (-) Devolução e (-) Estorno de venda batem com a consulta (estorno só quando a nota estornada era venda).
SELECT t.tipo_natop, COUNT(DISTINCT c.id) AS docs,
       ROUND(SUM(p.valor_total * IF(c.idmoeda = f.idmoeda_local OR IFNULL(c.valor_cambio,0) = 0, 1, c.valor_cambio)), 2) AS valor
FROM faturamento_compra_carne c
JOIN filial f ON f.id_filial = c.idfilial
JOIN tipo_faturamento t ON t.id = c.idtipo_faturamento
JOIN faturamento_compra_carne_produtos p ON p.idfaturamento_compra_carne = c.id AND IFNULL(p.excluido,'F') <> 'T'
WHERE IFNULL(c.excluido,'F') <> 'T' AND t.tipo_natop IN ('devolucao_venda','cancelamento_venda')
  AND c.idtipo_faturamento NOT IN (1121,11195,11196,11203)     -- critério GERENCIAL da BMG
  AND c.data_emissao >= '2026-09-01' AND c.data_emissao < '2026-10-01'
GROUP BY t.tipo_natop
3Mensal de 01/01 a 30/09/2026, coluna 06/2026: Fiscal e Gerencial.Fiscal ≈ −44,7 mi; Gerencial ≈ +35,9 mi (03/10). A diferença são os tipos 11195/11196/11203.SELECT chave, valor_string FROM system_config WHERE chave LIKE 'DEMONSTRATIVO%'. Rode o caso 1 com idtipo_faturamento IN (11195) e as devoluções 11196.
4Filtro Excluir Tipo = 114, Mensal de setembro.A linha Venda: 114 ... some da composição; a exportação (113) permanece.A mesma consulta do caso 1 sem o 114 (NOT IN (1121,114)).
5Semanal de 01/09 a 30/09/2026.Cinco semanas: 01/09 a 06/09, 07/09 a 13/09, 14/09 a 20/09, 21/09 a 27/09, 28/09 a 30/09; cada uma com Acum.01/09/2026 é terça; semanas fecham no domingo.
6Comparativo com data final 15/09/2026, depois 30/09/2026.Rótulos Mês 09/2026 até dia 15, Mês 09/2025 até dia 15, Acum. 2026 até 15/09, Acum. 2025 até 15/09, Mês 08/2026 até dia 15. Com 30/09 os rótulos perdem o até.Conferir cada coluna com o caso 1 mudando só o intervalo de datas.
7Mensal 01/01/2024–30/09/2026; Semanal 01/07–30/09/2026.Recusas 24 meses ... tem 33 e 10 semanas ... tem 14. Escolha um mês.—
8Converter para dólar no central.Sai, com o painel de avisos N dia(s) convertido(s) para ... cotação de mais de 7 dias antes.SELECT MAX(data) FROM moeda_valores WHERE idmoeda = <dólar> (2022).
9Estorno: ache um estorno do mês e a nota estornada.Estorno de venda abate; de devolução soma; de transferência (1151) não aparece em lugar nenhum.
SELECT c.id, c.idfilial, c.idtipo_faturamento, DATE(c.data_emissao) AS dia,
       SUBSTRING(n.nfe_conteudo_xml, LOCATE('<refNFe>', n.nfe_conteudo_xml) + 8, 44) AS chave_estornada
FROM faturamento_compra_carne c
JOIN tipo_faturamento t ON t.id = c.idtipo_faturamento AND t.tipo_natop = 'cancelamento_venda'
JOIN faturamento_nfe n ON n.idfaturamento = c.id AND n.idtipo_faturamento = c.idtipo_faturamento
     AND LOCATE('<refNFe>', n.nfe_conteudo_xml) > 0
WHERE IFNULL(c.excluido,'F') <> 'T' AND c.data_emissao >= '2026-09-01' AND c.data_emissao < '2026-10-01'
-- o tipo da nota estornada:
SELECT idtipo_faturamento FROM faturamento_nfe WHERE nfe_nome_xml = '<chave_estornada>-nfe.xml'
10"Ver em tela": alternar Fiscal | Gerencial; clicar Atualizar.Os números do mês coincidem com o XLS do mesmo critério; atualizado em muda após Atualizar.Gerar o XLS dos mesmos filtros e comparar FATURAMENTO TOTAL.
11Lançar uma venda de teste (homologação) e gerar o XLS em seguida.Pode não aparecer por até 20 min; o painel com Atualizar mostra na hora.Aguardar 20 min e regerar.
12Usuário com 1–2 filiais.O arquivo só traz as filiais dele; a página da diretoria vem com parcial; filial de fora: A filial N não está entre as filiais do usuário.—
13Enviar agora sem e-mails; depois com e-mail e sem SMTP.1º: Cadastre os e-mails.... 2º: a janela mostra falhou — sem servidor de e-mail (filial 1, aba NF-e).SELECT valor_string FROM system_config WHERE chave = 'PAINEL_FATURAMENTO_ULTIMO_ENVIO'
14Período sem nenhuma venda (ex.: futuro).Não foram encontrados dados nessas condições.—
G

Limitações, pendências e achados

O que ainda não existe ou merece atenção

Fora desta versão: frete (CT-e / frete avulso) como terceira classe (a planilha tem as linhas das transportadoras 68/71, zeradas o ano todo); seção "Paralisadas".

Não testado na tela (sem sessão; o backend precisa reiniciar); e-mail real não testado (sem SMTP); falta configurar no servidor PAINEL_FATURAMENTO_URL_WEB e PAINEL_FATURAMENTO_BASES, ligar PAINEL_FATURAMENTO, preencher os e-mails e criar o usuário da diretoria.

Conferência contra a planilha: semanal 01–30/09 bate em todas as linhas, menos as lojas (NFC-e atrasada) e 1 centavo de arredondamento do frete em 05/11 exportação. Jan–set difere por lançamento retroativo, junho digitado à mão na planilha e Vila Bela sem notas no central.

Defeitos da planilha (exemplo, não corrigidos): linha 77 (Confinamento) fora do total anual (−729.150); junho digitado em vez de puxado da semanal; M87 = M83/K83-1 divide uma variação por outra; rótulo "FRETE NO MERCADO EXTERNO" somando frete interno.

Achados ao ler o código (não corrigidos)

1. Sem trava de permissão no resumo por e-mail. GET /lancamento/relatorios/painelFaturamento/situacao e POST .../enviar só exigem estar logado: qualquer usuário do banco vê os destinatários e o servidor SMTP e pode disparar o e-mail (mesmo com PAINEL_FATURAMENTO desligado).

2. Comentário desatualizado. O javadoc de RelatorioDemonstrativoFaturamentoService.CHAVE_EXCLUIR e o de PainelFaturamento ainda citam 11195/11196/11203 como parte de DEMONSTRATIVO_FATURAMENTO_EXCLUIR_TIPOS; desde 03/10 eles estão na chave _GERENCIAL (a tela e o central estão corretos). Corrigido em 04/10/2026: comentários acertados.

3. Câmbio zero vale 1. IFNULL(valor_cambio,0)=0 → fator 1: nota em moeda estrangeira sem câmbio entra pelo valor nominal, sem aviso.

4. Conversão com cotação futura. Sem cotação anterior ao dia, usa a primeira cotação existente (pode ser posterior ao dia); só avisa quando a distância passa de 7 dias. Corrigido em 04/10/2026: o dia sem cotação anterior fica fora da conversão (zero) e entra no aviso; o 31C (DRE gerencial, mesma classe DreGerencialConversao) passou à mesma regra no mesmo dia (decisão do usuário) e a opção semCotacaoFutura() deixou de existir: comportamento único da classe.

H

Como o erro chega na tela

Para o QA reproduzir e reportar

Toda resposta sai com HTTP 200; quem diz o que aconteceu é o statuscode no corpo — 400 para as recusas deste documento.

O arquivo é pedido como download, mas a recusa chega como mensagem: a tela mostra a frase no lugar do arquivo. Enquanto gera, o botão mostra o contador Gerando… (Ns).

Avisos (cotação faltando, foto sem produção, estorno sem nota...) não interrompem: vêm no cabeçalho X-Aviso-Sistema e a tela mostra o painel de avisos. Teste sempre olhando o painel, não só o arquivo.

Ao abrir chamado, copie o código de ocorrência de 8 caracteres dos erros inesperados. Erro de tela vai para o log em POST /cadastro/erros-front.

Nenhuma regra bate com essa busca. Tente um trecho menor da mensagem, ou limpe os filtros.