Sự thay thế chính xác cho RC.local trong systemd là gì thay vì tạo lại RC.local


25

Tôi không thể tìm thấy cách chính xác để thực thi một số tập lệnh cục bộ (hoặc các lệnh rất cục bộ) tại systemd, tôi đã biết rằng tôi không được tạo dịch vụ (trong systemd một đơn vị) cho các loại tập lệnh này (hoặc tôi phải?) ....

Cách giải quyết mà tôi tìm thấy là tạo RC.local và cấp cho nó quyền thực thi.

printf '#!/bin/bash \n\nexit 0' >/etc/rc.local 
chmod +x /etc/rc.local

Ví dụ: nếu tôi nhận được một máy chủ cũ với một RC.local đơn giản được cấu hình bởi bạn, tôi sẽ biết bạn đã làm gì và sẽ đau đến mức nào khi nâng cấp hoặc cài đặt một cái gì đó mới trên distro, vì RC.local được bên ngoài tôn trọng các gói, nhưng mặt khác, nếu tôi cài đặt một máy chủ và tạo một đơn vị systemd hoặc hai hoặc ba (hoặc thậm chí các dịch vụ sysvinit), chỉ để thực hiện một nhiệm vụ đơn giản, điều này đôi khi có thể làm cho cuộc sống của bạn khó khăn hơn, và nhiều hơn các đơn vị của tôi tên một ngày nào đó có thể xung đột với tên của các dịch vụ mới được tạo bởi sự phát triển phân phối và có thể được cài đặt trên bản nâng cấp, gây rắc rối cho các tập lệnh của tôi!

Tôi thấy một câu hỏi khác hỏi về RC.local ở đâu và câu trả lời là tạo ra nó và cấp quyền thực thi, tôi nghĩ rằng câu hỏi của tôi thực sự không phải là một bản sao , vì tôi không muốn biết nó ở đâu - tin tôi đi, tôi chỉ muốn để chấp nhận rằng nó không được chấp nhận , nhưng tôi không thể tìm ra cách chính xác để làm những việc như thế này, tôi có nên thực sự tạo ra một đơn vị chỉ cho một số đơn giản như vậy không?


4
systemd "di chuyển chiến thắng duy nhất là không chơi"; cách khác, tùy thuộc vào những gì bạn muốn, bạn có thể tạo Đơn vị systemd. Bây giờ tôi có thể sử dụng RC.local và quan tâm đến nó khi nó biến mất.
Rui F Ribeiro

Vì vậy, bạn nghĩ cách chính thức là tạo ra một đơn vị như một dịch vụ? Xin vui lòng gửi như một câu trả lời làm thế nào để làm điều đó.
Luciano Andress Martini

1
Khi tôi dùng thử Ubuntu, tôi đã tạo một Đơn vị để có bộ đệm ssh-agent liên tục trong máy tính để bàn của mình trong khi tôi không khởi động lại và một cái khác cho một thứ khác mà tôi không thể nhớ được; bạn cũng có thể tạo một trỏ tới /etc/rc.local nhưng có vẻ như hệ thống đang tự làm điều đó cho đến bây giờ .... Tôi sẽ RC.local trong thời gian này và nếu bị gián đoạn, hãy tạo một trỏ đến giả mạo /etc/rc.local rồi.
Rui F Ribeiro

Điều này có khả năng phá vỡ các tài liệu như thể một số cuốn sách nói rằng bạn phải đặt một cái gì đó vào /etc/rc.local và bạn cố gắng nâng cấp các tài liệu này, ví dụ như RC.local phải được đánh dấu là có thể thực thi được, khi nó bị phản đối hoàn toàn tài liệu bị hỏng, nhưng nếu bạn nói rằng bạn phải tạo đơn vị để trỏ đến /etc/rc.local, tài liệu này sẽ giới thiệu vì systemd đang xung đột với đơn vị của bạn. Tôi tin rằng nếu bạn đúng, có lẽ họ đã không quyết định liệu nó có bị phản đối hay không, bởi vì họ vẫn không có người thay thế ... khi họ quyết định tất cả tài liệu sẽ bị phá vỡ một lần nữa.
Luciano Andress Martini

Những loại kịch bản nào bạn cần phải thực hiện? Systemd có rất nhiều loại đơn vị. "Dịch vụ" chỉ là một trong nhiều loại đơn vị . Ví dụ: đơn vị Mount, đơn vị tự động, đơn vị hẹn giờ, đơn vị mục tiêu. Một trong số họ có thể giải quyết vấn đề của bạn?
andcoz

Câu trả lời:


17

