web-dev-qa-db-fra.com

Comment vérifier si un service est en cours d'exécution via un fichier de commandes et le démarrer, s'il ne fonctionne pas?

Je veux écrire un fichier de commandes qui effectue les opérations suivantes: 

  • Vérifiez si un service est en cours d'exécution
    • S'il est en cours d'exécution, quittez le lot 
    • S'il ne fonctionne pas, démarrez le service 

Les échantillons de code que j'ai googés jusqu'à présent ne fonctionnaient pas, alors j'ai décidé de ne pas les poster. 

Le démarrage d'un service se fait par:

net start "SERVICENAME"
  1. Comment puis-je vérifier si un service est en cours d'exécution et comment créer une instruction if dans un fichier batch? 
  2. Je suis un peu confus. Quel est l'argument que je dois passer sur le net start? Le nom du service ou son nom d'affichage?
78
citronas

Pour vérifier l'état d'un service, utilisez sc query <SERVICE_NAME>. Pour les blocs dans les fichiers de commandes, consultez la documentation .

Le code suivant vérifiera le statut du service MyServiceName et le lancera s'il n'est pas en cours d'exécution (le bloc if sera exécuté si le service n'est pas en cours d'exécution):

for /F "tokens=3 delims=: " %%H in ('sc query "MyServiceName" ^| findstr "        STATE"') do (
  if /I "%%H" NEQ "RUNNING" (
   REM Put your code you want to execute here
   REM For example, the following line
   net start "MyServiceName"
  )
)

Explication de ce qu'il fait:

  1. Interroge les propriétés du service.
  2. Recherche la ligne contenant le texte "STATE"
  3. Tokenizes cette ligne et extrait le 3ème jeton, qui contient l'état du service.
  4. Teste l'état résultant avec la chaîne "RUNNING"

En ce qui concerne votre deuxième question, l'argument que vous souhaitez transmettre à net start est le nom du service, not le nom complet.

141
lc.

Pour basculer un service, utilisez ce qui suit:

NET START "Transaction distribuée Coordonnateur" || NET STOP "Distributed Transaction Coordinator"

29
Coops

Vous pouvez utiliser la commande suivante pour voir si un service est en cours d'exécution ou non:

sc query [ServiceName] | findstr /i "STATE"

Lorsque je l'exécute pour mon antivirus NOD32, je reçois:

STATE                       : 4 RUNNING

Si c'était arrêté, j'aurais:

STATE                       : 1 STOPPED

Vous pouvez utiliser cela dans une variable pour déterminer ensuite si vous utilisez ou non NET START.

Le nom du service doit être le nom du service, pas le nom d'affichage.

18
LittleBobbyTables

Ça devrait le faire:

FOR %%a IN (%Svcs%) DO (SC query %%a | FIND /i "RUNNING"
IF ERRORLEVEL 1 SC start %%a)
13
Kristina Brooks

Version indépendante de la langue.

@Echo Off
Set ServiceName=Jenkins


SC queryex "%ServiceName%"|Find "STATE"|Find /v "RUNNING">Nul&&(
    echo %ServiceName% not running 
    echo Start %ServiceName%

    Net start "%ServiceName%">nul||(
        Echo "%ServiceName%" wont start 
        exit /b 1
    )
    echo "%ServiceName%" started
    exit /b 0
)||(
    echo "%ServiceName%" working
    exit /b 0
)
10
Dr.eel

Je viens de trouver ce fil et je voulais ajouter à la discussion si la personne ne veut pas utiliser un fichier de commandes pour redémarrer les services. Sous Windows, il existe une option si vous allez dans Services, Propriétés du service, puis Récupération. Ici, vous pouvez définir les paramètres du service. Aime redémarrer le service si le service s'arrête. En outre, vous pouvez même demander à une deuxième tentative d’échec de faire quelque chose de différent, comme lors du redémarrage de l’ordinateur. 

5
sagelightning

Vous pouvez utiliser Windows en Español, le code disque est exact (lorsque vous utilisez Windows en espagnol, le code est):

for /F "tokens=3 delims=: " %%H in ('sc query MYSERVICE ^| findstr "        ESTADO"') do (
  if /I "%%H" NEQ "RUNNING" (
    REM Put your code you want to execute here
    REM For example, the following line
    net start MYSERVICE
  )
)

