ReflectCmdlet.psm1
function Get-CommandSource { <# .SYNOPSIS Gets command source code. .DESCRIPTION The Get-CommandSource cmdlet finds the source code/implementation for a cmdlet. .PARAMETER Name Specifies the path or name of the command to retrieve the source code. .PARAMETER Decompiler Specifies which decompiler or source will be used for browsing the source code. .LINK https://www.github.com/aberus/ReflectCmdlet #> [CmdletBinding()] [OutputType([string],[PSObject])] [Alias('gcmso')] param( [Parameter(Position=0, Mandatory=$true, ValueFromPipeline=$true)] [ValidateNotNullOrEmpty()] [String]$Name, [Decompiler]$Decompiler ) $commandInfo = if ($_ -is [System.Management.Automation.CommandInfo]) {$_} else {Get-Command -Name $Name} if($commandInfo -is [System.Management.Automation.AliasInfo]) { $commandInfo = $commandInfo.ResolvedCommand } if($commandInfo -is [System.Management.Automation.FunctionInfo]) { $modulePath = Split-Path -Path $commandInfo.Module.Path Invoke-Item $modulePath $object = New-Object PSObject -Property @{ Name = $commandInfo.Name #Type = $type ModulePath = $modulePath } return $object } if($commandInfo -is [System.Management.Automation.CmdletInfo]) { $assembly = $commandInfo.ImplementingType.Assembly.Location if(!$assembly) { $assembly = $commandInfo.DLL } $type = $commandInfo.ImplementingType.FullName if (($Decompiler -eq [Decompiler]::dnSpy -or !$Decompiler) -and (Get-Command dnSpy -ErrorAction SilentlyContinue)) { Start-Process -FilePath dnSpy -ArgumentList "$assembly --select T:$type" } elseif (($Decompiler -eq [Decompiler]::ILSpy -or !$Decompiler) -and (Get-Command ILSpy -ErrorAction SilentlyContinue)) { Start-Process -FilePath ILSpy -ArgumentList "$assembly /navigateTo:T:$type" } elseif (($Decompiler -eq [Decompiler]::dotPeek -or !$Decompiler) -and (Get-Command dotPeek32 -ErrorAction SilentlyContinue)) { dotPeek32 /select=$assembly!$type } elseif (($Decompiler -eq [Decompiler]::JustDecompile -or !$Decompiler) -and (Get-Command JustDecompile -ErrorAction SilentlyContinue)) { Start-Process -FilePath JustDecompile -ArgumentList "/target:$assembly" } elseif (($Decompiler -eq [Decompiler]::Reflector -or !$Decompiler) -and (Get-Command reflector -ErrorAction SilentlyContinue)) { Start-Process -FilePath reflector -ArgumentList "/select:$type $assembly" } elseif ($Decompiler -eq [Decompiler]::GitHub -or !$Decompiler) { $class = $commandInfo.ImplementingType.Name $uri = "https://api.github.com/search/code?q=`"class+${class}`"+in:file+repo:powershell/powershell" [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 $result = Invoke-RestMethod -Uri $uri -Method Get if ($result) { $url = $result.items | Select-Object -ExpandProperty html_url Start-Process -FilePath $url } } else { throw 'No decompiler is present in your path' } $object = New-Object PSObject -Property @{ Name = $commandInfo.Name Type = $type Assembly = $assembly } return $object } } enum Decompiler { dnSpy ILSpy dotPeek JustDecompile Reflector GitHub } |