Như đã chỉ ra ở nơi khác, nó trở nên ô uế vừa phải để sử dụng rc-local.servicetheo systemd.

  1. Về mặt lý thuyết có thể là phân phối của bạn sẽ không cho phép nó. (Tôi nghĩ rằng điều này không phổ biến, ví dụ vì vô hiệu hóa cùng một tùy chọn xây dựng cũng loại bỏ poweroff/ rebootcác lệnh mà nhiều người sử dụng).
  2. Các ngữ nghĩa không hoàn toàn rõ ràng. Systemd định nghĩa rc-local.servicemột cách, nhưng Debian cung cấp một tệp thả xuống làm thay đổi ít nhất một cài đặt quan trọng.

rc-local.servicethường có thể làm việc tốt Nếu bạn lo lắng về những điều trên, tất cả những gì bạn cần làm là tạo bản sao của chính nó! Đây là phép màu:

# /etc/systemd/system/my-startup.service
[Service]
Type=oneshot
RemainAfterExit=yes
ExecStart=/usr/local/libexec/my-startup-script

[Install]
WantedBy=multi-user.target

Tôi không nghĩ bạn cần hiểu từng chi tiết [*], nhưng có hai điều bạn cần biết ở đây.

  1. Bạn cần kích hoạt tính năng này với systemctl enable my-startup.service.

  2. Nếu tập lệnh của bạn có sự phụ thuộc vào bất kỳ dịch vụ nào khác, bao gồm network-online.target, bạn phải khai báo nó. Ví dụ, thêm một [Unit]phần, với các dòng Wants=network-online.targetAfter=network-online.target.

    Bạn không cần phải lo lắng về sự phụ thuộc vào các dịch vụ "khởi động sớm" - cụ thể là các dịch vụ đã được đặt hàng trước đó basic.target. Các dịch vụ như my-startup.serviceđược tự động đặt hàng sau basic.target, trừ khi chúng được đặt DefaultDependencies=no.

    Nếu bạn không chắc chắn liệu một trong những phụ thuộc của bạn có phải là dịch vụ "khởi động sớm" hay không, một cách tiếp cận là liệt kê các dịch vụ được đặt hàng trước basic.target, bằng cách chạy systemctl list-dependencies --after basic.target. (Lưu ý rằng --after, không phải --before).

Có một số cân nhắc mà tôi nghĩ cũng áp dụng cho pre-systemd rc.local:

  1. Bạn cần đảm bảo các lệnh của bạn không xung đột với một chương trình khác cố gắng kiểm soát điều tương tự.
  2. Tốt nhất là không bắt đầu các chương trình dài hay còn gọi là daemon rc.local.

[*] Tôi đã sử dụng Type=oneshot+ RemainAfterExit=yesvì nó có ý nghĩa hơn đối với hầu hết các tập lệnh one-shot. Nó chính thức hóa rằng bạn sẽ chạy một loạt các lệnh, my-startupsẽ được hiển thị là "hoạt động" khi chúng đã hoàn thành và bạn sẽ không bắt đầu một trình nền.


Chà, có một số nơi "địa phương" để tạo dịch vụ hoặc đoạn trích, hoặc bất cứ điều gì - hoặc tôi có thể tin đây là địa phương và không nên thay đổi? nếu tôi phát triển daemon của riêng tôi? Bởi vì tôi không muốn thay đổi tính nguyên bản của hệ thống, vì vậy khi tôi cài đặt một số apt-get, tôi không muốn thấy hệ thống của mình bị cháy do tập lệnh thay thế, hoặc một cái gì đó như thế này chẳng hạn. Tôi chỉ muốn tin rằng daemon sẽ chỉ được bắt đầu một lần, mà không làm thêm bất kỳ điều điên rồ nào mà tôi sợ ... như cố gắng khởi động lại nó là vô hạn nếu nó bị hỏng, v.v ...
Luciano Andress Martini

1
@LucianoAndressMartini nếu bạn hỏi cách đúng để bắt đầu một daemon là gì, bạn thực sự nên xác định một dịch vụ riêng cho nó. Đó có thể là một .serviceđơn vị hệ thống gốc hoặc nếu bạn thực sự muốn viết một tập lệnh init LSB, bạn có thể làm điều đó thay vào đó. Tôi không muốn khuyên bạn nên đặt một số daemon rc-local.servicehoặc tương đương, tôi nghĩ rằng nó có thể hoạt động, nhưng nó có vẻ đẹp hơn nhiều nếu bạn có thể khởi động lại từng daemon systemctl restart my-daemongiống như mọi thứ khác. Đó là dự định mà bạn đặt dịch vụ địa phương của bạn vào /etc/systemd/system.
sourcejedi

