//Đây là code Wokwi
#include <WiFi.h>
#include <PubSubClient.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include "DHT.h"
// Wi-Fi credentials
const char* ssid = "Wokwi-GUEST";
const char* password = "";
// MQTT Broker details
const char* MQTTServer = "test.mosquitto.org";
const char* MQTT_ID = "ESP32_Client";
int Port = 1883;
// Pin definitions
#define DHTPIN 15
#define DHTTYPE DHT22
// Initialize objects
WiFiClient espClient;
PubSubClient client(espClient);
LiquidCrystal_I2C lcd(0x27, 20, 4); // LCD I2C address and size
DHT dht(DHTPIN, DHTTYPE);
// Function to connect to Wi-Fi
void WIFIConnect() {
lcd.setCursor(0, 0);
lcd.print("Connecting WiFi...");
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
lcd.print(".");
}
lcd.clear();
lcd.setCursor(0, 0);
lcd.print("WiFi connected!");
lcd.setCursor(0, 1);
lcd.print("IP: ");
lcd.print(WiFi.localIP());
}
// Function to reconnect to MQTT broker
void MQTT_Reconnect() {
while (!client.connected()) {
lcd.setCursor(0, 2);
lcd.print("Connecting MQTT...");
if (client.connect(MQTT_ID)) {
lcd.setCursor(0, 2);
lcd.print("MQTT connected! ");
} else {
lcd.setCursor(0, 2);
lcd.print("MQTT failed. Retry");
delay(5000);
}
}
}
void setup() {
Serial.begin(115200);
lcd.init();
lcd.backlight();
dht.begin();
// Connect to Wi-Fi and MQTT
WIFIConnect();
client.setServer(MQTTServer, Port);
}
void loop() {
// Reconnect if disconnected
if (!client.connected()) {
MQTT_Reconnect();
}
client.loop();
// Read DHT sensor data
float temperature = dht.readTemperature();
float humidity = dht.readHumidity();
// Generate random wind speed and pressure data
float windSpeed = random(0, 150) / 10.0; // Random wind speed (m/s)
float pressure = random(950, 1050); // Random pressure (hPa)
// Check if readings are valid
if (isnan(temperature) || isnan(humidity)) {
Serial.println("Error reading from DHT sensor!");
} else {
// Display sensor values on serial monitor
Serial.print("Temperature: ");
Serial.print(temperature);
Serial.println(" °C");
Serial.print("Humidity: ");
Serial.print(humidity);
Serial.println(" %");
Serial.print("Wind Speed: ");
Serial.print(windSpeed);
Serial.println(" m/s");
Serial.print("Pressure: ");
Serial.print(pressure);
Serial.println(" hPa");
// Publish data to MQTT
char payload[100];
snprintf(payload, sizeof(payload), "{\"temperature\":%.2f,\"humidity\":%.2f,\"windSpeed\":%.2f,\"pressure\":%.2f}",
temperature, humidity, windSpeed, pressure);
client.publish("esp32/sensors", payload);
}
delay(2000); // Delay to avoid flooding
}
//Đây là code python
import paho.mqtt.client as mqtt
import mysql.connector
import json
import hashlib
from datetime import datetime
# Kết nối MySQL
def connect_db():
return mysql.connector.connect(
host="localhost", # Thay bằng host của bạn
user="root", # Thay bằng user MySQL của bạn
password="", # Thay bằng mật khẩu MySQL của bạn
database="weather_monitoring" # Thay bằng tên database của bạn
)
# Xử lý dữ liệu khi nhận được từ MQTT
def on_message(client, userdata, msg):
try:
data = json.loads(msg.payload.decode("utf-8"))
temperature = data.get("temperature")
humidity = data.get("humidity")
wind_speed = data.get("windSpeed")
pressure = data.get("pressure")
id_user = 1 # ID người dùng giả định, có thể thay đổi
id_weather = 1 # ID điều kiện thời tiết giả định, có thể thay đổi
created_at = datetime.now().strftime('%Y-%m-%d %H:%M:%S')
conn = connect_db()
cursor = conn.cursor()
sql = """
INSERT INTO sensor_data (temp_value, humidity_value, pressure_value, wind_value, created_at, id_user, id_weather)
VALUES (%s, %s, %s, %s, %s, %s, %s)
"""
cursor.execute(sql, (temperature, humidity, pressure, wind_speed, created_at, id_user, id_weather))
conn.commit()
print(
f"Dữ liệu đã lưu: Temperature={temperature}, Humidity={humidity}, Wind Speed={wind_speed}, Pressure={pressure}, Created At={created_at}")
cursor.close()
conn.close()
except Exception as e:
print("Lỗi xử lý dữ liệu:", str(e))
# Cấu hình MQTT
MQTT_BROKER = "test.mosquitto.org"
MQTT_TOPIC = "esp32/sensors"
client = mqtt.Client()
client.on_message = on_message
# Kết nối MQTT
def start_mqtt():
client.connect(MQTT_BROKER, 1883, 60)
client.subscribe(MQTT_TOPIC)
client.loop_forever()
if __name__ == "__main__":
print("Đang lắng nghe dữ liệu từ MQTT...")
start_mqtt()
//Đây là code web
// connect.php
<?php
// Kết nối tới cơ sở dữ liệu MySQL
$servername = "localhost";
$username = "root";
$password = "";
$dbname = "weather_monitoring";
try {
$conn = new PDO("mysql:host=$servername;dbname=$dbname", $username, $password);
// Thiết lập chế độ lỗi PDO
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
// Truy vấn lấy 4 bản ghi mới nhất từ bảng sensor_data
$stmt = $conn->prepare("SELECT temp_value, humidity_value, pressure_value, wind_value, created_at
FROM sensor_data ORDER BY created_at DESC LIMIT 1");
$stmt->execute();
// Lấy tất cả các kết quả
$data = $stmt->fetchAll(PDO::FETCH_ASSOC);
} catch(PDOException $e) {
echo "Lỗi kết nối: " . $e->getMessage();
}
// Đóng kết nối
$conn = null;
?>
//data_display.php
<?php
include('connect.php');
?>
<!DOCTYPE html>
<html lang="vi">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Weather Monitoring</title>
<style>
table {
width: 100%;
border-collapse: collapse;
}
table, th, td {
border: 1px solid black;
}
th, td {
padding: 10px;
text-align: center;
}
h2 {
text-align: center;
}
</style>
</head>
<body>
<h2>Dữ liệu cảm biến mới nhất</h2>
<table>
<thead>
<tr>
<th>Temperature (°C)</th>
<th>Humidity (%)</th>
<th>Pressure (hPa)</th>
<th>Wind Speed (m/s)</th>
<th>Created At</th>
</tr>
</thead>
<tbody>
<?php
if (!empty($data)) {
foreach ($data as $row) {
echo "<tr>";
echo "<td>" . htmlspecialchars($row['temp_value']) . "</td>";
echo "<td>" . htmlspecialchars($row['humidity_value']) . "</td>";
echo "<td>" . htmlspecialchars($row['pressure_value']) . "</td>";
echo "<td>" . htmlspecialchars($row['wind_value']) . "</td>";
echo "<td>" . htmlspecialchars($row['created_at']) . "</td>";
echo "</tr>";
}
} else {
echo "<tr><td colspan='5'>Không có dữ liệu</td></tr>";
}
?>
</tbody>
</table>
</body>
</html>
//Cơ sở dữ liệu:
Tên bảng: users
Tên cột Kiểu dữ liệu Mô tả
id_user int Khóa chính; Tự động tăng
first_name varchar(50)
full_name varchar(50)
email varchar(50)
password varchar(50) Mã hóa MD5
permissions int 1 là "Admin", 0 là "User"
Bảng sensor_data
Table name: sensor_data
Column name Data type Description
id_data int Khóa chính, tự động tăng
temp_value float
humidity_ value float
pressure_value float
wind_value float
created_at timeslap
id_user int Khóa ngoại
id_ weather int Khóa ngoại
Bảng weather
Table name: weather
Column name Data type Description
id_ weather int Khóa chính, tự động tăng
name varchar(50)
description varchar(50)