Dynamic server value in powershell - variables

I am using below query to get the server details,
$intFreeSpace = Get-WmiObject -Class win32_logicalDisk -ComputerName Server1,server2 | Select-Object SystemName, deviceid, freespace, size
Now, instead of hard coded value I tried to supply server value from a variable like below
$serverlist = "server1,server2"
$intFreeSpace = Get-WmiObject -Class win32_logicalDisk -ComputerName $serverlist | Select-Object SystemName, deviceid, freespace, size
but this isn't working, any solution?
Edit:
ServerList = #("Server1") #Initialization with dummy value to insure that variable will be an array
if($row[0] -eq "ServerList"){
$ServerList= $row[1]
}
WRITE-HOST $ServerList
Output: Server1,Server2
It is working fine when my column value is Server1.

Pass in an array, instead! Otherwise, you make an attempt on 'one' computer called "server1,server2".
$serverlist = #("server1","server2")
$intFreeSpace = Get-WmiObject -Class win32_logicalDisk -ComputerName $serverlist | Select-Object SystemName, deviceid, freespace, size
EDIT: Bill is right, you'll need to turn your string of servers into an array. Since the result is comma delimited, you can -split on the comma. This leaves you with an array.
$serverlist = $serverlist -split ','
$intFreeSpace = Get-WmiObject -Class win32_logicalDisk -ComputerName $serverlist | Select-Object SystemName, deviceid, freespace, size

Related

Devices locking an account after password reset

Trying to find what devices a user is logged on to because her account keeps locking.
This is my script but it gives me the dreaded Get-User.Name is not recognized as a cmdlet, etc...Relatively new to powershell. User names are first. Last and Domain is OCSD Any ideas?
$Computers = OCSD -Filter {(enabled -eq "true") -and (OperatingSystem -Like "*XP*")} | Select-Object -ExpandProperty Name
$output=#()
ForEach($PSItem in $Computers) {
$Celeste.Mott = .\Get-$User.name Win32_ComputerSystem -ComputerName $PSItem | Select-Object -ExpandProperty UserName
$Obj = New-Object -TypeName PSObject -Property # {
"Computer" = $PSItem
"User" = $User.name
}
$output += $Obj
}
$output

Get the SQL Versions of all servers with get-wmiobject

