#Running a powershell script in the background
1 messages · Page 1 of 1 (latest)
Start-ThreadJob
how do I enable scripts?
in 1 command
with no user interaction
Start-Job or Start-ThreadJob are the only ways to run in the background.
Set-ExecutionPolicy RemoteSigned to enable scripts
but if you push it all into the background, and let PS end, it'll all be torn down
Or, make sure you start PowerShell with -ExecutionPolicy RemoteSigned
(or use "Unrestricted" in place of RemoteSigned)
also Start-ThreadJob : The term 'Start-ThreadJob' 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.
it stays like that forever
sure
but putting it in the background is no fix for this
you need to figure out why it stays, assuming you never get back control of the console
well id assume the startup script makes the setup wait
If you're on Windows PowerShell, Start-ThreadJob is in the Microsoft.PowerShell.ThreadJob module now, but you have to install it
so maybe making it be in the background
then sleeping for the duration of the setup
and then making it run would work
by magic?
There's nothing in that script that would sleep
putting what you have into the background is no solution for it hanging.
I mean, obviously Add-WindowsCapability can take some time ...
But it wouldn't lock up forever
if I sleep in the initial script
windows doesn't setup as well
...
I don't understand what you mean by that
I gave it 3h to run
and nothing happened ...
its just like this
Right, so my point is ... it's getting locked up on something, and you need to add some lines like: Write-Host "I got as far as line 4" to it
for hours
so why do you think making it run in the background is a fix for this?
is that triggered by autounattend or something?
I can't tell which thing is causing it to lock up
here is why I think it will work
if I run it as is, it just doesn't work. if I run it after setup manually, it does.
Running this in the background:
#ps1
Start-Sleep -Seconds 900
Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
Start-Service sshd
Set-Service -Name sshd -StartupType 'Automatic'
if (!(Get-NetFirewallRule -Name ""OpenSSH-Server-In-TCP"" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
Write-Output ""Firewall Rule 'OpenSSH-Server-In-TCP' does not exist, creating it...""
New-NetFirewallRule -Name 'OpenSSH-Server-In-TCP' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
} else {
Write-Output ""Firewall rule 'OpenSSH-Server-In-TCP' has been created and exists.""
}
Set-MpPreference -DisableRealtimeMonitoring $true
will wait for the setup to complete and then run the program, by that the two won't collide
I think its an issue with the server
No, it will not
wdym?
I mean it will not wait for setup to complete then run the program
if you push it into the background it still runs immediately, you just don't see it
if you need to wait for setup to complete then you need to wait for setup to complete before starting your other stuff
lieka fter
What "Setup" are we talking about? Windows first-run stuff?
Or some other script you're running?
like windows setting up
unattended installation of Windows?
don't u need to setup unattended before in the iso file?
its an rdp from a cloud provider
I'm not sure that's a description of a thing...
how do you get that cmd.exe prompt while windows is still "Getting ready"?
the cloudprovider has an option for an initial script
how would I run this without user input?
I think I still dont understand whats the actual problem
Set-ExecutionPolicy RemoteSigned -Confirm:$false
either that or -Force, cannot remember which
Set-ExecutionPolicy Bypass -scope Process -Force
I think -Force
works
#ps1
Set-ExecutionPolicy Bypass -scope Process -Force
$cmd = "#ps1
Start-Sleep -Seconds 900
Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
Start-Service sshd
Set-Service -Name sshd -StartupType 'Automatic'
if (!(Get-NetFirewallRule -Name ""OpenSSH-Server-In-TCP"" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
Write-Output ""Firewall Rule 'OpenSSH-Server-In-TCP' does not exist, creating it...""
New-NetFirewallRule -Name 'OpenSSH-Server-In-TCP' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
} else {
Write-Output ""Firewall rule 'OpenSSH-Server-In-TCP' has been created and exists.""
}
Set-MpPreference -DisableRealtimeMonitoring $true"
$cmd | Out-File -FilePath script.ps1
Start-Job -FilePath .\script.ps1
will the start job run this as admin?
it's probably already elevated since DISM isn't kicking you out right away; but since you don't disclose what cloud provider or how the original process is started it's not possible to definitively say
moving it into start job will certainly "work" in the sense that it will start a job
If you're elevated, it is
it won't magically fix anything else though
wdym?
Oh, nothing. Just not sure about the elevation
But it turned out my check was a typo
jobs run with the same permission as the parent process
Unless you remote
I am
made it send webhooks so I know if something failed and where
not the best way to do it but yeah lol
it seems like it never runs the
Start-Job -FilePath .\script.ps1
any idea on why that would happen?
do you feel like you're going in circles yet?
Start-Job will start a job... but if the process that started it ends, so does the job
yAP
how would I get around it hten?
change when you run the script in the first place
wdym?
#ps1
Set-ExecutionPolicy Bypass -scope Process -Force
$cmd = "#ps1
Start-Sleep -Seconds 900
Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
Start-Service sshd
Set-Service -Name sshd -StartupType 'Automatic'
if (!(Get-NetFirewallRule -Name ""OpenSSH-Server-In-TCP"" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
Write-Output ""Firewall Rule 'OpenSSH-Server-In-TCP' does not exist, creating it...""
New-NetFirewallRule -Name 'OpenSSH-Server-In-TCP' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
} else {
Write-Output ""Firewall rule 'OpenSSH-Server-In-TCP' has been created and exists.""
}
Set-MpPreference -DisableRealtimeMonitoring $true"
$cmd | Out-File -FilePath script.ps1
Start-Job -FilePath .\script.ps1
what should I change in here?
something so it runs after setup is finished rather than during
@delicate kelp https://stackoverflow.com/questions/19535493/keep-a-job-running-even-after-shell-window-has-been-closed
u think that would work?
no, not really
not because the idea won't work, but because the problem and running context isn't very well defined
ehhhhhhhhh
do u know of any commands that will keep the process alive after the main program is finished?
@delicate kelp does Start-Thread keep running after main program has finished?
so much assumptions while little to no understanding...
ik im a noobie
stop assuming, process what is being said. Don't ask leading questions.
No, it does not
you need to do this another way
wha
wdym
do I just compile a py script with a subprocess to do this ;-;
💀
and wget and run
uh
you don't need to run python
you can run powershell
The point is, if you want it to stay running, you need to leave it running
If your problem is that your whole script is just Start-Job ...
Then pass that to Wait-Job
You can't just put it on a background thread and then exit
because exiting kills the background
well waiting stops it and the setup
nope
OK, let me ask a different way: how does waiting stop the setup?
#ps1
Set-ExecutionPolicy Bypass -scope Process -Force
$cmd = "#ps1
Start-Sleep -Seconds 900
Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
Start-Service sshd
Set-Service -Name sshd -StartupType 'Automatic'
if (!(Get-NetFirewallRule -Name ""OpenSSH-Server-In-TCP"" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
Write-Output ""Firewall Rule 'OpenSSH-Server-In-TCP' does not exist, creating it...""
New-NetFirewallRule -Name 'OpenSSH-Server-In-TCP' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
} else {
Write-Output ""Firewall rule 'OpenSSH-Server-In-TCP' has been created and exists.""
}
Set-MpPreference -DisableRealtimeMonitoring $true
"
$cmd | Out-File -FilePath script.ps1
Start-Sleep -Seconds 5
Start-Job -FilePath .\script.ps1
Wait-Job -Id 1
its just an initial script that starts like 5m into the rdp setup
Can you not put this into Packer or DSC or whatever you use to initialize the box?
nope
its stupid
I would've just made a complete screenshot of what I need and load it on each server
Seems like your only option would be to create a scheduled task to run it in then
That way, you can schedule it to run "later"
I mean, that ... or figure out what's actually causing the hang up
seems like its the
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
that its getting stuck on
It makes sense that if other feature installs are running, that would cause problems
Well, since it sounds like you're in Windows PowerShell, you can just use Register-ScheduledJob
Summary: Microsoft Scripting Guy, Ed Wilson, introduces the Windows PowerShell scheduled job feature. Microsoft Scripting Guy, Ed Wilson, is here. In all the hubbub about all the great features introduced in Windows PowerShell 3.0, one (actually more than one) feature was somewhat overlooked.
This is a Windows 10 vm right?
yes
$Later = New-JobTrigger -Once -At ([DateTime]::Now.AddMinutes(5))
How is this script being fed to the machine?
Register-ScheduledJob -Name AddOpenSSH -Trigger $later -ScriptBlock { ... }
and shove your $cmd into the scriptblock
#ps1
Set-ExecutionPolicy Bypass -scope Process -Force
$cmd = {
Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
Start-Service sshd
Set-Service -Name sshd -StartupType 'Automatic'
if (!(Get-NetFirewallRule -Name "OpenSSH-Server-In-TCP" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
Write-Output "Firewall Rule 'OpenSSH-Server-In-TCP' does not exist, creating it..."
New-NetFirewallRule -Name 'OpenSSH-Server-In-TCP' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
} else {
Write-Output "Firewall rule 'OpenSSH-Server-In-TCP' has been created and exists."
}
Set-MpPreference -DisableRealtimeMonitoring $true
}
$Later = New-JobTrigger -Once -At ([DateTime]::Now.AddMinutes(10))
Register-ScheduledJob -Name AddOpenSSH -Trigger $later -ScriptBlock $cmd
?
no ... the code in your $cmd should be inside the { } instead
I do feel like it would be better to tack this on to the end of whatever other setup is running ... rather than hoping for luck with the timing.
This is definitely something we would do with DSC.
If you do $cmd = { .. }
Then do -ScriptBlock $cmd
like this?
yeah
I would just move the code to the bottom, and loose the $cmd variable, but that should do the trick
At the very least, now you can "get" the results of the job later
I don't follow