1
@LucianoAndressMartini bạn phải tránh sử dụng cùng tên với bất kỳ dịch vụ nào khác - giống như trong sysvinit. Trong những tình huống tương tự, đôi khi tôi đã bắt đầu tên của mình bằng local-...
sourcejedi

1
Cảm ơn bạn!!! Lưu lại sau nửa ngày. Những chi tiết này rất quan trọng đối với tôi: Type = oneshot, RemainAfterExit = yes, Wants = network-online.target, After = network-online.target. Chỉ cần triển khai bản dựng apache và đặt IP tĩnh thành 192.168.1.80, để bộ định tuyến có thể hướng lưu lượng truy cập đến đó. Nên tầm thường. Thật khó chịu trong Debian9. Hầu như không có lời khuyên trực tuyến nào ngoại trừ "apt-get apache", "systemctl start apache" hoặc hướng dẫn với init.d, không ai trong số đó áp dụng cho Apache được xây dựng nguồn trong Debian9.
MichaelsonBritt

1
@MichaelsonBritt Tốt nhất không nên bắt đầu các chương trình chạy dài hay còn gọi là daemon từ RC.local. Tôi đã sử dụng Type=oneshot... nó chính thức hóa rằng ... bạn sẽ không bắt đầu một daemon. Nếu bạn muốn thông tin về việc bắt đầu một daemon, xin vui lòng đặt một câu hỏi mới.
nguồn

15

Quên đi rc.local.

Như tôi đã nói về CentOS 7về Debian 8về Ubuntu 15 :

Bạn đang sử dụng hệ điều hành systemd + Linux. /etc/rc.locallà một cơ chế tương thích ngược kép trong systemd, bởi vì nó là một cơ chế tương thích ngược cho một cơ chế mà chính nó là một cơ chế tương thích trong rcbản sao hệ thống van Smoorenburg 5 .

Sử dụng /etc/rc.localcó thể đi sai lầm khủng khiếp. Mọi người đã rất ngạc nhiên bởi thực tế là systemd không chạy rc.localtheo cùng một cách, ở cùng một vị trí trong bootstrap, như họ đã từng sử dụng. (Hoặc sai lầm mong đợi: Nó không, trên thực tế, chạy cuối cùng . Trong hệ thống cũ, như hướng dẫn OpenBSD vẫn chỉ ra) Những người khác đã bị ngạc nhiên bởi thực tế rằng những gì họ thiết lập trong rc.localmong đợi những cách cũ làm việc, là sau đó hoàn toàn hoàn tác bởi những người như mới udevquy tắc, NetworkManager, systemd-logind, systemd-resolved, hoặc khác nhau "Kit" s.

Như được minh họa bởi " Tại sao` init 0` lại dẫn đến "Đối số dư thừa" khi cài đặt Arch? ", Một số hệ điều hành đã cung cấp systemd mà không có các tính năng tương thích ngược như trình systemd-rc-local-generatortạo . Trong khi Debian vẫn giữ các tính năng tương thích ngược , Arch Linux xây dựng systemd với chúng bị tắt . Vì vậy, trên Arch và các hệ điều hành như nó dự kiến /etc/rc.local sẽ hoàn toàn bị bỏ qua .

Quên đi rc.local. Đó không phải là con đường để đi. Bạn có một hệ điều hành systemd + Linux. Vì vậy, hãy tạo một đơn vị dịch vụ systemd phù hợp và đừng bắt đầu từ một điểm có hai mức độ tương thích ngược. (Trên Ubuntu và Fedora, nó đã bị xóa ba lần, rcbản sao của Hệ thống 5 Smoorenburg rc.localsau đó đã được thay thế hai lần , hơn một thập kỷ trước, đầu tiên là khởi động và sau đó bởi systemd.)

Cũng nhớ quy tắc đầu tiên để di chuyển sang systemd .

Đây thậm chí không phải là một ý tưởng mới dành riêng cho systemd. Trên rccác hệ thống van Smoorenburg và Upstart, điều cần làm là tạo một rckịch bản van Smoorenburg phù hợp hoặc tập tin công việc Upstart thay vì sử dụng rc.local. Ngay cả các ghi chú thủ công của FreeBSD mà ngày nay người ta tạo ra một rckịch bản Mewburn thích hợp thay vì sử dụng /etc/rc.local. Mewburn rcđược NetBSD 1.5 giới thiệu vào năm 2000.

/etc/rc.localbắt đầu từ thời điểm phiên bản thứ bảy Unix và trước đó. Nó đã được thay thế bởi /etc/inittabvà một runlevel dựa trên rcAT & T Unix System 3 (với một chút khác biệt /etc/inittabtrong AT & T Unix System 5) vào năm 1983 . Thậm chí đó là lịch sử.

