Подтвердить что ты не робот

Пропустить путь с пробелами в качестве параметра в файл bat

У меня есть простая bat script, которая копирует файлы из известного каталога в каталог, заданный пользователем. Как передать путь (он может содержать пробелы) на мой script и использовать его с помощью команды 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
    )

Если я просто вызываю script, я получаю следующую ошибку:

C:\Projects\Setup>install.cmd "C:\program files (x86)"

-----------------
SETUP SCRIPT
-----------------

files was unexpected at this time.
C:\Projects\Setup>
4b9b3361

Ответ 1

Интересный. Мне нравится собирать цитаты о обработке кавычек в команде cmd/.

Ваши конкретные скрипты фиксируются с помощью% 1 вместо "% 1"!!!

Добавив "echo on" (или избавившись от эха), вы могли бы легко найти это.

Ответ 2

Используйте "%~1". %~1 только удаляет окружающие кавычки. Однако, поскольку вы не можете знать, имеет ли входной параметр %1 кавычки или нет, вы должны убедиться, что "%~1" уверены, что они добавлены. Это особенно полезно при объединении переменных, например. convert.exe "%~1.input" "%~1.output"

Литература:

Ответ 3

Я думаю, что проблема с OP заключалась в том, что он хочет сделать ОБА из следующего:

  • Передайте параметр, который может содержать пробелы
  • Проверьте, отсутствует ли параметр

Как упоминалось несколькими плакатами, чтобы передать параметр, содержащий пробелы, вы должны окружить фактическое значение параметра двойными кавычками.

Чтобы проверить, отсутствует ли параметр, метод, который я всегда изучал, был:

if "%1" == ""

Однако, если фактический параметр указан (как и должно быть, если значение содержит пробелы), это становится

if ""actual parameter value"" == ""

который вызывает "неожиданную" ошибку. Если вы используете

if %1 == ""

тогда ошибка больше не возникает для цитируемых значений. Но в этом случае тест больше не работает, когда значение отсутствует - оно становится

if  == ""

Чтобы исправить это, используйте любые другие символы (кроме символов со специальным значением для DOS) вместо кавычек в тесте:

if [%1] == []
if .%1. == ..
if abc%1xyz == abcxyz

Ответ 4

Если у вас есть путь с пробелами, вы должны окружить его кавычками (").

Не уверен, что именно это вы спрашиваете?

Ответ 5

"% ~ 1" будет работать большую часть времени. Однако есть несколько вещей, которые вам нужно отметить для этого:

  • Он не поддерживается в Windows NT 4.0. Вам нужна Windows 2000 или новее. (Если вы кодируете script, совместимый со старой ОС, будьте осторожны.)
  • Он не делает параметры безопасными и дезинфицированными. Мое замечание состоит в том, что в сценариях CMD нет не правильно деактивировать аргументы командной строки.

Чтобы продемонстрировать вторую точку, позвольте мне привести пример:

REM example.cmd
ECHO %~1

Выполнить с example.cmd dummy^&DIR. Амперсанд скрывается здесь (^&), чтобы интерпретировать интерпретатор оболочки как разделитель команд, чтобы он стал частью аргумента, переданного в script. DIR интерпретируется как команда внутри суб-оболочки, запускающей script, где он не должен.

Цитата: это может сработать некоторое время, но все еще небезопасно:

REM example2.cmd
SETLOCAL EnableExtensions EnableDelayedExpansion
SET "arg1=%~1"
ECHO "%~1"
ECHO !arg1:"=!

example2.cmd foo^"^&DIR^&^"bar сломает его. Команда DIR будет запускаться два раза, один сразу после SET, а другой сразу после первого ECHO. Вы видите, что "%~1", который, по вашему мнению, имеет котировку, хорошо не сортируется самим аргументом.

Таким образом, невозможно обеспечить безопасный анализ аргументов.

(EDIT: EnableDelayedExpansion также не работает в Windows NT 4. Благодаря информации здесь: http://www.robvanderwoude.com/local.php)

Ответ 6

@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"", что означает:

  • 'пустая строка' (""),
  • а затем 'c:\Program',
  • а затем "неожиданно здесь" "Файлы\xxx",
  • за которым следует пустая строка ("")

Обратите внимание, что если вам нужно использовать PWA_PATH в вашем предложении IF, вам нужно указать if as !PWA_PATH! (следовательно, enabledelayedexpansion в качестве начала script)

Ответ 7

Если ваш путь содержит пробел, попробуйте использовать %~s1. Это удалит пространство и добавит ~1 к вашему пути, и, что более важно, это относится к абсолютному пути вашего файла. Попробуйте использовать его.