既知のディレクトリからユーザーが指定したディレクトリにファイルをコピーする単純なバットスクリプトがあります。スクリプトにパス(スペースが含まれている場合があります)を渡してxcopyコマンドで使用するにはどうすればよいですか?
私のコードには次のものがあります
:READ_PWA_PATH
if "%1" == "" (
rem Set default path
set PWA_PATH="C:\Program Files\PWA"
rem
echo You have not specified your PWA url.
echo Default will be assumed: C:\Program Files\PWA.
choice /C:YN /M:"Do you wish to continue [Y] or cancel the script [N]?"
IF ERRORLEVEL ==2 GOTO CANCEL
IF ERRORLEVEL ==1 GOTO READ_WSS_SERVER_EXTENSIONS_PATH
GOTO END
) else (
set PWA_PATH=%1
)
単にスクリプトを呼び出すと、次のエラーが表示されます。
C:\Projects\Setup>install.cmd "C:\program files (x86)"
-----------------
SETUP SCRIPT
-----------------
files was unexpected at this time.
C:\Projects\Setup>
興味深いもの。 cmd/commandでの引用符の処理に関する引用符の収集が大好きです。
特定のスクリプトは、「%1」の代わりに%1を使用して修正されます!!!
「エコーオン」を追加する(またはエコーオフを取り除く)ことで、簡単にそれを見つけることができます。
つかいます "%~1"
。 %~1
単独で周囲の引用符を削除します。ただし、入力パラメータ%1
に引用符があるかどうかは、"%~1"
確実に追加されること。これは、変数を連結するときに特に役立ちます。 convert.exe "%~1.input" "%~1.output"
「%〜1」はほとんどの場合機能します。ただし、このために注意しなければならないことがいくつかあります。
2番目のポイントを示すために、例を挙げましょう。
REM example.cmd
ECHO %~1
example.cmd dummy^&DIR
で実行します。アンパーサンドはここでエスケープされ(^&
)、シェルがコマンド区切り文字として解釈されないようにし、スクリプトに渡される引数の一部になります。 DIRはコマンドとして解釈されますスクリプトを実行しているサブシェルの内部。
それを引用することはしばらくは働くかもしれないが、それでも安全ではない
REM example2.cmd
SETLOCAL EnableExtensions EnableDelayedExpansion
SET "arg1=%~1"
ECHO "%~1"
ECHO !arg1:"=!
example2.cmd foo^"^&DIR^&^"bar
はそれを壊します。 DIRコマンドは、SETの直後と最初のECHOの直後の2回実行されます。引用符で囲まれていると思われる"%~1"
は、引数自体によって引用符で囲まれていないことがわかります。
そのため、解析引数を安全にする方法はありません。
(編集:EnableDelayedExpansion
はWindows NT 4でも機能しません。ここの情報のおかげで: http://www.robvanderwoude.com/local.php )
パスにスペースが含まれている場合は、引用符( ")で囲む必要があります。
それがまさにあなたが求めているものかどうかはわかりませんか?
@echo off
setlocal enableextensions enabledelayedexpansion
if %1=="" (
rem Set default path
set PWA_PATH="C:\Program Files\PWA"
rem
echo You have not specified your PWA url.
echo Default will be assumed: C:\Program Files\PWA.
choice /C:YN /M:"Do you wish to continue [Y] or cancel the script [N]?"
IF ERRORLEVEL ==2 GOTO CANCEL
IF ERRORLEVEL ==1 GOTO READ_WSS_SERVER_EXTENSIONS_PATH
GOTO END
) else (
set PWA_PATH=%1
@echo !PWA_PATH! vs. %1
goto end
)
:READ_WSS_SERVER_EXTENSIONS_PATH
echo ok
goto end
:CANCEL
echo cancelled
:end
echo. final %PWA_PATH% vs. %1
VardhanDotNet が言及しているように、%1
で十分です。
"%1%"
は、引用符を囲む引用符を追加します:""c:\Program Files\xxx""
""
)、""
)ただし、IF
句内でPWA_PATH
を使用する必要がある場合は、!PWA_PATH!
として参照する必要があります(したがって、enabledelayedexpansion
をスクリプトの先頭として)
パスにスペースが含まれている場合は、%~s1
を使用してみてください。これにより、スペースが削除され、~1
がパスに追加されます。さらに重要なことは、ファイルの絶対パスを指します。使ってみてください。