Monitore o clima com Node.js, Raspberry Pi e display LCD

O número de dispositivos domésticos inteligentes vendidos tem crescido continuamente nos últimos anos. Espera-se que 1,5 bilhão desses dispositivos sejam vendidos em 2021 . O número médio desses dispositivos por família inteligente é 8,7. Portanto, é bem possível que você tenha pelo menos vários desses dispositivos em casa.



Nesta área, os programadores têm algumas vantagens sobre outras pessoas, uma vez que os programadores podem criar dispositivos para uma casa inteligente de forma independente.







Temos à disposição componentes que nos permitem construir rapidamente uma ampla variedade de dispositivos. Quero falar aqui sobre como, usando um Raspberry Pi, um display LCD e algumas linhas de código, organiza o monitoramento do clima. Nosso sistema estará conectado à Internet, permitindo que você monitore o clima em qualquer lugar da Terra.



Pré-requisitos



Quero mostrar imediatamente o que consegui.



imagem


Sistema de monitoramento do clima em ação



Como este é um projeto DIY, você precisará obter algumas coisas antes de reproduzi-lo. Ou seja, estamos falando sobre o seguinte:



  • Raspberry Pi 3 (ou superior).
  • Tela de LCD.
  • Fios de conexão.
  • Resistência variável (opcional).
  • Placa de ensaio (opcional).


Agora vamos falar sobre como juntar tudo e configurá-lo.



Etapa 1. Preparando-se para trabalhar com a API ClimaCell e conectando o display à placa



O primeiro passo em nosso trabalho é obter uma chave para acessar a API ClimaCell e conectar o display à placa.



Aqui, usaremos a API ClimaCell Weather como fonte de dados meteorológicos . Esta API dá acesso a uma variedade de métricas, incluindo métricas de qualidade do ar.



Para trabalhar com a API ClimaCell, você precisa criar uma conta no site do projeto e obter uma chave de API que será usada para assinar solicitações ao sistema.





Limites da API ClimaCell O



registro no sistema é gratuito, você pode fazer até 100 solicitações por hora, o número de solicitações que podem ser realizadas diariamente é limitado a 1000. Isso é mais que suficiente para o nosso projeto.



Assim que tivermos a chave API à nossa disposição, podemos prosseguir para trabalhar com os componentes de hardware e começar a conectar o display LCD ao Raspberry Pi. Antes de conectar o monitor à placa, desligue a alimentação.



O layout das portas GPIO no Raspberry Pi 3 é mostrado na figura a seguir.









Diagrama da porta GPIO do Raspberry Pi 3 Aqui está um diagrama para conectar o monitor à placa.





Diagrama de



conexão do display à placa Com esta conexão, o display irá operar com brilho total e contraste total. O nível de brilho não é um problema, mas o contraste precisa de ajustes adicionais, caso contrário você não conseguirá distinguir nada na tela.



É por isso que precisamos de pelo menos um resistor variável com o qual ajustaremos o nível de contraste da tela.





Diagrama de fiação do resistor variável



Depois que o display for conectado à placa, podemos ligar o Raspberry Pi. Se tudo estiver conectado corretamente, o display será ligado. E com a ajuda de um resistor variável, podemos ajustar o nível de seu contraste.



Etapa 2. Preparando o projeto Node.js



A parte do nosso projeto de software será baseado em Node.js . Se o seu Raspberry Pi ainda não tem essa plataforma instalada, verifique este guia simples.



Crie uma nova pasta e execute o comando nela npm init -ypara inicializar um novo projeto Node.js. Em seguida, execute o comando npm install lcd node-fetchpara instalar as duas dependências de que precisamos.



  • O pacote lcdserá usado para organizar o trabalho com o display LCD.
  • node-fetchPrecisamos do pacote para fazer solicitações HTTP à API ClimaCell.


Foi dito acima que precisamos de uma chave de API para interagir com a API ClimaCell. Essa chave pode ser colocada no código do programa ou em um arquivo especial config.jsonprojetado para armazenar as configurações do projeto.



No caso de uso, config.jsonestamos falando sobre adicionar o seguinte a ele:



"cc_key": "<your_ClimaCell_API_key>"}


Agora, concluindo a etapa de preparação preliminar do projeto Node.js, vamos adicionar o seguinte código ao seu arquivo principal:



