Сценарий PowerShell для возврата версий of.NET рамки на машине?
каким должен быть сценарий PowerShell для возврата версий .NET Framework на машине?
моя первая догадка-это что-то с участием WMI. Есть ли что-то лучше?
Он должен быть однострочным, чтобы возвращать только последнюю версию для каждой установки .NET [на каждой строке].
13 ответов:
Если вы собираетесь использовать реестр, вы должны повторить для того, чтобы получить полную версию для 4.х рамках. Более ранние ответы возвращают корневой номер в моей системе для .NET 3.0 (где номера WCF и WPF, которые вложены под 3.0, выше-я не могу этого объяснить) и не возвращают ничего для 4.0 ...
EDIT: для .Net 4.5 и выше это снова немного изменилось, так что теперь есть хороший статья MSDN здесь объясняя, как преобразовать релиз значение для номера версии .Net, это полное крушение поезда: - (
Это выглядит правильно для меня (обратите внимание, что он выводит отдельные номера версий для WCF & WPF на 3.0. Я не знаю, что это). Он также выводит оба клиент и полное на 4.0 (если они у вас установлены):
Get-ChildItem 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' -recurse | Get-ItemProperty -name Version,Release -EA 0 | Where { $_.PSChildName -match '^(?!S)\p{L}'} | Select PSChildName, Version, Releaseна основе статьи MSDN можно построить таблицу поиска и вернуть номер версии маркетингового продукта для выпусков после 4.5:
$Lookup = @{ 378389 = [version]'4.5' 378675 = [version]'4.5.1' 378758 = [version]'4.5.1' 379893 = [version]'4.5.2' 393295 = [version]'4.6' 393297 = [version]'4.6' 394254 = [version]'4.6.1' 394271 = [version]'4.6.1' 394802 = [version]'4.6.2' 394806 = [version]'4.6.2' 460798 = [version]'4.7' 460805 = [version]'4.7' 461308 = [version]'4.7.1' 461310 = [version]'4.7.1' 461808 = [version]'4.7.2' 461814 = [version]'4.7.2' } Get-ChildItem 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' -Recurse | Get-ItemProperty -name Version, Release -EA 0 | # For One True framework (latest .NET 4x), change match to PSChildName -eq "Full": Where-Object { $_.PSChildName -match '^(?!S)\p{L}'} | Select-Object @{name = ".NET Framework"; expression = {$_.PSChildName}}, @{name = "Product"; expression = {$Lookup[$_.Release]}}, Version, Releaseна самом деле, поскольку я продолжаю обновлять этот ответ, вот сценарий для создания сценария выше (с небольшим добавлением) из источника markdown для этой веб-страницы. Это, вероятно, сломается в какой-то момент, поэтому я сохраняю текущую копию выше.
# Get the text from github $url = "https://raw.githubusercontent.com/dotnet/docs/master/docs/framework/migration-guide/how-to-determine-which-versions-are-installed.md" $md = Invoke-WebRequest $url -UseBasicParsing $OFS = "`n" # Replace the weird text in the tables, and the padding # Then trim the | off the front and end of lines $map = $md -split "`n" -replace " installed [^|]+" -replace "\s+\|" -replace "\|$" | # Then we can build the table by looking for unique lines that start with ".NET Framework" Select-String "^.NET" | Select-Object -Unique | # And flip it so it's key = value # And convert ".NET FRAMEWORK 4.5.2" to [version]4.5.2 ForEach-Object { [version]$v, [int]$k = $_ -replace "\.NET Framework " -split "\|" " $k = [version]'$v'" } # And output the whole script @" `$Lookup = @{ $map } # For extra effect we could get the Windows 10 OS version and build release id: try { `$WinRelease, `$WinVer = Get-ItemPropertyValue "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion" ReleaseId, CurrentMajorVersionNumber, CurrentMinorVersionNumber, CurrentBuildNumber, UBR `$WindowsVersion = "`$(`$WinVer -join '.') (`$WinRelease)" } catch { `$WindowsVersion = [System.Environment]::OSVersion.Version } Get-ChildItem 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' -Recurse | Get-ItemProperty -name Version, Release -EA 0 | # For The One True framework (latest .NET 4x), change match to PSChildName -eq "Full": Where-Object { `$_.PSChildName -match '^(?!S)\p{L}'} | Select-Object @{name = ".NET Framework"; expression = {`$_.PSChildName}}, @{name = "Product"; expression = {`$Lookup[`$_.Release]}}, Version, Release, # Some OPTIONAL extra output: PSComputerName and WindowsVersion # The Computer name, so output from local machines will match remote machines: @{ name = "PSComputerName"; expression = {`$Env:Computername}}, # The Windows Version (works on Windows 10, at least): @{ name = "WindowsVersion"; expression = { `$WindowsVersion }} "@
gci 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' | sort pschildname -des | select -fi 1 -exp pschildnameэтот ответ не возвращает 4.5, если он установлен. Ответ ниже от @Jaykul и с помощью recurse делает.
синтаксис:
[System.Runtime.InteropServices.RuntimeEnvironment]::GetSystemVersion() #or $PSVersionTable.CLRVersionThe
GetSystemVersionфункция возвращает строку, как это:v2.0.50727 #PowerShell v2.0 in Win 7 SP1или такой
v4.0.30319 #PowerShell v3.0 (Windows Management Framework 3.0) in Win 7 SP1
$PSVersionTableявляется объектом только для чтения. Свойство CLRVersion является структурированным номером версии следующим образом:Major Minor Build Revision ----- ----- ----- -------- 4 0 30319 18444
добавлена поддержка V4.7. 2 для скрипта:
Get-ChildItem 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' -recurse | Get-ItemProperty -name Version,Release -EA 0 | Where { $_.PSChildName -match '^(?![SW])\p{L}'} | Select PSChildName, Version, Release, @{ name="Product" expression={ switch -regex ($_.Release) { "378389" { [Version]"4.5" } "378675|378758" { [Version]"4.5.1" } "379893" { [Version]"4.5.2" } "393295|393297" { [Version]"4.6" } "394254|394271" { [Version]"4.6.1" } "394802|394806" { [Version]"4.6.2" } "460798|460805" { [Version]"4.7" } "461308|461310" { [Version]"4.7.1" } "461808|461814" { [Version]"4.7.2" } {$_ -gt 461814} { [Version]"Undocumented version (> 4.7.2), please update script" } } } }
Я нашел это через завершение вкладки в powershell для osx:
[System.Runtime.InteropServices.RuntimeInformation]::get_FrameworkDescription() .NET Core 4.6.25009.03
нет надежного способа сделать это для всех платформ и архитектур с помощью простого скрипта. Если вы хотите узнать, как это сделать надежно, начните с сообщения в блоге обновленный пример кода обнаружения .NET Framework, который выполняет более глубокую проверку.
Не очень. наверняка не очень:
ls $Env:windir\Microsoft.NET\Framework | ? { $_.PSIsContainer } | select -exp Name -l 1Это может или не может работать. Но что касается последней версии, это должно быть довольно надежным, так как есть по существу пустые папки для старых версий (1.0, 1.1), но не более новые – они появляются только после установки соответствующей платформы.
тем не менее, я подозреваю, что должен быть лучший способ.
обратитесь к странице скрипт для поиска, какие версии .NET установлены на удаленных рабочих станциях.
сценарий там может быть полезно найти версию .NET для нескольких машин в сети.
хорошее решение
попробуйте использовать загружаемые DotNetVersionLister модуль (на основе информации реестра и некоторой таблицы поиска версии для маркетинга).
который будет использоваться следующим образом:
PS> Get-DotNetVersion -LocalHost ComputerName : localhost >=4.x : 4.5.2 v4\Client : Installed v4\Full : Installed v3.5 : Installed v3.0 : Installed v2.0.50727 : Installed v1.1.4322 : Not installed (no key) Ping : True Error : Script start time: 09/03/2018 09:21:18 Script end time: 09/03/2018 09:21:19Или вот так, если вы просто хотите проверить его для некоторых .NET framework > = 4.* :
PS> (Get-DotNetVersion -LocalHost).">=4.x" Script start time: 09/03/2018 09:25:55 Script end time: 09/03/2018 09:25:55 4.5.2но он не будет работать (установка/импорт), например, с ПС П2.0 (Win 7,Win Server 2010 стандартные) из-за несовместимости...
мотивация для функций "наследие" ниже
(вы можете пропустить это и использовать код ниже)
мы должны были работать с PS 2.0 на некоторых машинах и не удалось установить / импортировать выше DotNetVersionLister.
На других машинах мы хотели обновить (с PS 2.0) к PS 5.1 (который в turn needs .NET Framework > = 4.5) С помощью двух компаний-customInstall-DotnetLatestCompanyиInstall-PSLatestCompany.
Чтобы хорошо направлять администраторов в процессе установки/обновления, нам нужно было бы определить версию .NET в этих функциях на всех существующих машинах и версиях PS.
Таким образом, мы использовали также следующие функции, чтобы определить их более безопасно во всех средах...функции для устаревших сред PS (например ПС П2.0)
так следующий код и ниже (извлеченные) примеры использования полезны здесь (на основе других ответов здесь):
function Get-DotNetVersionByFs { <# .SYNOPSIS NOT RECOMMENDED - try using instead: Get-DotNetVersion from DotNetVersionLister module (https://github.com/EliteLoser/DotNetVersionLister), but it is not usable/importable in PowerShell 2.0 Get-DotNetVersionByReg reg(istry) based: (available herin as well) but it may return some wrong version or may not work reliably for versions > 4.5 (works in PSv2.0) Get-DotNetVersionByFs (this): f(ile) s(ystem) based: determines the latest installed .NET version based on $Env:windir\Microsoft.NET\Framework content this is unreliable, e.g. if 4.0* is already installed some 4.5 update will overwrite content there without renaming the folder (works in PSv2.0) .EXAMPLE PS> Get-DotnetVersionByFs 4.0.30319 .EXAMPLE PS> Get-DotnetVersionByFs -All 1.0.3705 1.1.4322 2.0.50727 3.0 3.5 4.0.30319 .NOTES from https://stackoverflow.com/a/52078523/1915920 #> [cmdletbinding()] param( [Switch]$All ## do not return only latest, but all installed ) $list = ls $Env:windir\Microsoft.NET\Framework | ?{ $_.PSIsContainer -and $_.Name -match '^v\d.[\d\.]+' } | %{ $_.Name.TrimStart('v') } if ($All) { $list } else { $list | select -last 1 } } function Get-DotNetVersionByReg { <# .SYNOPSIS NOT RECOMMENDED - try using instead: Get-DotNetVersion From DotNetVersionLister module (https://github.com/EliteLoser/DotNetVersionLister), but it is not usable/importable in PowerShell 2.0. Determines the latest installed .NET version based on registry infos under 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' .EXAMPLE PS> Get-DotnetVersionByReg 4.5.51209 .EXAMPLE PS> Get-DotnetVersionByReg -AllDetailed PSChildName Version Release ----------- ------- ------- v2.0.50727 2.0.50727.5420 v3.0 3.0.30729.5420 Windows Communication Foundation 3.0.4506.5420 Windows Presentation Foundation 3.0.6920.5011 v3.5 3.5.30729.5420 Client 4.0.0.0 Client 4.5.51209 379893 Full 4.5.51209 379893 .NOTES from https://stackoverflow.com/a/52078523/1915920 #> [cmdletbinding()] param( [Switch]$AllDetailed ## do not return only latest, but all installed with more details ) $Lookup = @{ 378389 = [version]'4.5' 378675 = [version]'4.5.1' 378758 = [version]'4.5.1' 379893 = [version]'4.5.2' 393295 = [version]'4.6' 393297 = [version]'4.6' 394254 = [version]'4.6.1' 394271 = [version]'4.6.1' 394802 = [version]'4.6.2' 394806 = [version]'4.6.2' 460798 = [version]'4.7' 460805 = [version]'4.7' 461308 = [version]'4.7.1' 461310 = [version]'4.7.1' 461808 = [version]'4.7.2' 461814 = [version]'4.7.2' } $list = Get-ChildItem 'HKLM:\SOFTWARE\Microsoft\NET Framework Setup\NDP' -Recurse | Get-ItemProperty -name Version, Release -EA 0 | # For One True framework (latest .NET 4x), change match to PSChildName -eq "Full": Where-Object { $_.PSChildName -match '^(?!S)\p{L}'} | Select-Object ` @{ name = ".NET Framework" ; expression = {$_.PSChildName}}, @{ name = "Product" ; expression = {$Lookup[$_.Release]}}, Version, Release if ($AllDetailed) { $list | sort version } else { $list | sort version | select -last 1 | %{ $_.version } } }пример использования:
PS> Get-DotNetVersionByFs 4.0.30319 PS> Get-DotNetVersionByFs -All 1.0.3705 1.1.4322 2.0.50727 3.0 3.5 4.0.30319 PS> Get-DotNetVersionByReg 4.5.51209 PS> Get-DotNetVersionByReg -AllDetailed .NET Framework Product Version Release -------------- ------- ------- ------- v2.0.50727 2.0.50727.5420 v3.0 3.0.30729.5420 Windows Communication Foundation 3.0.4506.5420 Windows Presentation Foundation 3.0.6920.5011 v3.5 3.5.30729.5420 Client 4.0.0.0 Client 4.5.2 4.5.51209 379893 Full 4.5.2 4.5.51209 379893
вот общая идея:
получить дочерние элементы в каталоге .NET Framework, которые являются контейнерами, имена которых совпадают шаблон v номер точка номер. Отсортируйте их по убыванию имени, возьмите первый объект, и вернуть его свойство name.
вот скрипт:
(Get-ChildItem -Path $Env:windir\Microsoft.NET\Framework | Where-Object {$_.PSIsContainer -eq $true } | Where-Object {$_.Name -match 'v\d\.\d'} | Sort-Object -Property Name -Descending | Select-Object -First 1).Name
Я бы попробовал это в PowerShell: Работал на меня!
(Get-ItemProperty "HKLM: Software\Microsoft\NET Framework Setup\NDP\v4\Full").Версия
Comments