From c978a5a37d78a065a57d6dbf664c6a40c160aa56 Mon Sep 17 00:00:00 2001 From: Szymon Osiecki Date: Sat, 30 Sep 2023 01:01:02 +0200 Subject: [PATCH] feat(ps): wsl_get_distros --- wsl/wsl_get_distros.ps1 | 98 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 98 insertions(+) create mode 100644 wsl/wsl_get_distros.ps1 diff --git a/wsl/wsl_get_distros.ps1 b/wsl/wsl_get_distros.ps1 new file mode 100644 index 00000000..54e9be39 --- /dev/null +++ b/wsl/wsl_get_distros.ps1 @@ -0,0 +1,98 @@ +#!/usr/bin/pwsh -nop +<# +.SYNOPSIS +Script synopsis. +.EXAMPLE +wsl/wsl_get_distros.ps1 +wsl/wsl_get_distros.ps1 -FromRegistry +wsl/wsl_get_distros.ps1 -Online +#> +[CmdletBinding()] +param ( + [switch]$Online, + + [switch]$FromRegistry +) + +begin { + $ErrorActionPreference = 'Stop' + + if ($FromRegistry) { + # specify list of properties to get from Windows registry lxss + $prop = @( + @{ Name = 'Name'; Expression = { $_.DistributionName } } + 'DefaultUid' + @{ Name = 'Version'; Expression = { $_.Flags -lt 8 ? 1 : 2 } } + ) + } else { + $distros = [Collections.Generic.List[PSCustomObject]]::new() + $outputEncoding = [Console]::OutputEncoding + } +} + +process { + if ($FromRegistry) { + # get list of WSL distros from Windows Registry + $distros = Get-ChildItem HKCU:\Software\Microsoft\Windows\CurrentVersion\Lxss ` + | ForEach-Object { $_ | Get-ItemProperty } ` + | Where-Object { $_.DistributionName -notmatch '^docker-desktop' } ` + | Select-Object $prop + } else { + # change console encoding to utf-16 + [Console]::OutputEncoding = [System.Text.Encoding]::Unicode + if ($Online) { + # get list of online WSL distros + [string[]]$result = wsl.exe --list --online | Where-Object { $_ } + # get distros header + [string]$head = $result | Select-String 'NAME\s+FRIENDLY' -CaseSensitive | Select-Object -ExpandProperty Line + # calculate header line index + $idx = $result.IndexOf($head) + $dataIdx = if ($idx -ge 0) { + $idx + 1 + } else { + $result.Count - 1 + } + # calculate header columns indexes + $nameIdx = $head.IndexOf('NAME') + $friendlyIdx = $head.IndexOf('FRIENDLY') + # add results to the distros list + for ($i = $dataIdx; $i -lt $result.Count; $i++) { + $distro = [PSCustomObject]@{ + Name = $result[$i].Substring($nameIdx, $friendlyIdx - $nameIdx).TrimEnd() + FriendlyName = $result[$i].Substring($friendlyIdx, $result[$i].Length - $friendlyIdx).TrimEnd() + } + $distros.Add($distro) + } + } else { + # get list of installed locally WSL distros + [string[]]$result = wsl.exe --list --verbose + # get distros header + [string]$head = $result | Select-String 'NAME\s+STATE\s+VERSION' -CaseSensitive | Select-Object -ExpandProperty Line + # calculate header line index + $idx = $result.IndexOf($head) + $dataIdx = if ($idx -ge 0) { + $idx + 1 + } else { + $result.Count - 1 + } + # calculate header columns indexes + $nameIdx = $head.IndexOf('NAME') + $stateIdx = $head.IndexOf('STATE') + $versionIdx = $head.IndexOf('VERSION') + # add results to the distros list + for ($i = $dataIdx; $i -lt $result.Count; $i++) { + $distro = [PSCustomObject]@{ + Name = $result[$i].Substring($nameIdx, $stateIdx - $nameIdx).TrimEnd() + State = $result[$i].Substring($stateIdx, $versionIdx - $stateIdx).TrimEnd() + Version = $result[$i].Substring($versionIdx, $result[$i].Length - $versionIdx).TrimEnd() + } + $distros.Add($distro) + } + } + [Console]::OutputEncoding = $outputEncoding + } +} + +end { + return $distros +}