admin管理员组文章数量:1620366
之前发过esp32 2FA密码生成(TOTP方案),这里分享一种通过网页提交totp code,esp32接收到该code后与当前的code比对,一致则执行某操作,不一致则执行另一操作的方案。
void handleConfigWifi() {
//返回http状态
//server.send(200, "text/html", SUCCESS_HTML);
if (esp32_server.hasArg("totpkey")) {//判断是否有账号参数
Serial.print("GOT TOTP KEY:");
String totpkey = esp32_server.arg("totpkey"); //获取html表单输入框name名为"totpkey"的内容
// strcpy(sta_ssid, server.arg("ssid").c_str());//将账号参数拷贝到sta_ssid中
Serial.println(totpkey);
if (totpCode == totpkey) {
Serial.println("秘钥正确");
esp32_server.send(200, "text/plain", "TOTP CODE RIGHT");//向浏览器返回结果正确
//在这里添加秘钥正确后执行的操作
}
else {
Serial.println("秘钥错误");
esp32_server.send(200, "text/plain", "TOTP CODE ERROR");//向浏览器返回结果错误
//在这里添加秘钥错误后执行的操作
}
} else { //没有参数
Serial.println("error,not fund TOTP CODE");
esp32_server.send(200, "text/html", "<meta charset='UTF-8'>error,error,not fund TOTP CODE");//返回错误页面
return;
}
}
该代码为对输入秘钥的比对功能,全部代码见文末。
实现了以下功能:
1:esp32 AP与STA共存,连接wifi的同时打开AP,可通过两种方案访问网页。
2:totp code的生成。
3:建立web服务器,由网页输入totp code,点击按钮提交。
4:esp32接收到网页发过来的code,与自己生成的对比,执行相关操作,并向网页返回相关结果。
可以自行添加例如打开继电器,关闭继电器,向某个服务器发送消息等功能。
图一输入界面
图二正确界面
图三错误界面
完整代码如下:
#include<WiFi.h>
#include<WebServer.h>
#include <NTPClient.h>
#include <TOTP.h>
WebServer esp32_server(80); //声明一个 WebServer 的对象,对象的名称为 esp32_server
//设置网络服务器响应HTTP请求的端口号为 80
//定义根目录首页网页HTML源代码
#define ROOT_HTML "<!DOCTYPE html><html><head><title></title><meta name=\"viewport\" content=\"width=device-width, initial-scale=1\"></head><style type=\"text/css\">.input{display: block; margin-top: 10px;}.input span{width: 100px; float: left; float: left; height: 36px; line-height: 36px;}.input input{height: 30px;width: 200px;}.btn{width: 120px; height: 35px; background-color: #000000; border:0px; color:#ffffff; margin-top:15px; margin-left:100px;}</style><body><form method=\"POST\" action=\"TOTP\"><label class=\"input\"><span>TOTP KEY</span><input type=\"text\" name=\"totpkey\" value=\"\"></label><input class=\"btn\" type=\"submit\" name=\"submit\" value=\"Submie\"> <p><span></form>"
//设置wifi
const char *AP_SSID = "test";
const char *AP_Password = "";//ap的ssid和密码,这里设置空则为无密码
char ssid[] = "ssid";
char password[] = "password"; //要连接的ssid和密码
uint8_t hmacKey[] = {0x73, 0x65, 0x63, 0x72, 0x65, 0x74, 0x6b, 0x65, 0x79, 0x30};
WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP);
TOTP totp = TOTP(hmacKey, 10);
String totpCode = String("");
void handleRoot() //该函数内为处理网站根目录 “/” 时所执行的内容
{
Serial.print("客户端访问!");
esp32_server.send(200, "text/html", ROOT_HTML "</body></html>");
}
void handleFound()
{
esp32_server.send(200, "text/html", ROOT_HTML "</body></html>");
}
void handleConfigWifi() {
//返回http状态
//server.send(200, "text/html", SUCCESS_HTML);
if (esp32_server.hasArg("totpkey")) {//判断是否有账号参数
Serial.print("GOT TOTP KEY:");
String totpkey = esp32_server.arg("totpkey"); //获取html表单输入框name名为"ssid"的内容
// strcpy(sta_ssid, server.arg("ssid").c_str());//将账号参数拷贝到sta_ssid中
Serial.println(totpkey);
if (totpCode == totpkey) {
Serial.println("秘钥正确");
esp32_server.send(200, "text/plain", "TOTP CODE RIGHT");//向浏览器返回结果正确
//在这里添加秘钥正确后执行的操作
}
else {
Serial.println("秘钥错误");
esp32_server.send(200, "text/plain", "TOTP CODE ERROR");//向浏览器返回结果错误
//在这里添加秘钥错误后执行的操作
}
} else { //没有参数
Serial.println("error, not found ssid");
esp32_server.send(200, "text/html", "<meta charset='UTF-8'>error, not found ssid");//返回错误页面
return;
}
}
// 设置处理404情况的函数'handleNotFound'
void handleNotFound() { // 当浏览器请求的网络资源无法在服务器找到时通过此自定义函数处理
handleRoot(); //访问不存在目录则返回配置页面
// server.send(404, "text/plain", "404: Not found");
}
void setup() {
// put your setup code here, to run once:
Serial.begin(115200); //初始化串口通信并设置波特率为115200
WiFi.mode(WIFI_AP_STA);//设置ap和sta共存模式
WiFi.softAP(AP_SSID, AP_Password); //设置AP模式热点的名称和密码,密码可不填则发出的热点为无密码热点
Serial.print("\n ESP32建立的wifi名称为:");
Serial.print(AP_SSID); //串口输出ESP32建立的wifi的名称
Serial.print("\nESP32建立wifi的IP地址为:");
Serial.print(WiFi.softAPIP()); //串口输出热点的IP地址
WiFi.begin(ssid, password);//连接2wifi
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.println("Establishing connection to WiFi...");
}
Serial.print("Connected to WiFi with IP: ");
Serial.println(WiFi.localIP());
Serial.println();
esp32_server.on("/", HTTP_GET, handleRoot); // 当浏览器请求服务器根目录(网站首页)时调用自定义函数handleRoot处理,设置主页回调函数,必须添加第二个参数HTTP_GET,否则无法强制门户
esp32_server.on("/TOTP", HTTP_POST, handleConfigWifi); // 当浏览器请求服务器/configwifi(表单字段)目录时调用自定义函数handleConfigWifi处理
esp32_server.onNotFound(handleNotFound); //当浏览器请求的网络资源无法在服务器找到时调用自定义函数handleNotFound处理
//Tells the server to begin listening for incoming connections.Returns None
esp32_server.begin(); //启动WEB SERVER
timeClient.begin();
}
void loop() {
// put your main code here, to run repeatedly:
esp32_server.handleClient();
timeClient.update();
// 生成 TOTP 代码,如果与前一个代码不同,则串口输出
String newCode = String(totp.getCode(timeClient.getEpochTime()));
if (totpCode != newCode) {
totpCode = String(newCode);
Serial.print("TOTP code: ");
Serial.println(newCode);//串口输出totpcode,可以删除
}
}
版权声明:本文标题:基于ESP32的web网页输入2FA密码验证(TOTP方案) 内容由热心网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:https://www.elefans.com/dianzi/1728818143a1175147.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论