i-educar icon indicating copy to clipboard operation
i-educar copied to clipboard

Erro ao Gerar Relatório de Alunos por Turma (StudentsPerClass.php)

Open Nepturne opened this issue 3 years ago • 16 comments

MENU: Na Rota: /module/Reports/StudentsPerClass No menu Escola > Relatórios > Matrículas > Relatório de Alunos por Turma

DESCRIÇÃO:

Nesta tela:

Ao informar o ano 2022, a instituição, a escola , o curso, a série , e a turma ,e clicar em exibir. Ao mesmo tempo em que deixei aberto o log de acompanhamento do Postgresql com o comando: sudo tail -f /var/log/postgresql/postgresql-13-main.log Acontece tal problema, o relatório não é exibido, se exibe é em branco, ou nem carrega as vezes e no log obtém-se este erro:

Acredito que tudo esteja acontecendo por alguma falha neste arquivo:

OBSERVAÇÕES:

Fiquei muito pensativo sobre isto, pois gerando o mesmo relatório porém com o ano 2021, ele traz os dados e exibe o relatório em tela, porém com o ano 2022 acontece isto sempre e não consigo gerar o relatório. Uma boa forma de tentar verificar na minha opnião seria analisando onde ficaria a QUERIE:

INSERT INTO modules.nota_componente_curricular (id, nota_aluno_id, componente_curricular_id, nota, nota_arredondada, nota_recuperacao, nota_recuperacao_especifica, nota_original, etapa) VALUES () RETURNING id

Pois o erro aponta : ERROR: syntax error at or near ")" at character 195

É possível que isto seja a falta de um parênteses?

AMBIENTE:

  • Plataforma utilizada (instalação direta)
  • Sistema operacional e versão (Ubuntu 20.04)
  • Navegador e versão (Chrome na última versão)
  • Outros detalhes importantes

Nepturne avatar Feb 07 '22 19:02 Nepturne

@Nepturne Muito obrigado pelo report. Consegue confirmar para mim se é nessa classe que busca a query que executa o SQL: https://github.com/portabilis/i-educar-reports/blob/bd3bc3c1fb986892ae28946039f36ca5016f9814/ieducar/Queries/QueryAlunoTurma.php#L3

Se sim, é possível pegar os dados dos argumentos e testar apenas a query, assim teremos uma noção de como corrigir o problema.

Deste já agradeço a contribuição.

jrbarros avatar Feb 08 '22 09:02 jrbarros

@jrbarros Gratidão pelo feedback, identifiquei que executando a Query diretamente no banco de dados passando os dados dos argumentos não entrega retorno e fica somente carregando sem concluir. Isso só acontece quando o ano informado é 2022, estou analisando também que o caminho de diretório que você informou está diferente da estrutura de pastas que temos no atual sistema: O que você informou: https://github.com/portabilis/i-educar-reports/blob/bd3bc3c1fb986892ae28946039f36ca5016f9814/ieducar/Queries/QueryAlunoTurma.php#L3 Creio eu que a sua estrutura de pastas esteja assim: i-educar-reports/blob/bd3bc3c1fb986892ae28946039f36ca5016f9814/ieducar/Queries/QueryAlunoTurma.php

E a nossa estrutura está assim: ieducar/ieducar/modules/Reports/Reports/StudentsPerClassReport.php

A situação é que testamos a geração deste relatório na versão 2.6.2 e na versão 2.6.8

Para gerar o erro , Ir no menu Escola > Relatórios > Matrículas > Relatório de Alunos por Turma, Gerar algum relatório com o ano 2022. Porém o erro ainda é retornado assim nas duas versões:

Nepturne avatar Feb 08 '22 13:02 Nepturne

