ExecStart bukan shell: memperbaiki unit pembantu VPN
ExecStart menjalankan program dengan argumen, bukan pipeline shell. Gunakan penafsir eksplisit atau skrip sungguhan, lalu verifikasi unit dan baca jurnal.
Salin baris perintah yang berfungsi ke ExecStart, muat ulang, dan unit gagal atau keluar diam-diam karena argumen diperlakukan sebagai nama berkas. Tidak ada yang rusak di systemd. ExecStart adalah daftar argumen, bukan shell, sehingga pipa, pengalihan, dan kondisional kehilangan maknanya begitu keluar dari terminal Anda. Putuskan di mana shell seharusnya berada, lalu tulis unit yang menyatakan dengan tepat apa yang harus dijalankan.
Mengapa pipeline di ExecStart tidak melakukan apa pun
Saat perintah diketik di terminal, shell menguraikannya lebih dulu. Ia membangun pipeline, membuka berkas untuk pengalihan, dan memperluas variabel sebelum program apa pun mulai. systemd tidak melakukan semua itu: ia memecah ExecStart menurut aturannya sendiri dan menjalankan program yang dihasilkan dengan argumen tersebut. Karena itu > tiba sebagai argumen literal, dan | diserahkan ke program alih-alih menghubungkan dua proses. Unit tidak berperilaku salah; sintaksisnya bermaksud lain.
Itu disengaja, bukan kelalaian, karena penanganan argumen yang dapat diprediksi itulah yang membuat unit dapat diaudit. Itu hanya mengejutkan mereka yang menganggap ada shell.
Tulis unit yang menyatakan dengan tepat apa yang berjalan
Mulailah dengan unit kecil yang tujuannya terlihat di jurnal, agar masalah penguraian tetap terpisah dari masalah terowongan. Yang ini hanya melaporkan versi sebuah biner.
[Unit]
Description=Report the installed OpenVPN version
[Service]
Type=oneshot
ExecStart=/usr/sbin/openvpn --version
StandardOutput=journal
StandardError=journalJalurnya adalah pengganti, jadi gantilah dengan biner yang benar-benar terpasang. Type=oneshot cocok untuk perintah yang berjalan sampai selesai, dan pengaturan jurnal menaruh keluarannya di tempat yang bisa Anda baca tanpa terminal. Sengaja tidak ada bagian pemasangan, jadi unit dipanggil dengan tangan alih-alih diaktifkan saat boot. Validasi berkas sebelum menjalankannya, karena salah ketik pada nama direktif gagal dengan cara berbeda dari salah ketik pada jalur.
systemd-analyze verify /etc/systemd/system/openvpn-version.service
systemctl start openvpn-version.serviceSimpan logika shell dalam skrip
Ketika pembantu benar-benar membutuhkan logika bersyarat, taruh logika itu dalam skrip dan panggil secara eksplisit. Skrip membutuhkan baris penafsir, izin eksekusi, dan kode keluar yang bisa dilaporkan layanan. Menjalankan /bin/sh -c dengan perintah dalam tanda kutip memang berhasil, tetapi menyembunyikan aturan kutipan di dalam unit dan mempersulit peninjauan. Skrip bernama bisa diuji dengan tangan dan diganti kemudian tanpa menyunting unit. Jangan bergantung pada profil shell pengguna interaktif, karena layanan dimulai dengan lingkungannya sendiri.
Setel WorkingDirectory ketika jalur relatif penting, dan teruskan lingkungan melalui direktif unit yang didukung alih-alih mengekspornya di terminal. Rahasia berada di berkas terlindungi atau kredensial, bukan di daftar argumen yang mungkin dicatat jurnal.
Periksa unit yang benar-benar ada
Berkas drop-in mengubah perilaku tanpa menyentuh berkas yang Anda ingat telah disunting. Baca apa yang dimuat manajer dan apa yang dilaporkan jalannya terakhir.
systemctl cat vpn-helper.service
journalctl -u vpn-helper.service -n 20 --no-pagerDump unit menyertakan berkas drop-in dalam urutan pemuatan, dan dari sanalah ExecStart tak terduga biasanya berasal. Setelah setiap perubahan, muat ulang manajer dan pastikan definisi baru adalah yang dicetak systemctl cat. Jurnal menunjukkan baris perintah persis dan status keluar, yang memisahkan masalah argumen dari biner yang hilang atau galat izin. Lalu putuskan apakah pembantu itu milik siklus hidup VPN yang ada atau harus tetap menjadi diagnostik manual, karena proses terowongan latar belakang kedua menciptakan pemilik yang bersaing.
Unit yang mencetak keluaran benar saat diminta adalah tonggak pertama yang baik. Itu belum terowongan, dan tidak boleh berpura-pura menjadi terowongan.