ExecStart ei ole shell: VPN-apuyksikön korjaaminen
ExecStart käynnistää ohjelman argumenteilla, ei shell-putkea. Käytä nimenomaista tulkkia tai oikeaa skriptiä, tarkista sitten yksikkö ja lue journal.
Kopioi toimiva komentorivi ExecStartiin, lataa uudelleen, ja yksikkö epäonnistuu tai päättyy äänettömästi, koska argumentit tulkitaan tiedostonimiksi. systemd:ssä ei ole mitään rikki. ExecStart on argumenttiluettelo, ei shell, joten putket, uudelleenohjaus ja ehdot menettävät merkityksensä heti, kun ne poistuvat päätteeltäsi. Päätä, mihin shell kuuluu, ja kirjoita sitten yksikkö, joka kertoo täsmälleen, mitä pitää suorittaa.
Miksi ExecStartin putki ei tee mitään
Kun komento kirjoitetaan päätteelle, shell jäsentää sen ensin. Se rakentaa putken, avaa tiedostoja uudelleenohjausta varten ja laajentaa muuttujat ennen kuin mikään ohjelma käynnistyy. systemd ei tee mitään tästä: se jakaa ExecStartin omien sääntöjensä mukaan ja suorittaa tuloksena olevan ohjelman näillä argumenteilla. Siksi > saapuu kirjaimellisena argumenttina ja | annetaan ohjelmalle sen sijaan, että se yhdistäisi kaksi prosessia. Yksikkö ei käyttäydy väärin; syntaksi tarkoitti jotain muuta.
Se on tahallista eikä huolimatonta, koska ennustettava argumenttien käsittely tekee yksiköistä auditoitavia. Se yllättää vain ne, jotka olettavat shellin olevan läsnä.
Kirjoita yksikkö, joka kertoo täsmälleen, mitä ajetaan
Aloita pienestä yksiköstä, jonka tarkoitus näkyy journalissa, jotta jäsennysongelmat pysyvät erillään tunneliongelmista. Tämä ilmoittaa vain binäärin version.
[Unit]
Description=Report the installed OpenVPN version
[Service]
Type=oneshot
ExecStart=/usr/sbin/openvpn --version
StandardOutput=journal
StandardError=journalPolku on paikkamerkki, joten korvaa se binäärillä, joka on todella asennettu. Type=oneshot sopii komennolle, joka ajetaan loppuun asti, ja journalin asetukset vievät sen tulosteen sinne, missä voit lukea sen ilman päätettä. Asennusosiota ei ole tarkoituksella, joten yksikkö kutsutaan käsin sen sijaan, että se otettaisiin käyttöön käynnistyksessä. Validoi tiedosto ennen sen käynnistämistä, koska kirjoitusvirhe direktiivin nimessä epäonnistuu eri tavalla kuin virhe polussa.
systemd-analyze verify /etc/systemd/system/openvpn-version.service
systemctl start openvpn-version.servicePidä shell-logiikka skriptissä
Kun apuri todella tarvitsee ehdollista logiikkaa, laita se logiikka skriptiin ja kutsu sitä nimenomaisesti. Skripti tarvitsee tulkkirivin, suoritusoikeuden ja poistumiskoodit, jotka palvelu voi ilmoittaa. Käynnistäminen /bin/sh -c lainatulla komennolla toimii, mutta se kätkee lainausmerkkisäännöt yksikön sisään ja vaikeuttaa tarkistusta. Nimetty skripti voidaan testata käsin ja korvata myöhemmin muokkaamatta yksikköä. Älä luota interaktiivisen käyttäjän shell-profiiliin, koska palvelu käynnistyy omassa ympäristössään.
Aseta WorkingDirectory, kun suhteelliset polut ovat tärkeitä, ja välitä ympäristö yksikön tuettujen direktiivien kautta sen sijaan, että veisit sen päätteellä. Salaisuudet kuuluvat suojattuihin tiedostoihin tai tunnistetietoihin, eivät argumenttiluetteloihin, jotka journal voi tallentaa.
Tarkista yksikkö, joka todella on olemassa
Drop-in-tiedostot muuttavat käyttäytymistä koskematta tiedostoon, jonka muistat muokanneesi. Lue, mitä hallinta latasi ja mitä viimeisin ajo ilmoitti.
systemctl cat vpn-helper.service
journalctl -u vpn-helper.service -n 20 --no-pagerYksikön tuloste sisältää drop-in-tiedostot latausjärjestyksessä, ja juuri sieltä odottamaton ExecStart yleensä tulee. Lataa hallinta uudelleen jokaisen muutoksen jälkeen ja varmista, että uusi määritelmä on se, mitä tulostaa systemctl cat. Journal näyttää tarkan komentorivin ja poistumistilan, mikä erottaa argumenttiongelman puuttuvasta binääristä tai käyttöoikeusvirheestä. Päätä sitten, kuuluuko apuri olemassa olevaan VPN-elinkaareen vai pitäisikö sen jäädä manuaaliseksi diagnostiikaksi, koska toinen taustalla oleva tunneliprosessi luo kilpailevan omistajan.
Yksikkö, joka tulostaa oikean tulosteen pyydettäessä, on hyvä ensimmäinen virstanpylväs. Se ei ole vielä tunneli, eikä sen pidä teeskennellä olevansa.