
Quản lý thư viện và version cho dự án IoT
Vì sao pin version thư viện quan trọng với dự án IoT: dùng Arduino Library Manager và PlatformIO lib_deps để khoá đúng phiên bản DHT sensor library, tránh lỗi "chạy trên máy này nhưng qua máy khác thì không chạy".
Một bản build chạy tốt hôm nay có thể vỡ vào tuần sau chỉ vì thư viện tự cập nhật lên version mới có breaking change. Bài này giải thích cách quản lý thư viện trong Arduino IDE (Library Manager) và PlatformIO (lib_deps với version pin), minh hoạ bằng firmware đọc DHT22 phụ thuộc "DHT sensor library" và "Adafruit Unified Sensor".
Hướng dẫn chi tiết
Vì sao pin version thư viện quan trọng: dùng Arduino Library Manager và PlatformIO lib_deps để khoá đúng phiên bản DHT sensor library, tránh breaking change bất ngờ.
1. Giới thiệu
Một bản build chạy tốt hôm nay có thể vỡ vào tuần sau chỉ vì thư viện tự cập nhật lên version mới có breaking change - đây là kiểu lỗi "chạy trên máy tôi nhưng không chạy trên máy bạn" rất phổ biến khi nhiều người cùng làm một dự án IoT, hoặc khi quay lại một project cũ sau vài tháng. Bài này giải thích cách quản lý thư viện trong Arduino IDE (Library Manager) và PlatformIO (lib_deps với version pin), minh hoạ bằng firmware đọc DHT22 phụ thuộc hai thư viện: "DHT sensor library" và "Adafruit Unified Sensor".
2. Linh kiện cần có
| Linh kiện | Số lượng | Giá tham khảo |
|---|---|---|
| ESP32 DevKit V4 (ESP32-WROOM-32) | 1 | ~75.000 - 120.000đ |
| Cảm biến DHT22 (AM2302) | 1 | ~45.000 - 70.000đ |
| Dây jumper cái - đực | 3 | ~5.000đ |
3. Sơ đồ kết nối
| DHT22 | ESP32 DevKit V4 |
|---|---|
| VCC | 3V3 |
| GND | GND |
| DATA | GPIO4 |
Cấp nguồn DHT22 bằng 3.3V, không dùng 5V - chân DATA giao tiếp trực tiếp với GPIO 3.3V của ESP32.
4. Vì sao version thư viện quan trọng
Firmware đọc DHT22 trong bài này phụ thuộc 2 thư viện: "DHT sensor library" (đọc giao thức 1-Wire của DHT11/DHT22) và "Adafruit Unified Sensor" (interface chuẩn hoá mà DHT sensor library dùng bên trong). Nếu không khai báo version cụ thể:
- Arduino Library Manager có thể tự đề xuất cập nhật lên version mới nhất mỗi khi bạn mở IDE.
- Một thay đổi API nhỏ ở bản mới (đổi tên hàm, đổi kiểu trả về) có thể khiến code cũ không compile được nữa, dù bạn không hề sửa file
.ino. - Hai máy tính cùng mở project nhưng cài thư viện ở hai thời điểm khác nhau sẽ có version khác nhau - rất khó tái hiện lỗi khi debug cùng nhau.
5. Code ví dụ #1 — quản lý version qua Arduino Library Manager
Trong Arduino IDE: Sketch → Include Library → Manage Libraries (Ctrl+Shift+I). Library Manager hiển thị version đang cài và cho phép chọn version cụ thể từ dropdown thay vì luôn lấy bản mới nhất:
Library Manager -> tim "DHT sensor library" (tac gia Adafruit)
-> chon dropdown Version -> chon dung "1.4.4" thay vi "Install latest"
-> lam tuong tu voi "Adafruit Unified Sensor" -> chon "1.1.9"
Arduino IDE không có file khai báo dependency như package.json hay platformio.ini - version bạn chọn chỉ tồn tại trên máy đang cài, không tự động chia sẻ cho người khác. Vì vậy nên ghi rõ version đã test trong comment đầu file .ino hoặc trong README của project để người khác biết cần cài version nào.
6. Code ví dụ #2 — pin version bằng platformio.ini (lib_deps)
PlatformIO giải quyết triệt để vấn đề trên: version thư viện được khai báo ngay trong file cấu hình, đi theo project khi bạn commit lên git:
; platformio.ini - vi du "pin" version thu vien chinh xac (khong dung dau ^)
; De tai hien duoc build sau nay, khoa dung 1 version thay vi cho phep tu dong len ban moi.
[env:esp32dev]
platform = espressif32
board = esp32dev
framework = arduino
monitor_speed = 115200
; Pin dung version (KHONG dung ^1.4.4 - dau ^ cho phep minor/patch tu do len version moi
; va co the mang breaking change ma ban khong hay biet).
lib_deps =
adafruit/DHT sensor library@1.4.4
adafruit/Adafruit Unified Sensor@1.1.9
So sánh hai cách viết version trong lib_deps:
| Cú pháp | Ý nghĩa | Khi nào nên dùng |
|---|---|---|
@1.4.4 | Pin đúng version 1.4.4, không tự nâng cấp | Dự án đã ổn định, cần build lặp lại giống hệt (production, CI) |
@^1.4.4 | Cho phép tự lấy bản mới nhất cùng major version (1.x.x) | Đang phát triển, muốn nhận bản vá lỗi mới mà không đổi API lớn |
| Không ghi version | Luôn lấy bản mới nhất tại thời điểm build | Không khuyến khích cho dự án IoT cần tái hiện được kết quả |
7. Code ví dụ #3 — firmware dùng thư viện đã pin version
// src/main.cpp - firmware doc DHT22, phu thuoc thu vien duoc pin dung version
// (xem platformio.ini: lib_deps khoa dung "1.4.4" va "1.1.9", khong dung dau ^)
#include <Arduino.h>
#include <DHT.h>
#define DHT_PIN 4
#define DHT_TYPE DHT22
DHT dht(DHT_PIN, DHT_TYPE);
unsigned long lastReadAt = 0;
const unsigned long READ_INTERVAL_MS = 2000;
void setup() {
Serial.begin(115200);
delay(300);
Serial.println(F("=== Firmware voi thu vien duoc pin version ==="));
Serial.println(F("DHT sensor library@1.4.4 + Adafruit Unified Sensor@1.1.9"));
dht.begin();
}
void loop() {
unsigned long now = millis();
if (now - lastReadAt < READ_INTERVAL_MS) {
return;
}
lastReadAt = now;
float humidity = dht.readHumidity();
float tempC = dht.readTemperature();
if (isnan(humidity) || isnan(tempC)) {
Serial.println(F("[WARN] Doc DHT22 that bai"));
return;
}
Serial.print(F("Nhiet do: "));
Serial.print(tempC);
Serial.print(F(" C | Do am: "));
Serial.print(humidity);
Serial.println(F(" %"));
}
Build project này ở bất kỳ máy nào, bất kỳ thời điểm nào, PlatformIO đều tải đúng "DHT sensor library@1.4.4" và "Adafruit Unified Sensor@1.1.9" - không phụ thuộc vào việc máy đó đã từng cài thư viện gì trước đó.
8. Lỗi thường gặp
| Lỗi | Nguyên nhân | Cách sửa |
|---|---|---|
| Code cũ đột nhiên không compile được sau khi cập nhật thư viện | Arduino IDE tự động đề xuất/cài version mới có breaking change API | Hạ về đúng version đã test qua Library Manager, hoặc chuyển sang PlatformIO pin version |
Could not find library dependency hoặc lỗi version không khớp trong PlatformIO | Ghi sai tên package hoặc version không tồn tại trên registry | Kiểm tra đúng tên + version trên registry.platformio.org, hoặc bỏ pin để lấy version gần nhất tồn tại |
| Hai máy build ra kết quả khác nhau dù cùng code | Không pin version, mỗi máy cài thư viện ở thời điểm khác nhau | Chuyển toàn bộ dependency sang khai báo trong lib_deps với version cụ thể |
9. Tổng kết
Pin version thư viện không phải là việc "làm cho chắc" thừa thãi - đó là điều kiện để một dự án IoT có thể build lại giống hệt sau nhiều tháng, hoặc trên máy của người khác. Arduino IDE cho phép chọn version thủ công qua Library Manager nhưng không lưu lựa chọn đó vào project; PlatformIO giải quyết vấn đề này triệt để bằng cách khai báo version ngay trong platformio.ini, đi theo code khi commit lên git.