PowerShell Issue With GUI - visual-studio

I am having an issue when setting labels text with a PowerShell command. I am trying to set a label to the size of the mailbox, this is the command I use.
$MailBoxSize.Text = Get-Mailbox -Identity $comboBox1.SelectedItem | Get-MailboxStatistics | Select TotalItemSize | ft -HideTableHeader
Here is the result I get.
Microsoft.PowerShell.Commands.Internal.Format.FormatStartData Microsoft.PowerShell.Commands.Internal.Format.GroupStartData Microsoft.PowerShell.Commands.Internal.Format.FormatEntryData Microsoft.PowerShell.Commands.Internal.Format.GroupEndData Microsoft.PowerShell.Commands.Internal.Format.FormatEndData

You should never be capturing the output of a Format-Table (or any other Format- command). Those commands are used for formatting output, usually to the console. Instead, if you wish to get the value to a property use the -ExpandProperty parameter of the Select-Object cmdlet. Change your line to read:
$MailBoxSize.Text = Get-Mailbox -Identity $comboBox1.SelectedItem | Get-MailboxStatistics | Select -ExpandProperty TotalItemSize

Related

How to reformat date from Get-ADComputer output

Using a PowerShell script, how do I reformat the output from "Get-ADComputer -Filter * -Properties Created | FT Name,Created" and then write to reformated output to the computer description in AD.
the current output looks like this below
Name Created
---- -------
LAPTOP12 30/06/2011 10:22:52 AM
LAPTOP03 18/01/2016 3:47:06 PM
LAPTOP01 12/07/2011 11:04:29 AM
LAPTOP11 30/10/2015 8:27:00 AM
PC06 11/07/2011 2:03:17 PM
The format I am looking to create is
computername Provisioned ddMMyyyy
Then write this revised output of "Provisioned ddMMyyy" to the computer description in AD
Get-ADComputer -Filter * -Properties Created | foreach-object { Set-ADComputer $_ -Description "Provisioned $($_.Created.ToString("ddMMyy"))" }
No need for ft Name,Created here because ft is for a human-readable output
Use the | (pipe) character to send the results of Get-ADComputer to the next command
Use foreach-object on the piped output to iterate through each item from the Get-ADComputer output
Use Set-ADComputer with the -Description parameter to update the AD description
Use the .ToString method to reformat the $_.Created value to your desired format

"gwmi win32_quickfixengineering" but only need InstalledOn date