@jrbarros A query que está sendo especificada com erro: 2022-02-08 13:27:25.777 UTC [1302] ieducar@ieducar ERROR: syntax error at or near ")" at character 195 2022-02-08 13:27:25.777 UTC [1302] ieducar@ieducar STATEMENT: INSERT INTO modules.nota_componente_curricular (id, nota_aluno_id, componente_curricular_id, nota, nota_arredondada, nota_recuperacao, nota_recuperacao_especifica, nota_original, etapa) VALUES () RETURNING id

Acredito eu que esteja no arquivo : modules.copia_notas_transf.sql ( Que seria uma function lá no Postgresql ) , mas não sei o que pode estar ocorrendo

Nepturne avatar Feb 08 '22 13:02 Nepturne

Ao gerar o relatório em 2022 ou ele resulta nisso: Ou aparece uma tela escrito : 504 Gateway Time-out E no log do Postgresql:

Nepturne avatar Feb 08 '22 15:02 Nepturne

@Nepturne tudo bem?

Erro erro apresentado no log do Postgres me parece não ter relação direta com a exibição do relatório em branco, me parece ser dois cenários.

Diria que no 1° cenário, ao tentar consultar o ano de 2022 você deve ter algum cadastro faltando, por exemplo, além de abrir o ano letivo, é necessário vincular os componentes curriculares para o determinado ano, como também séries e se não me engano alguma coisa relacionado a regra de avaliação.

Falo isso do primeiro cenário pois é possível consultar o ano de 2021!

Para o 2°cenário, o erro apresentado no log do postgres ocorre para dados de 2021 e 2022 e está relacionado a inserção de dados, coisa que o relatório não faz, logo, venho a pensar que por algum motivo "regra de negócio" existente para a função copia_notas_transf se faz necessário a validação do tipo da nota vinculada a regra de avaliação IF (v_tipo_nota >0) THEN se for atendida determinada condição, o i-Educar fará a inserção de dados em nota_aluno e nota_componente_curricular ocasionando o erro mencionado no log do postgres

Conclusão, para o seu problema, eu recomendaria revalidar todos as relações de cadastros para o ano de 2022!

msoares94 avatar Feb 08 '22 20:02 msoares94

@marcosoliveirasoares94 Muito obrigada marcos, a gente avaliou e viu que está funcionando a geração dos relatórios no sistema porém o comportamento que está estranho. Olha só. Gerando relatórios no sistema como um todo ( os outros ) ele gera em menos de 2 segundos e apresenta em tela, e vendo a tela de log de uso de CPU , a gente vê que o Postgres abre um processo para executar e quando termina o processo ele finaliza em 2 segundos.

Porém ao gerar especificamente o [ Relatório de alunos por turma ] , o nosso log apresenta que o processo de geração deste relatório demora MUITO TEMPO tanto tempo que as vezes a tela da erro e não exibe o relatório, e vemos que o processo fica usando 100% da CPU Segue a imagem abaixo: Acreditamos que seja a querie que se encontra em:

ieducar/ieducar/modules/Reports/Reports/StudentsPerClassReport.php

Nepturne avatar Feb 09 '22 19:02 Nepturne

Olá @Nepturne, então só para ficar claro, o sistema está retornando dados de 2021 e 2022 após revisarem as configurações de ano letivo para 2022 certo ?

Agora quando ao consumo de recurso elevado por parte do Postgres, gostaria de colocasse como anexo o log do Postgres com o nível de log "DEBUG" ou "TRACE"

Além disso, conseguiria executar a query com os parâmetros que são passados na consulta do relatório no modo "plan", conforme esta imagem de resultado? image

Você pode pegar o SQL no método getSqlMainReport na classe StudentsPerClassReport e alterar os valores que começam com {$this->args['$nomeatributo']} pelos valores do seus parâmetros para investigar melhor se tem algum dado causando a lentidão, pois executando no meu ambiente sem dados completos a query foi retornada em menos de 1segundo

msoares94 avatar Feb 09 '22 19:02 msoares94

