Mình từng gặp một tình huống khá đau đầu khi mới bắt đầu làm sysadmin: cần cho user deploy đọc được log của ứng dụng, nhưng file đó lại thuộc sở hữu của user www-data, và không muốn thêm deploy vào group www-data vì lý do bảo mật. Dùng chmod 644? Không được, vì còn những user khác không được phép đọc file đó. Đây là lúc ACL (Access Control List) giải quyết vấn đề mà chmod/chown bó tay.
Công ty mình vẫn còn vài con server chạy CentOS 7, và việc migrate sang AlmaLinux là bài toán mình đã xử lý. Mỗi lần migrate, ACL là thứ cần kiểm tra lại — vì rsync thông thường không giữ ACL và dễ gây ra lỗi permission khó debug sau khi chuyển xong.
ACL là gì và tại sao cần nó?
Permission truyền thống trên Linux chỉ có 3 đối tượng: owner, group, và others. Đơn giản, nhưng thiếu linh hoạt khi số lượng user tăng lên trong môi trường doanh nghiệp.
ACL cho phép đặt permission riêng cho bất kỳ user hoặc group nào, không phụ thuộc vào owner hay group hiện tại của file. Hệ thống vẫn chạy POSIX permission bình thường — ACL chỉ là lớp mở rộng thêm bên trên.
Một số tình huống thực tế cần ACL:
- Thư mục
/var/www/htmlcần cho team frontend đọc/ghi, nhưng không phải toàn bộ groupwheel - File log cần cho monitoring agent đọc, không expose cho các user khác
- Thư mục project chung cần phân quyền khác nhau cho dev, QA, PM
Khái niệm cốt lõi cần nắm
Hai công cụ chính
getfacl— xem ACL hiện tại của file hoặc thư mụcsetfacl— thiết lập ACL
Mask là gì?
Mask là giới hạn permission tối đa mà named user, named group, hoặc owning group có thể có. Nó không ảnh hưởng đến owner và others. Khi bạn chạy chmod trên file có ACL, lệnh đó cập nhật mask chứ không xóa ACL — đây là điểm hay bị hiểu nhầm khi mới dùng.
Thực hành: Từng bước quản lý ACL trên CentOS Stream 9
Bước 1: Cài đặt và kiểm tra hỗ trợ ACL
Trên CentOS Stream 9, XFS (filesystem mặc định) đã bật ACL sẵn. Chỉ cần cài gói acl:
sudo dnf install acl -y
# Xác nhận cài xong
getfacl --version
Nếu muốn chắc chắn filesystem đang mount với ACL support:
mount | grep -E "^/dev"
# XFS thường không hiển thị 'acl' vì nó bật mặc định
Bước 2: Xem ACL hiện tại của file
# Tạo môi trường test
mkdir -p /tmp/acl-demo
touch /tmp/acl-demo/testfile.txt
# Xem ACL
getfacl /tmp/acl-demo/testfile.txt
Output khi chưa có ACL mở rộng:
# file: tmp/acl-demo/testfile.txt
# owner: root
# group: root
user::rw-
group::r--
other::r--
Bước 3: Thêm ACL cho user và group cụ thể
# Cú pháp: setfacl -m u:<username>:<permissions> <file>
sudo setfacl -m u:alice:rw /tmp/acl-demo/testfile.txt
# Thêm cho group
sudo setfacl -m g:developers:r /tmp/acl-demo/testfile.txt
# Kiểm tra kết quả
getfacl /tmp/acl-demo/testfile.txt
Output sau khi thêm ACL:
# file: tmp/acl-demo/testfile.txt
# owner: root
# group: root
user::rw-
user:alice:rw-
group::r--
group:developers:r--
mask::rw-
other::r--
Dấu + sẽ xuất hiện khi chạy ls -la: -rw-rw-r--+ — đây là cách nhanh nhận biết file có ACL mà không cần chạy getfacl.
Bước 4: Default ACL — tính năng quan trọng nhất
Default ACL là thứ mình dùng nhiều nhất trong thực tế: file mới tạo trong một thư mục sẽ tự động kế thừa ACL, không cần set lại từng lần.
mkdir /tmp/acl-demo/shared
# Flag -d = default ACL
sudo setfacl -d -m u:alice:rwx /tmp/acl-demo/shared
sudo setfacl -d -m g:developers:rx /tmp/acl-demo/shared
# Xem cấu hình
getfacl /tmp/acl-demo/shared
Phần default: trong output sẽ tự động áp dụng cho file và thư mục con mới tạo bên trong.
Bước 5: Áp dụng ACL đệ quy
# -R = recursive
sudo setfacl -R -m u:alice:rx /var/www/html
# Kết hợp recursive + default để cả cây thư mục lẫn file mới đều được cover
sudo setfacl -R -d -m u:alice:rx /var/www/html
Bước 6: Xóa ACL
# Xóa ACL của một user cụ thể
sudo setfacl -x u:alice /tmp/acl-demo/testfile.txt
# Xóa toàn bộ ACL mở rộng (chỉ giữ POSIX cơ bản)
sudo setfacl -b /tmp/acl-demo/testfile.txt
# Xóa default ACL của thư mục
sudo setfacl -k /tmp/acl-demo/shared
Ví dụ thực tế: Môi trường đa nhóm phát triển
Giả sử có thư mục /opt/webapp với yêu cầu phân quyền như sau:
- User
deploy: đọc/ghi/thực thi toàn bộ - Group
dev: đọc/ghi code, không thực thi script tùy ý - Group
qa: chỉ đọc - User
monitor: chỉ đọc thư mụclogs
# Phân quyền cho thư mục gốc
sudo setfacl -R -m u:deploy:rwx /opt/webapp
sudo setfacl -R -m g:dev:rw /opt/webapp
sudo setfacl -R -m g:qa:r /opt/webapp
# Phân quyền riêng cho logs
sudo setfacl -R -m u:monitor:rx /opt/webapp/logs
# Đặt default ACL để file mới kế thừa
sudo setfacl -d -m u:deploy:rwx /opt/webapp
sudo setfacl -d -m g:dev:rw /opt/webapp
sudo setfacl -d -m g:qa:r /opt/webapp
# Kiểm tra tổng thể
getfacl /opt/webapp
ls -la /opt/webapp
Backup và restore ACL khi migrate server
Điểm này mình học được từ lần migrate CentOS 7 sang AlmaLinux — sau khi rsync xong, một số service không chạy vì mất ACL. Từ đó mình luôn backup ACL trước khi di chuyển:
# Backup toàn bộ ACL của /var/www
getfacl -R /var/www > /backup/www-acl-backup.txt
# Restore từ backup
setfacl --restore=/backup/www-acl-backup.txt
# Dùng rsync với flag -A để giữ ACL
rsync -aAX /source/ /destination/
Kết luận
ACL không thay thế chmod/chown mà bổ sung thêm một lớp kiểm soát khi permission POSIX truyền thống không đủ linh hoạt. Nên dùng ACL khi:
- Cần phân quyền cho nhiều user/group khác nhau trên cùng một file mà không muốn thay đổi ownership
- Muốn file mới tạo trong thư mục tự động kế thừa permission qua default ACL
- Môi trường nhiều team có yêu cầu phân quyền chồng chéo
Nếu đang quản lý server CentOS Stream 9 hoặc AlmaLinux, hãy kiểm tra xem có ACL nào đang chạy trên hệ thống không bằng lệnh getfacl — đôi khi người dùng trước để lại ACL mà không document lại, và đó có thể là nguyên nhân của những lỗi permission khó giải thích.

