Возникли проблемы с сохранением вывода wmic csproduct get vendor / format: list | findstr / c = как переменная

Спасибо, что ответили на мой вопрос. Я пытаюсь:

  • получить вывод wmic-запроса в переменную

Вот некоторая справочная информация о том, почему мне нужно это сделать. Моя работа требует, чтобы на ноутбуках и планшетах, оснащенных веб-камерами, они были отключены в BIOS.

Теперь, когда мы работаем удаленно, нам необходимо включить веб-камеры в BIOS.

Мы есть инструменты, которые можно использовать для включения функций BIOS во время работы системы.

Я хочу написать сценарий, который будет выполнять psexec в машине, извлекать информацию о поставщике и сохранять ее в переменной, к которой можно будет получить доступ позже в сценарии после выхода psexec.

Я могу написать остальную часть своего сценария без проблем Я думаю, однако мне сложно понять, как сохранить результаты следующей команды в переменной:

wmic csproduct get vendor /format:list | findstr/c=

Например, вывод этой команды на моем компьютере:

Vendor=Dell Inc.



Я хочу захватить вывод и сохранить его в переменной для дальнейшего использования в сценарии, который я буду писать, чтобы я мог обрабатывать манипуляции с BIOS, специфичные для поставщика.

Я пробовал
set sysvend=wmic csproduct get vendor /format:list | findstr/c=
Но когда я повторяю %sysvend%, чтобы увидеть, сработало ли это, я получаю вместо того, что хотел:
wmic csproduct get vendor /format:list | findstr/c=

Если кто-нибудь знает, как это сделать, я был бы очень признателен за помощь. Я открыт для других альтернатив для определения поставщика.


person Proximus    schedule 19.05.2020    source источник


Ответы (4)


Даже проще, чем использовать find или findstr и без проблемных 0x0D0D0A окончаний строк:

@Echo Off & SetLocal EnableExtensions
For /F Tokens^=6Delims^=^" %%G In (
    '%__APPDIR__%wbem\WMIC.exe CSProduct Get Vendor /Format:MOF 2^>NUL'
) Do Set "vendor=%%G"

Это решение также предотвращает нежелательные завершающие символы в строке имени поставщика, которые могут быть обычным явлением.

person Compo    schedule 19.05.2020

Существует известная wmic ошибка, поэтому вам нужно проанализировать wmic вывод, используя два вложенных цикла, например следующее:

