2017-07-03 4 views
0

J'essaye de faire un script qui fonctionnera constamment en arrière-plan. Son but est de détecter les lecteurs flash USB, les disques durs externes ou tout autre appareil inscriptible que vous connecteriez à votre ordinateur. Une fois qu'il en a détecté un, il copiera un fichier à la racine de ce périphérique. Voici mon code (les lignes d'écho pour le débogage sont plus clairs):La variable de niveau d'erreur ne change pas après une erreur ..?

@echo off 
:loop 
for /F "tokens=1*" %%a in ('fsutil fsinfo drives') do (
    for %%c in (%%b) do (
     for /F "tokens=4" %%d in ('fsutil fsinfo drivetype %%c') do (
      if %%d equ amovible (
       echo Found out that %%c is removable. Trying to echo the content... 
       dir %%c >NUL 
       echo Error: %errorlevel% 
       if %errorlevel%==0 (
        echo Errorlevel is 0! Copying... 
        if not exist %%c\test.txt (
         copy .\test.txt %%c\test.txt 
         echo. 
        ) 
       ) else (
        echo Errorlevel isn't 0. Looks like the drive isn't here, or is unavailable. Aborting copying... 
        echo. 
       ) 
      ) 
     ) 
    ) 
) 
TIMEOUT 2 
goto :loop 

Et est là le problème. La condition "if% errorlevel% == 0" est supposée vérifier si la commande "dir %% c> NUL" a réussi, donc si errorlevel est 0, cela signifie qu'il y a un système de fichiers sur l'appareil, et ce n'est pas comme une carte vide lecteur ou un lecteur de disquette vide. La chose est quand j'exécute mon code, errorlevel est toujours 0, et je ne peux pas comprendre pourquoi ("echo Error:% errorlevel%" le dit). Donc, le fichier test.txt copie sur mon lecteur flash USB, donc cela fonctionne essentiellement, la chose est quand il s'agit de copier le fichier sur mon lecteur de disquette, une boîte d'erreur apparaît, disant que je devrais insérer un périphérique dans le lecteur , c'est pourquoi je veux faire ce contrôle errorlevel. Donc, si quelqu'un a une solution, s'il vous plaît, aidez-moi, je suis vraiment coincé. Merci d'avance.

+1

vous devez utiliser [expansion retardée] (http://ss64.com/nt/delayedexpansion.html) ('' ErrorLevel), parce que sinon, vous obtenez le 'ErrorLevel'! présent lorsque le bloc entier entre parenthèses (boucle) est analysé ... – aschipfl

+0

Whoaaw, merci l'homme! Travaillé comme un charme! – Alpha

+1

Vous pouvez bien sûr utiliser le classique 'if not errorlevel 1 ...' qui ne nécessite pas d'extension retardée. – LotPings

Répondre

2

Vous devez utiliser delayed expansion (!ErrorLevel!), parce que sinon, vous obtenez la valeur ErrorLevel qui est présent lorsque le bloc entier parenthesised (qui est la structure de boucle for imbriquée ici) est analysé. Étant donné que les points d'exclamation sont consommés par la fonction d'expansion retardée, je l'activer que si elle est réellement nécessaire, comme ceci:

@echo off 
setlocal EnableExtensions DisableDelayedExpansion 
:loop 
for /F "tokens=1*" %%a in ('fsutil fsinfo drives') do (
    for %%c in (%%b) do (
     for /F "tokens=4" %%d in ('fsutil fsinfo drivetype %%c') do (
      if "%%d"=="amovible" (
       echo Found out that %%c is removable. Trying to echo the content... 
       dir "%%~c" > nul 
       setlocal EnableDelayedExpansion 
       echo Error: !ErrorLevel! 
       if !ErrorLevel! equ 0 (
        endlocal 
        echo ErrorLevel is 0! Copying... 
        if not exist "%%~c\test.txt" (
         copy ".\test.txt" "%%~c\test.txt" 
         echo/ 
        ) 
       ) else (
        endlocal 
        echo ErrorLevel isn't 0. Looks like the drive isn't here, or is unavailable. Aborting copying... 
        echo/ 
       ) 
      ) 
     ) 
    ) 
) 
timeout 2 
goto :loop 
endlocal 

Sinon, depuis dir ne jamais mis ErrorLevel à une valeur négative, vous pouvez également utiliser la if not errorlevel 1 syntax, ce qui signifie « sinon ErrorLevel est supérieur ou égal à 1 », et donc « si ErrorLevel est inférieur à 1 » (apparemment, vous ne pouvez pas l'écho de la valeur réelle ErrorLevel alors):

   ... 
       dir "%%~c" > nul 
       if not ErrorLevel 1 (
        echo ErrorLevel is 0! Copying... 
        if not exist "%%~c\test.txt" (
         copy ".\test.txt" "%%~c\test.txt" 
         echo/ 
        ) 
       ) else (
        echo ErrorLevel isn't 0. Looks like the drive isn't here, or is unavailable. Aborting copying... 
        echo/ 
       ) 
       ... 

Une autre méthode consiste à utiliser le conditional execution operators && and/or ||, qui permet d'exécuter la commande ou le bloc suivant uniquement si la commande précédente renvoie un code de sortie nul (la plupart du temps, et également pour la commande dir ici, le code de sortie est la même valeur comme ErrorLevel):

   ... 
       dir "%%~c" > nul && (
        echo ErrorLevel is 0! Copying... 
        if not exist "%%~c\test.txt" (
         copy ".\test.txt" "%%~c\test.txt" 
         echo/ 
        ) 
       ) || (
        echo ErrorLevel isn't 0. Looks like the drive isn't here, or is unavailable. Aborting copying... 
        echo/ 
       ) 
       ... 
+0

+1 pour la très bonne réponse Je ne comprends pas pourquoi les gens utilisent' if% ERRORLEVEL % == 0' ou dans un bloc de commande 'if! ERRORLEVEL!== 0' au lieu de 'sinon errorlevel 1' pour tester le code de sortie de la commande/application précédente exécutée étant 0 (ou négatif) car la méthode ne développant pas la variable d'environnement fonctionne depuis MS-DOS et pour laquelle Microsoft a même écrit un support article il y a plusieurs années, voir [Test d'un niveau d'erreur spécifique dans les fichiers batch] (https://support.microsoft.com/en-us/kb/69576). – Mofi

+0

Merci, @Mofi! Oui, je suis tout à fait d'accord, je pense que la syntaxe 'if ErrorLevel' existait avant même que la pseudo-variable'% ErrorLevel% 'ait été introduite; de toute façon, les gens semblent être encore confus par cette syntaxe; Je crois qu'ils rencontrent des problèmes en interprétant mal "si ErrorLevel 1" comme "si' ErrorLevel' est égal à "1'" plutôt que "si' ErrorLevel' est supérieur ou égal à "1'", donc ils préfèrent les variantes les plus évidentes ' if% ErrorLevel% equ 1', etc ... – aschipfl

+0

+ aschipfl Ooooh, c'est "supérieur ou égal" ?? Je ne le savais pas! Je pensais que c'était juste "est égal à", merci pour le tip man ^^! – Alpha