Can someone assist on how to fill a combobox with the result of a powershell command?
Im trying to fill a combobox with the result of a "Get" cmdlet but I only get some powershell parameters as result.
$ButtonCollectionSearch.Add_Click({
$name = $textboxlogonname.text
$ComboBox = New-Object System.Windows.Forms.ComboBox
$ComboBox.Width = 400
$Collections = Get-RDSessionCollection | fl -Property CollectionName
Foreach ($Collection in $Collection) {
$ComboBox.Items.Add($Collection);
}
$ComboBox.Location = New-Object System.Drawing.Point(120, 10)
$main_form.Controls.Add($ComboBox)
})
The reason you're getting formatting metadata is that you asked for formatting metadata - by piping all your data through fl (which is a alias for Format-List).
Since we just want the value of the CollectionName, use ForEach-Object -MemberName in place of fl -Property:
$Collections = Get-RDSessionCollection | ForEach-Object -MemberName CollectionName
You'll also want to address the typo in the foreach loop declaration - change:
Foreach ($Collection in $Collection) {
to:
Foreach ($Collection in $Collections) {
Related
In my script, I the user to add values to a list that I will use for the rest of the script.
I'm currently using this:
Add-Type -AssemblyName System.Windows.Forms
$form = New-Object System.Windows.Forms.Form
$form.Size = New-Object System.Drawing.Size(350,380)
$form.Padding = New-Object System.Windows.Forms.Padding(20,100,20,20)
$textBox = New-Object System.Windows.Forms.TextBox
$textBox.Multiline = $true
$textBox.ScrollBars = "Vertical"
$textBox.ReadOnly = $true
$textBox.Dock = [System.Windows.Forms.DockStyle]::Fill
$form.Controls.Add($textBox)
$inputLabel = New-Object System.Windows.Forms.Label
$inputLabel.Text = "Doc:"
$inputLabel.Size = New-Object System.Drawing.Size(50,20)
$inputLabel.Location = New-Object System.Drawing.Point(20,22)
$form.Controls.Add($inputLabel)
$addDocButton = New-Object System.Windows.Forms.Button
$addDocButton.Text = "Add to project"
$addDocButton.Size = New-Object System.Drawing.Size(85,23)
$addDocButton.Location = New-Object System.Drawing.Point(220,20)
$docs = #()
$addDocButton.Add_Click({
$docs += $inputBox.Text
$textBox.AppendText("Document added to project: $docs`r`n")
$inputBox.Clear()
})
$form.Controls.Add($addDocButton)
$inputBox = New-Object System.Windows.Forms.TextBox
$inputBox.Size = New-Object System.Drawing.Size(140,20)
$inputBox.Location = New-Object System.Drawing.Point(70,20)
$form.Controls.Add($inputBox)
$form.ShowDialog()
but the list is getting rewritten every time I click the button.
Shouldn't the "+=" be appending the values and not rewriting it?
If variable $docs is needed after the window has been closed, best define it as List object because that is optimized for adding and removing items as opposed to a static array.
When adding items to an array defined with #() using +=, the entire array needs to be rebuilt in memory, which is time and memory consuming
When an event handler scriptblock needs to address a variable defined outside the scriptblock, you need to scope it with $script:, otherwise the variable will be simply a new variable, local to the scriptblock.
$docs = [System.Collections.Generic.List[string]]::new()
$addDocButton.Add_Click({
if (![string]::IsNullOrWhiteSpace($inputBox.Text)) {
$str = $inputBox.Text.Trim()
# refer to the $docs object defined OUSIDE this scriptblock with $script: scoping
$script:docs.Add($str)
$textBox.AppendText("Document added to project: $str`r`n")
}
$inputBox.Clear()
})
I had created this function to attempt to break strings into groups of tokens that can be made into PowerShell object. This is what I have so far. If I use the code outside of the function I get the desired result but if I attempt to use it within the function I get nothing. I believe the output is disappearing. I know I am not using the right terminology to describe what is happening. Any assistance would be appreciated.
Function Convert-MatchToPSCustomObject
{
<#
.SYNOPSIS
Converts $matches to PSCustomObject
.DESCRIPTION
Takes an input string and converts it to PSCustomObject
.PARAMETER Pattern
Mandatory. Pattern which to match within the string
.PARAMETER String
Mandatory. Input String
.EXAMPLE
Convert-MatchToPSCustomObject -Pattern '(?<descriptor>^\b[A-Z]{2})(?>[=])(?<value>[\w \.\-]+\b$)' -String 'CN=Only Da Best'
.LINK
https://regex101.com/r/1hYb2J/1/
.LINK
https://vexx32.github.io/2018/11/08/Named-Regex-Matches-PSCustomObject/
.NOTES
Version: 1.0
Author: Kino Mondesir
#>
[cmdletbinding()]
param
(
[Parameter(HelpMessage="Pattern to match", Position=0, Mandatory=$false, ValueFromPipelineByPropertyName=$true)]
[ValidateNotNullorEmpty()]
[string]$pattern = '(?<descriptor>^\b[A-Z]{2})(?>[=])(?<value>[\w \.\-]+\b$)',
[Parameter(HelpMessage="Input string", Position=1, Mandatory=$true, ValueFromPipeline=$true)]
[ValidateNotNullorEmpty()]
[string]$string
)
Try
{
return $string -split ',' | ForEach-Object {
if ($PSItem -match $pattern)
{
$Matches.Remove(0)
[PSCustomObject]$Matches
}
else
{
Throw "No matching items found!"
}
}
}
Catch
{
$exception = $_.Exception
Write-Error $exception.Message
return -1
}
}
This code is supposed to find a line with a regular expression and replace the line with "test". It is finding that line and replace it with "test" but also deleting the line under it, no matter what is in the next line down. I feel like I am just missing something about how a switch works in PowerShell.
Note: This is super boiled down code. There is a larger program this is part of.
$reg = '^HI\*BH'
$appendText = ''
$file = Get-ChildItem (join-path $PSScriptRoot "a.txt.BAK")
foreach ($f in $file){
switch -regex -file $f {
$reg
{
$appendText = "test"
}
default {
If ($appendText -eq '') {$appendText = $_}
$appendText
$appendText = ''
}
}
}
a.txt.BAK
HI*BH>00>D8>0*BH>00>D8>0*BH>A1>D8>0*BH>B1>D8>0000000~
HI*BE>02>>>0.00*BE>00>>>0.00~
NM1*71*1*TTT*NAME****XX*0000000~
PRV*AT*PXC*000V00000X~
Output:
test
NM1*71*1*TTT*NAME****XX*0000000~
PRV*AT*PXC*000V00000X~
The switch is not "deleting" anything - but you explicit ask it to overwrite $appendText on match, and you only ever output (and reset the value of) $appendText when it doesn't.
This code is supposed to find a line with a regular expression and replace the line with "test".
In that case I suggest you simplify your switch:
switch -regex -file $f {
$reg {
"test"
}
default {
$_
}
}
That's it - no fiddling around with variables - just output "test" on match, otherwise output the line as-is.
If you insist on using the intermediate variable, you'll need to output + reset the value in both cases:
switch -regex -file $f {
$reg {
$appendText = "test"
$appendText
$appendText = ''
}
default {
$appendText = $_
$appendText
$appendText = ''
}
}
I am new to Magento and I'm building a bookshop. I have an attribute called author, and I would like to show a list of all authors (a list of their attribute values). I tried to create a widget and use this code in it but it returns me an empty array. How can I achieve this? Where should I place the code, in a widget, a block?
protected function _toHtml()
{
$name='author';
$attributeInfo = Mage::getResourceModel('eav/entity_attribute_collection')->setCodeFilter($name)->getFirstItem();
$attributeId = $attributeInfo->getAttributeId();
$attribute = Mage::getModel('catalog/resource_eav_attribute')->load($attributeId);
$attributeOptions = $attributeInfo->getSource()->getAllOptions(false);
$html = '<ul>';
foreach($attributeOptions as $opt)
$html .= '<li>'.$opt[0].'</li>';
$html .= '</ul>';
return $html;
}
$attributes = $product->getAttributes();
foreach ($attributes as $attribute) {
if ($attribute->getIsVisibleOnFront()) {
$value = $attribute->getFrontend()->getValue($product);
echo $value
}
}
you can get attribute with this code just write this code in view.phtml
Thank you very much, your code worked quite good for a particular product, however i finally get what I wanted using this:
$attributeCode='author';
// build and filter the product collection
$products = Mage::getResourceModel('catalog/product_collection')
->addAttributeToFilter($attributeCode, array('notnull' => true))
->addAttributeToFilter($attributeCode, array('neq' => ''))
->addAttributeToSelect($attributeCode);
// get all distinct attribute values
$usedAttributeValues = array_unique($products->getColumnValues($attributeCode));
sort($usedAttributeValues);
So below is my script on how to call recursive members in groups across a trusted domain. what i need help with is to convert this from looking up a single group to multiple groups.
At the line $objGrp = [ADSI]"LDAP://CN=Administrators,CN=Builtin,DC=domain,DC=com" i have to manually change it to whatever group i want to search for. i instead want this script to call a text file with a list of groups.
for example, in the text file there would be
CN=Administrators,CN=Builtin,DC=domain,DC=com
CN=domain admins,CN=users,DC=domain,DC=com
CN=enterprise admins,CN=users,DC=domain,DC=com
what do i need to add/change to be able to do this?
# Script begins
#
# Bind to the AD group
$objGrp = [ADSI]"LDAP://CN=Administrators,CN=Builtin,DC=domain,DC=com"
#[ADSI]"LDAP://CN=Administrators,CN=Builtin,DC=domain,DC=com"
#
$Global:GroupMembers = #()
# Function to read the group members - nested members
Function GetGroupMember($objGrp)
{
# Enumerate the group members
foreach($member in $objGrp.member)
{
# Bind to the each user using DN
$strTemp = "LDAP://" + $member
$objTemp = [ADSI]$strTemp
# Check for AD Group object based on objectCategory
$strCat = [System.String]$objTemp.objectCategory
#foreign object
$res = $strCat.StartsWith("CN=Foreign-Security-Principal")
#$strCat
If($res -eq $True)
{
# bind to the foreign object
$strTemp = "LDAP://" + $member
$tempObj = [ADSI]$strTemp
# convert binary SID to bindable string SID
$objBin = $tempObj.objectSID.Item(0)
$objSID = New-Object System.Security.Principal.SecurityIdentifier($objBin,0)
$srchDomain = New-Object System.DirectoryServices.DirectoryEntry("LDAP://dc=domain,dc=com")
$dirSrchObj = New-Object System.DirectoryServices.DirectorySearcher($srchDomain)
#$objSID.Value
[System.Environment]::NewLine
$dirSrchObj.Filter = "((objectSID=" + $objSID.Value + "))"
# Search scope to sub-level
$dirSrchObj.SearchScope = "Subtree"
$dirSrchObj.PageSize = 1
# Array of result collection - users
$srchResArr = $dirSrchObj.FindOne()
"======================================="
If ($srchResArr -ne $NULL)
{
# bind to the object
#$strTem = [System.String]$srchResArr.ToString()
$objEntry = $srchResArr.GetDirectoryEntry()
# read and compare the object category for group object
[System.String]$strTemp1 = $objEntry.objectcategory
$res1 = $strTemp1.StartsWith("CN=Group")
if($res1 -eq $True)
{
#enumerate the group members
Write-Host "The members of foreign group " $objEntry.Name "are: "
Foreach($obj in $objEntry.member)
{
$strTemp2 = "LDAP://" + $obj
$objTemp2 = [ADSI]$strTemp2
[System.String]$strTemp3 = $objTemp2.objectCategory
$res2 = $strTemp3.StartsWith("CN=Group")
if($res2 -eq $True)
{
GetGroupMember($objTemp2)
}
Else
{
$objTemp2.distinguishedName
$Global:GroupMembers += $objTemp2.distinguishedName
}
}
}
Else
{
"Foreign user object: "
$objEntry.distinguishedName
$Global:GroupMembers += $objEntry.distinguishedName
}
}
"======================================="
[System.Environment]::NewLine
}
Else
{
$flag = $strCat.StartsWith("CN=Group")
# If it is a Group object then call this method (recursive)
If($flag -eq $TRUE)
{
Write-Host "++++++++++++++++++++++Recursive Call to Enumerate" $objTemp.distinguishedName
GetGroupMember($objTemp)
Write-Host "---------------------- End Recursive Call to Enumerate" $objTemp.distinguishedName
}
# If user object then display its DN
if($flag -eq $False)
{
$objTemp.distinguishedName
$Global:GroupMembers += $objTemp.distinguishedName
#$objTemp.sAMAccountname
}
}
}
}
#
GetGroupMember $objGrp
""
""
"Final List:"
$Global:GroupMembers | sort -uniq | out-file c:\temp\test.csv
If your list of groups is in C:\grouplist.txt then you can use Get-Content to get the names, then loop through them:
$groupNames = Get-Content 'C:\grouplist.txt'
foreach($groupName in $groupNames)
{
GetGroupMember [ADSI]$groupName
}
"Final List:"
$Global:GroupMembers | sort -uniq | out-file c:\temp\test.csv