Application Layer trong AMR: máy trạng thái điều phối nhiệm vụ
Atlasbot · 22/8/2026 · 11 phút đọc
Bốn tầng trước — Hardware, Driver, ROS2, Localization, Navigation — đều lo phần "làm sao robot di chuyển đúng và an toàn". Application Layer trả lời câu hỏi khác hẳn: robot nên đi đâu tiếp theo, và làm gì khi tới nơi. Đây là tầng cao nhất trong mô hình 5 tầng đã học ở bài Kiến trúc AMR.
Khái niệm chính
Application Layer trong một AMR thực tế thường gồm 2 phần:
- Máy trạng thái nhiệm vụ (task state machine) — theo dõi robot đang ở bước nào của một nhiệm vụ cụ thể (đi tới điểm lấy hàng, đang lấy hàng, đi tới điểm giao, đang giao hàng)
- Hàng đợi nhiệm vụ (task queue) — danh sách nhiệm vụ chờ xử lý, quyết định thứ tự ưu tiên khi có nhiều yêu cầu cùng lúc
Với hệ thống nhiều robot (fleet), Application Layer còn thêm vai trò điều phối — tránh 2 robot cùng tranh chấp một điểm giao cắt hẹp, phân bổ nhiệm vụ cho robot phù hợp nhất (gần điểm lấy hàng nhất, còn nhiều pin nhất).
Nguyên lý hoạt động
Một nhiệm vụ giao hàng điển hình đi qua các trạng thái nối tiếp:
Idle (chờ nhiệm vụ)
→ nhận nhiệm vụ mới → Navigating (gọi action NavigateToPose của Nav2)
→ tới đích → Picking/Dropping (chờ thao tác lấy/trả hàng, có thể chờ người xác nhận)
→ hoàn tất → quay lại Idle (hoặc nhận nhiệm vụ tiếp theo trong hàng đợi)
Nhánh lỗi: bất kỳ trạng thái nào cũng có thể chuyển sang Failed
(timeout không tới đích, Nav2 báo không tìm được đường, cảm biến báo lỗi)
Điểm quan trọng về ranh giới: Application Layer chỉ điều phối trạng thái và gọi Nav2 — nó không tự tính đường đi, không tự né vật cản. Nó gửi một goal (NavigateToPose) xuống Navigation Layer rồi theo dõi kết quả trả về, đúng nguyên tắc "mỗi tầng chỉ giao tiếp với tầng liền kề" đã học ở bài Kiến trúc AMR.
Kiến thức kỹ thuật
Công thức
Ước lượng thời gian hoàn thành một chuỗi nhiệm vụ — hữu ích cho việc lập lịch và ước lượng SLA (thời gian cam kết) trong vận hành thực tế:
Thời_gian_tổng = Σ (Khoảng_cách_i / Vận_tốc_trung_bình + Thời_gian_thao_tác_i)
VD: nhiệm vụ gồm 3 điểm dừng, khoảng cách lần lượt 15m, 8m, 12m,
vận tốc trung bình 0.6 m/s (đã tính cả thời gian giảm tốc/tăng tốc thực tế,
thấp hơn tốc độ tối đa danh nghĩa), mỗi điểm dừng mất 20 giây thao tác
Thời_gian_di_chuyển = (15+8+12)/0.6 = 58.3 giây
Thời_gian_thao_tác = 3 × 20 = 60 giây
Thời_gian_tổng ≈ 118.3 giây ≈ 2 phút
Thông số
| Quy mô | Yêu cầu điều phối | Độ phức tạp |
|---|---|---|
| 1 robot, 1 hàng đợi | Xử lý tuần tự, không cần điều phối liên robot | Thấp |
| Nhiều robot, khu vực chung | Cần tránh tranh chấp điểm giao cắt/khu vực hẹp | Trung bình-cao (fleet management) |
Ứng dụng thực tế
Trong một kho hàng vận hành nhiều AMR cùng lúc, Application Layer của hệ thống trung tâm (fleet manager) thường dùng chiến lược đặt trước khu vực (zone reservation) — trước khi một robot đi qua một hành lang hẹp hoặc giao lộ, nó "đặt trước" khu vực đó với fleet manager; robot khác nhận nhiệm vụ đi qua cùng khu vực sẽ phải chờ hoặc đi đường khác. Đây là cơ chế điều phối ở tầng Application, hoàn toàn tách biệt với việc từng robot riêng lẻ né vật cản động ở tầng Navigation — hai cơ chế phối hợp nhau nhưng giải quyết hai vấn đề khác nhau (tránh xung đột có kế hoạch trước so với phản ứng tức thời với vật cản bất ngờ).
Ví dụ thực tế
from enum import Enum
class TaskState(Enum):
IDLE = "idle"
NAVIGATING = "navigating"
PICKING = "picking"
FAILED = "failed"
class TaskManager:
def __init__(self):
self.state = TaskState.IDLE
self.queue = []
def them_nhiem_vu(self, diem_den):
self.queue.append(diem_den)
def cap_nhat(self, nav2_ket_qua=None):
if self.state == TaskState.IDLE and self.queue:
self.diem_den_hien_tai = self.queue.pop(0)
self.state = TaskState.NAVIGATING
print(f"Bat dau di toi {self.diem_den_hien_tai}")
elif self.state == TaskState.NAVIGATING:
if nav2_ket_qua == "thanh_cong":
self.state = TaskState.PICKING
print("Da toi noi, bat dau lay/tra hang")
elif nav2_ket_qua == "that_bai":
self.state = TaskState.FAILED
print("Nav2 bao loi - chuyen sang trang thai Failed")
elif self.state == TaskState.PICKING:
self.state = TaskState.IDLE
print("Hoan tat nhiem vu, quay lai Idle")
tm = TaskManager()
tm.them_nhiem_vu("Ke A3")
tm.cap_nhat()
tm.cap_nhat(nav2_ket_qua="thanh_cong")
tm.cap_nhat()
Output:
Bat dau di toi Ke A3
Da toi noi, bat dau lay/tra hang
Hoan tat nhiem vu, quay lai Idle
Máy trạng thái đơn giản này là hạt nhân của mọi hệ thống điều phối AMR phức tạp hơn — fleet manager thực tế chỉ mở rộng thêm nhiều instance song song (một cho mỗi robot) cộng thêm logic điều phối chung giữa chúng.
Lỗi thường gặp
- Nhét logic thời gian thực vào Application Layer — vi phạm nguyên tắc phân lớp đã học ở bài Kiến trúc AMR; Application Layer chạy ở tần số thấp (giây, không phải mili-giây), không phù hợp cho bất kỳ logic cần phản ứng nhanh nào.
- Không có trạng thái/xử lý timeout rõ ràng — nếu Nav2 "treo" không bao giờ trả kết quả thành công lẫn thất bại, robot có thể kẹt vĩnh viễn ở trạng thái Navigating mà không có cơ chế tự thoát.
- Bỏ qua điều phối đa robot khi mở rộng từ 1 robot lên nhiều robot — logic hoạt động tốt với 1 robot có thể gây tắc nghẽn hoặc va chạm khi chạy nhiều robot cùng lúc trong cùng khu vực mà không có cơ chế đặt trước/điều phối.
- Không tách biệt rõ trạng thái Failed khỏi trạng thái Idle — coi "nhiệm vụ thất bại" giống "chờ nhiệm vụ mới" khiến hệ thống giám sát khó phát hiện robot đang gặp sự cố cần can thiệp.
Kết luận
Application Layer là nơi "ý định nghiệp vụ" (giao hàng, dọn dẹp, tuần tra) chuyển thành chuỗi lệnh cụ thể gửi xuống Navigation Layer — bản thân nó chỉ điều phối trạng thái, không tính toán đường đi hay né vật cản. Máy trạng thái đơn giản là nền tảng đủ dùng cho một robot, còn hệ thống nhiều robot cần thêm cơ chế điều phối như đặt trước khu vực. Đây là bài cuối của chuyên mục AMR Software Architecture — toàn bộ 5 tầng từ Hardware tới Application giờ đã được trình bày đầy đủ. Chuyên mục Thiết kế AMR thực tế tiếp theo đưa mọi kiến thức này vào một quy trình thiết kế cụ thể, từ chọn linh kiện tới tính toán tải trọng.