I’m working on a PowerShell WPF GUI tool where I’m stuck with binding pipeline output to listview…I have gone through couple of blogs/articles but couldnt find way to pass pipeline output to listview columns.
I have attached code from xaml and powershell...
xaml code:
<ListView Name="listdisk" HorizontalAlignment="Left" Height="415" Margin="20,67,0,0" VerticalAlignment="Top" Width="830" Grid.ColumnSpan="3" ScrollViewer.VerticalScrollBarVisibility="Visible">
<ListView.View>
<GridView>
<GridViewColumn Header="Server Name" DisplayMemberBinding ="{Binding 'ServerName'}" Width="200"/>
<GridViewColumn Header="C Disk Size(GB)" DisplayMemberBinding ="{Binding 'Csize'}" Width="105"/>
<GridViewColumn Header="C Free Space(GB)" DisplayMemberBinding ="{Binding 'Cfree'}" Width="105"/>
<GridViewColumn Header="C % Free Space" DisplayMemberBinding ="{Binding 'CPercentfree'}" Width="100"/>
<GridViewColumn Header="D Disk Size(GB)" DisplayMemberBinding ="{Binding 'Dsize'}" Width="105"/>
<GridViewColumn Header="D Free Space(GB)" DisplayMemberBinding ="{Binding 'Dfree'}" Width="100"/>
<GridViewColumn Header="D % Free Space" DisplayMemberBinding ="{Binding 'DPercentfree'}" Width="100"/>
</GridView>
</ListView.View>
</ListView>
Powershell function-
Function Get-diskinfo{
$dsk=#()
$Getservers = Get-Content $dsksvr
foreach ($CompName in $Getservers)
{
$cdrivespace= Get-WMIObject Win32_logicaldisk -ComputerName $CompName | ?{$_.DeviceID -eq 'C:'} | Select #{Name=‘cTotalSize’;Expression={[int]($_.Size / 1gb)}},`
#{Name=‘cFreeSpace’;Expression={[int]($_.FreeSpace / 1gb)}}, #{Name=‘cPercentFree’;Expression={[math]::Round($_.FreeSpace / $_.Size,2)*100}}
$ddrivespace= Get-WMIObject Win32_logicaldisk -ComputerName $CompName | ?{$_.DeviceID -eq 'D:'} | Select #{Name=‘dTotalSize’;Expression={[int]($_.Size / 1gb)}},`
#{Name=‘dFreeSpace’;Expression={[int]($_.FreeSpace / 1gb)}}, #{Name=‘dPercentFree’;Expression={[math]::Round($_.FreeSpace / $_.Size,2)*100}}
$diskinfo = New-Object psobject
Add-Member -InputObject $diskinfo -membertype noteproperty -name "ServerName" -value $CompName
Add-Member -InputObject $diskinfo -membertype noteproperty -name "cSize" -value $cdrivespace.cTotalSize
Add-Member -InputObject $diskinfo -membertype noteproperty -name "cFree" -value $cdrivespace.cFreeSpace
Add-Member -InputObject $diskinfo -membertype noteproperty -name "cPercentfree" -value $cdrivespace.cPercentFree
Add-Member -InputObject $diskinfo -membertype noteproperty -name "DSize" -value $ddrivespace.dTotalSize
Add-Member -InputObject $diskinfo -membertype noteproperty -name "DFree" -value $ddrivespace.dFreeSpace
Add-Member -InputObject $diskinfo -membertype noteproperty -name "DPercentfree" -value $ddrivespace.dPercentFree
$dsk +=$diskinfo
} Return, $dsk
}
This is the part where I'm thinking am not doing it properly...can someone guide me on this please..? Thanks
$btndiskinfo.Add_Click({
get-diskinfo | % {$listdisk.items.add([pscustomobject]($_))}
})
Use {Binding WhatEverYouWant} instead of {Binding 'WhatEverYouWant'},
When you need to pass a custom object in a listview you can use :
$btndiskinfo.Add_Click({
$listdisk.ItemsSource = #(get-diskinfo)
})
Be sure your columns names in the listview have the same name as your custom object properties
I've got a work-around you can try. Instead of creating an array of PSObjects inside the foreach and adding it to the ListView after the function is over, try creating 1 PSCustomObject like you're already doing but instead add it to the ListView then and there where you call $dsk += $diskinfo
Something like:
...
Add-Member -InputObject $diskinfo -membertype noteproperty -name "DPercentfree" -value $ddrivespace.dPercentFree
$listdisk.items.add([pscustomobject]($diskinfo))
Related
Hi I hope someone can help me, I'm not great at scripting and my issue is...
I have a medium estate of around 15,000 users which is in a bit of a mess. There are around 3000 user accounts which are disabled. Some user accounts are disabled due to the user being on long term sick, maternity, or suspended, these 'known' accounts are not to be touched so I cannot do a broad "find accounts that are disabled and just delete them" script.
Currently I have a script which exports all disabled accounts to a csv, I then manually manipulate that data within the csv to tag known accounts that cannot be deleted. I then take that file and run this script...
Import-Module ActiveDirectory
$list = Import-CSV C:\temp\deleteuser.csv
forEach ($item in $list) {
$samAccountName = $item.samAccountName
#Get DistinguishedName from SamAccountName
$DN = Get-ADuser -Identity $Samaccountname -Properties DistinguishedName |
Select-Object -ExpandProperty DistinguishedName
try{
#Remove object using DN
Remove-ADObject -Identity $DN -Confirm:$false
"Remove successful for $SamAccountName" | Out-File 'C:\temp\Account Delete Success.txt' -Append }
Catch{
"Remove failed for $SamAccountName" | Out-File 'C:\temp\Account Delete Failed.txt' -Append
}
}
While this is great, I'd love to be able to check the user account is still disabled before the Remove-ADObject command is run and for it to skip the account and output the name of the skipped account to a txt file. Is that possible or am I over complicating things?
simply test 'Enabled' property before deleting user like this :
Import-Module ActiveDirectory
$list = Import-CSV C:\temp\deleteuser.csv
forEach ($item in $list) {
$samAccountName = $item.samAccountName
#Get DistinguishedName from SamAccountName
$DN = Get-ADuser -Identity $Samaccountname -Properties DistinguishedName, Enabled |
Select-Object -ExpandProperty DistinguishedName
try{
#Remove object using DN
if (!$DN.Enabled){
Remove-ADObject -Identity $DN -Confirm:$false
"Remove successful for $SamAccountName" | Out-File 'C:\temp\Account Delete Success.txt' -Append }
else {
"Remove aborted for $SamAccountName" | Out-File 'C:\temp\Account Delete aborted.txt' -Append }
}
}
Catch{
"Remove failed for $SamAccountName" | Out-File 'C:\temp\Account Delete Failed.txt' -Append
}
}
I'm looking at a SQL Server connection string. It looks like this:
Data Source=xxxxxxxx;Initial Catalog=xxxxxxxx;Provider=SQLNCLI11.1;Integrated Security=SSPI
My question is: how is the provider name (in general) mapped to a specific DLL or library?
Here's a second example (for Oracle):
Data Source=xxxxxxxx;User
ID=xxxxxxxx;Provider=OraOLEDB.Oracle.1;Persist Security Info=True;
Same question. How do I get from the provider name to the dll or library where the code is?
the dll path is stored in inprocserver32 of the provider (GUID) in the registry (HKEY_CLASSES\CLSID)
foreach ($provider in [System.Data.OleDb.OleDbEnumerator]::GetRootEnumerator())
{
$v = New-Object PSObject
for ($i = 0; $i -lt $provider.FieldCount; $i++)
{
Add-Member -in $v NoteProperty $provider.GetName($i) $provider.GetValue($i)
}
$reg = Get-ItemProperty "Registry::HKEY_CLASSES_ROOT\CLSID\$($v.SOURCES_CLSID)\InprocServer32" -ErrorAction SilentlyContinue
Add-Member -in $v "Dll path" $reg.'(default)'
$v
}
I have a program with a main window (powershell wpf/xaml). That program does a check for files and opens a second window, if something is missing it must have a link to the folder, i use .Add_PreviewMouseDown({ }) for that. That works, but if i run a second check, window 2 gets the same "link to folder" as window 3. How can i get it to work, that links of window 2 dont get updatet?
i already tried to get dynamic Label Names and PreviewMouseDown's but that isnt enough.
$Script:WindowNumber += 1
$WindowName = "Win$WindowNumber"
$CEMessage = '<Label Name="CEFout' + $WindowNumber + '" HorizontalAlignment="Left" Margin="30,288,0,0" VerticalAlignment="Top" Width="142" FontSize="14" ToolTip="Fileserver Folder" >
<Hyperlink NavigateUri="Bureaublad\Machine Folder">⨯ CE:</Hyperlink>
</Label>'
New-Variable -Name "BijlagenWPF$WindowNumber" -Value ($BijlagenWPF = #"
<Window
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
Title="Bijlagen" Height="420" Width="250" Icon="$Icon" ResizeMode="NoResize" ShowInTaskbar="True">
<Grid HorizontalAlignment="Center" Margin="0,0,0,0" Width="240">
$CEMessage
</Grid>
</Window>
"# -as [XML])
$NR2=(New-Object System.Xml.XmlNodeReader (Get-Variable | Where-Object Name -eq "BijlagenWPF$WindowNumber").Value)
New-Variable -Name $WindowName -Value ([Windows.Markup.XamlReader]::Load( $NR2 ))
$BijlagenWPF.SelectNodes("//*[#*[contains(translate(name(.),'n','N'),'Name')]]") | ForEach-Object {
New-Variable -Name $_.Name -Value (Get-Variable | Where-Object Name -eq $WindowName).Value.FindName($_.Name) -Force
}
(Get-Variable | Where-Object Name -eq "CEFout$WindowNumber").Value.Add_PreviewMouseDown({[system.Diagnostics.Process]::start("$Desktop\$Machine\Fileserver\manual\bijlagen")})
(Get-Variable | Where-Object Name -eq $WindowName).Value.Show()
This is a screenshot of the 2 windows with opened link. Now the link in the first window (2532-163) is the same as the second window (2532-164). But has to be 2532-163 folder
I've been lurking around grabbing code answers from this site for years, but this is my first time actually asking a question. I don't actually get paid to code, rather I use scripts to make routine tasks easier.
I've been using a powershell script with the following code (that I pretty much gleaned from this site) to gather disk usage on client servers:
$dataColl = #()#Makes an array, or a collection to hold all the object of the same fields
foreach ($serverName in (get-content c:\reporting\Disk_useage\My_servers.txt))
{
$path = “\\$serverName\d$\folder1\TargetSubdir“
$dirSize = Get-ChildItem $path -recurse -force | select Length |Measure-Object -Sum length
$dirSize.sum = $dirSize.sum/1MB
$finalResult = “{0:N2} MB” -f $dirsize.sum
$dataObject = New-Object PSObject
Add-Member -inputObject $dataObject -memberType NoteProperty -name “ServerName” -value $serverName
Add-Member -inputObject $dataObject -memberType NoteProperty -name “Dir_Size” -value $finalResult
$dataColl += $dataObject
$dataObject
}
$dataColl | Export-Csv -noTypeInformation -path c:\reporting\Disk_useage\Svr_disk.csv
This has been working fine, but we now have a 2nd domain with client servers, so I need to add credentials for servers in the 2nd domain. I've been researching ways to pass credentials along, and got this bit of code (PW has been stored already in the .TXT file):
$username = "MyDomain\MyAccount"
$password = cat C:\reporting\securestring.txt | convertto-securestring
$cred = new-object -typename System.Management.Automation.PSCredential `
-argumentlist $username, $password
But I'm supposed to add these parameters somewhere to actually USE the credentials that have been set up:
-Authentication default -Credential $Cred
I've tried it in several different spots without success. FYI, the list in My_servers.txt has a bunch of servers I DON'T need credentials for (since they're on the current domain), and a bunch of servers where I DO need credentials (because they're on another domain). But the credentials I'm using for the script are for a service account that exists in both domains with the same ID/PW. Any help in sorting this out would be greatly appreciated.
Adil's suggestion in code would be:
$dataColl = #()#Makes an array, or a collection to hold all the object of the same fields
$username = "MyDomain\MyAccount"
$password = Get-Content C:\reporting\securestring.txt | convertto-securestring
$cred = New-Object -typename System.Management.Automation.PSCredential `
-argumentlist $username, $password
foreach ($serverName in (get-content c:\reporting\Disk_useage\My_servers.txt))
{
$dirSize = Invoke-Command -Credential $cred -ComputerName $serverName -ScriptBlock {
Get-ChildItem “d:\folder1\TargetSubdir“ -recurse -force | select Length | Measure-Object -Sum length
}
$dirSize.sum = $dirSize.sum/1MB
$finalResult = “{0:N2} MB” -f $dirsize.sum
$dataObject = New-Object PSObject
Add-Member -inputObject $dataObject -memberType NoteProperty -name “ServerName” -value $serverName
Add-Member -inputObject $dataObject -memberType NoteProperty -name “Dir_Size” -value $finalResult
$dataColl += $dataObject
$dataObject
}
$dataColl | Export-Csv -noTypeInformation -path c:\reporting\Disk_useage\Svr_disk.csv
When trying to create users from a file I get an error when -otherAttributes #{} is added to ps script. I am new to powershell and can not get it to work. Any guidance is appreciated. This is My code:
Import-Module ActiveDirectory
$OU = 'ou=Staging OU, dc=Domain, dc=net'
$usrfile = "\\servername\testuser.csv"
Import-Csv $usrfile |
ForEach-Object {
New-ADUser -SamAccountName $_.samaccountname -UserPrincipalName $_.Userprincipalname -Name $_.Name -DisplayName $_.displayname -GivenName $_.givenname -Surname $_.sn -Initials $_.initials -Title $_.title -OtherName $_.middlename `
-Description $_.description -Department $_.department -EmployeeID $_.employeeid -Path $OU -Country $_.c `
-OtherAttributes #{departmentNumber=$user.departmentnumber;localeID=$user.localid;extensionAttribute1=$user.extensionAttribute1;employeeType=$user.employeetype} `
-AccountPassword (ConvertTo-SecureString "Password" -AsPlainText -Force) -Enabled $true `
-PasswordNeverExpires $false -ChangePasswordAtLogon $true -PassThru
} > Import.log
The parameter "-otherAttributes #{}" fails in my AD. I found other way change this value in AD.
Try with this:
PS> Set-ADuser -identity joseiba -Clear 'msRTCSIP-PrimaryUserAddress'
PS> Set-ADuser -identity joseiba -Add #{'msRTCSIP-PrimaryUserAddress'='4213#grupofibratel.com'}
BR
Make sure you have all your $'s as $_... when accessing the object in the current loop iteration. I see some aren't.
you left out your ' around the ldapdisplayname for the otherattributes
#{departmentNumber=$user.departmentnumber;
should be: #{'departmentNumber'=$user.departmentnumber;
you need the ' around each ldapdisplayname in otherattributes..
just fought this myself dealing with the notes field