đĄ Gallium
TĂ€rpit
Avainsanat
Aivan kuten BashissÀ, myös PowerShellissÀ on varattuja sanoja, joita ei voi kÀyttÀÀ muuttujaniminÀ. TÀssÀ on lista niistÀ:
The following are the reserved words in PowerShell:
assembly exit process
base filter public
begin finally return
break for sequence
catch foreach static
class from (*) switch
command function throw
configuration hidden trap
continue if try
data in type
define (*) inlinescript until
do interface using
dynamicparam module var (*)
else namespace while
elseif parallel workflow
end param
enum private
(*) These keywords are reserved for future use.
MistÀ nÀmÀ löytyivÀt?
Olettaen ettÀ Help on pÀivitetty, saat nÀmÀ auki komennolla:
Komennon help löytyy online: about_Reserved_Words.
Muuttujat
Koko totuus löytyy PowerShellin dokumentaatiosta (esim. about_Variables), mutta alla on pikaohje, jolla pÀÀset alkuun.
Dynaaminen
PowerShell on dynaamisesti tyypitetty kieli. TÀmÀ tarkoittaa, ettÀ sama muuttuja voi vaihtua kokoluvusta merkkijonoksi ja niin edelleen, ja tyyppi pÀÀtellÀÀn automaattisesti. Merkin =
vasemmalle puolella on muuttujanimi, oikealla on lauseke: {variable} = {expression}
. Lauseke voi olla literaali, kuten 123
, tai sisÀltÀÀ operaattoreita, kuten 100 + 125 - 2
. Oli niin tai nÀin, tulkki evaluioi =
-merkin oikealla puolella olevan lausekkeen ja yrittÀÀ sijoittaa kyseisen arvon muuttujaan. Muuttuja saa tÀmÀn tyypin.
$x = 1 # Kokonaisluku (Int32)
$x = 1 + 2 - 1 # ... kuten tÀmÀkin.
$x = 3.12 # Liukuluku (Double)
$x = "abc" # Merkkijono (String)
$x = @("abc", 42) # Taulukko (Array)
$x = @{a=1;b=2} # Hajautustaulu (Hash table)
Vaihtaminen
Tyypin voi myös itse mÀÀrÀtÀ, jolloin se kÀytÀnnössÀ castataan kyseiseksi muuttujaksi. Huomaa, ettÀ itse muuttuja on kuitenkin yhÀ dynaaminen:
$x = [byte] 255 # Nyt se onkin tavu (Byte)
$x = [int] 255 # ... eiku kokonaisluku (Int32)
$x = [string] "abc" # ... eiku merkkijono (String)
# Huomaa myös -as operaattori, joka palauttaa null jos castaus ei onnistu
$y = $x -as [int] # ... null, koska "abc" ei taivu luvuksi
TyypittÀminen
Voit myös kÀskeÀ muuttujan kÀyttÀmÀÀn tiettyÀ tyyppiÀ nyt ja jatkossa. Erona yllÀ olevaan on, ettÀ [type]$variable
on nyt vasemmalla puolella =
-merkkiÀ. Kaikki muuttujaan sijoitetut arvot pyritÀÀn jatkossa muuttamaan tÀhÀn tyyppiin. Jos muutos ei onnistu, saat virheen.
[string]$x = 1 # Kerran merkkijono, aina merkkijono
$x = "Kissa" # ... ja yhÀ
$x = 1 # ... ja yhÀ
[int]$y = 12 # Nro
$y = "Koira" # Virhe
Sokeasti automaattiseen tyypitykseen luottamisessa on omat riskinsÀ. Mieti tarkkaan, mitÀ seuraavassa tapahtuu:
SkriptejÀ kirjoittaessa tuskin tarvitset muita simple typejÀ kuin yllÀ listatut, mutta loput löytyvÀt esimerkiksi C# Docs: Simple Types tai DevBlogs: Understanding Numbers in PowerShell. NÀiltÀ sivuilta selviÀÀ myös numeraalisten tyyppien minimi- ja maksimiarvot, mikÀli tarvitset kertausta asiasta.
SelvittÀminen
Jos olet epÀvarma, mitÀ jotakin cmdlet palauttaa, voit aina selvittÀÀ sen nÀin:
# NÀin saat myös metodit ja parametrit esille
Get-Location | Get-Member
# NĂ€in saat tyypin tiedot
(Get-Location).GetType() # itsessÀÀn System.RuntimeType
(Get-Location).GetType().Name # itsessÀÀn String
# Jos palautunut arvo on jo muuttujassa
$var | Get-Member
# tai
$var.GetType()
Drives
PowerShellissÀ on kÀsite "drive", joka on hieman erilainen kuin Linuxin tiedostojÀrjestelmÀ. Drive on kÀytÀnnössÀ jokin abstrakti kÀsite, joka voi olla esimerkiksi tiedostojÀrjestelmÀ, rekisteri tai jokin muu. Voit listata kaikki drivet komennolla Get-PSDrive
. Voit vaihtaa driveÀ komennolla Set-Location
. Alla on komentoja, joissa aloitetaan /home/-hakemistosta, vaihdetaan env:-driveen ja listataan muuttujia, josta vaihdetaan Variable:-driveen, ja lopulta takaisin kotoisin tieodstojÀrjestelmÀn puolelle.
cd /home # Aloitetaan tÀstÀ (1)
cd env: # Vaihdetaan env:-driveen (2)
Get-ChildItem # Listataan muuttujat
cd Variable: # Vaihdetaan Variable:-driveen
cd / # Vaihdetaan takaisin kotihakemistoon
- Huomaa, ettÀ
cd
on AliasSet-Location
-komentoon. env:
-drive sisÀltÀÀ ympÀristömuuttujat. Huomaa, ettÀ BashissÀ nÀmÀ ovat ihan vain muuttujia samassa namespacessa (esim.$PATH
). PowerShell abstrahoi nÀmÀ omaksi drivekseen.
VianetsintÀ
Voimme kÀyttÀÀ Bash-kielestÀ tuttuja tapoja, mutta luonnolliseti niille on eri syntaksi. Tuttu set -u
korvautuu StrictMode-asetuksella ja set -e
korvautuu ErrorActionPreference-asetuksella.
StrictMode
PowerShellin StrictMode on hieman monimutkaisempi kuin Bashin set -u
(eli nounset
). KÀytÀnnössÀ se kuitenkin esimerkiksi tarkistaa, ettÀ et yritÀ kutsua kÀyttÀmÀttömiÀ muuttujia. Voit kytkeÀ skriptissÀ sen pÀÀlle nÀin:
Voit kÀyttÀÀ myös muita versioita, 1.0 tai 3.0. Tutustu niiden dokumentaatioon: Set-StrictMode
Kuinka testata?
Luo ja aja tiedosto:
Set-StrictMode -Version 2.0
Write-Host "Starting script with strict mode enabled..."
Write-Host "We are referencing: $undefinedVar"
Write-Host "This will never print."
Luo myös tiedosto strictmode_no.ps1
, joka on muutoin identtinen, mutta muokkaa riviÀ yksi. Aseta se muotoon Set-StrictMode -Off
. Aja molemmat tiedostot ja vertaa tuloksia.
ErrorActionPreference
PowerShellissÀ on useita preference-muuttujia (ks. about_Preference_Variables), joilla voit sÀÀtÀÀ, kuinka PowerShell kÀyttÀytyy. NÀistÀ set -e
:tÀ eli errexit
-toiminnallisuutta vastaa parhaiten ErrorActionPreference
. Voit asettaa sen arvoksi Stop
, jolloin skripti pysÀhtyy ensimmÀiseen virheeseen. Vakioarvo on Continue
, jolloin skripti jatkaa virheistÀ huolimatta.
Kuinka testata?
Luo ja aja tiedosto:
$ErrorActionPreference = "Stop"
Write-Host "Starting script with ErrorActionPreference set to Stop..."
Set-Location -Path "/thisdoesnotexist" 2>$null
Write-Host "This will never print."
Luo myös tiedosto preference_continue.ps1
, joka on muutoin identtinen, mutta muokkaa riviÀ yksi. Aseta se muotoon $ErrorActionPreference = "Continue"
. Aja molemmat tiedostot ja vertaa tuloksia.
Write-Something
Yksi luonnollinen tapa debugata lÀhes mitÀ tahansa ohjelmointikieltÀ on tulostaa muuttujien arvo kesken skriptin terminaaliin. TÀmÀ ei kuulosta rakettitieteeltÀ, mutta voi olla hyvin tehokas tapa debugata. Bashin kanssa ehkÀ opit, ettÀ echo
-komentoja on ÀrsyttÀvÀ lisÀtÀ ja poistaa tarpeen mukaan. KÀsin lisÀtty -v
option (verbose) auttaa, mutta vaatii argumenttien parsimista ja if-lausekkeita. Yksi tapa on ohjata komennot stderr
-virtaan, mutta se on sinÀnsÀ vÀÀrÀoppista, ettÀ debug-viestit eivÀt varsinaisesti ole virheitÀ.
PowerShell tarjoaa tÀhÀn ratkaisun tukemalla useita eri virtoja. NÀitÀ on useita. Alla olevassa esimerkissÀ kÀytÀmme virtoja: Success (1), Verbose (4) ja Warning(3). Verbose ei tulostu ruudulle tavallisesti, mutta jos asetat preference variablen VerbosePreference
arvoksi Continue
, nÀet myös Debug-virran tulosteet. Lue lisÀÀ ohjeista about_Output_Streams sekÀ about_Preference_Variables.
Write-Output "I am typical output!"
Write-Verbose "Ah, you must have VerbosePreference set up properly! đ”ïžââïž"
Write-Warning "Warning! Warning! đš"
Debuggaus
PowerShellissÀ on myös debugger, joka on kÀytettÀvissÀ Visual Studion Code -editorissa, olettaen, ettÀ PowerShell Extension on asennettuna. Voit kÀynnistÀÀ sen painamalla F5
. Se on erityisen hyödyllinen breakpoint-toiminnon avulla esimerkiksi silmukoiden debuggaamisessa.
Tutustumme tÀmÀn kÀyttöön live-tunneilla.
TehtÀvÀt
TehtÀvÀ: DevausympÀristö ja runpwsh.sh
Warning
Huomaa, ettÀ jos työskentelet siten, ettÀ Windows on host-kÀyttöjÀrjestelmÀsi, voit kirjoittaa tÀmÀn saman skriptin PowerShell-kielellÀ. TÀssÀ esimerkissÀ kÀytetÀÀn Bashia, koska kurssin oletuksena on Linux-host.
PowerShell-osion ensimmÀisessÀ koodaustehtÀvÀssÀ luot itsellesi devausympÀristön. Pohja tÀtÀ varten sinulla pitÀisi olla jo olemassa Bash-osiosta. KÀytÀnnössÀ luot:
- Hakemistorakenteen tehtÀvien vastauksia varten
- Skriptin
runpwsh.sh
, joka joko:- Ajaa valitun skriptin kontissa
- KÀynnistÀÀ interaktiivisen shellin (pwsh)
- Varmistat, ettÀ kaikki on versionhallinnassa
Jatka samassa repositoriossa työskentelyÀ, missÀ olet jo aiemmin työskenenlly. Jatka rakennetta seuraavanalaisesti:
johnanderton
âââ README.md
âââ bash/
âââ pwsh
| âââ README.md
â âââ runpwsh.sh # Uusi tiedosto
â âââ .help/powershell-help/ # Uusi hakemisto
â âââ scripts/ # Uusi hakemisto
âââ python
âââ .gitkeep
Tiedoston runpwsh.sh
luominen olisi hyvÀÀ kertausta Bash-osiosta, mutta jotta voimme keskittyÀ PowerShell-osioon, voit ladata skriptin tÀmÀn repositorion polusta: gh:sourander/skriptiohjelmointi/exercise-assets/scripts/runpwsh.sh
TehtÀvÀ: PowerShell Hello World
Luo skripti `hello.ps1, joka tulostaa terminaaliin tekstin "Hello World!".
Sijoita se repositorion juuresta lukien relatiiviseen polkuun pwsh/scripts/hello.ps1
. Aja skripti ./runpwsh.sh scripts/hello.ps1
ja varmista, ettÀ se tulostaa "Hello World!". KÀytÀ alla olevaa templaattia:
TehtÀvÀ: PowerShell Turboahdettu Hello World
<#
.SYNOPSIS
Prints "Hello World!" to the terminal.
... ADD MORE HELP HERE ...
#>
# IMPLEMENT
Jalosta yllÀ nÀkyvÀÀ skriptin alkua. Lopullisen skriptin tulisi:
- tulostaa absoluuttinen polku työhakemistoon
- tulostaa absoluuttinen polku skriptin sijaintiin
- tulostaa
PSEdition
-muuttujan arvon, mutta vain Debug-virtaan. - tukea
Get-Help
-komentoa. Implementoi ainakin:- Synopsis (yllÀ)
- Description
- Example
Ohjelman tulosteen pitÀisi kÀyttÀytyÀ seuraavanlaisesti:
PS> pwsh /app/scripts/hello_turbo.ps1
========= Turbo Hello World! =========
Current working directory: /
Script directory: /app/scripts
PS> cd root
PS> $VerbosePreference = "Continue"
PS> pwsh /app/scripts/hello_turbo.ps1
========= Turbo Hello World! =========
Current working directory: /root
Script directory: /app/scripts
VERBOSE: Your PowerShell Edition: Core
Varmista, ettÀ osaat tulostaa komennon helpin termiinaaliin.
Vinkki: Get-Help
Huomaa <# ... #>
tiedoston alussa. TÀmÀ on monirivinen kommentti.
Vinkki: src_path
Katso about_automatic_variables
ja $MyInvocation
.
TehtÀvÀ: Save-Help
TehtÀvÀnÀsi on tallentaa .help/powershell-help
-hakemistoon PowerShellin help-tiedostot.
Jos ajoit PowerShell 101-osion komentoja, huomasit varmasti, ettÀ Update-Help
-komennon suorittamisessa kestÀÀ tovin. Se lataa Help-tiedostot verkosta. TÀmÀ pitÀisi ajaa joka kerta uusiksi, kun avaamme PowerShellin konttiin. Nopeutetaan tÀtÀ siten, ettÀ tallennetaan meille lokaali offline-kopio helpistÀ.
SkriptissÀ runpwsh.sh
on mÀÀritetty bind mount read-write oikeuksin seuraavasti:
Host | Container |
---|---|
.help/powershell-help |
/srv/powershell-help |
Nyt tehtÀvÀnÀsi on tallentaa help-tiedostot kontin hakemistoon, joka on bind-mountattu sinun host-koneellesi. Alla on ajettavat komennot. Huomaa, ettÀ komennot tulee ajaa kontissa, ei sinun host-koneellasi.
# Create the directory
New-Item -ItemType Directory -Path /.help/PowerShellHelp
# Save the help files
Save-Help -DestinationPath /.help/PowerShellHelp
Tip
Vaihtoehtoinen tapa tÀlle tehtÀvÀlle olisi luoda oma Dockerfile ja rakentaa siltÀ pohjalta image, joka sisÀltÀÀ pÀivitetyn helpin. VÀltellÀÀn kuitenkin docker buildx
:ÀÀ tÀllÀ kursilla ja pysytÀÀn skriptien ajamisen parissa.
TehtÀvÀ: gitignore .help
LisÀÀ lopuksi .help/
-hakemisto sinun .gitignore
-tiedostoon. Tiedostot ovat aina ladattavissa netistÀ, joten niiden sÀilöminen pitkÀaikaisesti omana kopiona Gitlabiin olisi turhuutta.
TehtÀvÀ: localhelp.ps1
Jatkossa voit instansoida uuden kontin ja ottaa lokaalisti tallennetun helpin kÀyttöön nÀin:
Hakemisto on kuitenkin .gitignore
-tiedostossa, joten voi olla, ettÀ pÀÀdyt ajamaan tÀtÀ koodia uudella koneella. SiispÀ on tarpeellista luoda localhelp.ps1
-skripti, joka:
- PÀivittÀÀ helpin aina, jos
-Update
-parametri on annettu- Ajaa:
Save-Help -DestinationPath /var/powershell-help
- Ajaa:
- Lataa helpin, pÀivittyi se tai ei.
- Ajaa:
Update-Help -SourcePath /var/powershell-help
- Ajaa: