Làm cách nào để chạy các dịch vụ systemd trong thùng chứa Arch Linux Docker?


7

Dường như có rất nhiều cách khác nhau để mọi người có thể chạy các dịch vụ systemd trong các container Docker. Ví dụ mới nhất về lời khuyên trực tiếp mà tôi đã tìm thấy là chạy Docker với --volume=/sys/fs/cgroup:/sys/fs/cgroup:ro --cap-add=SYS_ADMIN --security-opt=seccomp:unconfined. Tuy nhiên, nó vẫn chỉ thất bại :

Lỗi: Không thể khởi động Dịch vụ [ntpd]: Thi hành '/ usr / sbin / systemctl start ntpd' return 1: Không thể kết nối với bus: Không có tệp hoặc thư mục như vậy

Mức tối thiểu tuyệt đối tôi cần làm là gì để có được các dịch vụ đơn giản chạy theo systemd 231 trên bộ chứa docker 1.12.1 với bản phân phối Arch Linux cập nhật?


1
Docker liên quan nhiều hơn đến việc chạy daemon trực tiếp khi bạn cung cấp cho nó một ENTRYPOINThệ thống được xác định trước không có yếu tố nào trong đó. Nếu bạn đang tìm kiếm một loại tích hợp container nào đó với systemd, bạn có thể xem xét việc tạo một dịch vụ
nspawn

1
Tôi không sử dụng Docker để chạy một dịch vụ. Tôi đang sử dụng nó để kiểm tra một Puppet run (trong số những thứ khác) bắt đầu nhiều dịch vụ. Nếu tôi đặc biệt là môi trường thử nghiệm (sử dụng nspawn thay vì systemd) thì thử nghiệm là vô ích.
l0b0

"Tôi không sử dụng Docker để chạy một dịch vụ" Sau đó, bạn hoàn toàn không thể sử dụng Docker. Nó dự định chạy một thực thi duy nhất và mọi thứ được xây dựng xung quanh thực tế đó. Đó có lẽ là lý do tại sao vấn đề này rất khó để bạn giải quyết. Nếu bạn đang kiểm tra một lần chạy rối, điều tôi thường làm trong trường hợp đó là có một VM mà tôi đã chụp trước khi thực hiện chạy. Nếu bạn đã có một cái gì đó giống như thiết lập Vagrant thì thật dễ dàng để xây dựng VM mới và thổi bay chúng (trái ngược với thực hiện một ảnh chụp nhanh).
Bratchley

Vấn đề ngay lập tức bạn dường như gặp phải là dbus không chạy bên trong container của bạn.
Bratchley

1
Tôi đang sử dụng Docker cho công tác này vì hai lý do: Các lớp được dễ dàng hơn để làm việc với hơn ảnh chụp nhanh để tránh một lượng lớn công việc không cần thiết khi tái chạy thử nghiệm, và các thiết lập Docker hiện nay là nhiều đơn giản hơn so với Vagrant một tương ứng. Tôi không hiểu tại sao Docker nên ngăn cản việc chạy nhiều dịch vụ - rốt cuộc chúng chỉ là các quy trình. Không có gì ngăn cản bất cứ ai chạy nhiều tiến trình trong Docker. Tôi không muốn bất kỳ ai trong số họ là ENTRYPOINT.
l0b0

Câu trả lời:


2

Tôi gặp vấn đề tương tự khi kiểm tra các vở kịch Ansible của tôi yêu cầu systemd. Và như bạn đã nói, docker có vẻ như là cách tiếp cận tốt nhất ở đây vì việc đưa lên và xuống một container dễ dàng hơn nhiều so với một máy ảo.
Trước hết, hình ảnh cơ sở / archlinux không được dùng nữa - thay vào đó bạn nên sử dụng archlinux / base . Sau đó, để chạy systemd hoàn toàn không có đặc quyền, cần thực hiện một số điều:

  • cung cấp biến "conrainer =", vì vậy systemd sẽ không thử thực hiện một số thứ mà nó thường khởi động máy phần cứng
  • systemd tích cực sử dụng cgroups, vì vậy liên kết hệ thống tệp mount / sys / fs / cgroup từ máy chủ
  • không cần gắn kết / sys / fs / cầu chì nhưng giúp tránh các sự cố với phần mềm phụ thuộc vào cầu chì
  • systemd nghĩ rằng sử dụng tmpfs ở mọi nơi là một cách tiếp cận tốt, nhưng việc chạy không được ưu tiên khiến nó không thể gắn tmpfs ở bất cứ nơi nào nó muốn, vì vậy hãy cài đặt tmpfs vào / tmp, / run và / run / lock
  • là bit cuối cùng bạn cần chỉ định sysinit.target làm đơn vị mặc định để khởi động thay vì multi-user.target hoặc bất cứ điều gì, vì bạn thực sự không muốn bắt đầu những thứ đồ họa bên trong một container

Dòng lệnh kết quả là

docker run \
  --entrypoint=/usr/lib/systemd/systemd \
  --env container=docker \
  --mount type=bind,source=/sys/fs/cgroup,target=/sys/fs/cgroup \
  --mount type=bind,source=/sys/fs/fuse,target=/sys/fs/fuse \
  --mount type=tmpfs,destination=/tmp \
  --mount type=tmpfs,destination=/run \
  --mount type=tmpfs,destination=/run/lock \
    archlinux/base --log-level=info --unit=sysinit.target

Nếu chúng ta đang nói về việc chạy dịch vụ cụ thể ở đó như ntpd từ ví dụ của bạn, bạn sẽ cần thêm

--cap-add=SYS_TIME

nếu không, ntpd sẽ thất bại với quyền từ chối vì không ai muốn một bộ chứa để đặt thời gian hệ thống theo mặc định.

Ps tôi đã dành khá nhiều thời gian để tìm hiểu cách systemd hành xử và quản lý để làm cho nó hoạt động trên số lượng hình ảnh hệ điều hành. Tôi đã mô tả kinh nghiệm của tôi trong một bài viết Chạy systemd trong container docker . Nó là tiếng Nga nhưng tôi tin rằng google dịch nên hoạt động trong trình duyệt của bạn. Cảm ơn

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.