Tạo định nghĩa dịch vụ gốc phù hợp cho hệ thống quản lý dịch vụ của bạn, cho dù đó là gói dịch vụ cho bộ công cụ nosh service-managersystem-control, /etc/rc.d/tập lệnh cho Mewburn rc, tệp đơn vị dịch vụ cho systemd, tệp công việc cho Upstart, thư mục dịch vụ cho runit / s6 / daemontools -encore, hoặc thậm chí là một /etc/init.d/kịch bản cho van Smoorenburg rc.

Trong systemd, các tệp đơn vị dịch vụ do quản trị viên thêm vào /etc/systemd/system/thường đi vào (hoặc /usr/local/lib/systemd/system/hiếm khi). Với người quản lý dịch vụ nosh, /var/local/sv/là một nơi thông thường cho các gói dịch vụ địa phương. Mewburn rctrên FreeBSD sử dụng /usr/local/etc/rc.d/. Đóng gói file đơn vị sự nghiệp và bó dịch vụ, nếu bạn đang làm cho họ, đi ở những nơi khác nhau, mặc dù.

đọc thêm


2
@LucianoAndressMartini Một câu hỏi hay hơn là làm thế nào để xử lý một đoạn mã cụ thể của RC.local trong một dịch vụ systemd. Vì vậy, nếu bạn có một đoạn trích cụ thể (bạn đề cập đến các hướng dẫn từ tài liệu của một số phần mềm), có thể gửi câu hỏi về câu hỏi đó thay thế? Có một số quy tắc chung nhất định có thể được sử dụng để chuyển đổi, nhưng bạn tận dụng được nhiều hơn bằng cách khai thác các tính năng của phần mềm bạn đang chạy (chẳng hạn như chạy ở nền trước, không cố gắng tạo da, v.v.) để hỏi về một trường hợp cụ thể có thể hữu ích
filbranden

4
Bạn phải tự hỏi nếu nó đã sống sót từ năm 1983, có lẽ nó sẽ có cái gì đó cho nó?
dan carter

4
Câu trả lời này mang tính thuyết giáo và thực sự không trả lời được câu hỏi đơn giản "tôi nên làm gì tầm thường thay thế". Nó có thể chứa thông tin và cung cấp hàng tấn tài liệu tham khảo, nhưng đánh bại mục đích của stackexchange.
gps

Tôi đưa cái này (phần cuối của RC.local) lên, cùng với dns giải quyết các vấn đề, vì lý do tại sao linux không phát triển, nhưng thực sự ngày càng trở thành mã spaghetti, systemd đã trở thành một hộp đen đối với nhiều người. Nếu người dùng hoặc quản trị viên muốn đặt một cái gì đó vào RC.local và không còn có thể, thì việc buộc họ trước tiên thực hiện các khóa học systemd hoặc bất cứ điều gì khác mà bạn giảng để đạt được kết quả cuối cùng trong vài ngày, thay vì vài phút. Tất nhiên, những kẻ ngốc có thể làm những điều ngu ngốc với mọi thứ hoạt động tốt và dễ làm việc, đó không bao giờ là một lý lẽ hợp lệ để kết thúc nó.
Julius

2

Tóm tắt https://www.linuxbabe.com/linux-server/how-to-enable-etcrc-local-with-systemd

Tạo /etc/systemd/system/rc-local.service:

# /etc/systemd/system/rc-local.service
[Unit]
 Description=/etc/rc.local Compatibility
 ConditionPathExists=/etc/rc.local

[Service]
 Type=forking
 ExecStart=/etc/rc.local start
 TimeoutSec=0
 StandardOutput=tty
 RemainAfterExit=yes
 SysVStartPriority=99

[Install]
 WantedBy=multi-user.target

Sau đó:

sudo touch /etc/rc.local
sudo chmod +x /etc/rc.local
sudo systemctl enable rc-local

Kiểm tra với:

sudo systemctl start rc-local.service
sudo systemctl status rc-local.service

Một sử dụng do systemd cung cấp StandardOutput=journal+console(bảng điều khiển tương đương với tty trong ví dụ của bạn), có vẻ như nó sẽ hữu ích hơn nhiều cho việc khắc phục sự cố. Cũng hỗ trợ cho SysVStartPriority=đã được gỡ bỏ tại một số điểm. Có lẽ bạn có thể nhận xét tầm quan trọng của SysVStartPriority=nó, hoặc loại bỏ nó. Ngoài ra, đó là một câu trả lời tốt.
nguồ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.