// * 
const Lcd = require("lcd");
const fs = require("fs");
const fetch = require("node-fetch");

// *  
const { cc_key } = JSON.parse(fs.readFileSync("./config.json"));


Etapa 3. Trabalhando com o display LCD



A saída de dados para um display LCD usando um pacote lcdé uma tarefa elementar. O pacote é uma camada de abstração acima dos mecanismos de exibição de baixo nível. O uso de tal pacote nos livra de ter que resolver uma série de pequenas tarefas ao exibir dados no visor.



Aqui está o código responsável por trabalhar com o monitor.



const lcd = new Lcd({ rs: 26, e: 19, data: [13, 6, 5, 11], cols: 16, rows: 2 });

function writeToLcd(col, row, data) {
  return new Promise((resolve, reject) => {
    lcd.setCursor(col, row);
    lcd.print(data, (err) => {
      if (err) {
        reject();
      }
      resolve();
    });
  });
}


Primeiro, criamos um objeto lcdpassando um objeto com parâmetros para o construtor apropriado, contendo, entre outras coisas, informações sobre os pinos usados ​​para conectar o monitor ao quadro.



Propriedades do objeto com parâmetros colse rowsespecificar o número de colunas e linhas da exibição. Ele usa uma tela de 16x2. Se você estiver usando outro monitor, por exemplo, um com 8 colunas e 1 linha, substitua os números 16 e 2, respectivamente, por 8 e 1.



Para exibir algo no monitor, você precisa usar os seguintes métodos de objeto em sequência lcd:



  • lcd.setCursor() - seleção da posição a partir da qual os dados serão exibidos.
  • lcd.print() - saída de dados.


Colocamos chamadas para essas funções em uma promessa para que possamos chamar as operações correspondentes de forma assíncrona usando a construção async / await.



Agora, você deve ser capaz de exibir algo no visor. Por exemplo, a execução do comando writeToLcd(0,0,'Hello World')deve resultar na exibição, na primeira linha, a partir da primeira coluna, de texto Hello World.



Etapa 4: Baixar informações meteorológicas e exibi-las



Vamos começar a baixar as informações meteorológicas e exibi-las no visor.



A plataforma ClimaCell fornece muitos indicadores meteorológicos e, além disso, informações sobre a qualidade do ar, informações sobre o nível de pólen no ar, sobre o nível de risco do tráfego, sobre incêndios. Temos muitos dados, mas não podemos esquecer que nosso display possui apenas 16 colunas e 2 linhas, ou seja, 32 caracteres.



Se você precisar exibir muitos dados em tal exibição e essa limitação parecer muito forte, você pode usar o efeito de rolagem.



imagem

Efeito scroll



Aqui, para não complicar o projeto, nos restringimos a exibir os seguintes dados na tela:



  • Data atual (hora, minuto, segundo).
  • Temperatura.
  • Intensidade de precipitação.


Aqui está o código responsável por carregar os dados e exibi-los:



function getWeatherData(apiKey, lat, lon) {
  const url = `https://api.climacell.co/v3/weather/realtime?lat=${lat}&lon=${lon}&unit_system=si&fields=temp&fields=precipitation&apikey=${apiKey}`;

  const res = await fetch(url);
  const data = await res.json();
  return data;
}

