Cannot insert variable into path for Get-Item - powershell

I am trying to take a list of strings separated by a return and split them by the = symbol, both sides match a registry key which is queried by Get-Item. The first half always matches fine, but referencing the second half only matches for the last item in the list:
First half example:
[string[]]$Patch = (".accda=Access.ACCDAExtension.16
.accdb=Access.Application.16" -split "`n")
Foreach ($a in $Patch) {
$RegKey = ($a -split "=")[0]
$Result = Get-Item -Path "Registry::HKEY_CLASSES_ROOT\$RegKey"
echo $Result
}
This returns:
Name Property
---- --------
.accda (default) : Access.ACCDAExtension.16
Content Type : application/msaccess.addin
.accdb (default) : Access.Application.16
Content Type : application/msaccess
Second half example:
[string[]]$Patch = ("
.accda=Access.ACCDAExtension.16
.accdb=Access.Application.16
" -split "`n")
Foreach ($a in $Patch) {
$RegKey = ($a -split "=")[1]
$Result = Get-Item -Path "Registry::HKEY_CLASSES_ROOT\$RegKey"
}
This returns:
Get-Item : Cannot find path 'HKEY_CLASSES_ROOT\Access.ACCDAExtension.16' because it does not exist.
At line:6 char:15
+ $Result = Get-Item -Path "Registry::HKEY_CLASSES_ROOT\$RegKey"
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : ObjectNotFound: (HKEY_CLASSES_RO...DAExtension.16:String) [Get-Item], ItemNotFoundException
+ FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.GetItemCommand
Hive: HKEY_CLASSES_ROOT
Name Property
---- --------
Access.Application.16 (default) : Microsoft Access Database
However, that registry key does exist and if I run the command manually it finds it:
get-item Registry::HKEY_CLASSES_ROOT\Access.ACCDAExtension.16
Hive: HKEY_CLASSES_ROOT
Name Property
---- --------
Access.ACCDAExtension.16 (default) : Microsoft Access Add-in
I'm pretty sure it's caused by the return at the end of each line.
PowerShell version 5.1

I have resolved this my making my list a list of strings:
[string[]]$Patch = (".accda=Access.ACCDAExtension.16",
".accdb=Access.Application.16" -split "`n")
Foreach ($a in $Patch) {
$RegKey = ($a -split "=")[1]
$Result = Get-Item -Path "Registry::HKEY_CLASSES_ROOT\$RegKey"
}
The issue was probably caused by the return at the end of each line, maybe I could have also filtered it out of the command.

Change this:
[string[]]$Patch = ("
.accda=Access.ACCDAExtension.16
.accdb=Access.Application.16
" -split "`n")
to this
[string[]]$Patch = (-split "
.accda=Access.ACCDAExtension.16
.accdb=Access.Application.16
")
That way you don't have any whitespaces.
Here is some more background on the split operator

Related

PowerShell - Use Dynamically Created Variable Name Within a Variable Name

So I have a powershell script that I am trying to get up and running. Most of it works but what I am trying to do to make it as easy as possible to run periodically is to have it reference a list of numbers (IPs) in a text file, and then create a new variable for each line of the text file. This part does work using the following.
$iplist = get-content c:\powershell\ips.txt | where-object { $_.Trim() -ne '' }
$startnum = 0
foreach($line in $iplist){
$startnum++
new-variable -name "ip$startnum" -Value $line -Force
}
This is great, but later on in the script it has to use the number stored in each of those dynamically created variables in two other parts of the script. One part is where is reverses the IP address and then stores its reversed variant in another variable, and on another part it uses that reversed IP address as part of a lookup using [System.Net.DNS].
So basically, using that first snippet of code the script does the following, using a text file called ips.txt with 1.2.3.4 on the first line and 5.6.7.8 on the second line
$ip1 = 1.2.3.4
$ip2 = 5.6.7.8
Then I want to take those $ip1 and $ip2 values and reverse them. I know the reverse part works cause it works with a static input, but when i try it with variables it doesn't work, below is a snippet of the code i'm trying to do this with. Its basically an updated version of the code snippet from above.
$iplist = get-content c:\powershell\ips.txt | where-object { $_.Trim() -ne '' }
$startnum = 0
foreach($line in $iplist){
$startnum++
new-variable -name "ip$startnum" -Value $line -Force
new-variable -name "ipParts$startnum" -Value "$ip$startnum".Split('.')
[array]::Reverse($ipParts$startnum)
$ipparts$startnum = [string]::join('.',$ipParts$startnum)
}
When I run that though I get the following errors
At line:8 char:30
+ [array]::Reverse($ipParts$startnum)
+ ~
Missing ')' in method call.
At line:8 char:30
+ [array]::Reverse($ipParts$startnum)
+ ~~~~~~~~~
Unexpected token '$startnum' in expression or statement.
At line:4 char:26
+ foreach($line in $iplist){
+ ~
Missing closing '}' in statement block or type definition.
At line:8 char:39
+ [array]::Reverse($ipParts$startnum)
+ ~
Unexpected token ')' in expression or statement.
At line:9 char:53
+ $ipparts.$startnum = [string]::join('.',$ipParts$startnum)
+ ~
Missing ')' in method call.
At line:9 char:53
+ $ipparts.$startnum = [string]::join('.',$ipParts$startnum)
+ ~~~~~~~~~
Unexpected token '$startnum' in expression or statement.
At line:9 char:62
+ $ipparts.$startnum = [string]::join('.',$ipParts$startnum)
+ ~
Unexpected token ')' in expression or statement.
At line:10 char:1
+ }
+ ~
Unexpected token '}' in expression or statement.
+ CategoryInfo : ParserError: (:) [], ParentContainsErrorRecordException
+ FullyQualifiedErrorId : MissingEndParenthesisInMethodCall
There are two parts to this, but i'm hoping if I can figure out this first part then the second part when I use the final value that is supposed to be stored in $ipParts$startnum to do the lookups will be easier.
EDIT
So I had an idea and change the script to this
$iplist = get-content c:\powershell\ips.txt | where-object { $_.Trim() -ne '' }
$startnum = 0
foreach($line in $iplist){
$startnum++
new-variable -name "ip$startnum" -Value $line -Force -ErrorAction SilentlyContinue
new-variable -name "ipParts$startnum" -Value "$ip$startnum".Split('.')
$iptemp = get-variable -name "ipparts$startnum"
[array]::Reverse("$iptemp")
$iptemp = [string]::join('.',"$iptemp")
set-variable -name "ipParts$startnum" -Value "$iptemp"
}
write-host "iplist is $iplist......ip1 is $ip1....ip2 is $ip2....ipparts1 is $ipparts1.......ipparts2 is $ipparts2....iptemp value is $iptemp"
Basically use set-variable to modify it as a string with other variable names in it, kind of works, but when i did write-host on the last part to make sure its actually writing the proper values to the variables, on $ipparts1, $ipparts2, and $iptemp, i have the following value
"System.Management.Automation.PSVariable"
I'm not entirely sure what that means.

how to append output to a CSV file

foreach ( $newfile in $file )
{
$b = Get-CMDeploymentStatus -PackageId $newfile -StatusType Any | select PackageID
Write-Output $b | Export-Csv -Path "C:\Users\PSM-6A1A000000000000\Documents\list.csv"
}
I am giving input to this with an input file which has number of package names listed and then I want to process it in such a way that the output comes one after the other right now I am getting an error as
Export-Csv : Cannot bind argument to parameter 'InputObject' because it is null. At line:16 char:20 + Write-Output $b | Export-Csv -Path "C:\Users\PSM-6A1A000000000000\Documents\lis ... + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : InvalidData: (:) [Export-Csv], ParameterBindingValidationException + FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,Microsoft.PowerShell.Commands.ExportCsvCommand
Your code is assuming that you will have a result coming back from $b, if it does not though, you'll get an error because you're piping $b, which is null, into Export-CSV.
$null |export-csv c:\temp\1.csv
Export-Csv : Cannot bind argument to parameter 'InputObject' because it is null.
At line:1 char:8
+ $null |export-csv c:\temp\1.csv
+ ~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidData: (:) [Export-Csv], ParameterBindingValidationException
+ FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,Microsoft.PowerShell.Commands.ExportCs
You should add a 'Guard Clause' before you try to export.
if ($null -ne $b){
Export-csv -Append -InputObject $b
}
At least this will continue executing. Now your next problem is to determine why $b would be empty...from my experience with CM, I bet you need to specify which property in your $file you need. Maybe that line should read:
$b = Get-CMDeploymentStatus -PackageId $newfile.PackageId -StatusType Any | select PackageID
Since you say "I am giving input to this with an input file which has number of package names listed", but your code uses PackageId..
It looks to me that this file contains a packageId, each on a single line.
Anyway, I don't see the code ever reading this file..
If my assumption about the text file is correct, try:
# read the content of the text file and loop through the lines
# collect the output from Get-CMDeploymentStatus in variable $result
$result = Get-Content -Path 'X:\TheFileWithPackageIds.txt' | ForEach-Object {
# inside the ForEach-Object, the $_ automatic variable represents a single line from the text file
Get-CMDeploymentStatus -PackageId $_ -StatusType Any | select PackageID
}
# output on screen
$result
# write to new CSV file
$result | Export-Csv -Path "C:\Users\PSM-6A1A000000000000\Documents\list.csv" -NoTypeInformation

Powershell Error: missing '=' operator after key in hash literal

I needed to create a script that checks to see if an IIS App Pool for a specific site and its child App Pools are started. (I have a separate script to start "stopped" App Pools as I just want to check if they are stopped) I was able to create the script however when I modified it to format the output better I keep getting this error,
At E:\iis\scripts\svc_pl_fm_app_pool_status.ps1:12 char:6
+ App Pool = $item.Name;
+ ~
Missing '=' operator after key in hash literal.
At E:\iis\scripts\svc_pl_fm_app_pool_status.ps1:7 char:29
+ foreach ($item in $results) {
+ ~
Missing closing '}' in statement block.
+ CategoryInfo : ParserError: (:) [], ParseException
+ FullyQualifiedErrorId : MissingEqualsInHashLiteral
I checked here and Microsoft but I left more confused about the error then when I first saw it. I saw this Missing closing '}' in statement block. so i assumed I was in fact missing one but I checked and I am not. I am not sure if it is a spacing/ indentation issue but I do not know enough about this error message. Here is my script below.
$results = $item = $appPool = $status = $NULL
$status = "1"
import-module WebAdministration
$AppPoolList = #()
$results = Get-ChildItem IIS:\AppPools\* | Where-Object { ($_.Name -like "someAppPool*" -and $_.Name -like "someChildAppPool*" )}
foreach ($item in $results) {
if ($item.State -ne "Started") {$status = "0"}
$AppPoolList += [PSCustomObject]#{
App Pool = $item.Name;
Status = $item.State;
}
}
$AppPoolList | Format-List

unable to fetch system.int64 registry datavalue in powershell

Below powershell code is for exporting the complete registry hive to CSV file. But it gives error for exporting REG_Binary type data whose value is big as shown in the attached registry screenshot. Though I tried to convert it to string but no luck. Please suggest on how to fetch the REG_Binary data or how to convert it to string.
Function Get_Reg_Keys ($reg_key) {
$actualKey = Get-Item -Path Registry::$reg_key
#Write-Host $actualKey
ForEach ($name in $actualKey.GetValueNames()) {
# Write-Host $name
$name.Property | foreach {
$type = $actualKey.GetValue($name).GetType()
#Write-Host $type
Write-Host $actualKey.Name " | " $name " | " $actualKey.GetValue($name) " | " $type
If ( $type -eq [System.Byte[]] -Or $type -eq [System.Int64[]]) {
$a = [System.BitConverter]::ToString($actualKey.GetValue($name))
( '"{0:0}","{1:0}", "{2:0}"' -f $actualKey.Name, $name, $a) |
Out-File "C:\Temp\Automation\HKCU.csv" -append -Encoding ascii -erroraction SilentlyContinue
}
Else {
( '"{0:0}","{1:0}", "{2:0}"' -f $actualKey.Name, $name, $actualKey.GetValue($name)) |
Out-File "C:\Temp\Automation\HKCU.csv" -append -Encoding ascii -erroraction SilentlyContinue
}
}
}
$keyinfo = Get-ChildItem Registry::$reg_key
if ($keyinfo.count -gt 0) {
ForEach ($keyitem in $keyinfo) { Get_Reg_Keys ($keyitem) }
}
}
Then running: Get_Reg_Keys ("HKEY_CURRENT_USER\")
Gives the error:
Cannot convert argument "index", with value: "MRUListEx", for "GetValue" to type "System.Int64": "Cannot convert value "MRUListEx" to type "System.Int64". Error: "Input string was
not in a correct format.""
At C:\Temp\Automation\HKCUregistrynew.ps1:27 char:21
+ ( '"{0:0}","{1:0}", "{2:0}"' -f $actualKey.Name, $name, $act ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [], MethodException
+ FullyQualifiedErrorId : MethodArgumentConversionInvalidCastArgument
Registry Key details:
To be honest, I'm having a tough time following your function. I'm not even sure how you're iterating over values in a key with that $name.properties | foreach... loop.
But, generally, this is pretty straight forward. For example, I've got a registry key HKCU:\Environment. I've created a property in that key named "thing", and I've stuffed it with some random binary data.
I'll take the guts of that property and output it to a file:
$reg_key = 'HKCU:\Environment'
$key_properties = Get-Item -Path $reg_key
[System.BitConverter]::ToString($key_properties.GetValue('thing')) | Out-File -FilePath .\Test.txt
cat .\Test.txt
Just to show there is nothing up my sleeve:
Good luck.
After making below changes I am able to export a registry hive to CSV file:
$actualKey = Get-Item -LiteralPath Registry::$reg_key
$keyinfo = Get-ChildItem -LiteralPath Registry::$reg_key

running a PowerShell command sp 2010

I am trying to create a site map with a PowerShell command from this example:
http://blogs.msdn.com/b/opal/archive/2010/04/13/generate-sharepoint-2010-sitemap-with-windows-powershell.aspx
My actions: I copied the code into a file named New-SPSiteMap
I opened the PowerShell and wrote
New-SPSiteMap –Url http://centerportal –SavePath C:\inetpub\wwwroot\wss\VirtualDirectories\80\sitemap.xml
The error I get is:
The term 'New-SPSiteMap' is not recognized as the name of a cmdlet,
function, script file, or operable program. Check the spelling of the name,
or if a path was included, verify that the path is correct and try again.
At line:1 char:14
+ New-SPSiteMap <<<< -Url http://mossdev2010 -SavePath C:\inetpub\wwwroot\wss\VirtualDirectories\80\sitemap.xml
+ CategoryInfo : ObjectNotFound: (New-SPSiteMap:String) [], CommandNotFoundException
+ FullyQualifiedErrorId : CommandNotFoundException
In order to have the New-SPSiteMap function available you have to execute the script containing the function:
& .\New-SPSiteMap.ps1
New-SPSiteMap –Url http://centerportal –SavePath C:\inetpub\wwwroot\wss\VirtualDirectories\80\sitemap.xml
Alliteratively, you could turn the PowerShell script into a "function" that is callable like this:
.\New-SPSiteMap.ps1 -Url http://centerportal –SavePath C:\inetpub\wwwroot\wss\VirtualDirectories\80\sitemap.xml
All you have to do is remove the function declaration function New-SPSiteMap:
param($SavePath="C:\inetpub\wwwroot\wss\VirtualDirectories\80\SiteMap.xml", $Url="http://sharepoint")
function New-Xml
{
param($RootTag="urlset",$ItemTag="url", $ChildItems="*", $SavePath="C:\SiteMap.xml")
Begin {
$xml="<?xml version=""1.0"" encoding=""UTF-8""?>
<urlset xmlns=""http://www.sitemaps.org/schemas/sitemap/0.9"">"
}
Process {
$xml += " <$ItemTag>"
foreach ($child in $_){
$Name = $child
$xml += " <$ChildItems>$url/$child</$ChildItems>"
}
$xml += " </$ItemTag>"
}
End {
$xml += "</$RootTag>"
$xmltext=[xml]$xml
$xmltext.Save($SavePath)
}
}
$web = Get-SPWeb $url
$list = $web.Lists | ForEach-Object -Process {$_.Items} | ForEach-Object -Process {$_.url.Replace(" ","%20")}
# excludes directories you don’t want in sitemap. you can put multiple lines here:
$list = $list | ? {$_ -notmatch "_catalogs"}
$list = $list | ? {$_ -notmatch "Reporting%20Templates"}
$list = $list | ? {$_ -notmatch "Reporting%20Metadata"}
$list | New-Xml -RootTag urlset -ItemTag url -ChildItems loc -SavePath $SavePath