gwmi win32_quickfixengineering InstalledOn |sort installedon -desc | select -First 1
I've tried but that gives me an odd formatting. I simply need to return the installedOn date and maybe the name.
i'm trying to find the most recently installed patch on a system and get that date value.
I've also tried.
gwmi win32_quickfixengineering |sort installedon -desc | select -First 1
better formatting but still too much information.
To get just the InstalledOn properties, you can use the -ExpandProperty option as below.
GWMI win32_quickfixengineering | sort -Descending InstalledOn `
| Select -ExpandProperty InstalledOn -First 1
Otherwise you can do something like the below to get a brief overview of the installed KBs.
GWMI win32_quickfixengineering | Select HotFixID, InstalledOn, Caption
Info:
Select -ExpandProperty
Get-HotFix / win32_quickfixengineering
The easiest way to get specific information you want is the following:
Lets say you need a name of a service for a command:
$Service = Get-Service Spooler
That command would retrieve more information than just the name, but to get the only name, you can type:
$Service.name
That will return only that value from the saved variable.
So in your case you could do:
(Here you save all the information into a variable)
$Quickfix = gwmi win32_quickfixengineering | sort installedon -desc | select -First 1
(You can then use that variable to return specific information from that variable)
Then use: $Quickfix.InstalledOn
That will return you JUST the date.
Then you could do something like:
Write-Output "Latest update was $($Quickfix.HotFixID) installed on: $($Quickfix.InstalledOn)"
That will give you an output of the KB and the date installed. You can of course edit the text, it was just an example.

Save the powershell's output in a CSV file

I have a powershell script in which i can get information about my operating system (windows version, build...). However all that information is shown in the powershell console and I want them to be exported to a CSV or a XML file.
The script is :
Get-CimInstance Win32_OperatingSystem |
Select-Object Caption, CSDVersion, ServicePackMajorVersion, BuildNumber |
FL
Use Export-Csv cmdlet:
Get-CimInstance Win32_OperatingSystem | Select-Object Caption, CSDVersion, ServicePackMajorVersion, BuildNumber | Export-Csv -NoTypeInformation -Path .\OS_Info.csv
Result (OS_Info.csv):
"Caption","CSDVersion","ServicePackMajorVersion","BuildNumber"
"Microsoft Windows Server 2012 R2 Datacenter",,"0","9600"
Thank you it worked, the file is generated in the folder System32
As Rohin Sidharth mentioned, .\ prefix for the path will create file in the current dir ($PWD in PowerShell). You probably run PowerShell as administrator: in this case the default directory is %WinDir%\System32. Just use full path or GetFolderPath .Net method to get common folder path, like desktop:
... | Export-Csv -NoTypeInformation -Path 'C:\OS_Info.csv'
... | Export-Csv -NoTypeInformation -Path (Join-Path -Path [System.Environment]::GetFolderPath('Desktop') -ChildPath 'OS_Info.csv')
Can you also show me how to export many results in the same file ? for
example i have a script in which i can know all the update that are
installed :
Get-Hotfix | Select HotfixID,Description,InstalledOn | Sort InstalledOnfunction
and i want the results saves in the same CSV file
You can do this by using Select-Object's calculated properties:
# Get OS info
$OsInfo = Get-CimInstance -ClassName Win32_OperatingSystem
Get-Hotfix | # Get HotFixes
Sort-Object -Property InstalledOnfunction | # Sort them
Select-Object -Property #( # Select required fields
# Add Caption property from $OsInfo variable
#{
Name = 'Caption'
Expression = {$OsInfo.Caption}
}
# Add CSDVersion property from $OsInfo variable
#{
Name = 'CSDVersion'
Expression = {$OsInfo.CSDVersion}
}
# Add ServicePackMajorVersion property from $OsInfo variable
#{
Name = 'ServicePackMajorVersion'
Expression = {$OsInfo.ServicePackMajorVersion}
}
# Add BuildNumber property from $OsInfo variable
#{
Name = 'BuildNumber'
Expression = {$OsInfo.BuildNumber}
}
# Add other properties from original HotFix object
'HotfixID'
'Description'
'InstalledOn'
) | Export-Csv -NoTypeInformation -Path 'C:\OS_Info.csv'
You can also try to join objects using custom function.
Quick tip: Make sure you don't pipe to Format List (FL) then pipe to export-csv or you'll open the CSV file and your data will look like this.
ClassId2e4f51ef21dd47e99d3c952918aff9cd pageHeaderEntry pageFooterEntry
autosizeInfo shapeInfo groupingEntry
033ecb2bc07a4d43b5ef94ed5a35d280
Microsoft.PowerShell.Commands.Internal.Format.ListViewHeaderInfo
9e210fe47d09416682b841769c78b8a3
27c87ef9bbda4f709f6b4002fa4af63c
4ec4f0187cb04f4cb6973460dfe252df
cf522b78d86c486691226b40aa69e95c

Powershell order objects by property which is numeric string [duplicate]

I want the greatest value (mailboxSize) at the top of the file. I have a cvs as inport.
When I do the following sort cmd:
Import-Csv import.csv| Sort-Object MailboxSize,DisplayName -Descending | Export-Csv SORT.csv
I get the following result:
"DisplayName","MailboxSize"
"persone6","9941"
"persone3","8484"
"persone1","7008"
"persone4","4322"
"persone5","3106"
"persone7","27536"
"persone10","24253"
"persone8","1961"
"persone9","17076"
"persone11","17012"
"persone2","15351"
"persone12","11795"
"persone14","1156"
"persone13","1008"
But I want this as a result!
"persone7","27536"
"persone10","24253"
"persone9","17076"
"persone11","17012"
"persone2","15351"
"persone12","11795"
"persone6","9941"
"persone3","8484"
"persone1","7008"
"persone4","4322"
"persone5","3106"
"persone14","1156"
"persone13","1008"
When importing a CSV-file, all properties are made string-type. You have to cast the MailboxSize to an int before you can sort it properly. Try:
Import-Csv import.csv |
Sort-Object {[int]$_.MailboxSize}, DisplayName -Descending |
Export-Csv SORT.csv
You should also use the -NoTypeInformation switch in Export-CSV to avoid the #TYPE ..... line (first line in an exported CSV-file).
Sample:
$data = #"
"DisplayName","MailboxSize"
"persone6","9941"
"persone3","8484"
"persone1","7008"
"persone4","4322"
"persone5","3106"
"persone7","27536"
"persone10","24253"
"persone8","1961"
"persone9","17076"
"persone11","17012"
"persone2","15351"
"persone12","11795"
"persone14","1156"
"persone13","1008"
"# | ConvertFrom-Csv
$data |
Sort-Object {[int]$_.MailboxSize}, DisplayName -Descending |
Export-Csv SORT.csv -NoTypeInformation
SORT.csv
"DisplayName","MailboxSize"
"persone7","27536"
"persone10","24253"
"persone9","17076"
"persone11","17012"
"persone2","15351"
"persone12","11795"
"persone6","9941"
"persone3","8484"
"persone1","7008"
"persone4","4322"
"persone5","3106"
"persone8","1961"
"persone14","1156"
"persone13","1008"
I'm guessing the usernames are fake, but be aware that the same issue goes for DisplayName if your usernames actually was personeXX where XX is an int. Like:
persone7 27536
persone20 27536
persone13 27536
To sort them probably, you'd have to create a scriptblock for Sort-Object or create your own function to split the value and sort them correctly.

Continuously monitors the CPU usage % of top X processes

I want to be able to to output to a log file the top CPU consumers every 5 seconds. That way I will be able to see who uses the most of the cpu during my tests.
I have found this answer very common:
$cpu = Get-Counter -ComputerName localhost "\Process(*)\% Processor Time" `
| Select-Object -ExpandProperty countersamples `
| where {$_.InstanceName -ne 'idle' } `
| where {$_.InstanceName -ne '_total' }`
| Select-Object -Property instancename, cookedvalue `
| Sort-Object -Property cookedvalue -Descending `
| Select-Object -First 5 `
| ft #{L='Date';E={Get-Date}}, InstanceName, #{L='CPU';E={(($_.Cookedvalue/100)/$NumberOfLogicalProcessors).toString('P')}} -HideTableHeaders `
| Format-Table -Auto | Out-String
I have 2 issues with it:
Sometimes I get:
Get-Counter : The data in one of the performance counter samples is not valid. View the Status property for each PerformanceCounterSample object to make sure it contains valid data.
I would like to get the full process name, and not
java 25%
idea64 0.8%
...
I'll try to answer your two questions at once with following script:
Get-Counter "\Process(*)\% Processor Time" -ErrorAction SilentlyContinue `
| select -ExpandProperty CounterSamples `
| where {$_.Status -eq 0 -and $_.instancename -notin "_total", "idle"} `
| sort CookedValue -Descending `
| select TimeStamp,
#{N="Name";E={
$friendlyName = $_.InstanceName
try {
$procId = [System.Diagnostics.Process]::GetProcessesByName($_.InstanceName)[0].Id
$proc = Get-WmiObject -Query "SELECT ProcessId, ExecutablePath FROM Win32_Process WHERE ProcessId=$procId"
$procPath = ($proc | where { $_.ExecutablePath } | select -First 1).ExecutablePath
$friendlyName = [System.Diagnostics.FileVersionInfo]::GetVersionInfo($procPath).FileDescription
} catch { }
$friendlyName
}},
#{N="CPU";E={($_.CookedValue/100/$env:NUMBER_OF_PROCESSORS).ToString("P")}} -First 5 `
| ft -a -HideTableHeaders
This results in following table:
24.07.2016 21:00:53 Microsoft Edge Content Process 9,68%
24.07.2016 21:00:53 system 0,77%
24.07.2016 21:00:53 Microsoft Edge 0,39%
24.07.2016 21:00:53 runtimebroker 0,39%
24.07.2016 21:00:53 Host Process for Windows Services 0,39%
As specified, you sometimes get:
Get-Counter : The data in one of the performance counter samples is
not valid. View the Status property for each PerformanceCounterSample
object to make sure it contains valid data.
This is related to process management in windows environment. While you execute query, some processes may appear, some of them may disappear (i.e. wmiprvse process responsible for executing wmi queries). Some processes may require more permissions you have. This all leads to error when obtaining process information. It can be safely skipped using -ErrorAction SilentlyContinue switch and filtered with Status -eq 0 expression.
You also want to see more friendly process name. I don't know if there is better way of getting that name than from executable itself using GetVersionInfo method. If such information is available FileDescription property stores that value. If it's not available then non-friendly process name is used.
you get output something like this
Name CPU CPUPercent Description
---- --- ---------- -----------
chrome 10.4988673 8.79 Google Chrome
powershell_ise 6.5364419 7.16 Windows PowerShell ISE
chrome 38.0174437 4.88 Google Chrome
chrome 26.2549683 4.87 Google Chrome
chrome 16.9417086 3.16 Google Chrome
cavwp 10.2648658 2.67 COMODO Internet Security
chrome 13.1820845 2.44 Google Chrome
chrome 675.016327 2.02 Google Chrome
7.9.7_42331 1037.1570484 1.51 BitTorrent
chrome 340.8777851 1.02 Google Chrome
With
$CPUPercent = #{
Name = 'CPUPercent'
Expression = {
$TotalSec = (New-TimeSpan -Start $_.StartTime).TotalSeconds
[Math]::Round( ($_.CPU * 100 / $TotalSec), 2)
}
}
Get-Process -ComputerName $env:computername |
Select-Object -Property Name, CPU, $CPUPercent, Description |
Sort-Object -Property CPUPercent -Descending |
Select-Object -First 10 |format-table -autosize | out-file c:\pro.log
credit :http://powershell.com/cs/blogs/tips/archive/2013/04/16/documenting-cpu-load-for-running-processes.aspx
Get-Process -ComputerName $env:computername for remote computers you can have in csv
Import-CSV c:\"computers.csv" | % {
$Server = $_.ServerName
$alivetest = Test-Path "\\$Server\c$\"
If ($alivetest -eq "True")
{Get-Process -ComputerName $server |
Select-Object -Property Name, CPU, $CPUPercent, Description |
Sort-Object -Property CPUPercent -Descending |
Select-Object -First 10 |format-table -autosize | out-file c:\pro.log}
}}

Resources