A VSCode-ban és a PowerShellben történő fájlkódolás megértése

Ha a VS Code használatával hoz létre és szerkeszt PowerShell-szkripteket, fontos, hogy a fájlok a megfelelő karakterkódolási formátum használatával legyenek mentve.

Mi a fájlkódolás, és miért fontos?

A VS Code kezeli az interfészt a karakterek emberi bevitele között egy pufferbe, valamint a fájlrendszerbe bájtokból álló olvasási/írási blokkok között. Amikor a VS Code ment egy fájlt, egy szövegkódolással határozza meg, hogy az egyes karakterek milyen bájtok lesznek. További információ: about_Character_Encoding.

Hasonlóképpen, amikor a PowerShell futtat egy szkriptet, a fájlban lévő bájtokat karakterekké kell konvertálnia, hogy a fájlt PowerShell-programmá alakítsa. Mivel a VS Code megírja a fájlt, és a PowerShell beolvassa a fájlt, ugyanazt a kódolási rendszert kell használniuk. A PowerShell-szkriptek elemzésének folyamata a következő: bájt -characters ->>tokens ->abstract szintaxisfa ->execution.

A VS Code és a PowerShell is ésszerű alapértelmezett kódolási konfigurációval van telepítve. A PowerShell által használt alapértelmezett kódolás azonban megváltozott a PowerShell 6 kiadásával. Annak érdekében, hogy ne okozhasson problémát a PowerShell vagy a PowerShell-bővítmény használata a VS Code-ban, megfelelően kell konfigurálnia a VS Code- és a PowerShell-beállításokat.

Kódolási problémák gyakori okai

Kódolási problémák akkor fordulnak elő, ha a VS Code vagy a szkriptfájl kódolása nem egyezik meg a PowerShell várt kódolásával. A PowerShell nem tudja automatikusan meghatározni a fájlkódolást.

