Компьютерный форум OSzone.net  

Компьютерный форум OSzone.net (http://forum.oszone.net/index.php)
-   Скриптовые языки администрирования Windows (http://forum.oszone.net/forumdisplay.php?f=102)
-   -   Bat поиск строчки в xml файле закодированого pbase64 (http://forum.oszone.net/showthread.php?t=333079)

ivsh01 09-02-2018 16:36 2797005

Bat поиск строчки в xml файле закодированого pbase64
 
Привет, Ребята!

Помогите решить задачку.

Есть файл такого вида (он в одну строчку):

<?xml version="1.0" encoding="windows-1251"?><ТК xmlns="urn:sss" ОтправительТК="dd" ПолучательТК="dd" ИмяЗадачи="dd" ДатаВремяТК="2018-02-01T15:41:29" УникИдТК="00000000-0000-0000-0000-000000000000"><ДанныеТК ИдДанныхТК="1"><ЭС Содержит="ИЭС1" ФорматЭС="XML" ШифрованиеЭС="Нет" ИмяФайлаЭС="_ies1.xml" КодЭС="0403203" ВидОрг="ТУ" КодОрг="45" УникИдЭС="00000000-0000-0000-0000-000000000000">PD94bWwgdmVycTEST7uvK7u3y8O7r/TEsSTyAvPjwvyN3RMT4=</ЭС><КА УстановленКА="ddddd">bzBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBAAA=</КА><Регистрация ПредставленВ="" ОтправительИсхТК="" ДатаВремяРегистрИсхТК="2" СпособПредставления="TTT" УникИдИсхТК="00000000-0000-0000-0000-000000000000" ИдДанныхИсхТК="1" /></ДанныеТК><КА УстановленКА="ddd">bzBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB AAA=</КА></ТК>

Нужно:

Извлечь значение из тега ЭС где он всегда будет начинаться с >PD и заканчиваться </ЭС> то есть получить вот эти символа: PD94bWwgdmVycTEST7uvK7u3y8O7r/TEsSTyAvPjwvyN3RMT4=

alpap 10-02-2018 01:34 2797102

Надеюсь здесь:
Цитата:

...ИдДанныхТК="1"> <ЭС Содержит="ИЭС1...
ошибка и пробела в реалии между > и < нет

Код:

@echo off
>nul chcp 1251
<"file.xml" set /p s=
for %%m in ("%s:><=" "%") do for /f "tokens=2 delims=><" %%a in ('echo "%%~m"^|find "</ЭС"') do echo %%a
>nul chcp 866
pause


ivsh01 12-02-2018 16:18 2797542

Цитата:

Цитата alpap
Надеюсь здесь:
Цитата:
...ИдДанныхТК="1"> <ЭС Содержит="ИЭС1...
ошибка и пробела в реалии между > и < нет »

Да конечно. там нет пробела!

Но вот что то на реальных данных значение обрезается :( Как это можно поправить?

<?xml version="1.0" encoding="windows-1251"?><ТК xmlns="urn:sss" ОтправительТК="dd" ПолучательТК="dd" ИмяЗадачи="dd" ДатаВремяТК="2018-02-01T15:41:29" УникИдТК="00000000-0000-0000-0000-000000000000"><ДанныеТК ИдДанныхТК="1"><ЭС Содержит="ИЭС1" ФорматЭС="XML" ШифрованиеЭС="Нет" ИмяФайлаЭС="_ies1.xml" КодЭС="0403203" ВидОрг="ТУ" КодОрг="45" УникИдЭС="00000000-0000-0000-0000-000000000000">PD94bWwgdmVyc2lvbj0iMS4wsFSDFSDFdfsdfsdf67dfgzd5g4gh46hsdLjEiINPt6OrI5Mjd0T0iMDAwMDAwM DMdsfkKDSFkSDFksdfkNUU4NTExQUYyRjhBIiDT7ejqyOTSyj0iMTNGNUJENjYtQjE2Ri00QjZGLTlFOUYtRTEzOUFCRDYwQkRFI iDI5MTg7e379dLKPSIxIj480OXq4s7d0SDK7uTU7vDs+z0iMDQwOTM1MCIgz+Xw6O7k6Pft7vHy/D0i5OXq4OTt4P8iIMLo5M7y9+Xy4D0i0eLu5O376SDu8vfl8iIgzvL3xODy4D0iMjAxOC0wMi0wMSIgwujkzvDjPSLKziIgyu7kz vDjPSI5MzciIM7K08Q9IjA0MDkzNTAiIM7KwNLOPSI0NSIgxODy4MLw5ez/1O7w7Ojw7uLgGFGFDFDGKJfksldjfSDKfjsdlkFDJSLKDFJSLD9gdfg9dfg9sg876fdg6dg5dfg9fdFDG&DE4LTAyLTAxVDE1OjU 3OjAzIiDE4Py4gdfzgFGFDGggdfgggsdfgsSDSDFSDFDSdgsdfgDgOjQ5OjE0IiDK7uTQ5efK7u3y8O7r/z0iMCIg0OXnyu7t8vDu6/89IvDg5+Tl6yDO3dEg7eUg8e7k5fDm6PIg7vjo4e7qIiDI5MTg7e379c7d0T0iMSI+PC/E4O3t++XO3dE+PC/I3dEyPg==</ЭС><КА УстановленКА="ddddd">bzBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBAAA=</КА><Регистрация ПредставленВ="" ОтправительИсхТК="" ДатаВремяРегистрИсхТК="2" СпособПредставления="TTT" УникИдИсхТК="00000000-0000-0000-0000-000000000000" ИдДанныхИсхТК="1" /></ДанныеТК><КА УстановленКА="ddd">bzBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB AAA=</КА></ТК>

alpap 13-02-2018 01:47 2797623

Цитата:

Цитата ivsh01
можно поправить? »

Код:

@echo off
>nul chcp 1251
<"file.xml" (for /f "delims=" %%a in ('find /v ""') do @set "s=%%a")
for %%m in ("%s:><=" "%") do for /f "tokens=2 delims=><" %%a in ('echo "%%~m"^|find "</ЭС"') do echo %%a
>nul chcp 866
pause


ivsh01 13-02-2018 10:09 2797642

Спасибо огромное! Прямо то, что нужно!!!

Только не пойму как этот код в крутить в цикл for когда файлов 100 штук с которыми нужно провести это манипуляцию.

на выходе получить тоже 100 файлов с этим содержимым

----
Следующее использование оператора пути при подстановке параметров
в пакетных файлах является недопустимым: %~m"^|find "</ЭС"') do echo %%a >> 11111.txt

alpap 13-02-2018 11:53 2797673

ivsh01,
во-первых все лучше делать в кодировке 866
во-вторых при уже текущих запросах, например:
Код:

@echo off
>nul chcp 1251
for /f "delims=" %%a in ('dir /a-d/b "Papka\*.xml"') do call :m "%%a" "%%~na_OUT.txt"
>nul chcp 866
pause& exit

:m
 <"%~1" (for /f "delims=" %%a in ('find /v ""') do @set "s=%%a")
 >"%~2" (for %%m in ("%s:><=" "%") do for /f "tokens=2 delims=><" %%a in ('echo "%%~m"^|find "</ЭС"') do @echo %%a)
exit /b

но вообще не для cmd задача, столкнетесь с проблемами и похлеще и спецсимволы и кодировки и концы строк и длина строки и главное скорость выполнения
попросите сделать на vbs/js или PowerShell

megaloman 13-02-2018 13:33 2797698

Цитата:

Цитата alpap
не для cmd задача, .... попросите сделать на vbs/js »

CMD+js. CMD сохранить в 866 кодировке
Код:

@set @E=1; /*
@Echo Off
cls

Set "FileIn=Z:\Box_In\У попа была собака.xml"
Set T1=">PD"
Set T2="</ЭС>"

FOR /F "usebackq delims=" %%s IN (`2^>nul Cscript //NoLogo /E:jscript "%~dpnx0" "%FileIn%" %T1% %T2%`) DO Set "String=%%s"

Echo %String%
Pause
GoTo :Eof
*/

var oArg = WScript.Arguments;
if (oArg.Count()<3) WScript.Quit(1);

var inFile,AllTxt;
var FSO=WScript.CreateObject("Scripting.FileSystemObject");

try {inFile=FSO.OpenTextFile(oArg(0),1)}
catch (err) {if (err != 0) {WScript.Echo(oArg(0)+" ErrorLevel=2: "+err.description);WScript.Quit(2)}}
AllTxt=inFile.ReadAll();
inFile.Close();

var i1=AllTxt.indexOf(oArg(1));    if(i1<0) {WScript.Echo(oArg(1)+" not found in  "+oArg(0)); WScript.Quit(2)}
var i2=AllTxt.indexOf(oArg(2),i1); if(i2<0) {WScript.Echo(oArg(2)+" not found in  "+oArg(0)); WScript.Quit(2)}

WScript.Echo(AllTxt.slice(i1+oArg(1).length,i2));
WScript.Quit(0);

Цитата:

Цитата ivsh01
Только не пойму как этот код в крутить в цикл for когда файлов 100 штук с которыми нужно провести это манипуляцию. на выходе получить тоже 100 файлов с этим содержимым »

Если делать из ста файлов *.xml txt-файлы c тем же именем
Код:

@set @E=1; /*
@Echo Off
cls

Set "FileIn=Z:\Box_In\*.xml"
Set T1=">PD"
Set T2="</ЭС>"

FOR %%f IN ("%FileIn%") DO Echo %%f &Cscript //NoLogo /E:jscript "%~dpnx0" "%%f" %T1% %T2% "%%~dpnf.txt"

Pause
GoTo :Eof

Echo %String%
Pause
GoTo :Eof
*/

var oArg = WScript.Arguments;
if (oArg.Count()<4) WScript.Quit(1);

var inFile,AllTxt;
var FSO=WScript.CreateObject("Scripting.FileSystemObject");

try {inFile=FSO.OpenTextFile(oArg(0),1)}
catch (err) {if (err != 0) {WScript.Echo(oArg(0)+" ErrorLevel=2: "+err.description);WScript.Quit(2)}}
AllTxt=inFile.ReadAll();
inFile.Close();

var i1=AllTxt.indexOf(oArg(1));    if(i1<0) {WScript.Echo(oArg(1)+" not found in  "+oArg(0)); WScript.Quit(2)}
var i2=AllTxt.indexOf(oArg(2),i1); if(i2<0) {WScript.Echo(oArg(2)+" not found in  "+oArg(0)); WScript.Quit(2)}

//WScript.Echo(AllTxt.slice(i1+oArg(1).length,i2));

try {inFile=FSO.OpenTextFile(oArg(3),2,true)}
catch (err) {if (err != 0) {WScript.Echo(oArg(3)+" ErrorLevel=3: "+err.description);WScript.Quit(3)}}
inFile.Write(AllTxt.slice(i1+oArg(1).length,i2));
inFile.Close();
WScript.Quit(0);


gf100 23-03-2018 10:37 2804968

Пытаюсь приспособить скрипт к своему случаю, но туплю.
Прошу помочь:
есть XML в одну строку, длина файла может достигать 100к, в первых 200 символах есть подстрока (атрибут) EDate="2017-03-22", перед ней и после пробелы. Надо достать значение "2017-03-22" и положить этот файл в архив с таким именем.

вариант из этого поста не проходит по причине длины файла.

megaloman 23-03-2018 11:34 2804975

gf100,
Попробуйте эдак
Код:

@set @E=1; /*
@Echo Off
cls

Set "FileIn=Z:\Box_In\*.xml"
Set T1=" EDate="
Set T2=" "

FOR %%f IN ("%FileIn%") DO (
        FOR /F "usebackq delims=" %%s IN (`2^>nul Cscript //NoLogo /E:jscript "%~dpnx0" "%%~f" %T1% %T2%`) DO Call :Arhivator "%%~f" "%%~s"
)
Pause
GoTo :Eof

:Arhivator
        Echo %1 %~2
GoTo :Eof
*/

var oArg = WScript.Arguments;
if (oArg.Count()<3) WScript.Quit(1);

var inFile,AllTxt;
var FSO=WScript.CreateObject("Scripting.FileSystemObject");

try {inFile=FSO.OpenTextFile(oArg(0),1)}
catch (err) {if (err != 0) {WScript.Echo(oArg(0)+" ErrorLevel=2: "+err.description);WScript.Quit(2)}}
AllTxt=inFile.ReadAll();
inFile.Close();

var i1=AllTxt.indexOf(oArg(1));    if(i1<0) {WScript.Echo(oArg(1)+" not found in  "+oArg(0)); WScript.Quit(2)}
var i2=AllTxt.indexOf(oArg(2),i1+oArg(1).length); if(i2<0) {WScript.Echo(oArg(2)+" not found in  "+oArg(0)); WScript.Quit(2)}

WScript.Echo(AllTxt.slice(i1+oArg(1).length,i2));
WScript.Quit(0);

Если нужен один файл, напишите его имя
Код:

Set "FileIn=Z:\Box_In\У попа была собака.xml"
Батник сохранить в 866 кодировке
Строку для архивирования, надеюсь, напишите сами вместо или после Echo %1 %~2
Подозреваю, это плохой путь. Наверное, для xml-файлов есть другие способы извлечения

greg zakharov 23-03-2018 12:25 2804985

Цитата:

Цитата gf100
Прошу помочь

Берете sed и в консольке отдаете команду:
Код:

sed -nr "s|.+\sEDate=\"(....-..-..)\".+|\1|p" my.xml

DJ Mogarych 23-03-2018 23:00 2805127

Не могу экспериментировать с обрезанным файлом, но в Powershell есть прекрасный командлет Import-Clixml, который прекрасно парсит xml, из которого потом можно извлечь что угодно.


Время: 23:00.

Время: 23:00.
© OSzone.net 2001-