Launch script after Windows service start - windows

I would like to launch script after windows service start or restart.
Like monitor wsupdate and at start or restart execute a batch script test.bat
Any ideas ?

That could be easily done with a scheduled task:
You just need to:
1) Start and Stop the Service to got the appropriate Events in the Eventlog.
2) taskschd.msc and create a new Costum Task. As Trigger you can select the Events created before with the start and/or stop action.
3) As Action call your cmd/bat, whatever you want.
Hint:
You also can export the Event in the XML Format, explained here:
http://blogs.technet.com/b/askds/archive/2011/09/26/advanced-xml-filtering-in-the-windows-event-viewer.aspx
and then import the XML Snippet into the Scheduld Task.

Related

Is it possible to trigger a script execution when stopping a windows service from services.msc?

I want to know if it is possible to configure a service to call a batch/powershell script when I stop it from services.msc.
While in Linux init.d services are fully programmable and even systemd services can have additional procedures I've yet to find a way to accomplish this on Windows.
Thanks in advance
You can configure services to run a program on failure, but if you are stopping the service via services.msc then that likely wouldn't count as a failure.
The only other option I can think of would be to set up a PowerShell script running as a scheduled task that either periodically checks the services running status, or (for a more foolproof option) looks at the event log for events indicating that the service has been stopped (since the last time the script checked) and then performs whatever actions you require.
Per the comment from montonero, you wouldn't need to run the scheduled task periodically as it could be configured to run when the event itself occurs. This is described here: https://blogs.technet.microsoft.com/wincat/2011/08/25/trigger-a-powershell-script-from-a-windows-event/
Use the Event Viewer “Attach Task to This Event…” feature to
create the task.
Launch "Event Viewer" and find the event. Once found, right-click on the event and select "Attach Task to
This Event...".

executing a .bat file in background and daemon mode