@marcosoliveirasoares94 ao preencher a querie passando os dados , diretamente no Postgresql obtivemos resultado com esse tempo de espera ,14 min 42 secs:

Nepturne avatar Feb 09 '22 21:02 Nepturne

Agora sim melhorou, teria como mandar o seu SQL exatamente com os parâmetros preenchidos?

você poderia executar a query com explanação pois dessa forma obtemos o custo e time de cada consulta e subconsulta

msoares94 avatar Feb 09 '22 23:02 msoares94

@marcosoliveirasoares94 Concerteza olha só: De forma gráfica a query está assim:

A query com os parâmetros passados é essa: SELECT matricula_turma.sequencial_fechamento AS sequencial_fechamento, aluno.cod_aluno AS cod_aluno, aluno.aluno_estado_id AS serie_ciasc, educacenso_cod_aluno.cod_aluno_inep AS inep, fcn_upper(pessoa.nome) AS nome_aluno, ( CASE WHEN fisica.sexo = 'M' THEN 'Mas' ELSE 'Fem' END ) AS sexo, to_char(fisica.data_nasc, 'dd/mm/yyyy') AS data_nasc, nis_pis_pasep, curso.nm_curso AS nome_curso, turma.nm_turma AS nome_turma, serie.nm_serie AS nome_serie, turma.cod_turma AS cod_turma, escola.cod_escola AS cod_escola, juridica.fantasia AS nm_escola, turma_turno.nome AS periodo, ( SELECT infra_predio.nm_predio FROM pmieducar.infra_predio_comodo, pmieducar.infra_comodo_funcao, pmieducar.infra_predio WHERE TRUE AND infra_comodo_funcao.cod_infra_comodo_funcao = infra_predio_comodo.ref_cod_infra_comodo_funcao AND infra_comodo_funcao.ref_cod_escola = escola.cod_escola AND infra_predio.cod_infra_predio = infra_predio_comodo.ref_cod_infra_predio AND infra_predio.ref_cod_escola = escola.cod_escola AND infra_predio.ativo = 1 AND infra_predio_comodo.cod_infra_predio_comodo = turma.ref_cod_infra_predio_comodo ) AS predio, ( SELECT nm_comodo FROM pmieducar.infra_predio_comodo, pmieducar.infra_comodo_funcao, pmieducar.infra_predio WHERE TRUE AND infra_comodo_funcao.cod_infra_comodo_funcao = infra_predio_comodo.ref_cod_infra_comodo_funcao AND infra_comodo_funcao.ref_cod_escola = escola.cod_escola AND infra_predio.cod_infra_predio = infra_predio_comodo.ref_cod_infra_predio AND infra_predio.ref_cod_escola = escola.cod_escola AND infra_predio.ativo = 1 AND infra_predio_comodo.cod_infra_predio_comodo = turma.ref_cod_infra_predio_comodo ) AS sala, view_situacao.texto_situacao AS situacao, matricula.dependencia FROM pmieducar.instituicao INNER JOIN pmieducar.escola ON TRUE AND escola.ref_cod_instituicao = instituicao.cod_instituicao INNER JOIN pmieducar.escola_ano_letivo ON TRUE AND pmieducar.escola_ano_letivo.ref_cod_escola = pmieducar.escola.cod_escola INNER JOIN pmieducar.escola_curso ON TRUE AND escola_curso.ativo = 1 AND escola_curso.ref_cod_escola = escola.cod_escola INNER JOIN pmieducar.curso ON TRUE AND curso.cod_curso = escola_curso.ref_cod_curso AND curso.ativo = 1 INNER JOIN pmieducar.escola_serie ON TRUE AND escola_serie.ativo = 1 AND escola_serie.ref_cod_escola = escola.cod_escola INNER JOIN pmieducar.serie ON TRUE AND serie.cod_serie = escola_serie.ref_cod_serie AND serie.ativo = 1 INNER JOIN pmieducar.turma ON TRUE AND turma.ref_ref_cod_escola = escola.cod_escola AND turma.ref_cod_curso = escola_curso.ref_cod_curso AND turma.ref_ref_cod_serie = escola_serie.ref_cod_serie AND turma.ativo = 1 INNER JOIN pmieducar.matricula_turma ON TRUE AND matricula_turma.ref_cod_turma = turma.cod_turma INNER JOIN pmieducar.matricula ON TRUE AND matricula.cod_matricula = matricula_turma.ref_cod_matricula AND matricula.ativo = 1 INNER JOIN relatorio.view_situacao ON TRUE AND view_situacao.cod_matricula = matricula.cod_matricula AND view_situacao.cod_turma = turma.cod_turma AND view_situacao.cod_situacao = '10' AND matricula_turma.sequencial = view_situacao.sequencial LEFT JOIN pmieducar.turma_turno ON TRUE AND turma_turno.id = turma.turma_turno_id AND turma.cod_turma = matricula_turma.ref_cod_turma INNER JOIN pmieducar.aluno ON TRUE AND pmieducar.matricula.ref_cod_aluno = pmieducar.aluno.cod_aluno INNER JOIN cadastro.fisica ON TRUE AND cadastro.fisica.idpes = pmieducar.aluno.ref_idpes INNER JOIN cadastro.pessoa ON TRUE AND cadastro.pessoa.idpes = cadastro.fisica.idpes LEFT JOIN cadastro.juridica ON TRUE AND juridica.idpes = escola.ref_idpes LEFT JOIN cadastro.documento ON TRUE AND documento.idpes = fisica.idpes LEFT JOIN modules.educacenso_cod_aluno ON TRUE AND educacenso_cod_aluno.cod_aluno = aluno.cod_aluno WHERE TRUE AND pmieducar.instituicao.cod_instituicao = '1' AND pmieducar.escola_ano_letivo.ano = '2022' AND pmieducar.matricula.ano = pmieducar.escola_ano_letivo.ano AND ( SELECT CASE WHEN '3' = 0 THEN TRUE ELSE escola.cod_escola = '3' END ) AND ( SELECT CASE WHEN '2' = 0 /* curso / THEN TRUE ELSE pmieducar.escola_curso.ref_cod_curso = '2' END ) AND ( SELECT CASE WHEN '30' = 0 / SERIE / THEN TRUE ELSE pmieducar.serie.cod_serie = '30' END ) AND ( SELECT CASE WHEN '1170' = 0 / TURMA */ THEN TRUE ELSE pmieducar.turma.cod_turma = '1170' END ) AND ( CASE WHEN '0' = 1 THEN matricula.dependencia = TRUE WHEN '0' = 2 THEN matricula.dependencia = FALSE ELSE TRUE END ) ORDER BY nm_escola, nome_curso, nome_serie, nome_turma, cod_turma, ( CASE WHEN matricula.dependencia THEN 1 ELSE 0 END ) , sequencial_fechamento, nome_aluno