FOR /F "tokens=1* delims==" %%s IN ('
    wmic csproduct get vendor /value ^| find "="
') DO for /F "tokens=*" %%i in ("%%t") do SET "vendor=%%i"

Здесь for петли

  • %%s, чтобы получить значение vendor;
  • %%i, чтобы удалить завершающий возврат каретки в возвращаемом значении (поведение wmic): каждая строка вывода заканчивается 0x0D0D0A (CR + CR + LF) вместо обычного 0x0D0A (CR + LF).

См. WMIC и FOR /F: Исправление для завершающего <CR> проблема

person JosefZ    schedule 19.05.2020
comment
Что ж, я бы не назвал это ошибкой wmic, потому что на самом деле это происходит при использовании for /F для преобразования вывода Unicode в ASCII / ANSI. В любом случае, вам не нужен find "=", когда у вас есть две for /F петли. Самый общий метод - использовать "delims=" для внешнего цикла и "tokens=1* delims==" для внутреннего, чтобы избежать проблем в случае, если в значении есть начальные пробелы (хотя это маловероятно); но это все равно потеряло бы ведущие =-знаки (хотя даже маловероятно) ... - person aschipfl; 19.05.2020

Ответ опубликован, чтобы продемонстрировать, что команда может быть назначена и выполнена как переменная, в отличие от ответа Neko, в соответствии с вопросом OP.

@Echo Off
Set Get.Vendor=^>"%TEMP%\Vendor.log" (wmic csproduct get vendor /value ^| 
findstr /c:=) ^&^& (For /F "UsebackQ Tokens=2* Delims==^EOL" %%A In ("%TEMP%\Vendor.log") Do For /F "Delims=" %%T In ("%%A") Do Set "Vendor=%%~T") ^&^& Echo.!Vendor!
Setlocal EnableDelayedExpansion
%Get.Vendor%
pause
person T3RR0R    schedule 19.05.2020

Использование for %%i in (wmic csproduct get vendor /format:list ^| findstr/c=) do (set var=%%~I) Это означает, что переменная цикла for %%i становится выходом команды в цикле for, что позволяет вам установить другую переменную, переменную цикла for. Вам нужна вставка (^) перед | в цикле for, поскольку в противном случае команда выйдет из цикла for и не будет выполняться в цикле for. Вы также можете просто заключить команду в двойные кавычки ("), и вам не нужно будет экранировать конвейер. В результате выполнения команды %var% станет равным результату вашей команды wmic.

Последняя команда будет такой:

@echo off
for /f "tokens=* delims==" %%i in (' wmic csproduct get vendor /format:list ^| findstr /c:"=" ') do (set var=%%~i)
echo %var%
rem echoing var to make sure the variable is what you wanted

Вывод для меня:

Vendor=Microsoft Corporation

Если вы хотите, чтобы результат был конкретно Microsoft Corporation, вы можете добавить:

set var=%var:~7%

чтобы удалить первые 7 символов. Вы также можете изменить токены на 2* вместо *. :

for /f "tokens=2* delims==" %%j in (' wmic csproduct get vendor /format:list ^| findstr /c:"=" ') do (set var=%%~j)

Выходы:

Microsoft Corporation

Примечания:

В пакетных файлах, в отличие от PowerShell, вы не можете установить переменную как команду и сделать ее выходом, поэтому обычный способ установить выход команды в переменную использует цикл for. Кроме того, просто предпочтение, я бы предложил использовать переключатель /value, а не /format:list.

Проверено и у меня работает

person Nico Nekoru    schedule 19.05.2020
comment
Что касается невозможности установить переменную в качестве команды и сделать ее / сгенерировать вывод, вы ошибаетесь. Пакетные макросы могут облегчить это, однако это более сложно и требует более высокого уровня понимания пакетных сценариев для создания таких макросов. Кроме того, обстоятельства, при которых это уместно, в некоторой степени являются нишевыми. - person T3RR0R; 19.05.2020
comment
Извините, Neko, но ваш опубликованный вывод невозможен из вашего опубликованного решения. Ваш результат будет Vendor=Microsoft. Ваша переменная %var% будет содержать следующую строку Vendor=Microsoft, и я уверен, что OP хотел бы, чтобы она содержала, в данном случае Microsoft Corporation. - person Compo; 19.05.2020
comment
@Compo Почему это невозможно? У меня это сработало, есть ли на вашем компьютере определенные настройки, которые не позволяют это сделать? Или это что-то или мой компьютер? - person Nico Nekoru; 19.05.2020
comment
Ничего подобного, я нашел ошибку, отредактировал и теперь работает - person Nico Nekoru; 19.05.2020
comment
@NekoMusume, извините, но это все равно неверно. Содержимое вашей переменной по-прежнему будет Vendor=Microsoft Corporation, вам нужно изменить tokens=* на Tokens=1*, а затем использовать %%j для значения переменной вместо %%i. - person Compo; 19.05.2020
comment
Была ли переменная Vendor=Microsoft Corporation не предназначена? - person Nico Nekoru; 19.05.2020
comment
Что ж, @NekoMusume, только OP может ответить на это, но обычно, особенно с переменной, названной с использованием известного имени, не было бы необходимости, чтобы строковое значение также содержало часть Vendor=. - person Compo; 19.05.2020
comment
Понятно, я тоже добавлю ваше предложение в другой раздел - person Nico Nekoru; 19.05.2020
comment
Позвольте нам продолжить это обсуждение в чате. - person Nico Nekoru; 19.05.2020
comment
Что касается вашего последнего редактирования, @NekoMusume, я не предлагал 2*. Также, используя ваш пример, если строка поставщика включает символ =, она не будет захватывать всю строку, только до включенного =, все остальное после = будет присвоено %%k. - person Compo; 20.05.2020
comment
Это сработало для меня, и я не думаю, что *1 работает для моего цикла for - person Nico Nekoru; 20.05.2020
comment
vendor - 6 символов, = - 1 - person Nico Nekoru; 20.05.2020
comment
Я не набирал и не предлагал *1, @NekoMusume, прочтите снова мой комментарий! - person Compo; 20.05.2020
comment
@Compo Я изменил его, так что в нем не говорится, что вы это предлагали. Попробуйте мой точный код, 1* токен не работает - person Nico Nekoru; 20.05.2020
comment
@NekoMusume, я не верю, что for /f "tokens=2* delims==" %%j in (' wmic csproduct get vendor /format:list ^| findstr /c:"=" ') do (set var=%%~j) работает для вас, но мое предложение с вашей переменной теперь изменено с %%i на %%j, for /f "tokens=1* delims==" %%j in (' wmic csproduct get vendor /format:list ^| findstr /c:"=" ') do (set var=%%~k) изначально не определяет переменную с тем же содержимым, только без возможного удаления любого строкового значения, содержащего = характер и следующие за ним .. - person Compo; 20.05.2020