I have an ODBC connection set up on my Windows 2008 Server, and I'm trying to replace some .BAT files that do some processing with Powershell files.
Is there a way to do the same thing as this in PowerShell?
CALL osql /instanceName /Uuser /Ppassword /Q"EXECUTE storedProcName #Parm1= %ePROFILE%, #param2 = N'%eValList%'
SQL Server 2008 provides an osql Powershell cmdlet called invoke-sqlcmd that does that same type of thing as osql from Powershell. That said if you want to continue to use osql you should be able to do something like this and continue to use your Windows users varaialbes:
osql /instanceName /Uuser /Ppassword /Q"EXECUTE storedProcName #Parm1= $env:ePROFILE, #param2 = N'$env:eValList'
If you want an actual Powershell Object to work with after you query a database you can use a function like this that I recently wrote:
function Query-DatabaseTable ( [string] $server , [string] $dbs, [string] $sql )
{
$Columns = #()
$con = "server=$server;Integrated Security=true;Initial Catalog=$dbs"
$ds = new-object "System.Data.DataSet" "DataSet"
$da = new-object "System.Data.SqlClient.SqlDataAdapter" ($con)
$da.SelectCommand.CommandText = $sql
$da.SelectCommand.Connection = $con
$da.Fill($ds) | out-null
$ds.Tables[0].Columns | Select ColumnName | % { $Columns += $_.ColumnName }
$res = $ds.Tables[0].Rows | Select $Columns
$da.Dispose()
$ds.Dispose()
return $res
}
Related
I'm trying to write a powershell script that will output the contents of a column inside a spreadsheet to a txt file. I don't know powershell but I found and figured out how to get a cell, now I need the whole column. The spreadsheet in question has 8K+ rows. Here is what I have so far:
$SMTPApprovedXLS = "c:\temp\SMTP\SMTPAPPLIST.XLS"
$SheetName = "Active"
$objExcel = New-Object -ComObject Excel.Application
$objExcel.Visible = $False
$Workbook = $objExcel.Workbooks.open($SMTPApprovedXLS)
$Worksheet = $Workbook.sheets.item($SheetName)
$startRow = 4
[pscustomobject][ordered]#{
ApprovedIPs = $Worksheet.Cells.Item(4,$startRow).Value()
}
The column is "D" and should start at row 4.
Thanks in advance.
All you have to do is use a loop to run through all the entries and capture the data. Try this:
$SMTPApprovedXLS = "c:\temp\SMTP\SMTPAPPLIST.XLS"
$SheetName = "Active"
$objExcel = New-Object -ComObject Excel.Application
$objExcel.Visible = $False
$Workbook = $objExcel.Workbooks.open($SMTPApprovedXLS)
$Worksheet = $Workbook.sheets.item($SheetName)
$startRow = 4
$ApprovedIPs = #()
$count = $Worksheet.Cells.Item(65536,4).End(-4162)
for($startRow=4; $startRow -le $count.row; $startRow++)
{
$ApprovedIPs += $Worksheet.Cells.Item($startRow, 4).Value()
}
$ApprovedIPs | Out-File C:\ApprovedIPs.txt
Note that the last line is what creates the txt file with the desired data, where C:\ is the directory and ApprovedIPs is the file name. You can just substitute them for your desired location and name of the file.
Consider that CSV file:
Node Name,Client Name,Job Directory,Policy Name
server1,test.domain.com,"vmware:/?filter= VMHostName AnyOf "server2.domain.com", "server3.domain.com"",TEST
My code:
$events = Import-Csv "C:\file.csv" | foreach {
New-Object PSObject -prop #{
Server = $_.{Node Name};
Client = $_.{Client Name};
{JobDirectory/Script} = $_.{Job Directory};
Policy = $_.{Policy Name};
}
}
I have some problems when I try to parse the third field. I am not sure if its because the comma, or the double quote.
This is the object I would like to have:
Node Name : server1
Client Name : test.domain.com
JobDirectory/Script : vmware:/?filter= VMHostName AnyOf "server2.domain.com", "server3.domain.com"
Policy Name : TEST
Can someone help me?
Ok, so the easiest way to approach this is to read the file in with Get-Content and then split each line where the commas are not inside quotes. I borrowed the regex from this solution for this.
Using your current input data I would do something like this
$filedata = Get-Content C:\temp\test.csv
$asObject = ForEach($singlerow in ($filedata | Select-Object -Skip 1)){
$props = #{}
$singlerow = $singlerow -split ',(?=(?:[^"]*"[^"]*")*[^"]*$)'
[pscustomobject][ordered]#{
Server = $singlerow[0]
Client = $singlerow[1]
"JobDirectory/Script" = $singlerow[2]
Policy = $singlerow[3]
}
}
Sample Output from $asObject | Format-List
Server : server1
Client : test.domain.com
JobDirectory/Script : "vmware:/?filter= VMHostName AnyOf "server2.domain.com", "server3.domain.com""
Policy : TEST
Another way using your starting code
$obj = gc c:\temp\test.csv |
% { $_ -replace '"(\b[^"]*\b)"','$1' } |
convertfrom-csv | % { [pscustomobject][ordered] #{
Server = $_.{Node Name}
Client = $_.{Client Name}
{JobDirectory/Script} = $_.{Job Directory}
Policy = $_.{Policy Name} }
}
So I run this command
$driverRAIDv = $data|where-object{$_.Name -eq "$serverName" -and ($_.Description1 -match "hpsa")} | select -ExpandProperty version
And it returns this value:
HP HPSA Driver (v 5.0.0-28OEM)
I want to take this value/variable and parse it so that I only have 5.0.0-28OEM
Try this, matches anything between ( and ) brackets:
EDIT: ..and removes the v followed by a space:
$driverRAIDv = $data|where-object{$_.Name -eq "$serverName" -and ($_.Description1 -match "hpsa")} | select -ExpandProperty version
$regex = "(?<=\().*(?=\))"
[regex]::matches($driverRAIDv,$regex).Value -replace "v "
which returns:
5.0.0-28OEM
or you could use following regex which will match anything between (v and )
$regex="(?<=\(v\s).*(?=\))"
Give this a try. Basically, we're creating a "calculated property" that contains an expression to parse out the portion of the value that you want.
$driverRAIDv = $data|where-object{$_.Name -eq "$serverName" -and ($_.Description1 -match "hpsa")} | select -Property #{ Label = 'Version'; Expression = { [void]($_ -match ('v\s(.*?)\)')); $matches[1]; }; };
I tested this out using the following code:
#{ Version = 'HP HPSA Driver (v 5.0.0-28OEM)'} | select -Property #{ Label = 'Version'; Expression = { [void]($_ -match ('v\s(.*?)\)')); $matches[1]; }; };
If you check out the help for the Select-Object command, you will see that you can create calculated properties, which basically modify the value of a property, through a PowerShell expression. To do this, create a Hashtable that contains two items: Label and Expression. The Label can simply be set to the same property value that you're modifying. The Expression is a PowerShell ScriptBlock that performs some type of operation, and returns a result. In the example I gave above, we are running a regular expression against the Version property, and returning it as the result.
You have many ways to do it depending on your needs and variance of what you will get.
One way could be to use replace operator. Say, you got
$driverRAIDv="HP HPSA Driver (v 5.0.0-28OEM)"
$driverRAIDv -replace 'HP HPSA Driver \(v ','' -replace '\)',''
would get you 5.0.0-28OEM
In the same line:
$driverRAIDv = ($data|where-object{$_.Name -eq "$serverName" -and ($_.Description1 -match "hpsa")} | select -ExpandProperty version) -replace 'HP HPSA Driver \(v ','' -replace '\)',''
A non-regex option would be to split on (, ) and (space), and select the last non-empty string.
$driverRAIDv = $data|
where {$_.Name -eq $serverName -and $_.Description1 -match "hpsa"} |
foreach {$_.version.split('[() ]')| where {$_}| select -last 1}
(new-object System.Net.WebClient).Downloadfile("https://www.dropbox.com/sh/tsyz48qg0rq3smz/QAstBLgPgN/version.txt", "C:\Users\Brangle\Desktop\version.txt") API download invalid data.
version.txt file need to download. But actually it is downloading some xml file contains in version.txt on destination location
Thanks in advance
You are trying to download the dropbox page which presents your file in a nice dropbox-themed html. You need to extract the real url and can do so using the following code:
$wc = New-Object system.net.webclient;
$s = $wc.downloadString("https://www.dropbox.com/sh/tsyz48qg0rq3smz/QAstBLgPgN/version.txt");
$r = [regex]::matches($s, "https://.*token_hash.*(?=`")");
$realURL = $r[$r.count-1].Value;
$wc.Downloadfile($realURL, "U:\version.txt");
The regex part looks for a url starting https://, has a string token_hash in the middle and ends one character before double quotes character ". The line in question is:
FilePreview.init_text("https://dl.dropboxusercontent.com/sh/tsyz48qg0rq3smz/QAstBLgPgN/version.txt?token_hash=AAEGxMpsE-T4xodBPd3A6uPTCr0uqh7h4B2YUSmTDJHmjg", 0, null, 0)
Hope this helps.
Here is the function:
function download-dropbox($Url, $FilePath) {
$wc = New-Object system.net.webclient
$req = [System.Net.HttpWebRequest]::Create($Url)
$req.CookieContainer = New-Object System.Net.CookieContainer
$res = $req.GetResponse()
$cookies = $res.Cookies | % { $_.ToString()}
$cookies = $cookies -join '; '
$wc.Headers.Add([System.Net.HttpRequestHeader]::Cookie, $cookies)
$newurl = $url + '?dl=1'
mkdir (Split-Path $FilePath) -force -ea 0 | out-null
$wc.downloadFile($newurl, $tempFile)
}
Re: LogMeIn - theyuse a cookie base authentication so you can't use the previous code. Try this, it gets a cookie from the first response and then uses that to download using webclient:
$url = "https://secure.logmein.com/fileshare.asp?ticket=01_L5vwmOrmsS3mnxPO01f5FRbWUwVKlfheJ5HsfpTV"
$wc = New-Object system.net.webclient
$req = [System.Net.HttpWebRequest]::Create($url)
$req.CookieContainer = New-Object System.Net.CookieContainer
$res = $req.GetResponse()
$cookie = $res.Cookies.Name + "=" + $res.Cookies.Value
$wc.Headers.Add([System.Net.HttpRequestHeader]::Cookie, $cookie)
$newurl = $url + "`&download=1"
$wc.downloadFile($newurl, "c:\temp\temp.zip")
I'm using the following to query the firewall rules of a list of servers.
$servers = Get-Content fw_servers.txt
foreach($serv in $servers) {
$fw = New-Object -ComObject hnetcfg.fwpolicy2
$fw.rules |
Where-Object { $_.enabled -and $_.LocalPorts -like 3389 } |
Select-Object -Property direction,protocol, localports,name
}
I would like to export this information to a csv file. Can someone please let me know how I can use Export-CSV for this? I've tried making it into an array but it's not working for me. I'm using 2.0
I'd also like the exported data to look like the following
Server Direction Protocol LocalPorts Name
testsrv1 1 6 3389 Remote Desktop (TCP-In)
testsrv2 1 6 3389 Research Remote Desktop Policy
Thank you for your help.
Amelia
I had an epiphany and somehow figured it out. The following, although not pretty, works for me.
$servers = Import-CSV fw_servers.csv
$servers | Foreach {
$serv = $_.serv
foreach-object {
$name = $_."Server"
$fw = New-Object -ComObject hnetcfg.fwpolicy2
$fw.rules |
Where-Object { $_.enabled -and $_.LocalPorts -like 3389 } |
Select-Object #{Name="Server"; Expression={$name}}, direction, protocol, localports, name
}
} | Export-CSV C:\Users\trankaa\desktop\fw_res.csv -NoTypeInformation -Force