I have the following code that starts a service called uvnc_service on all hostnames I have in a text file called find.txt (see below). I want to add some sort of check to test if the service is already running on it so if it is - do nothing and output a message to the screen saying that its already running or if its not running on one of the hosts in the find.txt file - start the service and then output/append the hostname to this file.
Can someone help me please?
Thanks
find.txt...
pc1
pc2
pc3
...
set service = uvnc_service
for /F %%a in (c:\temp\find.txt) do sc \\%%a start %service% && >> out.txt echo %%a
You can use Service control to query the machine and see the status of the service ie is it running
http://ss64.com/nt/sc.html
Try this
set service = uvnc_service
for /F %%a in (c:\find.txt) do call :servicecheck %%a
:servicecheck
sc \\%1 query %service% | FIND "RUNNING"
IF %ERRORLEVEL% == 0 GOTO STARTSERVICE %1
GOTO END
:STARTSERVICE
sc \\%1 start %service% && >> out.txt echo %1
:END
I cant test it on my machine and i haven't done batch in a while so it might not be perfect
Related
I posted this a few days ago, but I am still having some issues. Please help if possible. Here is my code
#echo off
rem This script pings all IPAdresses on an Xfinity Router.
::v1.2 - BTE - 01Mar19
::
for /L %%i in (1,1,254) DO ping -n 1 10.0.0.%%i | findstr "ms" && (echo 10.0.0.%%i)>>"pingable_ips.txt"
The above was a batch file that I tried to create to ping all IP addresses on my network, then write all pingable IPs to a text file. After some troubleshooting from others here, I got it to at least ping all IPs on the network. I am still having trouble with getting the batch file to create a text file with the pingable IPs.
This batch file runs all the way from 10.0.0.1 to 10.0.0.254, but it stops after.
EDIT: Thank You, I got it to work!
While I don't know what went wrong with your code, I would suggest the following one which shouldn't produce any errors/misbehaviours except if this is your fault:
#echo off
rem This script pings all IPAdresses on an Xfinity Router.
rem v1.2 - BTE - 01Mar19
for /L %%A IN (1 1 254) do (
(ping -n 1 10.0.0.%%A | findstr "ms") && (
echo 10.0.0.%%A>>"pingable_ips.txt"
) || (
echo Failed to find string "ms" when pinging 10.0.0.%%A!
)
)
Or in one line:
#echo off
rem This script pings all IPAdresses on an Xfinity Router.
rem v1.2 - BTE - 01Mar19
for /L %%A IN (1 1 254) do (ping -n 1 10.0.0.%%A | findstr "ms") && (echo 10.0.0.%%A>>"pingable_ips.txt") || (echo Failed to find string "ms" when pinging 10.0.0.%%A!)
Actually, my code checks if command ping -n 1 10.0.0.%%A | findstr "ms" returns errorlevel EQUal to 0. If yes, then it runs command echo 10.0.0.%%A>>"pingable_ips.txt". If no, it will run echo Failed to find string "ms" when pinging 10.0.0.%%A!.
I am trying to create a batch script to see if Windows service, ex. wuauserv is set to an automatic start. So far, I have tried
sc query [ServiceName] | findstr /i "STATE"
but this only shows me the running state, and I want to know if it is set to start automatically. Bonus points for an IF statement that checks the state.
SOLUTION
Here is the solution that I engineered thanks to the below people and others on SO. Feel free to make improvements on this GitHub Gist
#ECHO OFF
ECHO This script re-enables Windows Update and sets it to Automatic.
ECHO However, this script needs to be run as admin.
net.exe session 1>NUL 2>NUL || goto :not_admin
echo Sucess! You ran this script with Admin rights!
sc qc "wuauserv" | findstr /i AUTO_START > nul
goto :check
:check
if %ERRORLEVEL% equ 0 (
ECHO The service is set to start automatically.
TIMEOUT 5
) ELSE (
echo The service is NOT set to start automatically. Trying again.
sc config "wuauserv" start= auto
net start wuauserv
goto :check
)
exit
:not_admin
echo ERROR: please run as admin
TIMEOUT 10 /nobreak
exit
Try this batch file, which takes the service name as a parameter and returns 0 if automatic, 1 if not:
#echo off
if [%1]==[] (
echo Missing service name. Returning 2.
exit /b 2
)
sc qc "%1" | findstr /i AUTO_START > nul
if %ERRORLEVEL% equ 0 (
echo The "%1" service is set to start automatically. Returning 0.
exit /b 0
) else (
echo The "%1" service is NOT set to start automatically ^(or the service is inaccessible^). Returning 1.
exit /b 1
)
An alternative option using win32_service via WMIC:
WMIC Service Where "Name='wuauserv' And StartMode='Auto'" Get State /Value 2>Nul|Find "State="||Echo Service is not set to Auto
If you wanted to change the start mode, should it not be set to automatic, you could probably do that as a single command too:
WMIC Service Where "Name='wuauserv' And StartMode!='Auto'" Call ChangeStartMode "Auto"
I would like to create a .bat file that will give me option to chose between different servers and perform actions such as stop/start services. So far I am getting System error 67 has occurred.The network name cannot be found. Is there a better way to do this. or can I chose the server name from a pop up option.
#ECHO OFF
CLS
ECHO 1.server1
ECHO 2.server2
ECHO 3.server3
ECHO 4.server4
ECHO.
set /p server_name=Enter server name:
IF %server_name%== 1 GOTO app1
IF %server_name%== 2 GOTO app2
IF %server_name%== 3 GOTO app3
IF %server_name%== 4 GOTO app4
:app1
call:restart "server1"
GOTO End
:app2
call:restart "server2"
GOTO End
:app3
call:restart "server3"
GOTO End
:app4
call:restart "server4"
GOTO End
:restart
net use \\%~1/User:%username%
SC \\%~1 Stop service
timeout 10
SC \\%~1 Start service
GOTO End
Instead of debugging your file, I'd like to present you a different solution:
On the servers where you want to restart your services create this bat file:
#ECHO OFF
:STOP
SC STOP <your_service>
ping 127.0.0.1 -n 6 > nul
SC QUERY <your_service> | find /I "STATE" | find "STOPPED"
if errorlevel 1 goto :STOP
SC START <your_service>
Now, create on your servers tasks with the task scheduler. Don't set any triggers but make the task execute your newly created bat file. Select any options you need (like a specific user with a specific password, whether to run the script when no one is logged in or not, whether to run it with admin priveledges or not, etc.) and give it name (your_task).
Finally, modify your script like this:
#ECHO OFF
CLS
ECHO 1.server1
ECHO 2.server2
ECHO 3.server3
ECHO 4.server4
ECHO.
:SELECT
set /p server_name=Enter server name:
IF %server_name%==1 GOTO app1
IF %server_name%==2 GOTO app2
IF %server_name%==3 GOTO app3
IF %server_name%==4 GOTO app4
GOTO SELECT
:app1
SCHTASKS /RUN /S "server1" /TN "your_task"
GOTO End
:app2
SCHTASKS /RUN /S "server2" /TN "your_task"
GOTO End
:app3
SCHTASKS /RUN /S "server3" /TN "your_task"
GOTO End
:app4
SCHTASKS /RUN /S "server4" /TN "your_task"
GOTO End
:End
You can also pass a user and a password to the SCHTASKS command if needed.
It should be clear how it works. I'd recommend taking a closer look at the first bat file. Using this:
SC \\%~1 Stop service
timeout 10
SC \\%~1 Start service
might cause trouble. Sometimes service won't stop within 10 seconds out of various reasons. Trying to start the service while it hasn't stopped yet, will result in an error and the service will remain stopped.
Instead, our bat script within the scheduled task will try to stop the service, then wait for 5 seconds (yes, -n 6 means 5 seconds ^^) and then it will check whether the service has the state "STOPPED". If it is, it will start it, otherwise, it will re-try to stop it, wait 5 more seconds and so on.
I am writing a batch script which should stopp services on a remote computer, copy something and then start it again.
The fact, that sc doesn't wait for the service to return a full stop / start signal doesn't satisfy me, as I fear that the service might be inconsistend or failing, and then could damage the program code / database which is depending on those services.
therefore I searched for a workaround, to have something similiar to usage of net , and come around this:
sc \\remote_server stop Service1 >> %LOGFILE%
:askservice1
for /f "tokens=4" %%a in (' sc \\remote_server query Service ^|findstr STATE') do set ServiceResult=%%a
if %ServiceResult%=STOPPED (goto nextservice2)
goto askservice1
:nextservice2
sc \\remote_service stop Service2 >> %LOGFILE%
:askservice2
for /f "tokens=4" %%a in (' sc \\remote server query Service ^|findstr STATE') do set ServiceResult2=%%a
if %ServiceResult2%=STOPPED (goto nextservice3)
goto askservice2
this goes on for 6 services, then the copy will be done, and then the run should go other way round with starting up
as you can see, this is a. really strange and looks confusing and b, it could end in an endless loop if the service won't get to the state I am comparing to...
my questions would be, how can I terminate the goto after a few tries and just let it go to the next service ?
or do you have any other code for me that helps ? I am limited to use batch or powershell but as I've never used PS before, I couldn't understand the solutions I've found.
Try this and see if it works for you. I tested it on my local machine with 2 services and it worked well. You'll have to tweak some of the ping timeout settings and take out the echo for the file copy but overall it should give you a nice starting place.
#echo off
setlocal enabledelayedexpansion
set "stopstart=stop"
set "state=STOPPED"
set "remoteserver=REMSERV"
set "LogFile=Logfile.log"
if exist %LogFile% del /q %LogFile%
:Start
for %%S in (service1 service2 service3 service4 service5 service6) do (
sc \\%remoteserver% %stopstart% %%S>>%LogFile%
Call :WaitForService %remoteserver% %%S %state% ret && (
echo Service %%S %state%
set /a svc+=1) || (
Service %%S is !state!
)
)
if "%svc%" EQU "6" (
echo copy file now.
ping -n 10 127.0.0.1>nul
set "stopstart=start"
set "state=RUNNING"
goto :Start
)
if "%svc%" EQU "12" (Echo All services are now running.)
exit /b
:WaitForService <remoteserver> <service> <stopstart> <return>
setlocal
for /L %%a in (1,10,1) do (
for /f "tokens=4" %%a in ('
sc \\%~1 query %~2^|findstr "STATE"') do (
ping -n 2 -w 10000 127.0.0.1>nul
if "%%a" EQU "%~3" set %~4=%%a & exit /b 0
)
exit /b 1
)
What it's doing is setting some variables at the start then looping through all 6 of your services sending them to a subroutine that checks the wait state given to it. In the first iteration, it's STOPPED so it checks in a loop for the service to be stopped. Once it is STOPPED, it sends an exit code and we check that exit code to make sure the service stopped. At this point, we add a +1 to a variable to keep track of each service that has stopped. Once all 6 have stopped, we copy the file in question, flip the state of the services to RUNNING and run through the routine again waiting for each of the services to start. Once all of them are started, it Echo's all services are running and ends. You can probably expand upon it more by checking additional states and running through the WaitForService routine until everything has STOPPED if you need to but in my testing, the services just stopped and started without any hiccups.
What is the best method for creating a batch file (.bat) that will automatically map network drives after a internet connection has been established. The batch file will be remain in the windows start up folder and will only map the network drives if they are not already mapped. I have tried the following:
:Start
ping -n 1 www.google.com
If %errorlevel% == 0 Goto :Start
If %errorlevel% == 1 Goto :Connected
:Connected
Net Use F:\\ Server\Folder /Persistent:No
The ping reply is so fast that the Net use command doesn't map the drive even though the path is correct and will work if I manually enter the net use and path in the CMD window. I need for it to wait after the ping reply and then map the network drives and also for it to only map the network drives if they are not already mapped. I realize what I have tried doesn't address the "only map the network drives if they are not already mapped". I have done some extensive searching and I cannot find the answer to these issues. Would appreciate step by step and easy to follow instructions for resolving this.
Thank you very much.
Maybe additional "timeout" can help?
updated
I use windows vpn client.
To check available connection i make script like this
and wait 30 second before check by ping.
And i ping my server which available only under vpn.
#echo off
set myserver=192.168..
setlocal enabledelayedexpansion
rasdial FirstVPN /disconnect
rasdial SecondVPN /disconnect
echo ==== second vpn
start rasdial SecondVPN
timeout /T 30
for /f "Tokens=*" %%G in ('ping -n 1 %myserver% ^| FIND "TTL="') do set ans="%%G"
IF NOT [%ans%]==[] GOTO Connected
echo ==== first vpn
start rasdial FirstVPN
timeout /T 30
for /f "Tokens=*" %%G in ('ping -n 1 %myserver% ^| FIND "TTL="') do set ans="%%G"
IF [%ans%]==[] (exit)
:Connected
echo %ans%