2014-09-26 195 views
1

我想根據傳入的命令行參數在DOS批處理文件中執行一些操作。
該批次應使用任意數量的參數進行調用。可能的參數應爲(在最好的情況下可擴展):批處理:檢查批處理文件中的命令行參數

UPDATE [-verbose [outputFileName]] [-validate] [/?] 

此外,它應該可以以任意順序進入PARAMS。 尤其是參數-verbose有意義:如果給出以下參數'parameterParam'必須是outputfilename的名稱或可以是空的。注意參數有一個前導「 - 」。參數參數的參數沒有前導「 - 」。
例如:

UPDATE -verbose -validate 

應STDOUT(-verbose)顯示的執行步驟和驗證輸入。

UPDATE -verbose outputFileName.txt -validate 

應登錄的執行步驟到名爲<outputFilename.txt>(-verbose outputFileName.txt)文件和驗證輸入。

UPDATE -validate 

只應驗證輸入。

UPDATE -validate -verbose 

應做同樣的

UPDATE -verbose -validate 

UPDATE /? 

應顯示如何使用update.bat

我怎麼能這樣做?用FOR循環遍歷命令行參數?但是如何?我能夠迭代參數,但是如果找到-verbose,我怎樣才能預覽下面的參數來檢查是否提供了文件名?

根據所提供的參數,具體的行動應該發生(從不同批次的...) 我想通過java調用LiquiBase:

進行驗證:

java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info validate 
java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info validate 

對於離線SQL代:

java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info updateSQL > update_%_outputfilename% 
java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info updateSQL > viewsAndSP_%_outputfilename% 
+2

你是否正在使用DOS?或'cmd.exe'? – paxdiablo 2014-09-26 13:13:23

+0

我有一個名爲update.bat的文件,我想讓它在命令行工具中的Windows機器上運行。 – 2014-09-26 13:20:16

+0

然後,這將是'cmd.exe',我會更改標籤。 – paxdiablo 2014-09-26 13:26:53

回答

1
@echo off 

setlocal enableDelayedExpansion 
set "_verbose=no" 
set "_validate=no" 
set "_outputfilename=" 
rem set "arg_counter=0" 
set "_check_next=no" 

if "%~1" equ "/?" call :help 

for %%a in (%*) do (


    if "!_check_next!" equ "yes" (
     set "_check_next=no" 
     set "arg=%%~a" 

     if "!arg:~0,1!" neq "-" (
      set "_outputfilename=%%~a" 
     ) else (
      if "%%~a" equ "-validate" (
       set "_validate=yes" 
      ) 
     ) 
    ) 

    rem if "%%~a" equ "/?" call :help 

    if "%%~a" equ "-verbose" (
     set "_check_next=yes" 
     set "_verbose=yes" 
    ) 

    if "%%~a" equ "-validate" (
     set "_validate=yes" 
    ) 

) 

echo --%_validate%--%_verbose%--%_outputfilename%-- 

endlocal 
exit /b 0 

:help 

    echo %~0 [-verbose [outputFileName]] [-validate] [/?] 
    echo some explanations 

exit /b 0 

的順序參數不是必需的。不確定可擴展性如何,但即使在「嚴重」的編程語言中,arg檢查代碼也總是冗長。

+0

這樣我得到有關ECHO的消息... ECHO [ON | OFF]。我怎樣才能防止呢? 您的解決方案填充了一些變量。我如何使用它們?我想根據參數調用相應的程序。我可以在循環內調用像prog1這樣的標籤嗎?執行後循環會繼續嗎?或者我必須在循環檢查變量值並啓動程序之後放置一些IF?它不適合我。 – 2014-09-26 17:29:37

+0

@ du-it因爲沒有提供這些信息,所以我無法知道要調用哪些程序,具體取決於參數。最好是檢查變量並調用所需的程序。 Betrer提供更多信息,因爲您的問題範圍僅涉及解析 – npocmaka 2014-09-26 17:43:35

+0

請參閱我的擴展問題。在沒有任何命令行命令的情況下運行java命令就可以工作。 – 2014-09-26 18:10:27

1

我終於明白了。這是基於npocmaka的有用的代碼我的解決方案:

call _set-env.bat 

@echo off 

setlocal enableDelayedExpansion 
set argC=0 
for %%x in (%*) do Set /A argC+=1 

set "_verbose=no" 
set "_validate=no" 
set "_outputfilename=" 
set "_check_next=no" 
set "_sandbox=no" 

if "%~1" equ "/?" goto :help 

if %argC% == 1 (
    if "%~1" equ "-sandbox" (
     echo. 
     echo Running UPDATE with just -sandbox option does not do anything. 
     echo Run UPDATE /? for usage. 
     :: call :help 
     goto :eof 
    ) 
) 

for %%a in (%*) do (

    if "!_check_next!" equ "yes" (
     set "_check_next=no" 
     set "arg=%%~a" 

     if "!arg:~0,1!" neq "-" (
      set "_outputfilename=%%~a" 
     ) else (
      if "%%~a" equ "-validate" (
       set "_validate=yes" 
      ) 
     ) 
    ) 

    if "%%~a" equ "-verbose" (
     set "_check_next=yes" 
     set "_verbose=yes" 
    ) 

    if "%%~a" equ "-validate" (
     set "_validate=yes" 
    ) 

    if "%%~a" equ "-sandbox" (
     set "_sandbox=yes" 
    ) 
) 

if %_validate% equ yes (
    call :validateUpdate 
    echo !errorlevel! 
    if !errorlevel! neq 0 exit /b !errorlevel! 
) 
if "yes" equ "%_verbose%" (
    if "%_outputfilename%" neq "" (
     call :verboseUpdateToFile 
    ) else (
     call :verboseUpdate 
    ) 
    if !errorlevel! neq 0 exit /b !errorlevel! 
) 
if "no" equ "%_sandbox%" (
    call :update 
) 

:: echo --%_validate%--%_verbose%--%_outputfilename%-- 
exit /b 0 

:help 
    ::echo %~0 [-verbose [outputFileName]] [-validate] [/?] 
    @echo Executes LiquiBase changesets to take effect on the database. 
    @echo. 
    @echo UPDATE [-verbose [outputFileName]] [-validate] [/?] 
    @echo. /?    Shows this help. 
    @echo -validate  Validates the changesets without executing them. 
    @echo -verbose  Prints output of the generated SQL without executing them 
    @echo. 
    goto :eof 

:validateUpdate 
    java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info validate 
    :: java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info validate 
    goto :eof 

:verboseUpdate 
    java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info updateSQL 
    java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info updateSQL 
    goto :eof 

:verboseUpdateToFile 
    java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info updateSQL > update_"%_outputfilename%" 
    java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info updateSQL > viewsAndSP_"%_outputfilename%" 
    goto :eof 

:update 
@echo update... 
rem java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-update.xml --logLevel=info update 
rem java -jar %LIQUIBASE_EXEC% --changeLogFile=../changesets/changelog-views-and-sp.xml --logLevel=info update 

endlocal 
exit /b 0 

有一點仍不清楚: 比方說:validateUpdate執行和驗證錯誤發生了,LiquiBase打印出「Liquibase‘驗證’成功」和ERRORLEVEL是0。這是因爲LiquiBase打印出一個驗證錯誤發生,但退出本身0,因此ERRORLEVEL爲0? 這意味着我無法處理這種驗證錯誤。 我打算在標籤上運行代碼:僅在沒有錯誤發生時更新。