0. Indeks
- Ting som skjer med folk flest
- Struktur av et skript
- Skriv ut på skjermen
- Les brukerINNGANG
- Beregninger i bash
- Vilkår
- Sløyfer
- Funciones
- getops
1. Ting som skjer med folk flest
/ bin / bash eller / bin / sh
En av de første tingene maskinen gjør når man utfører skriptet vårt, er å se på hvilket skall det skal gjøre det med. På de fleste nåværende Linux-systemer / Bin / sh er en lenke til / bin / bash, men dette er ikke alltid tilfelle, for eksempel i distribusjoner som bruker opptattboks Traen Sh og vanligvis tar de også med seg Bash, men hvis du bruker / Bin / sh, den kjører ikke med Bash. Derfor anbefaler jeg alltid å bruke / bin / bash.
Unicode vs. ASCII
Har du noen gang lurt på hvorfor du ikke kan bruke "¿" eller "ñ" i manusene dine? Eller bruke aksenter? Det kan være ganske irriterende i interaktive skript. Det er fordi standardkodingen av Bash er ASCII, eller hva som er det samme, det engelske tegnsettet. For å endre det, trenger vi bare å fortelle skriptet vårt at vi vil bruke Unicode. For det må du legge til en linje like etter kommandotolken:
# - * - KODING: UTF-8 - * -
Vær forsiktig, det er viktig at denne linjen er i begynnelsen av skriptet.
Gjør skriptet kjørbart
Det er morsomt hvor mange som kjører manusene med «$ bashscript.sh" i stedet for "$ ./script.sh'Det er tross alt det vi har definert et skall for.
For å legge til kjøringstillatelser, må du utføre:
sudo + x script.sh
BIN = "mappe der vi har skriptene" PATH = "$ BIN $ PATH"
2. Struktur av et manus
- Hodegavl
- Definisjon av globale variabler
- Hjelp
- Funciones
- Hoveddelen
Overskriften er der vi indikerer hvilket skall vi vil bruke og kodingen. Fordelen med funksjonene er å gjenbruke kode som gjentas ved å skrive den bare én gang og gjøre det lettere å forstå skriptet, for kode som overstiger 100 linjer er det veldig nyttig.
For å kunne bruke funksjoner, må de defineres med før hoveddelen av skriptet vårt. Og hvis vi vil bruke variabler på globalt nivå gjennom hele skriptet, både i hoveddelen og i funksjonene, må vi definere dem i begynnelsen av alt, like etter overskriften.
Til slutt er det god praksis å skrive en hjelperfunksjon for når skriptet vårt kjører dårlig eller med dårlige parametere. Åpenbart vil vi i de tilfellene avslutte skriptet umiddelbart uten å lese funksjonene. For det kan vi bruke:
funksjonshjelp () {ekko "" "Vår velformaterte hjelpetekst." "" avslutt hvis [[-z $ 1 || $ 1 == "-h" || $ 1 == "--hjelp"]]; så hjelp fi
Hvis vi legger til "exit" i hjelpefunksjonen, vil vi avslutte skriptet hver gang vi kjører hjelp, for eksempel etter feilmeldinger osv. Vi sparer noen få kodelinjer.
Betingelsen indikerer visningshjelp på skjermen og avslutt hvis skriptet kjøres uten parametere eller hvis -h / –help er spesifisert. Hvis du ser på det, er det standardoppførselen til de fleste linux-programmer.
3. Skriv ut på skjermen
Det er to hovedkommandoer for utskrift til skjerm i bash: «savner»Y«printf«. De er begge like raske, og begge er en del av bash. Hovedforskjellen for en nybegynner er at ekko legger til en ny linje på slutten, mens «printf"Gjør ikke.
Ekko er veldig bra og er det folk flest bruker, men når du leser brukerens INNGANG, eller når du vil skrive ut variabler hentet fra filer ved tekstbehandling, kan rare ting skje. De løses vanligvis lett, like enkelt som å endre doble anførselstegn til enkelt eller omvendt, eller ta de variable referansene ut av anførselstegnene. «Echo»Gjør rare ting også avhengig av hvordan det ble samlet, hvis vi alltid bruker Ubuntu eller alltid Fedora, påvirker det ikke oss, men hvis vi endrer distribusjonen gjør det.
Det er derfor jeg bruker «printf«, Som ikke gir meg hodepine og oppfører seg mer som«printf»Fra C eller«skrive ut»Av Python er dette veldig viktig hvis du noen gang vil portere skriptet ditt til et annet programmeringsspråk.
4. Les brukerINNGANG
Alt vi skriver etter navnet på skriptet vårt og før vi trykker på ENTER-tasten lagres automatisk i spesielle variabler. Disse variablene er av typen $ X der X er et tall.
«$0»Angir navnet på skriptet vårt og fra«$1»Alt det vi har skrevet senere er uendelig variabelt. For eksempel:
cat << EOF >> test.sh #! / bin / bash # - * - KODING: UTF-8 - * - printf "\ $ 0 = $ 0 \ n" printf "\ $ 1 = $ 1 \ n" printf "\ $ 2 = $ 2 \ n" EOF chmod + x script.sh ./script.sh filen.txt
Vi oppretter et testskript, gjør det kjørbart og kjører det med to parametere. Vi får skjermutdata fra:
$ 0 = ./script.sh $ 1 = min $ 2 = file.txt
Ved å bruke anførselstegn kunne vi ha sendt "min fil.txt" til "$ 1".
Vi kan også lese INNGANGEN til en bruker med "lese" -kommandoen, som direkte indikerer variabelen der vi vil lagre parameteren. For eksempel:
printf "Hva heter du? \ n" les NAME printf "Hei, $ NAME. \ n"
5. Beregninger i Bash
Til det kan vi bruke «ekspr«Så lenge vi ikke trenger å gjøre komplekse beregninger. To ting skal bemerkes, den første er at «ekspr»Bare innrømmer hele tall, det andre er at inndelingen returnerer hele resultatet, for å se resten vi kan bruke«%".
Vanligvis vil vi tildele resultatet av expr til en variabel. Vi kan gjøre det på to måter:
VAR2 = `expr $ VAR1 / 10` VAR2 = $ (expr $ VAR1 / 100)
Du kan også hoppe over «ekspr»Bruke doble parenteser:
VAR2 = $ (($ VAR1 / 100))
6. vilkår
Det er allerede skrevet på en meget omfattende måte om «if" 'ellers" 'elif»Og forhold. Du kan lese om det i:
- Programmering i Bash: del 1
- Bash: hvis, da, ellers forhold
- Sjekk om en fil eller mappe eksisterer eller ikke, og mer med en if-loop
- Programmering i Bash: del 2
Jeg vil bare trekke frem forskjellen mellom bruk av enkle firkantede parenteser, «[]«, Og doble parenteser,«[[]]«, For forholdene. Med doble braketter kan vi bruke tilleggsbetingelser:
- «&&»For og
- «||»For eller
Å bruke "&&»Y«||»Med enkle firkantede parenteser, bør hver del skilles i separate firkantede parenteser. Eksemplet som brukes for den delen av skriptet som ser for å se om hjelp må utføres, er:
hvis [-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "--hjelp"]]; så hjelp fi
Det sparer oss også fra å måtte skrive variabelnavn i anførselstegn for å forhindre feil. For eksempel:
hvis [$ 1 = 1]; deretter printf "Parameteren er lik 1."; fi if ["$ 1" = 1]; deretter printf "Parameteren er lik 1."; fi hvis [[$ 1 = 1]]; deretter printf "Parameteren er lik 1."; fi
Hvis script.sh kjøres uten noen parametere, vil det første tilfellet gi en feil:
bash: [: =: forventet unary operatør
Det som ikke har blitt snakket om er «saken«, Brukes til å forenkle«if«. La oss begynne på begynnelsen når vi ikke har noen «if»All koden blir utført. Hvis vi legger til en betingelse «if»Vi vil ha to tilfeller, en der kodeblokken inne i«if»Og det andre tilfellet der denne blokken ikke blir utført.
Hvis vi legger til en «ellers«Vi vil også ha to saker, men disse to sakene er forskjellige fra de forrige. For nå vil det være to betingede kodeblokker, A og B, og en C-blokk, som er resten av programmet. A eller B vil bli henrettet, og C. I forrige tilfelle var det A og C eller bare C.
For å unngå skrivevilkår «hvis / annet"innenfor"ellers»Og for å forenkle lesingen av koden, ble den opprettet«elif«. Når vi har mange forhold som avhenger av den forrige, for eksempel tallrekke eller typen:
VAR1 = $ 1 hvis [[$ VAR1 = 1]]; deretter printf "1 \ n" elif [[$ VAR1 = 2]]; deretter printf "2 \ n" elif [[$ VAR1 = 3]]; deretter printf "3 \ n" annet printf "none \ n" fi
Når det gjelder den siste «elif»Mange forhold vil bli lest. I tilfelle er denne prosessen strømlinjeformet:
VAR1 = $ 1 sak $ VAR i 1) printf "1 \ n" ;; 2) printf "2 \ n" ;; 3 | 4) printf "3 eller 4, det kommer an \ n" ;; *) printf "ingen \ n" ;; at C
En variabel vil bli lest, i dette tilfellet VAR1, og det vil bli sjekket om den tilsvarer noen av tilfellene, hvis ikke, vil standardtilfellet "*" bli utført. Dobbelt semikolon tilsvarer «bryte", De forteller"saken»Det må ta slutt.
7. Sløyfer
Svært få sløyfer er kjent på noe programmeringsspråk. I Bash er de «mens" 'til»Y«forum«. Det er allerede skrevet i bloggen om disse:
Det er to typer løkker «forum«, De som er av typen«$ for VAR i LOQUESEA»Og hva er av type C«$ for ((I = 0; I <= 10; I ++))«. Den andre typen løkker «forum»Er veldig nyttige, den har 3 deler i begynnelsen av løkken:
- Erklæring og initiering av variabler (I dette tilfellet en hjelpevariabel "I = 0").
- Utførelsesbetingelse (til jeg er mindre enn eller lik 10).
- Økning av hjelpevariabelen
Etter min mening er det den mektigste sløyfen av alle. Et eksempel som skriver ut alle tall fra 0 til 10, inkludert:
#! / bin / bash for ((I = 0; I <= 10; I ++)); gjør printf "$ I \ n" ferdig
8. Funksjoner
Det er noen ting som Bash ikke tillater oss å gjøre, ikke sant? Ved første øyekast hindrer bash-funksjoner deg i å gjøre tre ting: å erklære lokale variabler i funksjoner, overføre parametere til funksjoner og returnere parametere. Alt har en løsning.
Gjør ingenting som:
#! / bin / bash VAR = 1 printc "$ VAR \ n" -funksjon hallo () {VAR = 2 printf "$ VAR \ n"} hallo printf "$ VAR \ n"
Dette skrives ut på skjerm 1, 2 og 2.
For å erklære lokale variabler, legg til «lokal»Når du erklærer:
#! / bin / bash VAR = 1 printf "$ VAR1 \ n" funksjon foo () {local VAR1 = 2 printf "$ VAR1 \ n"} printf "$ VAR1 \ n" foo printf "$ VAR1 \ n"
Dette skriver ut 1, 1, 2, 1 til skjermen.
Hvordan overfører du parametere til en funksjon?
#! / bin / bash # - * - KODING: UTF-8 - * - funksjon hei () {printf "Hei $ 1 \ n"}
printf "Hva heter du? \ n"
les VAR1
hei $ VAR1
Hvordan returneres parametere?
#! / bin / bash # - * - KODING: UTF-8 - * - funksjon hallo () {printf "Hello holita"} printf "Hva heter du? \ n" les VAR1 VAR1 = $ (hallo) # HER ER DET printf "$ VAR1 $ VAR2 \ n"
Som du kan se, har dette to ulemper, du kan bare returnere en parameter, som kan være en vektor 😀, og hvis du vil returnere en parameter, kan du ikke lenger skrive ut på skjermen fra den funksjonen.
9. Getops
En av de siste tingene du trenger å vite om Bash for å lage komplekse skript er «getops«. Den brukes til å overføre alternativer til skriptet uansett rekkefølge. Den eneste ulempen er at den bare påvirker korte alternativer:
#! / bin / bash # - * - KODING: UTF-8 - * - VARC = 0 funksjonshjelp () {printf "Hjelpemelding \ n" avslutt} hvis [[-z $ 1]]; så hjelp fi mens getopts: ha: b: c OPT; gjør saken $ OPT i h) hjelp ;; :) hjelp ;; a) VARA = $ OPTARG ;; b) VARB = $ OPTARG ;; c) VARC = 1 ;; \?) hjelp ;; esac done # Hovedblokk av skriptet som # gjør ting med VARA, VARB og VARC
«getopts»Les alternativene en etter en, så det kreves en løkke.
Det er to typer alternativer som kan overføres ved hjelp av «getopts':
- Parametere kalt flagg, i dette tilfellet -c eller -h. De er spesifisert med bokstaven vi vil bruke. De er som boolske variabler, «sant»(Are) eller«falsk"(De er ikke her).
- Parametere med tilhørende argumenter, -a hva som helst, -b hva som helst. De er spesifisert med bokstaven vi ønsker med et kolon nedenfor. Argumentet er lagret i OPTARG (dette navnet kan ikke endres).
Hva gjør dette skriptet?
Viser hjelpemeldingen når ingen valg sendes, når parameteren "-h" sendes, når en ugyldig parameter sendes (for eksempel "-x", gjøres dette med "\?") Eller når en gyldig parameter uten argument (":"). I resten av tilfellene sparer det tilstedeværelsen av "-c" som en 1 i VARC, og verdiene overført med "-a" og "-b" i VARA og VARB.
MESTLIG. Jeg sier ikke mer U_U
Hei veldig god artikkel.
Hei du satte for å gi tillatelser sudo + x i stedet for chmod + x
$ sudo chmod + x script.sh
(For å være mer nøyaktig, hehe)
Ah, gratulerer og takk!
Veldig bra innlegg, sannheten er at jeg gratulerer deg, fortsett, Hilsen
Og hvis du vil at skriptet skal være synlig når det kjøres, trinn for trinn, for eksempel å se hvordan variabler, betingelser og alt oppfører seg, kan du bruke:
sh -x skript
Hilsen
STYKK av veiledning. Utmerket og veldig godt forklart.
Takk.
Utmerket innlegg om emnet 😉
Veldig interessant og viktig, takk for informasjonen ....
JUBEL !!!
Takk alle for gratulasjonene dine, for Miguel-kommandoen, han lar meg ikke endre oppføringen når den er publisert. Jeg må forestille meg det.
Veldig bra!
Først av alt ønsket jeg å gratulere deg med innlegget, jeg syntes det var lett å forstå, og det hjelper virkelig å følge retningslinjene for å programmere godt i bash, spesielt for folk som begynner å programmere.
Imidlertid har jeg funnet et par detaljer som jeg mener bør rettes.
Først: i seksjon «2. STRUKTUR AV ET SKRIPT »funksjonen er ikke lukket, noe som vil føre til problemer når den kjøres i et skript.
Løsningen vil være å legge til en lukkestang til den like etter "exit" -kommandoen.
For det andre: i seksjon «4. LES BRUKERINNGANGEN ”du bekrefter at parameterne som brukeren kan angi varierer fra $ 0 til uendelig, men“ bash ”tolker bare fra $ 0 til $ 9, siden $ 10 vil være lik $ 1 + 0.
For å løse dette problemet kan du enten bruke kommandoen "shift" til å hente følgende variabler. Eller spesifiser variabelen i parentes "$ {10}", slik at bash tar verdiene sammen, ikke som $ 1 + 0.
Uten videre, hilsen!
Takk for kommentaren. Det mislyktes helt å forklare riktig bruk av exit, både i skriptet og i funksjonene. Når det gjelder $ {10} har jeg aldri testamentert så mye, så jeg har ikke fått det problemet, det er godt å vite at det er en løsning på det (jeg har allerede krysset av det nye som ble lært i dag 😀).
Tusen takk for artikkelen! Noen ting du nevner manglet fremdeles avklaring. For eksempel getops.
I delen av skjermutgangene måtte du nevne katten som du senere nevnte ...
katt <
***************************************
* DETTE SKJEMAET ER VELDIG UTRYKTIG *
***************************************
EOF
I eksemplet ditt:
katt << EOF >> test.sh
To ting bør nevnes ... >> det er "legg til" det vil si at hvis du gjentar den samme kommandoen, vil du ha hele skriptet i duplikat ... Du bør bare bruke en ...
katt << EOF> script.sh
Ja, det skal også kalles script.sh
Så inn
hvis [-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "–hjelp"]]; deretter
hjelpe
fi
Jeg synes det skal skrives ...
hvis [[-z "$ 1"] || ["$ 1" == "-h"] || ["$ 1" == "–hjelp"]]; deretter
...
Det er mye mer å oppdage fra BASH.
Kan du gi den tittelen "BASICS"? 🙂
For eksempel, parameter 'testere' som -z for å se om de er tomme, eller -f for å se om den eksisterer som en fil.
Takk igjen for innsatsen.
alberto
En veldig god bash script tutorial!
-- KODING: UTF-8 --
Det er første gang jeg har sett den linjen for å sette tegnkoding i et bash-skript. Det virker mer som Python enn Bash. Er det virkelig nødvendig? Jeg har søkt etter en referanse på Google, men jeg finner ikke noe. Har du en lenke for hånden som snakker om denne saken? Spesielt på egnetheten til den linjen.
Etter min mening, for å skrive skript i Bash ved bruk av UTF-8, trenger du bare å lagre tekstfilen som sådan (uten BOM) og ha visse miljøvariabler, (LANG og LC_ *), riktig innstilt.
Så er det åpenbart nødvendig at de utførte kommandoene er forberedt på andre kodinger enn ASCII. Hvis vi for eksempel vil gå til store bokstaver, ser det ikke ut til å fungere:
«Ekko áéíóú | tr az AZ »
o:
«Ekko áéíóú | tr [: nedre:] [: øvre:] »
og det er bedre å bruke:
«Ekko áéíóú | awk '{print toupper ($ 0)}' ».
Om «koding»Har blitt nevnt i denne bloggen før:
Bash: hvordan lage et skript som kan kjøres
Post installasjonsverktøy skript
Noen retter meg, men den kodende linjen (# -- KODING: UTF-8 --) Det har ingenting å gjøre med bash eller skallet: det er en kommentarlinje (begynner med #) og tjener til å fortelle redaktøren at vi bruker til å skrive skriptet (vim, emacs ...) kodingen av filen.
Bash ser faktisk ikke en slik linje, fordi det er en kommentarlinje.
Utmerket opplæring, ettersom Sysadmin å vite skript i Bash er viktig, er det nyttig for alt.
Veldig veldig bra!
Greetings!
Hvis det er nyttig for noen, er det flere bruksområder og eksempler for å lage dine egne skript: https://github.com/reduardo7/hsabx
Veldig bra. Nye ting å legge til i skriptene mine. Encodig ting og printf ting hadde ikke det.
Takk skal du ha!!!
Sååå god artikkel! Jeg holder denne for favoritter, det ville være fint å rette opp det som er galt og til og med utvide det med mer innhold. En applaus for all denne informasjonen !!!!