Nepturne avatar Feb 10 '22 18:02 Nepturne

@marcosoliveirasoares94 E a execução da Query com explanação:

Nepturne avatar Feb 10 '22 19:02 Nepturne

@Nepturne, bom, vai ser complicado de avaliar pois não tenho os mesmo resultado que você, devido a minha base de dados.

Extrai o modelo do JOIN, segue: postgresql_1644536981830

postgresql_1644537386551

Vamos ter que avaliar esse join que está demorando muito tempo para retornar e ver se tem como otimizar esse join.

msoares94 avatar Feb 10 '22 23:02 msoares94

@marcosoliveirasoares94 Excelente meu amigo, entendi primeiramente muito obrigada. Você poderia mandar a query do arquivo ieducar/ieducar/modules/Reports/Reports/StudentsPerClassReport.php , para ver se o desempenho melhora aqui? Já que na sua app tá indo bem? Caso continue a tornar esse tempo gigante de qualquer forma eu agradeço muito por essa ajuda

Nepturne avatar Feb 11 '22 13:02 Nepturne

@Nepturne, a query é a mesma presente no código fonte, mudando somente alguns valores para corresponder com meus dados cadastrados.

Segue Query:

SELECT     matricula_turma.sequencial_fechamento AS sequencial_fechamento,
           aluno.cod_aluno                       AS cod_aluno,
           aluno.aluno_estado_id                 AS serie_ciasc,
           educacenso_cod_aluno.cod_aluno_inep   AS inep,
           Fcn_upper(pessoa.nome)                AS nome_aluno, (
           CASE
                      WHEN fisica.sexo = 'M' THEN 'Mas'
                      ELSE 'Fem'
           END )                                   AS sexo,
           To_char(fisica.data_nasc, 'dd/mm/yyyy') AS data_nasc,
           nis_pis_pasep,
           curso.nm_curso    AS nome_curso,
           turma.nm_turma    AS nome_turma,
           serie.nm_serie    AS nome_serie,
           turma.cod_turma   AS cod_turma,
           escola.cod_escola AS cod_escola,
           juridica.fantasia AS nm_escola,
           turma_turno.nome  AS periodo,
           (
                  SELECT infra_predio.nm_predio
                  FROM   pmieducar.infra_predio_comodo,
                         pmieducar.infra_comodo_funcao,
                         pmieducar.infra_predio
                  WHERE  true
                  AND    infra_comodo_funcao.cod_infra_comodo_funcao = infra_predio_comodo.ref_cod_infra_comodo_funcao
                  AND    infra_comodo_funcao.ref_cod_escola = escola.cod_escola
                  AND    infra_predio.cod_infra_predio = infra_predio_comodo.ref_cod_infra_predio
                  AND    infra_predio.ref_cod_escola = escola.cod_escola
                  AND    infra_predio.ativo = 1
                  AND    infra_predio_comodo.cod_infra_predio_comodo = turma.ref_cod_infra_predio_comodo ) AS predio,
           (
                  SELECT nm_comodo
                  FROM   pmieducar.infra_predio_comodo,
                         pmieducar.infra_comodo_funcao,
                         pmieducar.infra_predio
                  WHERE  true
                  AND    infra_comodo_funcao.cod_infra_comodo_funcao = infra_predio_comodo.ref_cod_infra_comodo_funcao
                  AND    infra_comodo_funcao.ref_cod_escola = escola.cod_escola
                  AND    infra_predio.cod_infra_predio = infra_predio_comodo.ref_cod_infra_predio
                  AND    infra_predio.ref_cod_escola = escola.cod_escola
                  AND    infra_predio.ativo = 1
                  AND    infra_predio_comodo.cod_infra_predio_comodo = turma.ref_cod_infra_predio_comodo ) AS sala,
           view_situacao.texto_situacao                                                                    AS situacao,
           matricula.dependencia
FROM       pmieducar.instituicao
INNER JOIN pmieducar.escola
ON         true
AND        escola.ref_cod_instituicao = instituicao.cod_instituicao
INNER JOIN pmieducar.escola_ano_letivo
ON         true
AND        pmieducar.escola_ano_letivo.ref_cod_escola = pmieducar.escola.cod_escola
INNER JOIN pmieducar.escola_curso
ON         true
AND        escola_curso.ativo = 1
AND        escola_curso.ref_cod_escola = escola.cod_escola
INNER JOIN pmieducar.curso
ON         true
AND        curso.cod_curso = escola_curso.ref_cod_curso
AND        curso.ativo = 1
INNER JOIN pmieducar.escola_serie
ON         true
AND        escola_serie.ativo = 1
AND        escola_serie.ref_cod_escola = escola.cod_escola
INNER JOIN pmieducar.serie
ON         true
AND        serie.cod_serie = escola_serie.ref_cod_serie
AND        serie.ativo = 1
INNER JOIN pmieducar.turma
ON         true
AND        turma.ref_ref_cod_escola = escola.cod_escola
AND        turma.ref_cod_curso = escola_curso.ref_cod_curso
AND        turma.ref_ref_cod_serie = escola_serie.ref_cod_serie
AND        turma.ativo = 1
INNER JOIN pmieducar.matricula_turma
ON         true
AND        matricula_turma.ref_cod_turma = turma.cod_turma
INNER JOIN pmieducar.matricula
ON         true
AND        matricula.cod_matricula = matricula_turma.ref_cod_matricula
AND        matricula.ativo = 1
INNER JOIN relatorio.view_situacao
ON         true
AND        view_situacao.cod_matricula = matricula.cod_matricula
AND        view_situacao.cod_turma = turma.cod_turma
AND        view_situacao.cod_situacao = '10'
AND        matricula_turma.sequencial = view_situacao.sequencial
LEFT JOIN  pmieducar.turma_turno
ON         true
AND        turma_turno.id = turma.turma_turno_id
AND        turma.cod_turma = matricula_turma.ref_cod_turma
INNER JOIN pmieducar.aluno
ON         true
AND        pmieducar.matricula.ref_cod_aluno = pmieducar.aluno.cod_aluno
INNER JOIN cadastro.fisica
ON         true
AND        cadastro.fisica.idpes = pmieducar.aluno.ref_idpes
INNER JOIN cadastro.pessoa
ON         true
AND        cadastro.pessoa.idpes = cadastro.fisica.idpes
LEFT JOIN  cadastro.juridica
ON         true
AND        juridica.idpes = escola.ref_idpes
LEFT JOIN  cadastro.documento
ON         true
AND        documento.idpes = fisica.idpes
LEFT JOIN  modules.educacenso_cod_aluno
ON         true
AND        educacenso_cod_aluno.cod_aluno = aluno.cod_aluno
WHERE      true
AND        pmieducar.instituicao.cod_instituicao = '1'
AND        pmieducar.escola_ano_letivo.ano = '2021'
AND        pmieducar.matricula.ano = pmieducar.escola_ano_letivo.ano
AND
           (
                  SELECT
                         CASE
                                WHEN '3' = 0 THEN true
                                ELSE escola.cod_escola = '3'
                         END )
