Jakie istotne rzeczy (funkcje, aliasy, skrypty startowe) masz w swoim profilu?
Odpowiedzi:
Często potrzebuję kilku podstawowych agregatów, aby policzyć / zsumować niektóre rzeczy. Zdefiniowałem te funkcje i często ich używam, działają naprawdę dobrze na końcu potoku:
#
# useful agregate
#
function count
{
BEGIN { $x = 0 }
PROCESS { $x += 1 }
END { $x }
}
function product
{
BEGIN { $x = 1 }
PROCESS { $x *= $_ }
END { $x }
}
function sum
{
BEGIN { $x = 0 }
PROCESS { $x += $_ }
END { $x }
}
function average
{
BEGIN { $max = 0; $curr = 0 }
PROCESS { $max += $_; $curr += 1 }
END { $max / $curr }
}
Aby móc uzyskać czas i ścieżkę za pomocą kolorów w moim monicie:
function Get-Time { return $(get-date | foreach { $_.ToLongTimeString() } ) }
function prompt
{
# Write the time
write-host "[" -noNewLine
write-host $(Get-Time) -foreground yellow -noNewLine
write-host "] " -noNewLine
# Write the path
write-host $($(Get-Location).Path.replace($home,"~").replace("\","/")) -foreground green -noNewLine
write-host $(if ($nestedpromptlevel -ge 1) { '>>' }) -noNewLine
return "> "
}
Następujące funkcje zostały skradzione z bloga i zmodyfikowane tak, aby pasowały do mojego gustu, ale ls z kolorami jest bardzo ładny:
# LS.MSH
# Colorized LS function replacement
# /\/\o\/\/ 2006
# http://mow001.blogspot.com
function LL
{
param ($dir = ".", $all = $false)
$origFg = $host.ui.rawui.foregroundColor
if ( $all ) { $toList = ls -force $dir }
else { $toList = ls $dir }
foreach ($Item in $toList)
{
Switch ($Item.Extension)
{
".Exe" {$host.ui.rawui.foregroundColor = "Yellow"}
".cmd" {$host.ui.rawui.foregroundColor = "Red"}
".msh" {$host.ui.rawui.foregroundColor = "Red"}
".vbs" {$host.ui.rawui.foregroundColor = "Red"}
Default {$host.ui.rawui.foregroundColor = $origFg}
}
if ($item.Mode.StartsWith("d")) {$host.ui.rawui.foregroundColor = "Green"}
$item
}
$host.ui.rawui.foregroundColor = $origFg
}
function lla
{
param ( $dir=".")
ll $dir $true
}
function la { ls -force }
I kilka skrótów, aby uniknąć naprawdę powtarzalnych zadań filtrowania:
# behave like a grep command
# but work on objects, used
# to be still be allowed to use grep
filter match( $reg )
{
if ($_.tostring() -match $reg)
{ $_ }
}
# behave like a grep -v command
# but work on objects
filter exclude( $reg )
{
if (-not ($_.tostring() -match $reg))
{ $_ }
}
# behave like match but use only -like
filter like( $glob )
{
if ($_.toString() -like $glob)
{ $_ }
}
filter unlike( $glob )
{
if (-not ($_.tostring() -like $glob))
{ $_ }
}
Aby skonfigurować moje środowisko kompilacji Visual Studio z PowerShell, wziąłem VsVars32 stąd . i używaj go cały czas.
################################################## ############################# # Ujawnia zmienne środowiska w pakiecie i ustawia je w tej sesji PS ################################################## ############################# funkcja Get-Batchfile ($ file) { $ theCmd = "` "$ file`" & set " cmd / c $ theCmd | Foreach-Object { $ thePath, $ theValue = $ _. split ('=') Set-Item -path env: $ thePath -value $ theValue } } ################################################## ############################# # Ustawia zmienne VS do użycia w tej sesji PS ################################################## ############################# funkcja VsVars32 ($ wersja = "9.0") { $ theKey = "HKLM: SOFTWARE \ Microsoft \ VisualStudio \" + wersja $ $ theVsKey = get-ItemProperty $ theKey $ theVsInstallPath = [System.IO.Path] :: GetDirectoryName ($ theVsKey.InstallDir) $ theVsToolsDir = [System.IO.Path] :: GetDirectoryName ($ theVsInstallPath) $ theVsToolsDir = [System.IO.Path] :: Combine ($ theVsToolsDir, "Narzędzia") $ theBatchFile = [System.IO.Path] :: Combine ($ theVsToolsDir, "vsvars32.bat") Get-Batchfile $ theBatchFile [System.Console] :: Title = "Visual Studio" + $ wersja + "Windows Powershell" }
To iteruje poprzez skrypty PSDrive i dot-sources wszystko, co zaczyna się od „lib-”.
### ---------------------------------------------------------------------------
### Load function / filter definition library
### ---------------------------------------------------------------------------
Get-ChildItem scripts:\lib-*.ps1 | % {
. $_
write-host "Loading library file:`t$($_.name)"
}
start-transkrypcja . Spowoduje to zapisanie całej sesji do pliku tekstowego. Doskonały do szkolenia nowych pracowników w zakresie korzystania z programu Powershell w środowisku.
Mój monit zawiera:
$width = ($Host.UI.RawUI.WindowSize.Width - 2 - $(Get-Location).ToString().Length)
$hr = New-Object System.String @('-',$width)
Write-Host -ForegroundColor Red $(Get-Location) $hr
Co daje mi separator między poleceniami, który jest łatwy do zobaczenia podczas przewijania wstecz. Pokazuje również bieżący katalog bez używania spacji poziomej w wierszu, w którym piszę.
Na przykład:
C: \ Users \ Jay -------------------------------------------- -------------------------------------------------- ------------ [1] PS>
Oto mój niezbyt subtelny profil
#==============================================================================
# Jared Parsons PowerShell Profile (jaredp@rantpack.org)
#==============================================================================
#==============================================================================
# Common Variables Start
#==============================================================================
$global:Jsh = new-object psobject
$Jsh | add-member NoteProperty "ScriptPath" $(split-path -parent $MyInvocation.MyCommand.Definition)
$Jsh | add-member NoteProperty "ConfigPath" $(split-path -parent $Jsh.ScriptPath)
$Jsh | add-member NoteProperty "UtilsRawPath" $(join-path $Jsh.ConfigPath "Utils")
$Jsh | add-member NoteProperty "UtilsPath" $(join-path $Jsh.UtilsRawPath $env:PROCESSOR_ARCHITECTURE)
$Jsh | add-member NoteProperty "GoMap" @{}
$Jsh | add-member NoteProperty "ScriptMap" @{}
#==============================================================================
#==============================================================================
# Functions
#==============================================================================
# Load snapin's if they are available
function Jsh.Load-Snapin([string]$name) {
$list = @( get-pssnapin | ? { $_.Name -eq $name })
if ( $list.Length -gt 0 ) {
return;
}
$snapin = get-pssnapin -registered | ? { $_.Name -eq $name }
if ( $snapin -ne $null ) {
add-pssnapin $name
}
}
# Update the configuration from the source code server
function Jsh.Update-WinConfig([bool]$force=$false) {
# First see if we've updated in the last day
$target = join-path $env:temp "Jsh.Update.txt"
$update = $false
if ( test-path $target ) {
$last = [datetime] (gc $target)
if ( ([DateTime]::Now - $last).Days -gt 1) {
$update = $true
}
} else {
$update = $true;
}
if ( $update -or $force ) {
write-host "Checking for winconfig updates"
pushd $Jsh.ConfigPath
$output = @(& svn update)
if ( $output.Length -gt 1 ) {
write-host "WinConfig updated. Re-running configuration"
cd $Jsh.ScriptPath
& .\ConfigureAll.ps1
. .\Profile.ps1
}
sc $target $([DateTime]::Now)
popd
}
}
function Jsh.Push-Path([string] $location) {
go $location $true
}
function Jsh.Go-Path([string] $location, [bool]$push = $false) {
if ( $location -eq "" ) {
write-output $Jsh.GoMap
} elseif ( $Jsh.GoMap.ContainsKey($location) ) {
if ( $push ) {
push-location $Jsh.GoMap[$location]
} else {
set-location $Jsh.GoMap[$location]
}
} elseif ( test-path $location ) {
if ( $push ) {
push-location $location
} else {
set-location $location
}
} else {
write-output "$loctaion is not a valid go location"
write-output "Current defined locations"
write-output $Jsh.GoMap
}
}
function Jsh.Run-Script([string] $name) {
if ( $Jsh.ScriptMap.ContainsKey($name) ) {
. $Jsh.ScriptMap[$name]
} else {
write-output "$name is not a valid script location"
write-output $Jsh.ScriptMap
}
}
# Set the prompt
function prompt() {
if ( Test-Admin ) {
write-host -NoNewLine -f red "Admin "
}
write-host -NoNewLine -ForegroundColor Green $(get-location)
foreach ( $entry in (get-location -stack)) {
write-host -NoNewLine -ForegroundColor Red '+';
}
write-host -NoNewLine -ForegroundColor Green '>'
' '
}
#==============================================================================
#==============================================================================
# Alias
#==============================================================================
set-alias gcid Get-ChildItemDirectory
set-alias wget Get-WebItem
set-alias ss select-string
set-alias ssr Select-StringRecurse
set-alias go Jsh.Go-Path
set-alias gop Jsh.Push-Path
set-alias script Jsh.Run-Script
set-alias ia Invoke-Admin
set-alias ica Invoke-CommandAdmin
set-alias isa Invoke-ScriptAdmin
#==============================================================================
pushd $Jsh.ScriptPath
# Setup the go locations
$Jsh.GoMap["ps"] = $Jsh.ScriptPath
$Jsh.GoMap["config"] = $Jsh.ConfigPath
$Jsh.GoMap["~"] = "~"
# Setup load locations
$Jsh.ScriptMap["profile"] = join-path $Jsh.ScriptPath "Profile.ps1"
$Jsh.ScriptMap["common"] = $(join-path $Jsh.ScriptPath "LibraryCommon.ps1")
$Jsh.ScriptMap["svn"] = $(join-path $Jsh.ScriptPath "LibrarySubversion.ps1")
$Jsh.ScriptMap["subversion"] = $(join-path $Jsh.ScriptPath "LibrarySubversion.ps1")
$Jsh.ScriptMap["favorites"] = $(join-path $Jsh.ScriptPath "LibraryFavorites.ps1")
$Jsh.ScriptMap["registry"] = $(join-path $Jsh.ScriptPath "LibraryRegistry.ps1")
$Jsh.ScriptMap["reg"] = $(join-path $Jsh.ScriptPath "LibraryRegistry.ps1")
$Jsh.ScriptMap["token"] = $(join-path $Jsh.ScriptPath "LibraryTokenize.ps1")
$Jsh.ScriptMap["unit"] = $(join-path $Jsh.ScriptPath "LibraryUnitTest.ps1")
$Jsh.ScriptMap["tfs"] = $(join-path $Jsh.ScriptPath "LibraryTfs.ps1")
$Jsh.ScriptMap["tab"] = $(join-path $Jsh.ScriptPath "TabExpansion.ps1")
# Load the common functions
. script common
. script tab
$global:libCommonCertPath = (join-path $Jsh.ConfigPath "Data\Certs\jaredp_code.pfx")
# Load the snapin's we want
Jsh.Load-Snapin "pscx"
Jsh.Load-Snapin "JshCmdlet"
# Setup the Console look and feel
$host.UI.RawUI.ForegroundColor = "Yellow"
if ( Test-Admin ) {
$title = "Administrator Shell - {0}" -f $host.UI.RawUI.WindowTitle
$host.UI.RawUI.WindowTitle = $title;
}
# Call the computer specific profile
$compProfile = join-path "Computers" ($env:ComputerName + "_Profile.ps1")
if ( -not (test-path $compProfile)) { ni $compProfile -type File | out-null }
write-host "Computer profile: $compProfile"
. ".\$compProfile"
$Jsh.ScriptMap["cprofile"] = resolve-path ($compProfile)
# If the computer name is the same as the domain then we are not
# joined to active directory
if ($env:UserDomain -ne $env:ComputerName ) {
# Call the domain specific profile data
write-host "Domain $env:UserDomain"
$domainProfile = join-path $env:UserDomain "Profile.ps1"
if ( -not (test-path $domainProfile)) { ni $domainProfile -type File | out-null }
. ".\$domainProfile"
}
# Run the get-fortune command if JshCmdlet was loaded
if ( get-command "get-fortune" -ea SilentlyContinue ) {
get-fortune -timeout 1000
}
# Finished with the profile, go back to the original directory
popd
# Look for updates
Jsh.Update-WinConfig
# Because this profile is run in the same context, we need to remove any
# variables manually that we don't want exposed outside this script
Mam kilka funkcji, a ponieważ jestem autorem modułów, zazwyczaj ładuję konsolę i desperacko muszę wiedzieć, co gdzie jest.
write-host "Your modules are..." -ForegroundColor Red
Get-module -li
Die hard nerding:
function prompt
{
$host.UI.RawUI.WindowTitle = "ShellPower"
# Need to still show the working directory.
#Write-Host "You landed in $PWD"
# Nerd up, yo.
$Str = "Root@The Matrix"
"$str> "
}
Obowiązkowe wszystko, co mogę PowerShell, przejdę tutaj ...
# Explorer command
function Explore
{
param
(
[Parameter(
Position = 0,
ValueFromPipeline = $true,
Mandatory = $true,
HelpMessage = "This is the path to explore..."
)]
[ValidateNotNullOrEmpty()]
[string]
# First parameter is the path you're going to explore.
$Target
)
$exploration = New-Object -ComObject shell.application
$exploration.Explore($Target)
}
NADAL jestem administratorem, więc potrzebuję ...
Function RDP
{
param
(
[Parameter(
Position = 0,
ValueFromPipeline = $true,
Mandatory = $true,
HelpMessage = "Server Friendly name"
)]
[ValidateNotNullOrEmpty()]
[string]
$server
)
cmdkey /generic:TERMSRV/$server /user:$UserName /pass:($Password.GetNetworkCredential().Password)
mstsc /v:$Server /f /admin
Wait-Event -Timeout 5
cmdkey /Delete:TERMSRV/$server
}
Czasami chcę rozpocząć eksplorację jako ktoś inny niż zalogowany użytkownik ...
# Restarts explorer as the user in $UserName
function New-Explorer
{
# CLI prompt for password
taskkill /f /IM Explorer.exe
runas /noprofile /netonly /user:$UserName explorer
}
To tylko dlatego, że jest zabawne.
Function Lock-RemoteWorkstation
{
param(
$Computername,
$Credential
)
if(!(get-module taskscheduler))
{
Import-Module TaskScheduler
}
New-task -ComputerName $Computername -credential:$Credential |
Add-TaskTrigger -In (New-TimeSpan -Seconds 30) |
Add-TaskAction -Script `
{
$signature = @"
[DllImport("user32.dll", SetLastError = true)]
public static extern bool LockWorkStation();
"@
$LockWorkStation = Add-Type -memberDefinition $signature -name "Win32LockWorkStation" -namespace Win32Functions -passthru
$LockWorkStation::LockWorkStation() | Out-Null
} | Register-ScheduledTask TestTask -ComputerName $Computername -credential:$Credential
}
Mam też dla siebie, bo Win+ Ljest za daleko ...
Function llm # Lock Local machine
{
$signature = @"
[DllImport("user32.dll", SetLastError = true)]
public static extern bool LockWorkStation();
"@
$LockWorkStation = Add-Type -memberDefinition $signature -name "Win32LockWorkStation" -namespace Win32Functions -passthru
$LockWorkStation::LockWorkStation() | Out-Null
}
Kilka filtrów? Chyba tak...
filter FileSizeBelow($size){if($_.length -le $size){ $_ }}
filter FileSizeAbove($size){if($_.Length -ge $size){$_}}
Mam też kilka, których nie mogę jeszcze opublikować, ponieważ nie zostały one ukończone, ale w zasadzie są sposobem na zachowanie poświadczeń między sesjami bez zapisywania ich jako zaszyfrowanego pliku.
# ----------------------------------------------------------
# msdn search for win32 APIs.
# ----------------------------------------------------------
function Search-MSDNWin32
{
$url = 'http://search.msdn.microsoft.com/?query=';
$url += $args[0];
for ($i = 1; $i -lt $args.count; $i++) {
$url += '+';
$url += $args[$i];
}
$url += '&locale=en-us&refinement=86&ac=3';
Open-IE($url);
}
# ----------------------------------------------------------
# Open Internet Explorer given the url.
# ----------------------------------------------------------
function Open-IE ($url)
{
$ie = new-object -comobject internetexplorer.application;
$ie.Navigate($url);
$ie.Visible = $true;
}
Open-IE
używam wbudowanego ii
aliasu dla Invoke-Item
.
start http://google.com
dodam tę funkcję, aby móc łatwo sprawdzić użycie dysku:
function df {
$colItems = Get-wmiObject -class "Win32_LogicalDisk" -namespace "root\CIMV2" `
-computername localhost
foreach ($objItem in $colItems) {
write $objItem.DeviceID $objItem.Description $objItem.FileSystem `
($objItem.Size / 1GB).ToString("f3") ($objItem.FreeSpace / 1GB).ToString("f3")
}
}
apropos.
Chociaż myślę, że zostało to zastąpione przez ostatnie lub nadchodzące wydanie.
##############################################################################
## Search the PowerShell help documentation for a given keyword or regular
## expression.
##
## Example:
## Get-HelpMatch hashtable
## Get-HelpMatch "(datetime|ticks)"
##############################################################################
function apropos {
param($searchWord = $(throw "Please specify content to search for"))
$helpNames = $(get-help *)
foreach($helpTopic in $helpNames)
{
$content = get-help -Full $helpTopic.Name | out-string
if($content -match $searchWord)
{
$helpTopic | select Name,Synopsis
}
}
}
Zatrzymuję wszystko po trochu. Przeważnie mój profil konfiguruje całe środowisko (w tym wywoływanie skryptów w celu skonfigurowania mojego środowiska programistycznego .NET / VS i Java).
Przedefiniowuję również prompt()
funkcję w moim własnym stylu ( zobacz ją w akcji ), ustawiam kilka aliasów dla innych skryptów i poleceń. i zmień to, na co $HOME
wskazuje.
Oto mój pełny skrypt profilu .
Set-PSDebug -Strict
Skorzystasz, jeśli kiedykolwiek szukałeś głupiej literówki, np. wypisuje $ varsometext zamiast $ var cosext
##############################################################################
# Get an XPath Navigator object based on the input string containing xml
function get-xpn ($text) {
$rdr = [System.IO.StringReader] $text
$trdr = [system.io.textreader]$rdr
$xpdoc = [System.XML.XPath.XPathDocument] $trdr
$xpdoc.CreateNavigator()
}
Przydatne do pracy z XML, np. Dane wyjściowe poleceń svn z opcją --xml.
To tworzy skrypty: dysk i dodaje go do twojej ścieżki. Uwaga, musisz samodzielnie utworzyć folder. Następnym razem, gdy będziesz musiał do tego wrócić, po prostu wpisz „scripts:” i naciśnij Enter, tak jak każda litera dysku w systemie Windows.
$env:path += ";$profiledir\scripts"
New-PSDrive -Name Scripts -PSProvider FileSystem -Root $profiledir\scripts
Spowoduje to dodanie zainstalowanych snapinów do sesji PowerShell. Powodem, dla którego możesz chcieć zrobić coś takiego, jest to, że jest łatwy w utrzymaniu i działa dobrze, jeśli zsynchronizujesz swój profil z wieloma systemami. Jeśli snapin nie jest zainstalowany, nie zobaczysz komunikatu o błędzie.
$snapins = @(
"Quest.ActiveRoles.ADManagement",
"PowerGadgets",
"VMware.VimAutomation.Core",
"NetCmdlets"
)
$snapins | ForEach-Object {
if ( Get-PSSnapin -Registered $_ -ErrorAction SilentlyContinue ) {
Add-PSSnapin $_
}
}
Umieszczam wszystkie moje funkcje i aliasy w osobnych plikach skryptów, a następnie umieszczam je w moim profilu:
. c: \ scripts \ posh \ jdh-functions.ps1
Możesz zobaczyć mój profil PowerShell pod adresem http://github.com/jamesottaway/windowspowershell
Jeśli użyjesz Git do sklonowania mojego repozytorium do folderu Dokumenty (lub dowolnego folderu powyżej „WindowsPowerShell” w zmiennej $ PROFILE), dostaniesz całą moją dobroć.
Główny profile.ps1
ustawia podfolder o nazwie Addons
jako a PSDrive
, a następnie znajduje wszystkie pliki .ps1 w tym folderze do załadowania.
Bardzo podoba mi się go
polecenie, które przechowuje słownik skrótowych lokalizacji do łatwego odwiedzenia. Na przykład go vsp
zabierze mnie do C:\Visual Studio 2008\Projects
.
Lubię też zastępowanie Set-Location
cmdlet, aby uruchamiało zarówno Set-Location
iGet-ChildItem
.
Moim innym ulubionym jest to, mkdir
co robi Set-Location xyz
po biegu New-Item xyz -Type Directory
.
Function funcOpenPowerShellProfile
{
Notepad $PROFILE
}
Set-Alias fop funcOpenPowerShellProfile
Tylko roztropnie leniwy człowiek powiedziałby, że pisanie na klawiaturzefop
jest o wiele łatwiejsze niż Notepad $PROFILE
po znaku zachęty, chyba że, oczywiście, kojarzy ci się „fop” z XVII-wiecznym angielskim ninny .
Jeśli chcesz, możesz pójść o krok dalej i sprawić, by był nieco przydatny:
Function funcOpenPowerShellProfile
{
$fileProfileBackup = $PROFILE + '.bak'
cp $PROFILE $fileProfileBackup
PowerShell_ISE $PROFILE # Replace with Desired IDE/ISE for Syntax Highlighting
}
Set-Alias fop funcOpenPowerShellProfile
Aby zaspokoić paranoję survivalową:
Function funcOpenPowerShellProfile
{
$fileProfilePathParts = @($PROFILE.Split('\'))
$fileProfileName = $fileProfilePathParts[-1]
$fileProfilePathPartNum = 0
$fileProfileHostPath = $fileProfilePathParts[$fileProfilePathPartNum] + '\'
$fileProfileHostPathPartsCount = $fileProfilePathParts.Count - 2
# Arrays start at 0, but the Count starts at 1; if both started at 0 or 1,
# then a -1 would be fine, but the realized discrepancy is 2
Do
{
$fileProfilePathPartNum++
$fileProfileHostPath = $fileProfileHostPath + `
$fileProfilePathParts[$fileProfilePathPartNum] + '\'
}
While
(
$fileProfilePathPartNum -LT $fileProfileHostPathPartsCount
)
$fileProfileBackupTime = [string](date -format u) -replace ":", ""
$fileProfileBackup = $fileProfileHostPath + `
$fileProfileBackupTime + ' - ' + $fileProfileName + '.bak'
cp $PROFILE $fileProfileBackup
cd $fileProfileHostPath
$fileProfileBackupNamePattern = $fileProfileName + '.bak'
$fileProfileBackups = @(ls | Where {$_.Name -Match $fileProfileBackupNamePattern} | `
Sort Name)
$fileProfileBackupsCount = $fileProfileBackups.Count
$fileProfileBackupThreshold = 5 # Change as Desired
If
(
$fileProfileBackupsCount -GT $fileProfileBackupThreshold
)
{
$fileProfileBackupsDeleteNum = $fileProfileBackupsCount - `
$fileProfileBackupThreshold
$fileProfileBackupsIndexNum = 0
Do
{
rm $fileProfileBackups[$fileProfileBackupsIndexNum]
$fileProfileBackupsIndexNum++;
$fileProfileBackupsDeleteNum--
}
While
(
$fileProfileBackupsDeleteNum -NE 0
)
}
PowerShell_ISE $PROFILE
# Replace 'PowerShell_ISE' with Desired IDE (IDE's path may be needed in
# '$Env:PATH' for this to work; if you can start it from the "Run" window,
# you should be fine)
}
Set-Alias fop funcOpenPowerShellProfile
między innymi:
function w {
explorer .
}
otwiera okno eksploratora w bieżącym katalogu
function startover {
iisreset /restart
iisreset /stop
rm "C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\Temporary ASP.NET Files\*.*" -recurse -force -Verbose
iisreset /start
}
pozbywa się wszystkiego z moich tymczasowych plików asp.net (przydatne do pracy z kodem zarządzanym, który ma zależności od błędnego kodu niezarządzanego)
function edit($x) {
. 'C:\Program Files (x86)\Notepad++\notepad++.exe' $x
}
edytuje $ x w notatniku ++
Jeffrey Snover's Start-NewScope, ponieważ ponowne uruchomienie powłoki może być oporem.
Nigdy nie czułem się komfortowo z opcjami dirusów , więc :
function Get-FolderSizes {
[cmdletBinding()]
param(
[parameter(mandatory=$true)]$Path,
[parameter(mandatory=$false)]$SizeMB,
[parameter(mandatory=$false)]$ExcludeFolder
) #close param
$pathCheck = test-path $path
if (!$pathcheck) {"Invalid path. Wants gci's -path parameter."; break}
$fso = New-Object -ComObject scripting.filesystemobject
$parents = Get-ChildItem $path -Force | where { $_.PSisContainer -and $_.name -ne $ExcludeFolder }
$folders = Foreach ($folder in $parents) {
$getFolder = $fso.getFolder( $folder.fullname.tostring() )
if (!$getFolder.Size) { #for "special folders" like appdata
$lengthSum = gci $folder.FullName -recurse -force -ea silentlyContinue | `
measure -sum length -ea SilentlyContinue | select -expand sum
$sizeMBs = "{0:N0}" -f ($lengthSum /1mb)
} #close if size property is null
else { $sizeMBs = "{0:N0}" -f ($getFolder.size /1mb) }
#else {$sizeMBs = [int]($getFolder.size /1mb) }
New-Object -TypeName psobject -Property @{
name = $getFolder.path;
sizeMB = $sizeMBs
} #close new obj property
} #close foreach folder
#here's the output
$folders | sort @{E={[decimal]$_.sizeMB}} -Descending | ? {[decimal]$_.sizeMB -gt $SizeMB} | ft -auto
#calculate the total including contents
$sum = $folders | select -expand sizeMB | measure -sum | select -expand sum
$sum += ( gci -file $path | measure -property length -sum | select -expand sum ) / 1mb
$sumString = "{0:n2}" -f ($sum /1kb)
$sumString + " GB total"
} #end function
set-alias gfs Get-FolderSizes
Również przydatne do przeglądania miejsca na dysku:
function get-drivespace {
param( [parameter(mandatory=$true)]$Computer)
if ($computer -like "*.com") {$cred = get-credential; $qry = Get-WmiObject Win32_LogicalDisk -filter drivetype=3 -comp $computer -credential $cred }
else { $qry = Get-WmiObject Win32_LogicalDisk -filter drivetype=3 -comp $computer }
$qry | select `
@{n="drive"; e={$_.deviceID}}, `
@{n="GB Free"; e={"{0:N2}" -f ($_.freespace / 1gb)}}, `
@{n="TotalGB"; e={"{0:N0}" -f ($_.size / 1gb)}}, `
@{n="FreePct"; e={"{0:P0}" -f ($_.FreeSpace / $_.size)}}, `
@{n="name"; e={$_.volumeName}} |
format-table -autosize
} #close drivespace
Do wskazywania rzeczy:
function New-URLfile {
param( [parameter(mandatory=$true)]$Target, [parameter(mandatory=$true)]$Link )
if ($target -match "^\." -or $link -match "^\.") {"Full paths plz."; break}
$content = @()
$header = '[InternetShortcut]'
$content += $header
$content += "URL=" + $target
$content | out-file $link
ii $link
} #end function
function New-LNKFile {
param( [parameter(mandatory=$true)]$Target, [parameter(mandatory=$true)]$Link )
if ($target -match "^\." -or $link -match "^\.") {"Full paths plz."; break}
$WshShell = New-Object -comObject WScript.Shell
$Shortcut = $WshShell.CreateShortcut($link)
$Shortcut.TargetPath = $target
$shortCut.save()
} #end function new-lnkfile
Grep biedaka? Do wyszukiwania dużych plików txt.
function Search-TextFile {
param(
[parameter(mandatory=$true)]$File,
[parameter(mandatory=$true)]$SearchText
) #close param
if ( !(test-path $File) ) {"File not found:" + $File; break}
$fullPath = resolve-path $file | select -expand path
$lines = [system.io.file]::ReadLines($fullPath)
foreach ($line in $lines) { if ($line -match $SearchText) {$line} }
} #end function Search-TextFile
Zawiera listę programów zainstalowanych na komputerze zdalnym.
function Get-InstalledProgram { [cmdletBinding()] #http://blogs.technet.com/b/heyscriptingguy/archive/2011/11/13/use-powershell-to-quickly-find-installed-software.aspx
param( [parameter(mandatory=$true)]$Comp,[parameter(mandatory=$false)]$Name )
$keys = 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall','SOFTWARE\Wow6432Node\Microsoft\Windows\CurrentVersion\Uninstall'
TRY { $RegBase = [Microsoft.Win32.RegistryKey]::OpenRemoteBaseKey([Microsoft.Win32.RegistryHive]::LocalMachine,$Comp) }
CATCH {
$rrSvc = gwmi win32_service -comp $comp -Filter {name='RemoteRegistry'}
if (!$rrSvc) {"Unable to connect. Make sure that this computer is on the network, has remote administration enabled, `nand that both computers are running the remote registry service."; break}
#Enable and start RemoteRegistry service
if ($rrSvc.State -ne 'Running') {
if ($rrSvc.StartMode -eq 'Disabled') { $null = $rrSvc.ChangeStartMode('Manual'); $undoMe2 = $true }
$null = $rrSvc.StartService() ; $undoMe = $true
} #close if rrsvc not running
else {"Unable to connect. Make sure that this computer is on the network, has remote administration enabled, `nand that both computers are running the remote registry service."; break}
$RegBase = [Microsoft.Win32.RegistryKey]::OpenRemoteBaseKey([Microsoft.Win32.RegistryHive]::LocalMachine,$Comp)
} #close if failed to connect regbase
$out = @()
foreach ($key in $keys) {
if ( $RegBase.OpenSubKey($Key) ) { #avoids errors on 32bit OS
foreach ( $entry in $RegBase.OpenSubKey($Key).GetSubkeyNames() ) {
$sub = $RegBase.OpenSubKey( ($key + '\' + $entry) )
if ($sub) { $row = $null
$row = [pscustomobject]@{
Name = $RegBase.OpenSubKey( ($key + '\' + $entry) ).GetValue('DisplayName')
InstallDate = $RegBase.OpenSubKey( ($key + '\' + $entry) ).GetValue('InstallDate')
Version = $RegBase.OpenSubKey( ($key + '\' + $entry) ).GetValue('DisplayVersion')
} #close row
$out += $row
} #close if sub
} #close foreach entry
} #close if key exists
} #close foreach key
$out | where {$_.name -and $_.name -match $Name}
if ($undoMe) { $null = $rrSvc.StopService() }
if ($undoMe2) { $null = $rrSvc.ChangeStartMode('Disabled') }
} #end function
Idąc meta, szerząc ewangelię i tak dalej
function Copy-ProfilePS1 ($Comp,$User) {
if (!$User) {$User = $env:USERNAME}
$targ = "\\$comp\c$\users\$User\Documents\WindowsPowershell\"
if (Test-Path $targ)
{
$cmd = "copy /-Y $profile $targ"
cmd /c $cmd
} else {"Path not found! $targ"}
} #end function CopyProfilePS1
$MaximumHistoryCount=1024
function hist {get-history -count 256 | %{$_.commandline}}
New-Alias which get-command
function guidConverter([byte[]] $gross){ $GUID = "{" + $gross[3].ToString("X2") + `
$gross[2].ToString("X2") + $gross[1].ToString("X2") + $gross[0].ToString("X2") + "-" + `
$gross[5].ToString("X2") + $gross[4].ToString("X2") + "-" + $gross[7].ToString("X2") + `
$gross[6].ToString("X2") + "-" + $gross[8].ToString("X2") + $gross[9].ToString("X2") + "-" +`
$gross[10].ToString("X2") + $gross[11].ToString("X2") + $gross[12].ToString("X2") + `
$gross[13].ToString("X2") + $gross[14].ToString("X2") + $gross[15].ToString("X2") + "}" $GUID }
Mój profil jest pusty. Zamiast tego mam foldery skryptów, po których mogę wczytać funkcje i aliasy do sesji. Folder będzie modułowy, z bibliotekami funkcji i złożeń. Do pracy ad hoc będę miał skrypt ładujący aliasy i funkcje. Jeśli chcę przeglądać dzienniki zdarzeń, przechodzę do folderu scripts \ eventlogs i wykonuję
PS > . .\DotSourceThisToLoadSomeHandyEventLogMonitoringFunctions.ps1
Robię to, ponieważ muszę udostępniać skrypty innym lub przenosić je z maszyny na maszynę. Lubię mieć możliwość kopiowania folderu skryptów i zestawów, tak aby działał na dowolnym komputerze dla każdego użytkownika.
Ale chcesz zabawnej kolekcji sztuczek. Oto skrypt, od którego zależy wiele moich „profili”. Umożliwia wywoływanie usług internetowych, które używają samopodpisanego protokołu SSL do eksploracji ad hoc usług internetowych w fazie rozwoju. Tak, swobodnie mieszam C # w moich skryptach PowerShell.
# Using a target web service that requires SSL, but server is self-signed.
# Without this, we'll fail unable to establish trust relationship.
function Set-CertificateValidationCallback
{
try
{
Add-Type @'
using System;
public static class CertificateAcceptor{
public static void SetAccept()
{
System.Net.ServicePointManager.ServerCertificateValidationCallback = AcceptCertificate;
}
private static bool AcceptCertificate(Object sender,
System.Security.Cryptography.X509Certificates.X509Certificate certificate,
System.Security.Cryptography.X509Certificates.X509Chain chain,
System.Net.Security.SslPolicyErrors policyErrors)
{
Console.WriteLine("Accepting certificate and ignoring any SSL errors.");
return true;
}
}
'@
}
catch {} # Already exists? Find a better way to check.
[CertificateAcceptor]::SetAccept()
}
Świetne pytanie. Ponieważ mam do czynienia z kilkoma różnymi hostami PowerShell, rejestruję się trochę w każdym z kilku profili, aby lepiej zrozumieć kontekst innych komunikatów. W programie profile.ps1
obecnie tylko to mam, ale czasami zmieniam to na podstawie kontekstu:
if ($PSVersionTable.PsVersion.Major -ge 3) {
Write-Host "Executing $PSCommandPath"
}
Moim ulubionym gospodarzem jest ISE, Microsoft.PowerShellIse_profile.ps1
mam:
if ($PSVersionTable.PsVersion.Major -ge 3) {
Write-Host "Executing $PSCommandPath"
}
if ( New-PSDrive -ErrorAction Ignore One FileSystem `
(Get-ItemProperty hkcu:\Software\Microsoft\SkyDrive UserFolder).UserFolder) {
Write-Host -ForegroundColor Green "PSDrive One: mapped to local OneDrive/SkyDrive folder"
}
Import-Module PSCX
$PSCX:TextEditor = (get-command Powershell_ISE).Path
$PSDefaultParameterValues = @{
"Get-Help:ShowWindow" = $true
"Help:ShowWindow" = $true
"Out-Default:OutVariable" = "0"
}
#Script Browser Begin
#Version: 1.2.1
Add-Type -Path 'C:\Program Files (x86)\Microsoft Corporation\Microsoft Script Browser\System.Windows.Interactivity.dll'
Add-Type -Path 'C:\Program Files (x86)\Microsoft Corporation\Microsoft Script Browser\ScriptBrowser.dll'
Add-Type -Path 'C:\Program Files (x86)\Microsoft Corporation\Microsoft Script Browser\BestPractices.dll'
$scriptBrowser = $psISE.CurrentPowerShellTab.VerticalAddOnTools.Add('Script Browser', [ScriptExplorer.Views.MainView], $true)
$scriptAnalyzer = $psISE.CurrentPowerShellTab.VerticalAddOnTools.Add('Script Analyzer', [BestPractices.Views.BestPracticesView], $true)
$psISE.CurrentPowerShellTab.VisibleVerticalAddOnTools.SelectedAddOnTool = $scriptBrowser
#Script Browser End
Ze wszystkiego, czego jeszcze nie ma na liście, Start-Steroids musi być moim ulubionym, może z wyjątkiem Start-Transcript.