Isto é um título nível
3.5 DESENVOLVIMENTO DO BACK-END 1 Situação inicial
3.5.2 Estruturação do back-end
Dividir-se-á a estruturação do back-end em 3 partes: as ferramentas utilizadas para a construção do aplicativo, as linguagens e as bibliotecas escolhidas. Não se utilizaram frameworks no back-end, visto que não se encontrou necessidade para tal, ao longo da programação dessa parte. 3.5.2.1 Estrutura mínima para o desenvolvimento
Para a visualização de resultados e testes ao longo do desenvolvimento, utilizou-se o mesmo servidor Apache2, do front-end, rodando em um computador com sistema operacional Ubuntu 18.04. Além disso, instalou-se o PHP 5.6, para suportar a programação na linguagem PHP; e o MySQL 5.7.26, para rodar o banco de dados para testes. Como ambiente de desenvolvimento, utilizou-se também o Sublime 3.
3.5.2.2 Linguagens
Como já se dispunha dos cálculos implementados em PHP, escolheu-se por manter essa linguagem no back-end. Essa decisão evitou a necessidade da tradução do código já disponível para uma nova linguagem, e focou o trabalho nessa linguagem no provisionamento do
servidor. Além disso, fez-se a disponibilização das funções por meio de uma API para transferência de parâmetros e acesso aos resultados, em PHP.
Para acesso ao banco de dados, para as funções de controle de acesso e armazenamento de informações de documentação, utilizou-se um banco de dados de linguagem SQL. Para a versão inicial do aplicativo, optou-se por MySQL, pela facilidade de uso junto ao PHP e fácil gerenciamento de informações com a ferramenta phpMyAdmin.
Desse modo, separou-se o back-end: na parte matemática, com os cálculos e o uso da biblioteca CoolProp, citada em 3.5.2.3; e na parte de estrutura para funcionamento do aplicativo, com a estruturação do banco de dados e a disponibilização de APIs.
3.5.2.3 Bibliotecas
Utilizou-se a biblioteca CoolProp, para PHP, para a realização de cálculos envolvendo as propriedades de fluidos, essencial para que o aplicativo pudesse dimensionar o trocador de calor.
Enfrentaram-se dificuldades na configuração dessa biblioteca para o PHP na tentativa de sua instalação em um sistema operacional de 32 bits (Raspbian), no qual se tentava rodar o servidor. O problema encontrado foi o da não possibilidade de se compilar a biblioteca em sistema operacional de 32 bits, por conta de flags de compilação para 64 bits. Além disso, a biblioteca em versões mais antigas não funcionava com as versões mais novas do PHP. Após inúmeras tentativas, optou-se por rodar o servidor no sistema operacional Ubuntu 18.04, de 64 bits, como comentado na seção 3.5.2.1, no qual não se encontraram mais problemas para instalação.
3.5.3 Algoritmo
Nesta seção, descrever-se-ão os algoritmos base para as principais funções adaptadas ou implementadas no PHP. Entende-se que todas as rotinas implementadas se baseiam nesses algoritmos com poucas mudanças.
As chaves “{“ e “}” indicam, respectivamente, o início e o final de um trecho de código de iteração ou de condição. Utilizou-se os colchetes “[“ e “]” para acessar índices das variáveis tipo vetor, de uma dimensão, ou matriz, de mais dimensões. Usou-se os parênteses “(“ e “)” para a transferência de parâmetros para as funções. O símbolo de reticências “...” indica que naquela parte do código ocorre uma sequência de operações
semelhantes. A seta “->” indica acesso a algum atributo ou método do objeto. O texto entre “/* */” indica o comentário da função da linha. 3.5.3.1 Solver
Mostra-se o algoritmo do solver no Quadro 7. Esta parte do aplicativo responsabiliza-se por realizar o dimensionamento, através da resolução do problema térmico, com base nos parâmetros passados. Quadro 7 - Algoritmo do solver.
Algoritmo
aguardar_requisicao_servidor() {} /* Arquivo aguarda requisição do servidor */
se(recebeu_requisicao == true) { /* Evento de requisição do servidor */
parametros[] =
converter_json_para_vetor_objeto(ler_parametros_recebidos()) /* Lê os parâmetros enviados junto à requisição, ou seja, os parâmetros de cálculo */
numero_de_sistemas = conta_tamanho(parametros[]) /* Verifica a quantidade de objetos de parâmetros, ou seja, quantos sistemas devem ser simulados */
iterar(de numero_iteracao_sistema = 1 ate numero_de_sistemas) { /* Iterador para buscar a solução para cada sistema a ser simulado */
se(checa_validade_parametros(parametros[numero_iteracao_sistema]) == valido) { /* Verifica se os parâmetros estão íntegros e se são compatíveis com o cálculo solicitado (API genérica) */
continua() } se_nao { retorna_erro() finaliza() }
parametros_si =
converter_unidades(parametros[numero_iteracao_sistema]) /* Realiza conversão dos parâmetros para o sistema internacional de medidas, para uso nos cálculos */
iterar(de numero_iteracao_passo 1 ate numero_passos) { /* O número de passos que serão dados no cálculo, o que define a precisão do cálculo. Por exemplo, para um tubo de 1 metro, 10 passos, significaria que os cálculos seriam realizados para 10 centímetros, 20 centímetros e assim em diante até 1 metro */
se(parametros_si->parametro_1 == condicao_1) { /* Verificações e cálculos: a partir desse trecho, o software faz verificações e direciona os cálculos, salva os valores em variáveis e realiza todos os cálculos para cada passo indicado */
variavel_1[numero_iteracao_passo] = calculo_CoolProp_caso_1() } se_nao { variavel_1[numero_iteracao_passo] = calculo_CoolProp_nao_caso_1() } ...
se(parametros_si->parametro_N == condicao_N) { /* Por exemplo, verifica se algum parâmetro é um valor ou outro, ou se está dentro de um range de valores, para ver qual função utilizar. Como não há um padrão de verificação, não se pôde utilizar outro loop */
variavel_N[numero_iteracao_passo] = calculo_CoolProp_caso_N()
/* Salva o valor de um resultado para aquele passo */
} se_nao {
variavel_N[numero_iteracao_passo] = calculo_CoolProp_nao_caso_N() }
}
resultados_sistemas[numero_iteracao_sistema] =
criar_objeto(variavel_1[]..., variavel_N[]) /* Salva um objeto com os resultados de cada passo para aquele sistema */
}
responder_para_servidor(converter_vetor_objeto_para_json(resultados_s istemas[])) /* Retorna os resultados para o solicitante através do servidor */
}
Fonte: do Autor (2019).
3.5.3.2 Sistema de Autenticação
Mostra-se o algoritmo do Sistema de Autenticação no Quadro 8. Programou-se esta parte do aplicativo para controlar os acessos ao aplicativo, direcionar os usuários para as páginas corretas e gerenciar as informações e permissões de usuários.
Quadro 8 - Algoritmo do Sistema de Autenticação. Algoritmo
aguardar_requisicao_servidor() {} /* Arquivo aguarda requisição do servidor */
se(recebeu_requisicao == true) { /* Evento de requisição do servidor */
parametros = converter_json_para_objeto(ler_parametros_recebidos()) /* Lê os parâmetros enviados junto à requisição, ou seja, os parâmetros da operação com usuários a ser realizada */
se(checa_validade_parametros(parametros == valido) { /* Verifica se os parâmetros estão íntegros e se são compatíveis com a operação com usuários solicitada (API genérica) */
continua() }
retorna_erro() finaliza() }
seleciona(parametros->funcao_escolhida) { /* Um seletor para escolher, dentre as funções escolhidas, qual será o direcionamento do código */
caso "login": /* Quando o usuário já é cadastrado e solicita um login */
se(checa_credenciais_usuario(parametros->username, parametros- >senha) == "ativo") {
cria_token_usuario(parametros->username) /* Um token para manter sua sessão ativa é criado */
redirecionar_usuario(parametros->nivel_acesso) /* Redireciona o usuário para a página inicial do seu nível de acesso */
}
se_nao() { retorna_erro() }
caso "logout": /* Deleta o token e torna o usuário inativo naquele dispositivo até um novo login */
deleta_token_usuario(parametros->username)
caso "novo_usuario": /* Quando o usuário se cadastra na ferramenta */
se(checa_informacoes(parametros) == "ok") {
solicita_insercao_usuario(parametros) /* O usuário é inserido na base de dados, mas ainda não pode acessar antes da aprovação do Administrador */
} se_nao {
}
caso "modificar_acesso": /* Função disponível para o Administrador, para alterar o status de algum usuário */
modificar_acesso(parametros->username, nivel)
caso "recuperar_senha": /* Quando o usuário perde a sua senha e deseja recuperá-la */
enviar_codigo_recuperacao(parametros->username, parametros- >informacoes_recuperacao)
caso "atualizar_senha": /* Quando o usuário pretende alterar a senha */
se(checa_informacoes(parametros) == "ok") { atualiza_senha(parametros->username, parametros->senha) } se_nao { retorna_erro() } }
responder_para_servidor(codigo_resposta) /* Retorna código de sucesso ou erro para o servidor */
}
Fonte: do Autor (2019).
3.5.3.3 Gerenciador do Banco de Dados
Mostra-se o algoritmo do Gerenciador do Banco de Dados no Quadro 9. Essa parte do código no back-end serve para executar queries e acessar os dados salvos no banco de dados do aplicativo, tanto na base de usuários quanto na base de documentação.
Quadro 9 - Algoritmo do Gerenciador do Banco de Dados. Algoritmo
aguardar_requisicao_servidor() {} /* Arquivo aguarda requisição do servidor */
se(recebeu_requisicao == true) { /* Evento de requisição do servidor */
parametros = converter_json_para_objeto(ler_parametros_recebidos()) /* Lê os parâmetros enviados junto à requisição, ou seja, os parâmetros da operação com usuários a ser realizada */
se(checa_validade_parametros(parametros == valido) { /* Verifica se os parâmetros estão íntegros e se são compatíveis com a operação de banco de dados solicitada (API genérica) */
continua() } se_nao { retorna_erro() finaliza() }
seleciona(parametros->funcao_escolhida) { /* Um seletor para escolher, dentre as funções escolhidas, qual será a query executada no banco de dados */
caso "inserção": /* Quando se deseja inserir algo na tabela */
query = "INSERE NA tabela_1 (colunas) VALORES (parametros- >valores)"
caso "remoção": /* Quando se deseja remover algo da tabela */
query = "DELETA DE tabela_1 ONDE coluna_1 = parametros- >condicoes[1]"
caso "edição": /* Quando se deseja atualizar algo na tabela */
query = "ATUALIZA tabela_1 COLOQUE coluna_1 = parametros- >valores[1] ONDE coluna_2 = parametros->condicoes[2]" caso "consulta": /* Quando se deseja ler dados da tabela */
query = "SELECIONA DE tabela_1 ONDE coluna_1 = parametros- >condicoes_1"
se(verifica_credenciais(parametros->usernameDB, parametros->senhaDB) == "ok") { /* Se as credenciais do usuário estão de acordo para se conectar, executa a query */
resultado = executar_query(parametros->query)
responder_para_servidor(converter_vetor_objeto_para_json(resultado)) /* Retorna resultados da consulta */
} se_nao { retorna_erro() } } Fonte: do Autor (2019). 3.5.4 Banco de dados
Como comentado anteriormente, necessitava-se a adição de níveis de acesso para diferentes usuários castrados na ferramenta. Além disso, precisava-se salvar informações de documentação.
3.5.4.1 Tabela de Usuários
Fez-se uma tabela para usuários com as seguintes colunas: “id” (tipo número inteiro), “email” (tipo string “VARCHAR”), “password” (tipo string “VARCHAR”), “access_level” (tipo número inteiro) e “token” (tipo string “VARCHAR”). A coluna de “id” incrementa-se automaticamente e serve como uma chave para cada linha da tabela, facilitando-se o acesso de informações. Além disso, para manter a segurança das senhas inseridas, armazenaram-se elas utilizando-se a criptografia MD5.
No Quadro 10, mostra-se o formato dessa tabela no banco de dados, populada com dados meramente ilustrativos.
Quadro 10 - Tabela de Usuários no Banco de Dados.
id email password access_level token
0 admin@domain.com 1e877f98d8b... 0 34vryr66 1 user1@domain.com 493e8f9a9c3... 1 53hg535 2 user2@domain.com 42354efaa44... 2 y34534g 3 user3@domain.com 65465efa841... 1 645huki Fonte: do Autor (2019).
Cada entrada da tabela é representada por uma linha. Tem-se que há apenas um usuário do tipo administrador, mas pode-se haver diferentes usuários de outros tipos. Cada novo usuário é cadastrado nessa base. 3.5.4.2 Tabela de Documentação
Fez-se uma tabela para armazenar a documentação com as seguintes colunas: “id” (tipo número inteiro) e “doc” (tipo string “VARCHAR”). A coluna “doc” salva o texto da documentação, em formato HTML.
No Quadro 11, mostra-se o formato dessa tabela no banco de dados, populada com dados meramente ilustrativos.
Quadro 11 - Tabela de Documentação no Banco de Dados.
id doc
0 <p> Lorem ipsum dolor sit amet, consectetur … </p> Fonte: do Autor (2019).
4 RESULTADOS