AND
           (
                  SELECT
                         CASE
                                WHEN '2' = 0
                                       /* curso /
                   THEN
                   TRUE
                   ELSE
                   pmieducar.escola_curso.ref_cod_curso = '2'
                   END
                   )
                   AND
                   (
                   SELECT
                   CASE
                   WHEN
                   '30' = 0
                   / SERIE /
                   THEN
                   TRUE
                   ELSE
                   pmieducar.serie.cod_serie = '30'
                   END
                   )
                   AND
                   (
                   SELECT
                   CASE
                   WHEN
                   '1170' = 0
                   / TURMA */
                                THEN true
                                ELSE pmieducar.turma.cod_turma = '1170'
                         END )
AND        (
                      CASE
                                 WHEN '0' = 1 THEN matricula.dependencia = true
                                 WHEN '0' = 2 THEN matricula.dependencia = false
                                 ELSE true
                      END )
ORDER BY   nm_escola,
           nome_curso,
           nome_serie,
           nome_turma,
           cod_turma, (
           CASE
                      WHEN matricula.dependencia THEN 1
                      ELSE 0
           END ) ,
           sequencial_fechamento,
           nome_aluno

msoares94 avatar Feb 18 '22 04:02 msoares94

@Nepturne Aparentemente o problema é com seus dados, estou certo? Ainda ocorre o problema?

jrbarros avatar Mar 11 '22 14:03 jrbarros

@jrbarros ainda sim

Nepturne avatar Mar 11 '22 19:03 Nepturne