Nagyobb valószínűséggel tapasztal kódolási problémákat, ha olyan karaktereket használ, amelyek nem a 7 bites ASCII-karakterkészletben vannak. Például:

  • Hosszabb nem betűs karakterek, például gondolatjel (), nem törhető szóköz ( ) vagy bal oldali dupla idézőjel (")
  • Ékezetes latin karakterek (É, ü)
  • Nem latin karakterek, például cirill (Д, Ц)
  • CJK-karakterek (, , )

A kódolási problémák gyakori okai a következők:

  • A VS Code és a PowerShell kódolása nem változott az alapértelmezett értékükhöz. A PowerShell 5.1 és újabb verzió esetén az alapértelmezett kódolás eltér a VS Code-tól.
  • Egy másik szerkesztő megnyitotta és felülírta a fájlt egy új kódolással. Ez gyakran előfordul az ISE-vel.
  • A fájl a VS Code-tól vagy a PowerShelltől eltérő kódolásban van beadva a verziókövetésbe. Ez akkor fordulhat elő, ha a közreműködők különböző kódolási konfigurációkkal rendelkező szerkesztőket használnak.

Hogyan állapíthatja meg, ha kódolási problémák merülnek fel

A kódolási hibák gyakran elemzési hibákként jelentkeznek a szkriptekben. Ha furcsa karaktersorozatokat talál a szkriptben, ez lehet a probléma. Az alábbi példában egy gondolatjel () jelenik meg karakterként â€":

Send-MailMessage : A positional parameter cannot be found that accepts argument 'Testing FuseMail SMTP...'.
At C:\Users\<User>\<OneDrive>\Development\PowerShell\Scripts\Send-EmailUsingSmtpRelay.ps1:6 char:1
+ Send-MailMessage â&euro;"From $from â&euro;"To $recipient1 â&euro;"Subject $subject  ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Send-MailMessage], ParameterBindingException
    + FullyQualifiedErrorId : PositionalParameterNotFound,Microsoft.PowerShell.Commands.SendMailMessage

Ez a probléma azért fordul elő, mert a VS Code az UTF-8 karaktert bájtként 0xE2 0x80 0x93kódolja. Ha ezek a bájtok Windows-1252-ként vannak dekódolva, a rendszer karakterekként â&euro;"értelmezi őket.

Néhány furcsa karaktersorozat, amelyet láthat:

  • â&euro;" ahelyett, hogy
  • â&euro;" ahelyett, hogy
  • Ä2 ahelyett, hogy Ä
  • Â ahelyett, hogy   (nem törő szóköz)
  • Ã&copy; ahelyett, hogy é

Ez a hasznos referencia felsorolja azokat a gyakori mintákat, amelyek UTF-8/Windows-1252 kódolási problémát jeleznek.

Hogyan működik együtt a VS Code PowerShell-bővítménye a kódolásokkal?

A PowerShell-bővítmény többféleképpen kommunikál a szkriptekkel:

  1. A VS Code-ban szerkesztett parancsfájlok tartalmát a VS Code elküldi a bővítménynek. A Language Server Protocol előírja, hogy a tartalom átvitele az UTF-8-ban történik. Ezért nem lehetséges, hogy a bővítmény rossz kódolást kapjon.
  2. Amikor a szkripteket közvetlenül az integrált konzolon hajtja végre, a PowerShell közvetlenül olvassa be őket a fájlból. Ha a PowerShell kódolása eltér a VS Code-tól, itt hiba léphet fel.
  3. Ha egy VS Code-ban megnyitott parancsfájl egy másik, a VS Code-ban nem megnyitott parancsfájlra hivatkozik, a bővítmény visszaválás után betölti a szkript tartalmát a fájlrendszerből. A PowerShell-bővítmény alapértelmezés szerint UTF-8 kódolást használ, de bájtsorrendjelet vagy BOM-észlelést használ a megfelelő kódolás kiválasztásához.

A probléma akkor fordul elő, ha AOM nélküli formátumok kódolását feltételezi (például UTF-8 BOM és Windows-1252 nélkül). A PowerShell-bővítmény alapértelmezett értéke UTF-8. A bővítmény nem tudja módosítani a VS Code kódolási beállításait. További információ: 824.

A megfelelő kódolás kiválasztása

A különböző rendszerek és alkalmazások különböző kódolást használhatnak:

  • A .NET Standardban, a weben és a Linux-világban az UTF-8 a domináns kódolás.
  • Számos .NET-keretrendszer alkalmazás UTF-16-ot használ. Történelmi okokból ezt néha "Unicode-nak" is nevezik, amely most egy széles körű szabványra hivatkozik, amely az UTF-8 és az UTF-16 szabványt is magában foglalja.
  • Windows rendszeren a Unicode-ot elődként használó számos natív alkalmazás alapértelmezés szerint továbbra is a Windows-1252-t használja.

A Unicode-kódolások a bájtsorrendjel (BOM) fogalmával is rendelkeznek. A logikaiegység-objektumok a szöveg elején fordulnak elő, hogy egy dekódoló megállapítsa, melyik kódolást használja. Több bájtos kódolás esetén a BOM a kódolás endianitását is jelzi. A LOGIKAI-gépeket olyan bájtokra tervezték, amelyek ritkán fordulnak elő nem Unicode-szövegekben, így ésszerű becslést adnak arról, hogy a szöveg Unicode, ha egy anyagjegyzék jelen van.

A BOM-ok opcionálisak, és a bevezetésük nem olyan népszerű a Linux-világban, mert mindenhol az UTF-8 megbízható konvencióját használják. A legtöbb Linux-alkalmazás feltételezi, hogy a szövegbevitel UTF-8-ban van kódolva. Bár sok Linux-alkalmazás felismeri és helyesen kezeli az AB-t, egy szám nem, ami az alkalmazásokkal kezelt szövegösszetevőkhez vezet.

Ezért:

  • Ha elsősorban Windows-alkalmazásokkal és Windows PowerShell dolgozik, érdemes olyan kódolást használnia, mint az UTF-8 a BOM-val vagy az UTF-16-tal.
  • Ha több platformon dolgozik, érdemes inkább az UTF-8-et használnia a BOM-hez.
  • Ha főként Linuxhoz kapcsolódó környezetekben dolgozik, érdemes inkább az UTF-8-et használnia AOM nélkül.
  • A Windows-1252 és a latin-1 lényegében örökölt kódolás, amelyet lehetőség szerint el kell kerülnie. Egyes régebbi Windows-alkalmazások azonban függhetnek tőlük.
  • Azt is érdemes megjegyezni, hogy a szkript-aláírás kódolástól függ, ami azt jelenti, hogy az aláírt szkriptek kódolásának módosítása lemondást igényel.

A VS Code konfigurálása

A VS Code alapértelmezett kódolása az UTF-8 BOM nélkül.

A VS Code kódolásának beállításához lépjen a VS Code beállításaira (Ctrl+), és adja meg a "files.encoding" beállítást:

"files.encoding": "utf8bom"

Néhány lehetséges érték:

  • utf8: [UTF-8] BOM nélkül
  • utf8bom: [UTF-8] BOM-val
  • utf16le: Kis endian [UTF-16]
  • utf16be: Big endian [UTF-16]
  • windows1252: [Windows-1252]

Ehhez legördülő menüt kell kapnia grafikus felhasználói felületi nézetben, vagy a befejezéseket JSON nézetben.

Ha lehetséges, az alábbiakat is hozzáadhatja az automatikus kódoláshoz:

"files.autoGuessEncoding": true

Ha nem szeretné, hogy ezek a beállítások minden fájltípusra hatással legyen, a VS Code nyelvenkénti konfigurációkat is lehetővé tesz. Nyelvspecifikus beállításokat hozhat létre egy [<language-name>] mező beállításainak megadásával. Például:

"[powershell]": {
    "files.encoding": "utf8bom",
    "files.autoGuessEncoding": true
}

Érdemes megfontolnia a Visual Studio Code Gremlins-követőjének telepítését is. Ez a bővítmény felfed bizonyos Unicode-karaktereket, amelyek könnyen sérültek, mert láthatatlanok vagy más normál karakterekhez hasonlóan néznek ki.

A PowerShell konfigurálása

A PowerShell alapértelmezett kódolása a verziótól függően változik:

  • A PowerShell 6+-ban az alapértelmezett kódolás az UTF-8 az összes platformon, AOM nélkül.
  • Az Windows PowerShell az alapértelmezett kódolás általában a Windows-1252, a latin-1 kiterjesztése, más néven ISO 8859-1.

A PowerShell 5+-ban az alábbi módon keresheti meg az alapértelmezett kódolást:

[psobject].Assembly.GetTypes() | Where-Object { $_.Name -eq 'ClrFacade'} |
  ForEach-Object {
    $_.GetMethod('GetDefaultEncoding', [System.Reflection.BindingFlags]'nonpublic,static').Invoke($null, @())
  }

Az alábbi szkripttel meghatározhatja, hogy a PowerShell-munkamenet milyen kódolást következtet egy gépi objektum nélküli szkriptre.

$badBytes = [byte[]]@(0xC3, 0x80)
$utf8Str = [System.Text.Encoding]::UTF8.GetString($badBytes)
$bytes = [System.Text.Encoding]::ASCII.GetBytes('Write-Output "') + [byte[]]@(0xC3, 0x80) + [byte[]]@(0x22)
$path = Join-Path ([System.IO.Path]::GetTempPath()) 'encodingtest.ps1'

try
{
    [System.IO.File]::WriteAllBytes($path, $bytes)

    switch (& $path)
    {
        $utf8Str
        {
            return 'UTF-8'
            break
        }

        default
        {
            return 'Windows-1252'
            break
        }
    }
}
finally
{
    Remove-Item $path
}

A PowerShell konfigurálható úgy, hogy általánosabban használjon egy adott kódolást a profilbeállítások használatával. Lásd az alábbi cikkeket:

A PowerShell nem kényszeríthető egy adott bemeneti kódolás használatára. A PowerShell 5.1-es és újabb, windowsos, en-US területi beállítású, alapértelmezés szerint Windows 1252 kódolású, ha nincs gépi objektum. Más területi beállítások eltérő kódolást használhatnak. Az együttműködés biztosítása érdekében a legjobb, ha Unicode formátumban menti a szkripteket egy gépi objektumjegyzékkel.

Fontos

A PowerShell-szkripteket érintő egyéb eszközökre hatással lehetnek a kódolási lehetőségek, vagy újrakódolhatja a szkripteket egy másik kódolásra.

Meglévő szkriptek

Előfordulhat, hogy a fájlrendszerben már meglévő szkripteket újra kell kódolni az új választott kódolásra. A VS Code alsó sávján az UTF-8 felirat látható. Kattintson rá a műveletsáv megnyitásához, és válassza a Mentés kódolással lehetőséget. Most már választhat egy új kódolást a fájlhoz. A teljes útmutatásért tekintse meg a VS Code kódolását .

Ha több fájlt kell újrakódolnia, használja a következő szkriptet:

Get-ChildItem *.ps1 -Recurse | ForEach-Object {
    $content = Get-Content -Path $_
    Set-Content -Path $_.Fullname -Value $content -Encoding UTF8 -PassThru -Force
}

A PowerShell integrált szkriptelési környezete (ISE)

Ha szkripteket is szerkeszt a PowerShell ISE használatával, ott kell szinkronizálnia a kódolási beállításokat.

Az ISE-nek tiszteletben kell tartania az üzleti objektumokat, de a kódolás beállításához tükröződés is használható. Vegye figyelembe, hogy ez nem marad meg a startupok között.

Verziókövetési szoftver

Egyes verziókövetési eszközök, például a git, figyelmen kívül hagyják a kódolást; A git csak nyomon követi a bájtokat. Mások, például az Azure DevOps vagy a Mercurial, nem feltétlenül. Még néhány git-alapú eszköz is a szöveg dekódolására támaszkodik.

Ebben az esetben győződjön meg arról, hogy:

  • Konfigurálja a szövegkódolást a verziókövetésben a VS Code konfigurációjának megfelelően.
  • Győződjön meg arról, hogy az összes fájl be van jelölve a megfelelő kódolású verziókövetésbe.
  • Legyen óvatos a verziókövetésen keresztül kapott kódolás módosításaival. Ennek fő jele a változásokra utaló eltérés, de ahol úgy tűnik, hogy semmi sem változott (mivel a bájtok rendelkeznek, de a karakterek nem).

Közreműködői környezetek

A verziókövetés konfigurálása mellett győződjön meg arról, hogy a megosztott fájlok közreműködői nem rendelkeznek olyan beállításokkal, amelyek felülbírálják a kódolást a PowerShell-fájlok újrakódolásával.

Egyéb programok

A PowerShell-szkriptet olvasó vagy író bármely más program újrakódolhatja azt.

Néhány példa:

  • Parancsfájl másolása és beillesztése a vágólap használatával. Ez gyakori az olyan forgatókönyvekben, mint a következő:
    • Szkript másolása virtuális gépre
    • Parancsfájl másolása e-mailből vagy weblapról
    • Parancsfájl másolása Microsoft Word- vagy PowerPoint-dokumentumba vagy onnan onnan ki
  • Egyéb szövegszerkesztők, például:
    • Notepad
    • vim
    • Bármely más PowerShell-szkriptszerkesztő
  • Szövegszerkesztő segédprogramok, például:
    • Get-Content/Set-Content/Out-File
    • PowerShell-átirányítási operátorok, például > és >>
    • sed/awk
  • Fájlátviteli programok, például:
    • Webböngésző, szkriptek letöltésekor
    • Fájlmegosztás

Ezen eszközök némelyike nem szöveg, hanem bájtok használatával foglalkozik, míg mások kódolási konfigurációkat kínálnak. Azokban az esetekben, amikor kódolást kell konfigurálnia, a problémák elkerülése érdekében ugyanazt kell tennie, mint a szerkesztő kódolását.

Egyéb forrásanyagok kódoláshoz a PowerShellben

A Kódolás PowerShellben való kódolásával és konfigurálásával kapcsolatban van néhány további hasznos bejegyzés, amelyeket érdemes elolvasni: