Introdução
Um Web server é o local onde as páginas da web são armazenadas, as requisições são processadas e os serviços são oferecidos aos clientes da web. Embora as palavras “web” e “Internet” estejam intimamente relacionadas, elas não significam exatamente a mesma coisa. A Internet se refere à rede de computadores por onde trafegam diversos serviços diariamente. Já a World Wide Web (WWW), ou simplesmente Web, é uma camada acima da Internet, onde são construídas aplicações (como áudio, vídeo e texto) usando-se a Web como base. Um exemplo de aplicação é o navegador da web.
As páginas da web fazem parte desse contexto e são formatadas em uma linguagem de marcação chamada Hypertext Markup Language (HTML). Elas podem incluir estilos para dar identidade à aplicação web. O servidor web utiliza esses componentes para fornecer o conteúdo ao usuário. O protocolo utilizado para as requisições é conhecido como Hypertext Transfer Protocol (HTTP), que gerencia o processo de comunicação sempre que o usuário interage com a aplicação.
Neste artigo, mostraremos como criar um Web Server utilizando a Franzininho WiFi e exploraremos as possibilidades de uso em IoT, tornando seu projeto mais robusto. Acompanhe o projeto proposto nas próximas seções.
Biblioteca WebServer
Os métodos utilizado pela biblioteca “WebServer.h” no exemplo de projeto serão apresentados seguir:
begin()
Inicia o servidor, esse método normalmente é chamado após configuramos os elementos presente dentro do serviço a ser atendido, ou seja, quando cliente solicita as requisições.
void server.begin(void);
send()
Envia resposta ao cliente, neste caso quem acessa o server recebe a resposta enviada por esse método.
void server.send(int code,char *contet_type, char String& content);
- code : código de resposta HTTP, pode ser 200 (HTTP OK) ou 404 (HTTP SERVER NOT FOUND)
- contet_type : tipo de conteúdo da página, por exemplo : “text/plain” ou “image/png”
- contet : tipo de conteúdo, ou seja, a própria página em HTML
on()
Método para acessar a URL quando é realizado as requisições HTTP.
void server.on(const Uri &uri,THandlerFunction fn);
- uri : caminho para a URL, “/” indica que receberá as requisições do root
- fn : ponteiro para a função que vai ser chamada quando o servidor estiver ativo
handlerClient()
Responsável por detectar as solicitações HTTP, cria e notifica os eventos para os métodos on() e onNotFound().
void server.handlerClient(void);
onNotFound()
Aponta para a função quando o handler não é alocado.
void server.onNotFound(THandlerFunction fn);
- fn : ponteiro para a função
Materiais necessários
Para desenvolver nossa aplicação os materiais utilizados foram:
- Placa Franzininho WiFi
- LDR
- Resistor 10k ohms
- Jumpers
- Arduino IDE
Circuito
O circuito utilizado para este artigo será a placa Franzininho WiFi, o fotoresistor (LDR) para capturar a quantidade de luz captada no ambiente e para auxiliar no debug vamos usar o monitor serial do Arduino IDE.
Código
No projeto proposto, utilizaremos a Franzininho WiFi conectada à rede local para criar um Web Server que exibirá a intensidade luminosa a partir do LDR. Para isso, é necessário conectar a Franzininho à rede utilizando as credenciais da sua rede. Em seguida, copie o endereço IP apresentado no monitor serial (Figura 1) e cole-o no navegador de sua preferência (Figura 2).
#include "WiFi.h"
#include <WebServer.h>
#define LDR_PIN 3 // Define o pino do LDR
#define MIN_ANALOG 0
#define MAX_ANALOG 4096
#define MIN_PERCENT 0
#define MAX_PERCENT 100
// Configurações da rede Wi-Fi
const char *ssid = "sua rede local";
const char *password = "senha da rede local";
// Declara o objeto WebServer
WebServer server(80);
// Variável para armazenar a porcentagem de luz
int light_percent = 0;
// Função para retornar a página HTML com a porcentagem de luz
String html_page(int percent)
{
String index = "<!DOCTYPE html><html>\n";
index += "<head><meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0, user-scalable=no\">\n";
index += "<title>Franzininho WiFi Web Server</title>\n";
index += "<style>html { font-family: Helvetica; display: inline-block; margin: 0px auto; text-align: center;}\n";
index += "body{margin-top: 50px;} h1 {color: #37973f;margin: 50px auto 30px;}\n";
index += "p {font-size: 24px;color: #000000;margin-bottom: 10px;}\n";
index += "div { background-color: lightgrey;width: 400px;border: 20px solid green;padding: 30px;margin: 20px;}\n";
index += "</style>\n";
index += "</head>\n";
index += "<body>\n";
index += "<div id=\"franzininho_webpage\">\n";
index += "<h1>Franzininho WiFi Web Server</h1>\n";
index += "<p>Intensidade luminosa: ";
index += (int)percent;
index += " %</p>";
index += "</div>\n";
index += "</body>\n";
index += "</html>\n";
return index;
}
// Manipulador para a página principal
void handle_on_connect()
{
server.send(200, "text/html", html_page(light_percent));
}
// Manipulador para páginas não encontradas
void handle_not_found()
{
server.send(404, "text/plain", "Página não encontrada");
}
void setup()
{
Serial.begin(115200);
// Configura o driver WiFi para o modo Station
WiFi.mode(WIFI_STA);
// Inicializa o driver e conecta-se à rede local
WiFi.begin(ssid, password);
delay(5000);
// Aguarda até que esteja conectado à rede local
while (WiFi.status() != WL_CONNECTED)
{
Serial.println("Aguarde conectar-se à rede...");
delay(500);
}
// Imprime o endereço IP na serial
Serial.println("Conectado com sucesso!");
Serial.print("IP: ");
Serial.println(WiFi.localIP());
// Adiciona a função "handle_on_connect" quando o servidor estiver online
server.on("/", handle_on_connect);
// Adiciona a função "handle_not_found" quando o servidor estiver offline
server.onNotFound(handle_not_found);
// Inicia o servidor
server.begin();
// Informa que o Web Server foi inicializado
Serial.println("Web Server Ativo");
}
void loop()
{
// Trata as requisições HTTP e sinaliza os eventos
server.handleClient();
// Realiza uma conversão do valor de tensão para valor em percentual
light_percent = map(analogRead(LDR_PIN), MAX_ANALOG, MIN_ANALOG, MIN_PERCENT, MAX_PERCENT);
// Aguarda 5 milisegundos
delay(5);
}
Para acompanhar o funcionamento do projeto, abra o monitor serial e verifique as etapas de criação do servidor. Abaixo, você encontrará o endereço IP da Franzininho. Se você desejar configurar um endereço IP estático, consulte nosso artigo “Franzininho WiFi: Station“, onde mostramos como realizar essa configuração.
Abaixo, podemos ver o resultado ao acessar o servidor e a página HTML criada.
Figura 2: Página em HTML do serverExplicação do Código
Nesta seção, vamos explicar o código linha por linha, para garantir uma compreensão completa e entender a finalidade de cada função utilizada.
Inclui as bibliotecas para o driver WiFi e para o WebServer. Estas duas bibliotecas vão nos permitir utilizar os métodos para estabelecer uma conexão com a rede local e configurar o server e tratar as requisições HTTP sem preocupar-se com camadas mais baixas do protocolo, respectivamente.
#include "WiFi.h"
#include <WebServer.h>Declara as variáveis para receber as credenciais da rede (nome e senha).
// Configurações da rede Wi-Fi
const char *ssid = "sua rede local";
const char *password = "senha da rede local";Definimos os máximos e os mínimos da leitura analógica e o percentual mínimo e máximo para captação luminosa.
// Define o pino do LDR
#define LDR_PIN 3
#define MIN_ANALOG 0
#define MAX_ANALOG 4096
#define MIN_PERCENT 0
#define MAX_PERCENT 100Declara o objeto e recebe como parâmetro a porta do servidor que estará recebendo as requisições, entenda como porta apenas um canal de comunicação específico.
// Declara o objeto WebServer
WebServer server(80);Declara a variavel para receber o valor do percentual de luminosidade.
// Variável para armazenar a porcentagem de luz
int light_percent = 0;Função responsável por conter a página em HTML, inclui: cabeçalho (head), estilo (style) e corpo (body). Retorna uma String e recebe como parâmetro os valores de temperatura.
// Função para retornar a página HTML com a porcentagem de luz
String html_page(int percent)
{
String index = "<!DOCTYPE html><html>\n";
index += "<head><meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0, user-scalable=no\">\n";
index += "<title>Franzininho WiFi Web Server</title>\n";
index += "<style>html { font-family: Helvetica; display: inline-block; margin: 0px auto; text-align: center;}\n";
index += "body{margin-top: 50px;} h1 {color: #37973f;margin: 50px auto 30px;}\n";
index += "p {font-size: 24px;color: #000000;margin-bottom: 10px;}\n";
index += "div { background-color: lightgrey;width: 400px;border: 20px solid green;padding: 30px;margin: 20px;}\n";
index += "</style>\n";
index += "</head>\n";
index += "<body>\n";
index += "<div id=\"franzininho_webpage\">\n";
index += "<h1>Franzininho WiFi Web Server</h1>\n";
index += "<p>Intensidade luminosa: ";
index += (int)percent;
index += " %</p>";
index += "</div>\n";
index += "</body>\n";
index += "</html>\n";
return index;
}Função responsável por enviar ao cliente, neste caso quem acessa o endereço de IP, para renderizar uma página em HTML com o valor de temperatura.
// Manipulador para a página principal
void handle_on_connect()
{
server.send(200, "text/html", html_page(light_percent));
}
Função responsável por enviar ao cliente uma mensagem (“Página não encontrada”) quando o handler não é alocado.
// Manipulador para páginas não encontradas
void handle_not_found()
{
server.send(404, "text/plain", "Página não encontrada");
}No setup(), vamos inicializar o canal Serial na velocidade de 115200 bps, configurar o WiFi no modo Station e inicializar o drive para conectar-se à rede local. Em seguida vamos aguardar a conexão à rede até que a Franzininho estabeleça o canal de comunicação com o roteador. O driver do WiFi funciona por eventos, ou seja, sequências de ações notificadas a partir de estados. Desta forma utilizamos o WiFi.status() para monitorar como está o estado atual.
Após entrar na rede local vamos, mostrando no monitor Serial o endereço de IP registrado, como apresentado na figura 2.
Por último, vamos fazer a chamadas dos métodos para apontar a função responsável por criar a página em HTML quando a URL foi acessada (server.on), quando o client não consegue ter acesso ao server apontamos a função responsável por retornar o uma mensagem informando a falha (server.onNotFound) e por fim inicializamos o server (server.begin).
void setup()
{
Serial.begin(115200);
// Configura o driver WiFi para o modo Station
WiFi.mode(WIFI_STA);
// Inicializa o driver e conecta-se à rede local
WiFi.begin(ssid, password);
delay(5000);
// Aguarda até que esteja conectado à rede local
while (WiFi.status() != WL_CONNECTED)
{
Serial.println("Aguarde conectar-se à rede...");
delay(500);
}
// Imprime o endereço IP na serial
Serial.println("Conectado com sucesso!");
Serial.print("IP: ");
Serial.println(WiFi.localIP());
// Adiciona a função "handle_on_connect" quando o servidor estiver online
server.on("/", handle_on_connect);
// Adiciona a função "handle_not_found" quando o servidor estiver offline
server.onNotFound(handle_not_found);
// Inicia o servidor
server.begin();
// Informa que o Web Server foi inicializado
Serial.println("Web Server Ativo");
}No void loop, vamos aguardar as requisições HTTP sempre que o cliente desejar acessar o servidor. Recebe o valor percentual de luminosidade, para isso vamos utilizar a função map para converter as leituras analógicas em valores percentuais entre 0 a 100.
void loop()
{
// Trata as requisições HTTP e sinaliza os eventos
server.handleClient();
// Realiza uma conversão do valor de tensão para valor em percentual
light_percent = map(analogRead(LDR_PIN), MAX_ANALOG, MIN_ANALOG, MIN_PERCENT, MAX_PERCENT);
// Aguarda 5 milisegundos
delay(5);
}Conclusão
Neste artigo, mostramos como criar um servidor utilizando o Franzininho WiFi na rede local. Para aqueles leitores que não estão familiarizados com a estruturação de um arquivo HTML, pode haver alguma dificuldade, mas existem várias ferramentas online disponíveis que podem ajudar e servir como fonte de pesquisa.
Convidamos você a explorar os outros recursos da biblioteca Web Server, a fim de criar aplicações mais robustas e também compartilhar seus resultados com a comunidade por meio de artigos ou vídeos.