I want to create a .bat file and attach it to the boot processes so everytime I start the computer I wont have to execute the file.
This can be done with Task Scheduler.
Create a new task (don't use a basic task), for the trigger drop down (the default is scheduled) to At Startup.
You'll need to configure a user account to execute the batch file (likely there is no one logged in yet).

Schedule Powershell script to run every hour

Please check this picture as following
I was looking at Window task scheduler to schedule my script to run each hour. The script will do some checks and will send an email .
I did not find options to schedule it for each 1 hour. I only found for every day, daily, weekly and so on.
Task scheduler does show the option to configure hourly trigger as shown below.
Another option you have is to run your PowerShell script as a Service and add the logic in your PowerShell script to trigger your main code once every hour.
Refer: Video: Running PowerShell scripts as a real Windows Service!
How To Create a User-Defined Service
Call it from scheduled task eg task would be to start PowerShell and run the specified script see Run a powershell script in the background once per minute
create the task then -> new trigger -> daily -> repeat task every hour is one way of doing it. Or do it on commandline

Schedule a task to monitor a certain process start

I'm trying to tie two applications together, so that when one is started the other starts too.
I expected to find this in Task Scheduler under Events > Application or something like that, but only some applications have event sources there.
So I researched and found that you can detect a process start by registering a WMI event.
Register-WMIEvent -Query "SELECT * FROM __InstanceCreationEvent WITHIN 3 WHERE TargetInstance ISA 'Win32_Process' AND TargetInstance.Name = 'notepad.exe'" -sourceIdentifier 'NotepadStarted' -action {if(!(ps AutoHotKey)) { start Automator.ahk}}
However this is meant to run all the time, which means a powershell.exe process in the background, and WMI polling every 3 seconds (WITHIN 3 - yes I do need it to respond ASAP). The PC is powerful enough for this job as is, but if in the future I want to watch more than one app, this approach may turn out to use too much resources.
Is there a better way of watching for a process start on Windows? Without polling or running a script continually in the background, but rather simply scheduling a task to respond to the event of Notepad having started?
I have found a way through Auditing, which seems to work alright.
We're trying to get the process to raise an event when it starts, then in Task Scheduler to home in on that event as the trigger for our action.
UPDATE: Conjoined Twins - IFTTT-style application actions using auditing and scheduled tasks under Windows. It's a Powershell script that helps you set this up.
LATER EDIT: OK it does produce a few false positives. The action may fire without the program having actually been executed. So beware.
Go to your application.exe, right click > Properties > Security tab > Advances > Auditing tab > Edit
Add your username and tick Traverse folder / execute file. Click all of the OKs. Every successful execution of application.exe will now show up in Event Viewer. Go there to check them out:
Event Viewer > Windows Logs > Security
You can Filter current log for EventID 4663
Here is an event like that from my machine:
An attempt was made to access an object.
Subject:
Security ID: PC\Redacted
Account Name: Redacted
Account Domain: PC
Logon ID: 0xxxxxxx
Object:
Object Server: Security
Object Type: File
Object Name: C:\Program Files\Some Application\application.exe
Handle ID: 0x1e1c
Process Information:
Process ID: 0x374
Process Name: C:\Windows\explorer.exe
Access Request Information:
Accesses: Execute/Traverse
Access Mask: 0x20
You'll see more than one of these, it's not just one-to-one, 1 program start = 1 event. There are A handle was open, A handle was closed events as well.
In Task Scheduler you have to now create an event to target the program start.
Create New Task > Triggers Tab > New
Select Begin task: On an event from the drop-down.
Click the Custom radio button then Edit Event Filter... button
In the XML tab tick Edit query manually and paste something like this in:
<QueryList>
<Query Id="0" Path="Security">
<Select Path="Security">*[EventData[Data[#Name='ObjectName'] and (Data='C:\Program Files\Some Application\application.exe')]]
</Select>
</Query>
</QueryList>
¹
Pictures and more details at Quick Development Tips: How to monitor a folder and trigger an action for incoming files, in Windows 7
Once this is done, all that's left is to set up your Action, the program you want to run when application.exe starts. For me it was an AutoHotKey script - I just clicked Browse and navigated to it.
Now when I start the app I get that AutoHotKey script automating some initial steps. It wouldn't have worked to just create a batch file with application.exe & script.ahk in it, because sometimes the app starts from opening a file, sometimes it's started by something else, or who knows. This way no matter how it starts, script.ahk happens.
¹ Side note: Here's a catch. This XPath query works for Data='C:\no\wildcards\allowed.exe' but you'll be disappointed to find that you can't use wildcards or any other kind of matching. So if you want to select a file that doesn't move or change name, that's fine. But if you want to select a newly created file of unknown name inside a folder you're watching - you can't. At most you can do Data='variant1' OR Data='variant2'...
Keep in mind that using the task scheduler for this requires enabling auditing of ALL! processes on an OS-level. That can create quite a high load.
For monitoring a single process I would recommend creating a "permanent WMI event trigger". Details see here: https://learn-powershell.net/2013/08/14/powershell-and-events-permanent-wmi-event-subscriptions/
As a "consumer" you need to create a small VBscript as an "ActiveScriptEventConsumer" that starts the other process.

Do AutoIt scripts, executed as service, function for GUI actions?

I'm using an AutoIt script to start and automate a GUI application. I need to activate the script each hour.
Will AutoIt scripts (which perform actions on a GUI) work when used as a service? The script will be run as a service (not scheduled task).
You can easily make an autoit script run as a service using service.au3 written by archer of the autoit forums. Unfortunately or fortunately since it is a security measure. A service needs to start independent of the current user session (before login). It cant access send APIs for input manipulation of the current user session from there. It does sound much more like you need a scheduled task and not a service.
As mentioned above, a scheduled task is what you're looking for. To run a script as a service read this:
Q4. How can I run my script as a service?
This is also a question with multiple answers, and none of them are the only way to do it. The first question to ask yourself is whether or not you wish to install the service on other computers besides your own.
A1. If you only wish to install the service on your own computer, The easiest way to do this is to use Pirmasoft RunAsSvc. This program makes services easy to install and easy to remove when necessary.
A2. If you wish to make the service available to anyone running your script, you can use SRVANY.EXE and ServiceControl.au3. You can then use this code to install your script as a service:
#include "ServiceControl.au3"
$servicename = "MyServiceName"
_CreateService("", $servicename, "My AutoIt Script", "C:\Path_to_srvany.exe", "LocalSystem", "", 0x110)
RegWrite("HKLM\SYSTEM\CurrentControlSet\Services\" & $servicename & "\Parameters", "Application", "REG_SZ", #ScriptFullPath)
or use the following code to delete this service:
#include "ServiceControl.au3"
$servicename = "MyServiceName"
_DeleteService("", $servicename)
There is one caveat to setting up AutoIt as a service. If the service is not installed using the above code, it must have the "allow service to interact with the desktop" setting or else automation functions such as Control* or Win* functions will not function. To assure the service does indeed have this setting, use the following code:
RegWrite("HKLM\SYSTEM\CurrentControlSet\Services[ServiceName]", "Type", "REG_DWORD", 0x110)
Taken from the FAQ topic on the AutoIt Forums. www.autoitscript.com/forum/index.php?showtopic=37289)
It sounds like you're want to use a scheduled task instead of a service. Scheduled tasks can execute every hour, while you're logged in, and should also be able to interact with your desktop. Just remember that a task run as a normal user can not interact (send input) to a elevated program if you're using Vista/Windows Server 2008 with User Account Control enabled.

Resources