Lỗi gặp phải
failed to register layer: symlink /usr/bin/python3 /usr/bin/python: operation not permitted
error pulling image configuration: failed to register layer
Nửa đêm. Bạn đang pull image Python hoặc Node và Docker chết giữa chừng với thông báo khó hiểu này. Có thể hôm qua vẫn chạy được trên cùng máy. Có thể bạn vừa cài Windows mới và gặp lỗi ngay lập tức. Dù thế nào, image không thể pull xong, và mọi lệnh docker build tham chiếu đến nó cũng thất bại theo.
Nguyên nhân gốc rễ
Vấn đề cốt lõi: Docker phải tạo symlink thật sự trên filesystem khi giải nén các layer của image. NTFS — filesystem của Windows — hoặc không hỗ trợ symlink, hoặc yêu cầu quyền nâng cao mà phiên WSL2 của bạn không có.
Hai tình huống gây ra lỗi này:
- Project của bạn nằm trong
/mnt/c/hoặc/mnt/d/— WSL2 mount ổ đĩa Windows thông qua bridge giao thức 9P. Việc tạo symlink qua bridge đó bị chặn hoặc không ổn định. - Data-root của Docker trỏ đến đường dẫn trên Windows — Docker lưu các layer image ở đâu đó như
/mnt/c/Users/yourname/.docker, vốn không thể chứa symlink Linux.
Cùng nguyên nhân gốc, cùng cách sửa: đưa mọi thứ ra khỏi NTFS mount và vào filesystem ext4 native của WSL2.
Cách sửa 1: Chuyển project vào filesystem WSL2 (Nhanh nhất)
Đang chạy docker build hoặc docker pull từ trong /mnt/c/? Đó là nguyên nhân. Hãy copy project sang thư mục home Linux của bạn:
# Từ trong terminal WSL2
cp -r /mnt/c/Users/yourname/projects/myapp ~/myapp
cd ~/myapp
docker build .
Các đường dẫn như ~/ và /home/yourname/ nằm trên đĩa ảo nội bộ của WSL2 (ext4.vhdx). Đầy đủ ngữ nghĩa Linux — symlink hoạt động tốt.
Chỉ bước này thôi đã giải quyết lỗi cho khoảng 80% trường hợp.
Cách sửa 2: Kiểm tra và chuyển Data-Root của Docker
Dù project đã nằm trên filesystem Linux, Docker vẫn có thể gây ra đúng lỗi này nếu lưu các layer image trên ổ đĩa Windows. Kiểm tra Docker đang lưu dữ liệu ở đâu:
docker info | grep 'Docker Root Dir'
Nếu kết quả trỏ đến /mnt/c/... hoặc /mnt/d/..., bạn cần chuyển hướng nó.
Với Docker Engine bên trong WSL2 (không phải Docker Desktop), hãy sửa file cấu hình daemon:
sudo mkdir -p /etc/docker
sudo nano /etc/docker/daemon.json
Thêm hoặc cập nhật data-root:
{
"data-root": "/home/yourname/.docker-data"
}
Sau đó khởi động lại Docker:
sudo systemctl restart docker
Cách sửa 3: Docker Desktop — Kiểm tra cài đặt tích hợp WSL2
Docker Desktop với backend WSL2 tự quản lý đĩa ảo của riêng nó. Thủ phạm thông thường ở đây là chạy lệnh Docker từ đường dẫn được mount từ Windows trong terminal WSL2 — không phải lỗi của bản thân Docker Desktop.
Mở Docker Desktop → Settings → Resources → WSL Integration. Bật tích hợp cho distro WSL2 của bạn (Ubuntu, Debian, v.v.).
Sau đó, bên trong WSL2, xác nhận root của Docker đang trỏ vào đĩa ảo:
docker info | grep 'Docker Root Dir'
# Kết quả phải hiện: Docker Root Dir: /var/lib/docker
Thấy /var/lib/docker? Data-root ổn — build context mới là thủ phạm. Hãy chuyển nó về ~/ như ở Cách sửa 1.
Cách sửa 4: Bật Symlink trên NTFS Mount (Phương án cuối cùng)
Bắt buộc phải làm việc từ /mnt/c/? Bạn có thể thử bật hỗ trợ symlink trên NTFS, nhưng cần bật Developer Mode trên Windows và chỉnh thêm cấu hình WSL2.
Trước tiên, bật Developer Mode: Settings → System → For Developers → Developer Mode → On.
Sau đó sửa file /etc/wsl.conf bên trong distro WSL2 của bạn:
sudo nano /etc/wsl.conf
[automount]
options = "metadata"
Tùy chọn metadata cho phép WSL2 lưu metadata file Linux — bao gồm symlink — trên volume NTFS. Tắt WSL2 từ PowerShell rồi khởi động lại:
# Trong PowerShell (admin)
wsl --shutdown
# Sau đó mở lại terminal WSL2
Kiểm tra xem symlink đã hoạt động trên NTFS mount chưa:
cd /mnt/c/Users/yourname/
ln -s test_target test_link
ls -la test_link
Nếu ln -s thành công, hãy thử lại lệnh Docker build. Vẫn lỗi? Quá trình giải nén layer của Docker dùng một code path nội bộ khác. Cách sửa 1 hoặc Cách sửa 2 đáng tin cậy hơn.
Xác minh kết quả
Đã đến lúc xác nhận cách sửa thực sự có hiệu quả. Xóa image lỗi trước, rồi pull lại từ đầu:
# Xóa image đã pull dở/bị lỗi trước
docker rmi python:3.11-slim 2>/dev/null || true
# Pull lại từ đầu
docker pull python:3.11-slim
Không còn lỗi symlink? Xong rồi đó. Hãy kiểm tra luôn một lần build hoàn chỉnh:
docker build --no-cache -t myapp:test .
docker run --rm myapp:test python3 --version
Flag --no-cache buộc Docker phải giải nén lại toàn bộ layer — đúng thao tác đã thất bại trước đây.
Phòng ngừa
- Luôn đặt project Docker trong
~/— không phải trong/mnt/c/. Dùng thư mục home WSL2 làm không gian làm việc chính khi chạy Docker. Bạn vẫn có thể duyệt file từ Windows Explorer qua\\wsl$\Ubuntu\home\yourname\nếu cần. - Dùng VS Code với extension WSL — nó hoạt động trong suốt với các file bên trong filesystem WSL2 trong khi bạn vẫn chỉnh sửa từ Windows.
- Không bao giờ đặt
data-roottrỏ vào đường dẫn được mount từ Windows — luôn trỏ vào đường dẫn trong/home/hoặc/var/khi ghi đè vị trí lưu trữ của Docker.
Nguyên tắc bao quát tất cả: Docker trên WSL2 hoạt động hoàn hảo khi mọi thứ đều nằm trên đĩa ảo Linux. Ngay khi các layer image hoặc build context chạm vào NTFS mount, symlink sẽ vỡ và bạn sẽ phải debug lúc 2 giờ sáng.