I would like to get all the installed version values of SQL on over 200 different Servers.
The plan is, to have all the Server Names in the ServerListSQLVersions.txt
and to get all the SQL Versions into the CSV.
$Username = ''
$Password = ''
$pass = ConvertTo-SecureString -AsPlainText $Password -Force
$SecureString = $pass
# Users you password securly
$MySecureCreds = New-Object -TypeName
System.Management.Automation.PSCredential -ArgumentList $Username,$SecureString
$Array = #()
##Create a Folder called SQLVersions##
$scriptPath = "C:\Transfer to SV000229\SQL Script"
$server = Get-Content "$scriptPath\ServerListSQLVersions.txt"
$wmiobj = Get-WmiObject -class Win32_product | where Name -like '*SQL*' | Select-Object name,version
function getWMIObject($server, $wmiobj, $MySecureCreds) {
$result = Get-WmiObject $wmiobj -ComputerName $server -Credential $MySecureCreds
#Write-Host "Result: "$result
$Array+= $Result
}
$Array = Export-Csv $scriptpath\output.csv -NoTypeInformation
My output in the CSV is:
Length
0
I used a
foreach($computer in $computers){
instead of the function and gave the information manually.
Also the output was not abled to Export, because i used an = instead of an |
Works now.

Get variable from tenant in Octopus

Is there any way to get a variable from tenant in Octopus server?
I already extracting variable from projects, using code below, but this method is not working for tenants:
Import-Module "C:\Program Files\WindowsPowerShell\Modules\Octopus-Cmdlets\0.4.4\Octopus-Cmdlets.psd1"
connect-octoserver http://octohost.cloudapp.azure.com:8082 API-12345678901234567890
$raw = (Get-OctoVariable someproject somevariable | Where-Object { $_.Environment -eq "DEV" } )
$jsonfile = "c:\dataapi.json"
$raw.Value | ConvertFrom-Json | ConvertTo-Json | Out-File $jsonfile -Encoding UTF8
$data = Get-Content $jsonfile -Encoding UTF8 | ConvertFrom-Json
$data | ConvertTo-Json | Set-Content $jsonfile -Encoding UTF8
There is at least the following way to get a variable from a tenant in Octopus Deploy. I got this working with making OctopusClient.dll calls.
Add-Type -Path $OctopusClientDll #this should point to the dll
$Endpoint = New-Object Octopus.Client.OctopusServerEndpoint $octopusURI, $apiKey
$Repository = New-Object Octopus.Client.OctopusRepository $Endpoint
$TenantEditor = $Repository.Tenants.CreateOrModify($TenantName)
$Vars = $TenantEditor.Variables.Instance.LibraryVariables
$VarSet = $Vars[$COMMON_TENANT_VARSET_ID] # you need to know this
$VarTemplate = $VarSet.Templates | Where-Object -Property Name -eq "Tenant.VariableName"
$VariableValue = $VarSet.Variables[$varTemplate.Id].Value

Conflict with Get-Item

I have a line of code that has some conflict in it and I just cannot see what it is.
Here is the program
$Date = Get-Date -Format MM-dd-yyyy-HH-mm-ss-tt
<#*****SQL Session Variables*****#>
$Username = "sa"
$Password = "xyz" | ConvertTo-SecureString -asPlainText -Force
$Credentials = New-Object System.Management.Automation.PSCredential($Username,$Password)
$DatabaseNames = Invoke-SQLcmd -Query "Select * From sys.databases WHERE Name NOT LIKE '%Master%' AND Name NOT LIKE '%Tempdb%' AND Name NOT LIKE '%Model%' AND Name NOT LIKE '%Msdb%';" -ServerInstance "localhost" | Select Name -ExpandProperty Name
Write-Host "****Database Names****" -ForeGroundColor Red -BackGroundColor Black
$DatabaseNames
"`n`n"
<#****Get Database Size****#>
Push-Location
Import-Module sqlps -disablenamechecking
Invoke-Sqlcmd -Query "select name, physical_name, size * 8.0 / 1024 size from sys.master_files WHERE Type_Desc NOT LIKE '%LOG%' AND Name NOT LIKE '%Master%' AND Name NOT LIKE '%Tempdb%' AND Name NOT LIKE '%Model%' AND Name NOT LIKE '%Msdb%';" -ServerInstance "localhost" | Select #{Label="Database Name";Expression={$_.name}}, #{Label="Location";Expression={$_.physical_name}}, #{Label="SIze (MB)";Expression={$_.size}}
Pop-Location
"`n"
Start-Sleep 4
<#****Backup Databases****#>
ForEach ($DatabaseName in $DatabaseNames)
{
$SQLBackupPath1 = "C:\T2\SQlBackup\"
$SQLBackupPath2 = "$DatabaseName"
$SQLBackupPath3 = "_"
$SQLBackupPath4 = $Date
$SQLBackupPath5 = "_.bak"
$SQLBackupPath = $SQLBackupPath1 + $SQLBackupPath2 + $SQLBackupPath3 + $SQLBackupPath4 + $SQLBackupPath5
$SQLBackupPath
Backup-SQLDatabase -ServerInstance localhost -Database $DatabaseName -BackupFile $SQLBackupPath -Credential $Credentials
Write-Host "Database Backup of " -NoNewLine
Write-Host "$DatabaseName" -ForeGroundColor Red -BackGroundColor Black -NoNewLine
Write-Host " has been completed"
"`n"
}
<#****Delete Databases****#>
ForEach ($DatabaseName in $DatabaseNames)
{
Push-Location
Import-Module sqlps -disablenamechecking
Invoke-Sqlcmd -Query "EXEC msdb.dbo.sp_delete_database_backuphistory #database_name = N'$DatabaseName';" -ServerInstance "localhost"
Invoke-Sqlcmd -Query "USE [master];" -ServerInstance "localhost"
Invoke-Sqlcmd -Query "ALTER DATABASE [$DatabaseName] SET SINGLE_USER WITH ROLLBACK IMMEDIATE;" -ServerInstance "localhost"
Invoke-Sqlcmd -Query "DROP DATABASE [$DatabaseName];" -ServerInstance "localhost"
Pop-Location
Write-Host "Database: " -NoNewLine
Write-Host "$DatabaseName" -ForeGroundColor Red -BackGroundColor Black -NoNewLine
Write-Host " has been Dropped"
"`n"
}
Get-ChildItem -Path C:\T2\SQLBackup\ | Where-Object {$_.Name -match "ApOps*" } | Sort-Object LastWriteTime -Descending
If I move the final GetChildItem line under the first line $Date I get output. However if I use this in a loop or where it currently sits no results are returned. This makes me believe that there is some conflicting statement in the code. If so I cannot seem to find it and I am losing my mind looking for it. Please help.
You're being bitten by the output formatting, and being a bit careless with your output. Consider this, I'm in a directory with a couple of files:
List the files, simple and works fine:
PS D:\test> Get-ChildItem # list the files
Directory: D:\test
Mode LastWriteTime Length Name
---- ------------- ------ ----
-a---- 02/11/2016 07:01 1640 log.txt
-a---- 02/11/2016 07:01 0 testfile
Output an empty string, then list the files, simple and works fine. One blank line extra at the start:
PS D:\test> ""; Get-ChildItem
Directory: D:\test
Mode LastWriteTime Length Name
---- ------------- ------ ----
-a---- 02/11/2016 07:01 1640 log.txt
-a---- 02/11/2016 07:01 0 testfile
Get the string length, then list the files. Wait what? The output formatter is taking property you asked for from the first output it receives (string Length) and is then applying that to everything it receives (files) until the pipeline is empty:
PS D:\test> "" | select Length; Get-ChildItem # select string length, then...
Length # missing columns ??!!
------
0 # string length
1640 # file length
0 # file length
Get some property which doesn't exist, then list the files. This is the same idea, only this time it's not showing anything for the string or anything for the files, because Foobar doesn't exist on either type:
PS D:\test> "" | select Foobar; Get-ChildItem # select property which doesn't exist
Foobar
------
# ???? this is your "no output"
You are doing this kind of thing - sending mixed types to the output pipeline. They still go to the output, if you captured them in variables or wrote them to files the data would be there, but the output formatter which tries to work out how to display them on the console takes the first thing it gets and formats the output against that, assuming you'll have a consistent output. And the first complex objects it gets come from your code here:
Invoke-Sqlcmd -Query "select name, physical_name, size * 8.0 / 1024 size from sys.master_files WHERE Type_Desc NOT LIKE '%LOG%' AND Name NOT LIKE '%Master%' AND Name NOT LIKE '%Tempdb%' AND Name NOT LIKE '%Model%' AND Name NOT LIKE '%Msdb%';" -ServerInstance "localhost" | Select #{Label="Database Name";Expression={$_.name}}, #{Label="Location";Expression={$_.physical_name}}, #{Label="SIze (MB)";Expression={$_.size}}
# where you select these properties for display:
# Database Name, Location, Size (MB)
# None of these properties exist on files or directories,
# so they don't get shown on screen.
Fix:
$x = Invoke-SqlCmd ___
$y = Get-ChildItem
$x | Format-Table
$y | Format-Table
Or use more Write-Host, or output to files.

How to limit the number of concurrent jobs in powershell?

I'm trying to get uptime of 2000+ computers.
As winrm isn't configure on these computers I cannot use invoke-command -computername $computers.
So I tried to use start-job to speed up things but start-job doesnt come with a throttleLimit parameter as invoke-command. So my script fires large amount of powershell.exe until it kills my memory... Is there a way to limit the concurrent jobs?
this is what I've got now:
$jobs=#()
Get-QADComputer -SearchRoot $OU -SizeLimit 3000 |%{
$jobs+= Start-Job -ArgumentList $_.name -ScriptBlock {(param $cn)
if (Test-Connection -Quiet $cn){
$lastboottime=(Gwmi -computername $cn -Class Win32_OperatingSystem).lastbootuptime
$sysuptime = (Get-Date) – [System.Management.ManagementDateTimeconverter]::ToDateTime($lastboottime)
$cn +" "+$sysuptime.days
}
}
}
$jobs|%{ Wait-Job $_ -Timeout 30 |Receive-Job ;Remove-Job $_}
While this is a viable way to do it, you don't have to use jobs at all. Get-WMIObject takes a String[] for the ComputerName parameter, and if multiple computernames are passed, it will poll multiple machines simultaneously (I think up to 32, but I don't recall exactly) & return an extra field in the results, PSComputerName
You can do this much more simply.
$servernames = #();
$servernames += get-qadcomputer -searchroot $ou|select name|%{if(test-connection -quiet $_.name) {$_.name}}
get-wmiobject -computername $servernames win32_operatingsystem|select PSComputername,LastBootTime
then calculate your uptime from there for each computer.
Edit (Kayasax) : here is the final recipe :
$alive=#()
$obj=#()
Get-QADComputer -SearchRoot $ou -SizeLimit 4000 |select -ExpandProperty name |foreach-object {
if (Test-Connection -Quiet -count 1 $_){ $alive+=$_ }
}
Get-wmiobject -computername $alive -Class Win32_OperatingSystem |select PSComputerName, lastBootUpTime |foreach-object{
$sysuptime = (Get-Date) – [System.Management.ManagementDateTimeconverter]::ToDateTime($_.lastBootUpTime)
$props=#{"name"=$_.PSComputername;"uptime"=$sysuptime.days}
$obj+= new-Object -TypeName PSCustomObject -property $props
}
$obj |sort-object uptime -desc