async function printWeatherData() {
  const { temp, precipitation } = await getWeatherData(cc_key, 45.658, 25.6012);

  // *  
  await writeToLcd(0, 0, Math.round(temp.value) + temp.units);

  // *  
  const precipitationMessage =
    "Precip.: " + precipitation.value + precipitation.units;
  await writeToLcd(0, 1, precipitationMessage);


Para obter dados meteorológicos do ClimaCell, por exemplo, para uma determinada cidade, você precisa passar as coordenadas geográficas para a API - latitude e longitude.



Para encontrar as coordenadas de sua cidade, você pode usar um serviço gratuito como latlong.net e salvar as coordenadas em um arquivo config.jsonjunto com a chave API. É bem possível inserir esses dados diretamente no código.



Os dados retornados pela API são assim:



{
  lat: 45.658,
  lon: 25.6012,
  temp: { value: 17.56, units: 'C' },
  precipitation: { value: 0.3478, units: 'mm/hr' },
  observation_time: { value: '2020-06-22T16:30:22.941Z' }
}


Este objeto, utilizando o mecanismo de atribuição de desestruturação, pode ser analisado e, tendo recebido informações sobre a temperatura e precipitação, exibir esta informação na primeira e segunda linhas do display.



Etapa 5. Concluindo o projeto



Basta modificar o código e, quando novos dados chegarem, atualizar as informações exibidas na tela.



async function main() {
  await printWeatherData();

  setInterval(() => {
    printWeatherData();
  }, 5 * 60 * 1000);

  setInterval(async () => {
    await writeToLcd(8, 0, new Date().toISOString().substring(11, 19));
  }, 1000);
}

lcd.on("ready", main);

// *     ctrl+c,     .
process.on("SIGINT", (_) => {
  lcd.close();
  process.exit();
});


Os dados meteorológicos são atualizados a cada 5 minutos. Mas, como o ClimaCell limita o número de solicitações feitas ao serviço a 100 solicitações por minuto, podemos ir ainda mais longe e atualizar os dados a cada minuto.



Podemos exibir o tempo usando uma das duas abordagens:



  • Você pode usar a propriedade do observation_timeobjeto proveniente da API e exibir a hora de chegada dos dados.
  • Você pode fazer um relógio real e exibir a hora atual.


Escolhi a segunda opção, mas você pode muito bem fazer o contrário.



Para exibir a hora na parte superior direita da tela, você primeiro precisa encontrar a coluna a partir da qual a exibição deve começar. Isso permitirá que os dados se ajustem perfeitamente ao espaço disponível na tela. Para encontrar o número da coluna, use a seguinte fórmula:



   -  ,   


O comprimento das informações de tempo é de 8 caracteres e, como a linha de exibição tem 16 caracteres, você precisa começar a exibir essas informações na coluna # 8.



O trabalho com o display é organizado de forma assíncrona. Portanto, para saber quando o display está inicializado e pronto para funcionar, devemos usar o método da biblioteca lcd.on().



Outra técnica recomendada para trabalhar com sistemas embarcados é liberar recursos quando o programa termina. É por isso que usamos um manipulador de eventos SIGINTpara liberar recursos de exibição quando o programa termina.



Existem outros eventos semelhantes:



  • SIGUSR1e SIGUSR2- para interceptação kill PID, como reiniciar nodemon.
  • uncaughtException - para capturar exceções não tratadas.


Etapa 6. Organização da operação de script contínua



Nosso script está pronto e já podemos rodar o programa. Mas ainda temos algo a fazer antes de declarar o projeto concluído.



Neste ponto, você provavelmente está conectado ao Raspberry Pi usando SSH ou diretamente. Mas independentemente de como você se conecta à placa, ao fechar o terminal, o programa irá parar.



Ao mesmo tempo, se você desligar o quadro e, em seguida, imediatamente ou depois de algum tempo, ligá-lo novamente, o script não será iniciado automaticamente. Você terá que iniciá-lo manualmente.



Para resolver esses problemas, podemos usar um gerenciador de processos como o pm2 .



Aqui está o que fazer:



  • Instalando pm2: sudo npm install pm2 -g
  • Crie um script de inicialização para pm2: sudo pm2 startup
  • Lançamento do aplicativo: pm2 start index.js
  • Salvar uma lista de processos entre reinicializações do servidor: pm2 save


O Raspberry Pi agora pode ser reiniciado. O script será executado depois que o dispositivo estiver pronto para uso.



Resultado



Agora você tem à sua disposição um sistema de monitoramento do clima, que pode customizar da forma que desejar. Se conhecer os dados meteorológicos for muito importante para você (ou se quiser se manter atualizado sobre outras métricas fornecidas pelo ClimaCell, como os níveis de poluição do ar), você pode criar uma caixa Raspberry Pi na qual também pode montar um display LCD. E então, tendo equipado essa estrutura com uma bateria, ela pode ser perfeitamente colocada em algum lugar.



A Raspberry Pi é uma placa que se parece muito com um computador normal. Você pode fazer coisas muito mais interessantes com ele do que normalmente faz com microcontroladores como o Arduino . Portanto, o Raspberry Pi é fácil de emparelhar com outros dispositivos que você possui.



Você está planejando fazer algo semelhante ao que foi discutido neste material?






All Articles