Kaj so stdin, stdout in stderr v Linuxu?
Fatmawati Achmad Zaenuri/Shutterstock.com
|_+_|, |_+_| in |_+_| so trije podatkovni tokovi, ustvarjeni, ko zaženete ukaz Linux. Z njimi lahko ugotovite, ali so vaši skripti cevovodni ali preusmerjeni. Pokažemo vam, kako.
Tokovi združijo dve točki
Takoj, ko se začnete učiti o operacijskih sistemih Linux in Unixu podobnih, boste naleteli na izraze |_+_|, |_+_| in |_+_|. To so trije standardni tokovi ki se vzpostavijo, ko se izvede ukaz Linux. V računalništvu je tok nekaj, kar lahko prenaša podatke. V primeru teh tokov so ti podatki besedilo.
Podatkovni tokovi, tako kot vodni tokovi, imajo dva konca. Imajo izvor in odtok. Ne glede na ukaz Linuxa, ki ga uporabljate, zagotavlja en konec vsakega toka. Drugi konec je določen z lupino, ki je sprožila ukaz. Ta konec bo povezan s terminalskim oknom, povezan s cevjo ali preusmerjen v datoteko ali drug ukaz, v skladu z ukazno vrstico, ki je zagnala ukaz.
Standardni tokovi za Linux
V Linuxu |_+_| je standardni vhodni tok. To sprejme besedilo kot svoj vnos. Besedilni izhod iz ukaza v lupino se dostavi prek |_+_| (standardni izhodni) tok. Sporočila o napakah iz ukaza se pošljejo prek |_+_| (standardna napaka) tok.
Tako lahko vidite, da obstajata dva izhodna toka, |_+_| in |_+_| ter en vhodni tok, |_+_|. Ker imajo sporočila o napakah in običajni izhod vsak svoj vod za prenos do terminalskega okna, jih je mogoče obravnavati neodvisno drug od drugega.
Tokovi se obravnavajo kot datoteke
Tokovi v Linuxu – tako kot skoraj vse drugo – se obravnavajo, kot da so datoteke. Besedilo lahko berete iz datoteke in lahko pišete besedilo v datoteko. Oba dejanja vključujeta tok podatkov. Koncept ravnanja s tokom podatkov kot z datoteko torej ni tako zapleten.
OglasVsaki datoteki, povezani s procesom, je dodeljena edinstvena številka za njeno identifikacijo. To je znano kot deskriptor datoteke. Kadarkoli je treba izvesti dejanje nad datoteko, deskriptor datoteke se uporablja za identifikacijo datoteke.
Te vrednosti se vedno uporabljajo za |_+_|, |_+_| in |_+_|:
- 0 : stdin
- eno : stdout
- dve : stderr
Odziv na cevi in preusmeritve
Da bi nekomu olajšali uvajanje v predmet, je običajna tehnika poučevanje poenostavljene različice teme. Na primer, pri slovnici nam povedo, da je pravilo I pred E, razen za C. A pravzaprav tam je več izjem od tega pravila kot obstajajo primeri, ki ga ubogajo.
Podobno, ko govorimo o |_+_|, |_+_| in |_+_| priročno je izpostaviti sprejeti aksiom, da proces niti ne ve niti ne skrbi, kje se končajo njegovi trije standardni tokovi. Ali mora proces skrbeti, ali gre njegov izhod v terminal ali je preusmerjen v datoteko? Ali lahko sploh ugotovi, ali njegov vnos prihaja s tipkovnice ali se vanj prenaša iz drugega procesa?
Pravzaprav proces ve – ali vsaj lahko ugotovi, če se odloči za preverjanje – in lahko ustrezno spremeni svoje vedenje, če se avtor programske opreme odloči dodati to funkcionalnost.
OglasTo spremembo v vedenju lahko opazimo zelo enostavno. Poskusite ta dva ukaza:
stdin
stdout
|_+_| ukaz se obnaša drugače, če se njegov izhod (|_+_|) prestavi v drug ukaz. Je |_+_| ki preklopi na izhod enega stolpca, to ni pretvorba, ki jo izvede |_+_|. In |_+_| naredi isto, če je njegov izhod preusmerjen:
stderr
stdin
Preusmerjanje stdout in stderr
Prednost imajo sporočila o napakah, ki jih dostavi namenski tok. To pomeni, da lahko preusmerimo izhod ukaza (|_+_|) v datoteko in še vedno vidimo vsa sporočila o napaki (|_+_|) v terminalskem oknu. Po potrebi se lahko odzovete na napake, ko se pojavijo. Prav tako prepreči, da bi sporočila o napakah kontaminirala datoteko, ki |_+_| je bil preusmerjen v.
V urejevalnik vnesite naslednje besedilo in ga shranite v datoteko z imenom error.sh.
stdout
Naredite izvedljiv skript s tem ukazom:
stederr
Prva vrstica skripta odmeva besedilo v terminalsko okno prek |_+_| tok. Druga vrstica poskuša dostopati do datoteke, ki ne obstaja. To bo ustvarilo sporočilo o napaki, ki bo dostavljeno prek |_+_|.
Zaženite skript s tem ukazom:
stdin
Vidimo lahko, da sta oba toka izhoda, |_+_| in |_+_|, sta bila prikazana v oknih terminala.
Poskusimo preusmeriti izhod v datoteko:
stdout
Oglas
Sporočilo o napaki, ki je dostavljeno prek |_+_| je še vedno poslana v okno terminala. Vsebino datoteke lahko preverimo, ali je |_+_| izhod je šel v datoteko.
stderr
Izhod iz |_+_| je bil po pričakovanjih preusmerjen v datoteko.
|_+_| simbol za preusmeritev deluje z |_+_| privzeto. Uporabite lahko enega od deskriptorjev številskih datotek, da označite, kateri standardni izhodni tok želite preusmeriti.
Če želite izrecno preusmeriti |_+_|, uporabite to navodilo za preusmeritev:
stdout
Če želite izrecno preusmeriti |_+_|, uporabite to navodilo za preusmeritev:
stderr
Poskusimo znova preizkusiti in tokrat bomo uporabili |_+_|:
stdin
Sporočilo o napaki je preusmerjeno in |_+_| |_+_| sporočilo se pošlje v terminalsko okno:
Poglejmo, kaj je v datoteki capture.txt.
stdin
|_+_| sporočilo je v capture.txt po pričakovanjih.
Preusmerjanje Tako stdout kot stderr
Seveda, če lahko preusmerimo bodisi |_+_| ali |_+_| na datoteko neodvisno drug od drugega, bi morali biti sposobni preusmeriti obe hkrati v dve različni datoteki?
OglasJa lahko. Ta ukaz bo usmeril |_+_| v datoteko z imenom capture.txt in |_+_| v datoteko z imenom error.txt.
stdout,
Ker sta oba toka izhoda – standardni izhod in standardna napaka – preusmerjena v datoteke, v terminalskem oknu ni vidnega izhoda. Vrnjeni smo v poziv ukazne vrstice, kot da se ni nič zgodilo.
Preverimo vsebino vsake datoteke:
stderr
stdin
Preusmeritev stdout in stderr v isto datoteko
To je lepo, imamo vsak od standardnih izhodnih tokov, ki gredo v svojo namensko datoteko. Edina druga kombinacija, ki jo lahko naredimo, je, da pošljemo obe |_+_| in |_+_| na isto datoteko.
To lahko dosežemo z naslednjim ukazom:
stdout
Razčlenimo to.
- ./error.sh : Zažene skriptno datoteko error.sh.
- > capture.txt : Preusmeri |_+_| tok v datoteko capture.txt. |_+_| je okrajšava za |_+_|.
- 2> & 1 : To uporablja navodilo &> preusmeritev. To navodilo vam omogoča, da poveste lupini, naj en tok doseže isti cilj kot drugi tok. V tem primeru pravimo, da preusmeri tok 2, |_+_|, na isti cilj, na katerega je preusmerjen tok 1, |_+_|.
Ni vidnega izhoda. To je spodbudno.
Preverimo datoteko capture.txt in poglejmo, kaj je v njej.
stderr
Oba |_+_| in |_+_| tokovi so bili preusmerjeni v eno samo ciljno datoteko.
Če želite izhod toka preusmeriti in ga tiho zavreči, usmerite izhod na |_+_|.
Zaznavanje preusmeritve znotraj skripta
Razpravljali smo o tem, kako lahko ukaz zazna, ali je kateri od tokov preusmerjen, in se lahko odloči, da ustrezno spremeni svoje vedenje. Ali lahko to dosežemo z lastnimi scenariji? Ja lahko. In to je zelo enostavna tehnika za razumevanje in uporabo.
OglasVnesite naslednje besedilo v urejevalnik in ga shranite kot input.sh.
ls
Uporabite naslednji ukaz, da ga naredite izvršljivega:
stdout
Pameten del je preizkus v oglatih oklepajih . |_+_| (terminal) možnost vrne true (0), če je datoteka povezana z deskriptorjem datoteke konča v terminalskem oknu . Kot argument za test smo uporabili deskriptor datoteke 0, ki predstavlja |_+_|.
Če |_+_| je povezan s terminalskim oknom, se bo test izkazal za resničnega. Če |_+_| je povezan z datoteko ali cevjo, test ne bo uspel.
Za ustvarjanje vnosa v skript lahko uporabimo katero koli priročno besedilno datoteko. Tukaj uporabljamo enega, ki se imenuje dummy.txt.
ls
Izhod kaže, da skript prepozna, da vnos ne prihaja s tipkovnice, ampak iz datoteke. Če bi se tako odločili, bi lahko ustrezno spremenili vedenje svojega skripta.
Oglas
To je bilo s preusmeritvijo datoteke, poskusimo s cevjo.
cat
Skript prepozna, da je njegov vnos vanj speljan. Ali natančneje, še enkrat prepozna, da je |_+_| tok ni povezan s terminalskim oknom.
Zaženimo skript brez cevi ali preusmeritev.
ls
|_+_| tok je povezan s terminalskim oknom in skript o tem ustrezno poroča.
Če želite preveriti isto stvar z izhodnim tokom, potrebujemo nov skript. V urejevalnik vnesite naslednje in ga shranite kot output.sh.
stdout
Uporabite naslednji ukaz, da ga naredite izvršljivega:
stderr
Edina pomembna sprememba tega skripta je v testu v oglatih oklepajih. Številko 1 uporabljamo za predstavitev deskriptorja datoteke za |_+_|.
Preizkusimo ga. Izhod bomo prenesli skozi |_+_|.
stdout
Oglas
Skript prepozna, da njegov izhod ne gre neposredno v terminalsko okno.
Skript lahko preizkusimo tudi s preusmeritvijo izhoda v datoteko.
stdout
V terminalsko okno ni izhoda, tiho se vrnemo v ukazni poziv. Kot bi pričakovali.
Lahko pogledamo v datoteko capture.txt, da vidimo, kaj je bilo zajeto. Za to uporabite naslednji ukaz.
stderr
Ponovno preprost test v našem skriptu zazna, da |_+_| tok se ne pošilja neposredno v terminalsko okno.
OglasČe zaženemo skript brez cevi ali preusmeritev, bi moral zaznati, da |_+_| se dostavi neposredno v okno terminala.
stdout
In točno to vidimo.
Tokovi zavesti
Če veste, kako ugotoviti, ali so vaši skripti povezani s terminalskim oknom, cevjo ali so preusmerjeni, vam omogoča, da ustrezno prilagodite njihovo vedenje.
Beleženje in diagnostični izhod je lahko bolj ali manj podroben, odvisno od tega, ali gre na zaslon ali v datoteko. Sporočila o napakah se lahko zabeležijo v drugo datoteko kot običajni programski izhod.
Kot je običajno, več znanja prinaša več možnosti.
POVEZANO: Najboljši prenosni računalniki Linux za razvijalce in navdušence
PREBERITE NAPREJ- & rsaquo; Kako uporabljati at in serijsko na Linuxu načrtovati ukaze
- & rsaquo; Ukazne vrstice: zakaj se ljudje še vedno obremenjujejo z njimi?
- & rsaquo; Kako uporabljati ukaz Echo v Linuxu
- & rsaquo; Kako ustvariti stran man v Linuxu
- & rsaquo; Kako obdelati datoteko po vrstici v skriptu Linux Bash
- & rsaquo; 15 posebnih znakov, ki jih morate poznati za Bash
- › Kako najti svoj Spotify Wrapped 2021
- & rsaquo; Cyber ponedeljek 2021: najboljše tehnične ponudbe
Dave McKay je prvič uporabil računalnike, ko je bil v modi luknjani papirni trak, in od takrat se ukvarja s programiranjem. Po več kot 30 letih v IT industriji je zdaj redni tehnološki novinar. V svoji karieri je delal kot samostojni programer, vodja mednarodne ekipe za razvoj programske opreme, vodja projektov IT storitev in nazadnje kot pooblaščenec za varstvo podatkov. Njegovo pisanje so objavili howtogeek.com, cloudsavvyit.com, tenterpriser.com in opensource.com. Dave je evangelist Linuxa in zagovornik odprte kode.
Preberite celotno biografijo