Unable to delete certain files and folders using Powershell - powershell

I need to create a script that clears the Lync cache on remote machines. To do so I need to close Outlook and Lync if they are open, and then clear out two folders whilst deleting another. Here is what I have so far:
[System.Reflection.Assembly]::LoadWithPartialName('Microsoft.VisualBasic') | Out-Null
$computer = [Microsoft.VisualBasic.Interaction]::InputBox("Which computer do you wish to clear the Lync cache for?", "Computer", "$env:computername")
$username = Get-WMIObject -class Win32_ComputerSystem -ComputerName $computer | select username
$RSA = "C$\Users\$username\AppData\Roaming\Microsoft\Crypto\RSA"
$Tracing = "C$\Users\$username\AppData\Local\Microsoft\Office\15.0\Lync\Tracing"
$SIP = "C$\Users\$username\AppData\Local\Microsoft\Office\15.0\Lync"
(Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match "Outlook" }).Terminate()
(Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match "Lync" }).Terminate()
(Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match "Communicator" }).Terminate()
start-sleep -s 3
Get-ChildItem -path \\$computer\$RSA -include * | Remove-Item -recurse -force
Get-ChildItem -path \\$computer\$Tracing -include * | Remove-Item -recurse
Remove-Item -path \\$computer\$SIP\*sip* -recurse -force
The script closes the programs as required, but it doesn't appear to do anything with the folders. The only errors I get are below:
You cannot call a method on a null-valued expression.
At C:\Users\*myusername*\Desktop\Personal Powershell scripts\Clear Lync cache.ps1:10 char:1
+ (Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
You cannot call a method on a null-valued expression.
At C:\Users\*myusername*\Desktop\Personal Powershell scripts\Clear Lync cache.ps1:11 char:1
+ (Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
You cannot call a method on a null-valued expression.
At C:\Users\*myusername*\Desktop\Personal Powershell scripts\Clear Lync cache.ps1:12 char:1
+ (Get-WmiObject Win32_Process -ComputerName $computer | ?{ $_.ProcessName -match ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
ISE is open as admin. I have admin rights to the domain as well as the folders in question. Can anyone see where I'm going wrong?

Related

Update definition of SCEP on windows servers using powershell

i am trying to update the definition of SCEP on remote Windows Servers using MpCmdRun.exe which exists under "C:\ProgramData\Microsoft\Windows Defender\platform\*\MpCmdRun.exe. Unfortunately it is not accepting -filepath. says its null or empty. below is my code
$comp = "SRV1234"
$MpCmdRun = invoke-Command -ComputerName $comp -ScriptBlock {get-item -Path "C:\ProgramData\Microsoft\Windows Defender\platform\\*\MpCmdRun.exe" | Sort-Object -Property LastWriteTime -Descending |Select-Object -ExpandProperty fullname -First 1}
invoke-Command -ComputerName $comp -ScriptBlock {Start-Process -FilePath $MpCmdRun -ArgumentList "-signatureUpdate" -Wait}
Below is the error:
Cannot validate argument on parameter 'FilePath'. The argument is null
or empty. Provide an argument that is not null or empty, and then try
the command again.
+ CategoryInfo : InvalidData: (:) [Start-Process], ParameterBindingValidationException
+ FullyQualifiedErrorId : ParameterArgumentValidationError,Microsoft.PowerShell.Commands.StartProcessCommand

run powershell command over cmd

I'm trying to run this powershell command over cmd.. it worked when i run it directly from powershell.. but when i try to run if from cmd i get errors
Powershell Command:
(Get-WmiObject -Class Win32_Product -Filter "Name='Symantec Endpoint Protection'" -ComputerName localhost. ).Uninstall()
How I run it (cmd):
powershell.exe -Command (Get-WmiObject -Class Win32_Product -Filter Name='Symantec Endpoint Protection' -ComputerName localhost. ).Uninstall()
Output:
Get-WmiObject : Invalid query "select * from Win32_Product where Name=Symantec
Endpoint Protection"
At line:1 char:2
+ (Get-WmiObject -Class Win32_Product -Filter Name='Symantec Endpoint P ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidArgument: (:) [Get-WmiObject], Management
Exception
+ FullyQualifiedErrorId : GetWMIManagementException,Microsoft.PowerShell.C
ommands.GetWmiObjectCommand
You cannot call a method on a null-valued expression.
At line:1 char:1
+ (Get-WmiObject -Class Win32_Product -Filter Name='Symantec Endpoint P ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : InvalidOperation: (:) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
The other answers already answer your question of running powershell over CMD. I'd like to recommend you stop using the Win32_Product wmi class. You can read any of the never ending articles explaining why. As for building commands with arguments, I recommend splatting. As a bonus specifically regarding removing SEP, here is a snippet from a production script used to remove Symantec Endpoint using MSIexec and the guid.
$DateStamp = get-date -Format yyyyMMddTHHmmss
$logFile = '{0}-{1}-{2}.log' -f 'SymantecUninstall',$PC,$DateStamp
$locallog = join-path 'c:\windows\temp' -ChildPath $logFile
$uninstalljobs = Foreach($PC in $SomeList){
start-job -name $pc -ScriptBlock {
Param($PC,$locallog)
$script = {
Param($locallog)
$MSIArguments = #(
"/x"
('"{0}"' -f '{A0CFB412-0C01-4D2E-BAC9-3610AD36B4C8}')
"/qn"
"/norestart"
"/L*v"
$locallog
)
Start-Process "msiexec.exe" -ArgumentList $MSIArguments -Wait -NoNewWindow
}
Invoke-Command -ComputerName $pc -ArgumentList $locallog -ScriptBlock $script
} -ArgumentList $PC,$locallog
}
Just update the guid to match your product. If you want to pull the uninstall string from the registry and use that, it would also be preferable to Win32_Product.
Here are a couple of ways you can find the uninstallstring.
$script = {
$ErrorActionPreference = 'stop'
"HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall",
"HKLM\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall" | foreach{
try
{
$key = reg query $_ /f "Symantec Endpoint" /s | select -skip 1 -first 1
$key = $key -replace 'HKEY_LOCAL_MACHINE','HKLM:'
(Get-ItemProperty $key -Name UninstallString).UninstallString
}
catch{}
}
}
powershell.exe -command $script
or
$script = {
"HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall",
"HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall" | foreach{
Get-childitem $_ |
Where {($_ | get-itemproperty -Name displayname -ea 0).displayname -like 'Symantec Endpoint*'} |
Get-ItemPropertyValue -name UninstallString
}
}
powershell.exe -command $script
Try this:
powershell.exe -Command "& {(Get-WmiObject -Class Win32_Product -Filter """Name='Symantec Endpoint Protection'""" -ComputerName XOS-MS182. ).Uninstall()}"
Try these. The parentheses mean something special to cmd. The filter would require two sets of quotes. Since the pipe is inside the double quotes, cmd ignores it.
powershell "(Get-WmiObject -Class Win32_Product -ComputerName localhost | where name -eq 'symantec endpoint protection').Uninstall()"
powershell "Get-WmiObject win32_product -cn localhost | ? name -eq 'symantec endpoint protection' | remove-wmiobject"
You don't need to use powershell for this task, from an elevated Windows Command Prompt, (cmd), you could use wmic instead:
WMIC.exe Product Where "Name='Symantec Endpoint Protection'" Call Uninstall

PowerShell script to get logged in user

I am looking to run a script on a remote machine using an automation tool that runs the scripts in the system context.
What I have so far:
$userId = Get-Process -IncludeUserName explorer | % username | sort Username -Unique
Write-Host $userid.ToLower()
Results:
Get-Process : A parameter cannot be found that matches parameter name
'IncludeUserName'.
At line:1 char:39
+ $userId = Get-Process -IncludeUserName <<<< explorer | % username | sort Username -Unique
+ CategoryInfo : InvalidArgument: (:) [Get-Process], ParameterBindingException
+ FullyQualifiedErrorId : NamedParameterNotFound,Microsoft.PowerShell.Commands.GetProcessCommand
ToLower : You cannot call a method on a null-valued expression.
At line:2 char:27
+ Write-Host $userid.ToLower <<<< ()
+ CategoryInfo : InvalidOperation: (ToLower:String) [], RuntimeException
+ FullyQualifiedErrorId : InvokeMethodOnNull
Any ideas how to help this script? Or the cause of the errors?
The error says it all; the switch -IncludeUserName is not available on your computer. That's because it requires PowerShell 4.0 or above like Ansgar mentioned.
One solution is to install the latest Windows Mangement Framework (WMF) which includes the latest version of PowerShell.
You can also use the WMI-class Win32_Process to get the user and/or domain by calling the object's GetOwner()-method. Ex:
Get-WmiObject -Class Win32_Process -Filter "Name = 'explorer.exe'" |
ForEach-Object { $_.GetOwner() | % { "$($_.Domain)\$($_.User)" } } |
Sort-Object -Unique
the following script might help you. I'm not completely certain if the invoked command will get the remote logged in user, because I'm not on a work computer right now but it came from the internet so it must be true.
$Computers = (Get-Content "\\<sharedrive\<directory>\Computers.txt)
Foreach ($Computer in $Computers){ `
Invoke-Command -ComputerName $Computer -ScriptBlock `
{Get-WMIObject -Class Win32_ComputerSystem).Username} `
}

Connect remote server and execute script

I'm trying to connect a remote server and stop a process on it using this PowerShell command
Invoke-Command -ComputerName \\srvwebui3 -ScriptBlock {
Get-Process | Where-Object {
$_.Path -like "\\abd\net$\abd\versions\Bin\HttpServer.exe"
} | Stop-Process
}
but I got this error message after executing it:
Invoke-Command : One or more computer names is not valid. If you are trying to
pass a Uri, use the -ConnectionUri parameter or pass Uri objects instead of
strings.
At C:\powerShell\stop-process.ps1:4 char:15
+ Invoke-Command <<<< -ComputerName \\srvwebui3 -ScriptBlock { Get-Process | Where-Object {$_.Path -like "\\gaia\netlims$\Autolims\MainRls\Bin\HttpServer.exe"} | Stop-Process }
+ CategoryInfo : InvalidArgument: (System.String[]:String[]) [Invoke-Command], ArgumentException
+ FullyQualifiedErrorId : PSSessionInvalidComputerName,Microsoft.PowerShell.Commands.InvokeCommandCommand
Here a PowerShell code that worked:
Invoke-Command -ComputerName <computerName> -ScriptBlock {
Get-Process | Where-Object {
$_.Path -like \\bbb\abab$\bs\MainRls\Bin\HttpServer.exe"
} |
Stop-Process -Force
}

PowerShell Path Parameter Invoke-Command (UnauthorizedAccessException)

When running this simple script I am receiving the error message:
+ CategoryInfo : OpenError: (:) [Import-Csv], UnauthorizedAccessException
+ FullyQualifiedErrorId : FileOpenFailure,Microsoft.PowerShell.Commands.ImportCsvCommand
Param(
[string]$Path,
[string]$Credential
)
Invoke-Command –cn DC –Credential $Credential -ArgumentList $Path –ScriptBlock `
{import-csv -Path $args[0] | select-object –property `
#{name='Identity';expression={$_.username}},#{name='Fax';expression={$_.'fax number'}} `
| foreach{Set-ADUser -Identity $_.identity -Fax $_.fax -Confirm:$false}}
Any idea why this may be happening? I have correct permissions the the path that I am using.
I found the issue and it was because I was not including the CSV file in my path. I was pointing to C:\Files\CSV instead of C:\Files\CSV\fax-users.csv.