Rappelez-vous MYSERVICE avec le nombre de services que vous souhaitez traiter. Puedes voir le nombre de services à travers les propriétés du service. (Remplacez MYSERVICE par le nom du service à traiter. Vous pouvez voir le nom du service dans les propriétés du service.)

4
Daniel Serrano
@echo off

color 1F


@sc query >%COMPUTERNAME%_START.TXT


find /I "AcPrfMgrSvc" %COMPUTERNAME%_START.TXT >nul

IF ERRORLEVEL 0 EXIT

IF ERRORLEVEL 1 NET START "AcPrfMgrSvc"
2
Logan78

Je souhaitais également recevoir un e-mail si le service était démarré de cette manière. J'ai donc ajouté un peu de code à @Ic, car je pensais le publier au cas où cela aiderait quelqu'un. J'ai utilisé SendMail mais il existe d'autres options de ligne de commande Comment envoyer un simple email à partir d'un fichier batch Windows?

set service=MyServiceName

for /F "tokens=3 delims=: " %%H in ('sc query %service% ^| findstr "        STATE"') do (
  if /I "%%H" NEQ "RUNNING" (

    net start %service%

    for /F "tokens=3 delims=: " %%H in ('sc query %service% ^| findstr "        STATE"') do (
      if /I "%%H" EQ "RUNNING" (
        SendMail /smtpserver localhost /to [email protected] /from [email protected] /subject Service Autostart Notification /body Autostart on service %service% succeded.
      ) else (
        SendMail /smtpserver localhost /to [email protected] /from [email protected] /subject Service Autostart Notification /body Autostart on service %service% failed.
      )
    )

  )
)
1
BYoung

Démarrage du service à l'aide du script Powershell. Vous pouvez le lier au planificateur de tâches et le déclencher à intervalles réguliers ou au besoin . Créez-le en tant que fichier PS1, c'est-à-dire un fichier avec l'extension PS1, puis laissez ce fichier être déclenché à partir du planificateur de tâches.

Pour démarrer le service d'arrêt

dans le planificateur de tâches si vous l'utilisez sur le serveur, utilisez-le en arguments

-noprofile -executionpolicy bypass -file "Scripts de redémarrage du service\StopService.PS1"

vérifier en exécutant la même chose sur cmd si cela fonctionne, il devrait également fonctionner sur le planificateur de tâches

$Password = "Enter_Your_Password"
$UserAccount = "Enter_Your_AccountInfor"
$MachineName = "Enter_Your_Machine_Name"
$ServiceList = @("test.SocketService","test.WcfServices","testDesktopService","testService")
$PasswordSecure = $Password | ConvertTo-SecureString -AsPlainText -Force
$Credential = new-object -typename System.Management.Automation.PSCredential -argumentlist $UserAccount, $PasswordSecure 

$LogStartTime = Get-Date -Format "MM-dd-yyyy hh:mm:ss tt"
$FileDateTimeStamp = Get-Date -Format "MM-dd-yyyy_hh"
$LogFileName = "C:\Users\krakhil\Desktop\Powershell\Logs\StartService_$FileDateTimeStamp.txt" 


#code to start the service

"`n####################################################################" > $LogFileName
"####################################################################" >> $LogFileName
"######################  STARTING SERVICE  ##########################" >> $LogFileName

for($i=0;$i -le 3; $i++)
{
"`n`n" >> $LogFileName
$ServiceName = $ServiceList[$i]
"$LogStartTime => Service Name: $ServiceName" >> $LogFileName

Write-Output "`n####################################"
Write-Output "Starting Service - " $ServiceList[$i]

"$LogStartTime => Starting Service: $ServiceName" >> $LogFileName
Start-Service $ServiceList[$i]

$ServiceState = Get-Service | Where-Object {$_.Name -eq $ServiceList[$i]}

if($ServiceState.Status -eq "Running")
{
"$LogStartTime => Started Service Successfully: $ServiceName" >> $LogFileName
Write-Host "`n Service " $ServiceList[$i] " Started Successfully"
}
else
{
"$LogStartTime => Unable to Stop Service: $ServiceName" >> $LogFileName
Write-Output "`n Service didn't Start. Current State is - "
Write-Host $ServiceState.Status
}
}

#code to stop the service

"`n####################################################################" > $LogFileName
"####################################################################" >> $LogFileName
"######################  STOPPING SERVICE  ##########################" >> $LogFileName

for($i=0;$i -le 3; $i++)
{
"`n`n" >> $LogFileName
$ServiceName = $ServiceList[$i]
"$LogStartTime => Service Name: $ServiceName" >> $LogFileName

Write-Output "`n####################################"
Write-Output "Stopping Service - " $ServiceList[$i]

"$LogStartTime => Stopping Service: $ServiceName" >> $LogFileName
Stop-Service $ServiceList[$i]

$ServiceState = Get-Service | Where-Object {$_.Name -eq $ServiceList[$i]}

if($ServiceState.Status -eq "Stopped")
{
"$LogStartTime => Stopped Service Successfully: $ServiceName" >> $LogFileName
Write-Host "`n Service " $ServiceList[$i] " Stopped Successfully"
}
else
{
"$LogStartTime => Unable to Stop Service: $ServiceName" >> $LogFileName
Write-Output "`nService didn't Stop. Current State is - "
Write-Host $ServiceState.Status
}
}
1
KR Akhil

En rapport avec la réponse de @DanielSerrano, je viens de connaître la localisation de la commande sc.exe, notamment en espagnol. Ma proposition est de localiser avec précision la ligne et le jeton qui contient l’état du service numérique et de l’interpréter, ce qui devrait être beaucoup plus robuste:

@echo off

rem TODO: change to the desired service name
set TARGET_SERVICE=w32time

set SERVICE_STATE=
rem Surgically target third line, as some locales (such as Spanish) translated the utility's output
for /F "skip=3 tokens=3" %%i in ('""%windir%\system32\sc.exe" query "%TARGET_SERVICE%" 2>nul"') do (
  if not defined SERVICE_STATE set SERVICE_STATE=%%i
)
rem Process result
if not defined SERVICE_STATE (
  echo ERROR: could not obtain service state!
) else (
  rem NOTE: values correspond to "SERVICE_STATUS.dwCurrentState"
  rem https://msdn.Microsoft.com/en-us/library/windows/desktop/ms685996(v=vs.85).aspx
  if not %SERVICE_STATE%==4 (
    echo WARNING: service is not running
    rem TODO: perform desired operation
    rem net start "%TARGET_SERVICE%"
  ) else (
    echo INFORMATION: service is running
  )
)

Testé avec:

  • Windows XP (32 bits) anglais
  • Windows 10 (32 bits) espagnol
  • Windows 10 (64 bits) anglais
0
Helder Magalhães

Pour Windows Server 2012, voici ce qui a fonctionné pour moi. Remplacez uniquement "SERVICENAME" par le nom de service actuel:

@ECHO OFF

SET SvcName = NOM DE SERVIC

SC QUERYEX "% SvcName%" | TROUVER "ÉTAT" | FIND/v "RUNNING"> NUL && (ECHO% SvcName% n'est pas en cours d'exécution ECHO START% SvcName%

NET START "%SvcName%" > NUL || (
    ECHO "%SvcName%" wont start 
    EXIT /B 1
)
ECHO "%SvcName%" is started
EXIT /B 0

) || (ECHO "% SvcName%" est en cours d'exécution EXIT/B 0)

0
Magige Daniel

Peut-être une manière beaucoup plus simple? Il suffit d'ajouter à la liste des réponses ici:

@for /f "tokens=1,* delims=: " %%a in ('sc queryex state=Inactive') do net start "%%b"
0
Gerhard Barnard
@Echo off

Set ServiceName=wampapache64

SC queryex "%ServiceName%"|Find "STATE"|Find /v "RUNNING">Nul&&(

echo %ServiceName% not running
echo  

Net start "%ServiceName%"


    SC queryex "%ServiceName%"|Find "STATE"|Find /v "RUNNING">Nul&&(
        Echo "%ServiceName%" wont start
    )
        echo "%ServiceName%" started

)||(
    echo "%ServiceName%" was working and stopping
    echo  

    Net stop "%ServiceName%"

)


pause
0
Aylian Craspa