Batch Scripting to Search text with space in a .log file - search

I want to search text in a log file.
If found show Error and Text.
Else show Not Found and Text.
set str2=Testing Failed in env
findstr "%str2%" SystemOut.log >nul
if not errorlevel 1 ( echo ERROR: Testing Failed in env)
if errorlevel 1 ( echo Not Found Testing Failed in env!)
Whenever in the log file it encounters Testing it says ERROR but it should not do that.
When I try to make changes by adding quotes or something Positive condition gets passed but it fails for negative condition.
Please help me with the script.
Thanks,
Machpatel

You need the /c: switch to include spaces in literal mode.
#echo off
set str2=Testing Failed in env
findstr /c:"%str2%" SystemOut.log >nul
if errorlevel 1 ( echo Not Found "%str2%")
if not errorlevel 1 ( echo found "%str2%")

Related

BATCH - Find string in text file and add a new string after that line

I'm trying to search a text file for a particular string from a bat file. If the string exist, add a new string after it on the next line. I can't seem to get the code below working correctly. Any Ideas?
This is the string i'm searching for in my text file. [/Script/MyGame.Mode]
Here's what the text file looks like.
[/Script/Config.Mode]
Something here 1
Something here 2
[/Script/MyGame.Mode]
Something here 1
Something here 2
[/Script/Edit.Mode]
Something here 1
Something here 2
And here's how I want it to look.
[/Script/Config.Mode]
Something here 1
Something here 2
[/Script/MyGame.Mode]
RedirectReferences=(PackageName="%Package%",PackageURLProtocol="%PackageURLProtocol%",PackageURL="%WebAddress%/%Package%%Ext%",PackageChecksum="")
Something here 1
Something here 2
[/Script/Edit.Mode]
Something here 1
Something here 2
Here's the code I have so far.
#echo off
:GETINFO
echo.
echo.
cls
echo.
echo Let's get some information for your config.
echo Note: The information you enter below is case sensitive. You can copy and paste.
echo.
echo Here's a Package Name example: "DM-MyTest-WindowsNoEditor"
echo.
set /p Package=Enter Package Name:
echo.
echo.
echo.
echo The Package URL Protocol will be "http" or "https"
echo.
set /p PackageURLProtocol=Enter Package URL Protocol:
echo.
echo.
echo.
echo Here's a WebAddress example: "www.myredirect.com/test" (Don't add the trailing /)
set /p WebAddress=Enter Redirect(WebAddress)URL:
echo.
echo.
echo.
echo The file extention is usually ".pak"
echo.
set /p Ext=Enter Map File Extention:
echo.
cls
echo.
echo Please wait... Currently Creating Test References.
:SHOWLINE
echo.
set NewURL=RedirectReferences=(PackageName="%Package%",PackageURLProtocol="%PackageURLProtocol%",PackageURL="%WebAddress%/%Package%%Ext%",PackageChecksum=""^^)
pause
:WRITENEW
set inputfile=game.txt
set outputfile=game.temp.txt
(for /f usebackq^ delims^=^ eol^= %%a in ("%inputfile%") do (
if "%%~a"=="[/Script/MyGame.Mode]" call echo %NewURL%
echo %%a
))>>"%outputfile%"
echo.
pause
When I run the posted code in Command Prompt console I see a syntax error:
) was unexpected at this time.
Apparently the parentheses inside NewURL break things when expanded in the loop.
A straightforward solution would be to delay the expansion by using the call trick:
call echo %%NewURL%%
Alternatively:
setlocal enableDelayedExpansion & echo !NewURL! & endlocal
Or double-escape the closing parenthesis with ^^ (one time for set and another for an expanded value inside the loop):
set NewURL=.............PackageChecksum=""^^)
Another issue is that the output file name is the same as the input file name but it's impossible to redirect output into the same file as you're reading.
Change the output name to a different file. Then replace the original after the loop is finished:
set inputfile=game.txt
set outputfile=game.temp.txt
...................
))>>"%outputfile%"
move/y "%outputfile%" "%inputfile%"
And to change the order of the new string to print it after the found line simply swap the two lines inside the inner loop:
echo %%a
if "%%~a"=="[/Script/MyGame.Mode]" call echo %%NewURL%%

How to show a string that appears after specific string in a file with a batch?

I need to create a batch file that would show me a string printed after a specific string in some log file.
For example: I have a log file with a line that ends with the string "Calculated number: XX". I want to create a batch file that would go to that log, find this string and print only XX part to the screen (XX is some number that changes every now and then). Any ideas what is the best way to do that?
Help will be much appreciated, thanks in advance!
The format of the string is what comes before and after the part you are interested in - as it can matter how the line is parsed.
This code is robust and will print the number at the end of the string, if it is indeed at the end.
It uses a helper batch file called repl.bat - download from: https://www.dropbox.com/s/qidqwztmetbvklt/repl.bat
Place repl.bat in the same folder as the batch file or in a folder that is on the path.
#echo off
type "file.log" | repl ".*Calculated number: (.*)" "$1" a
#ECHO OFF
SETLOCAL
FOR /f "delims=" %%a IN (q23040271.txt) DO (
ECHO "%%a"|FIND "Calculated number: " >NUL 2>nul
IF NOT ERRORLEVEL 1 SET "line=%%a"&GOTO found
)
ECHO target NOT found&GOTO :eof
:found
ECHO %line:~-2%
GOTO :EOF
I used a file named q23040271.txt containing junk text and sample data for my testing.
This relies heavily on the assumption that the very first occurrence of Calculated number:
will be the required ite, and that it will be at the end of the line - no checking is done that it is actually at the end of the line.
replacing
ECHO "%%a"|FIND "Calculated number: " >NUL 2>nul
with
ECHO "%%a"|FINDSTR /e /R /c:"Calculated number: ..." >NUL 2>nul
would perform that end-of-line check (in theory - I haven't checked it) - note the three consecutive dots.
This will be agonisngly slow if there are millions of lines - unless the target string is very early in the file.
The more information you provide, the better a solution that can be devised.

Batch file: Find if substring is in string (not in a file) Part 2 - Using Variables

In a Windows batch file, I have a string 'abcdefg'. I want to check if 'bcd' is in the string, but I also want each to be in a variable, or pass in a parameter for the string.
This solution comes close, but uses constants rather than variables.
Batch file: Find if substring is in string (not in a file)
try one:
set "var=abcdefg"
set "search=bcd"
CALL set "test=%%var:%search%=%%"
if "%test%"=="%var%" (echo %search% is not in %var%) else echo %search% in %var% found
set "var=abcdefg"
set "search=bcd"
echo %var%|findstr /lic:"%search%" >nul && echo %search% found || echo %search% not found
The solution is to use FindStr and the NULL redirect, >nul.
SET var=%1
SET searchVal=Tomcat
SET var|FINDSTR /b "var="|FINDSTR /i %searchVal% >nul
IF ERRORLEVEL 1 (echo It does't contain Tomcat) ELSE (echo It contains Tomcat)
Save as test.bat and execute with the parameter to be searched, as follows: test Tomcat7
C:\>test Tomcat9
It contains Tomcat

How to run batch script without using *.bat extension

Is there any method in Windows through which we can execute a batch script without *.bat extension?
This is an interesting topic to me! I want to do some observations about it.
The important point first: A Batch file is a file with .BAT or .CMD extension. Period. Batch files can achieve, besides the execution of usual DOS commands, certain specific Batch-file facilities, in particular:
Access to Batch file parameters via %1 %2 ... and execution of SHIFT command.
Execution of GOTO command.
Execution of CALL :NAME command (internal subroutine).
Execution of SETLOCAL/ENDLOCAL commands.
Now the funny part: Any file can be redirected as input for CMD.exe so the DOS commands contained in it are executed in a similar way of a Batch file, with some differences. The most important one is that previous Batch-file facilities will NOT work. Another differences are illustrated in the NOT-Batch file below (I called it BATCH.TXT):
#echo off
rem Echo off just suppress echoing of the prompt and each loop of FOR command
rem but it does NOT suppress the listing of these commands!
rem Pause command does NOT pause, because it takes the character that follows it
pause
X
rem This behavior allows to put data for a SET /P command after it
set /P var=Enter data:
This is the data for previous command!
echo Data read: "%var%"
rem Complex FOR/IF commands may be assembled and they execute in the usual way:
for /L %i in (1,1,5) do (
set /P line=
if "!line:~0,6!" equ "SHOW: " echo Line read: !line:~6!
)
NOSHOW: First line read
SHOW: Second line
NOSHOW: This is third line
SHOW: The line number 4
NOSHOW: Final line, number five
rem You may suppress the tracing of the execution redirecting CMD output to NUL
rem In this case, redirect output to STDERR to display messages in the screen
echo This is a message redirected to STDERR >&2
rem GOTO command doesn't work:
goto label
goto :EOF
rem but both EXIT and EXIT /B commands works:
exit /B
:label
echo Never reach this point...
To execute previous file, type: CMD /V:ON < BATCH.TXT
The /V switch is needed to enable delayed expansion.
More specialized differences are related to the fact that commands in the NOT-Batch file are executed in the command-line context, NOT the Batch-file context. Perhaps Dave or jeb could elaborate on this point.
EDIT: Additional observations (batch2.txt):
#echo off
rem You may force SET /P command to read the line from keyboard instead of
rem from following lines by redirecting its input to CON device.
rem You may also use CON device to force commands output to console (screen),
rem this is easier to write and read than >&2
echo Standard input/output operations> CON
echo/> CON
< CON set /P var=Enter value: > CON
echo/> CON
echo The value read is: "%var%"> CON
Execute previous file this way: CMD < BATCH2.TXT > NUL
EDIT: More additional observations (batch3.txt)
#echo off
rem Dynamic access to variables that usually requires DelayedExpansion via "call" trick
rem Read the next four lines; "next" means placed after the FOR command
rem (this may be used to simulate a Unix "here doc")
for /L %i in (1,1,4) do (
set /P line[%i]=
)
Line one of immediate data
This is second line
The third one
And the fourth and last one...
(
echo Show the elements of the array read:
echo/
for /L %i in (1,1,4) do call echo Line %i- %line[%i]%
) > CON
Execute this file in the usual way: CMD < BATCH3.TXT > NUL
Interesting! Isn't it?
EDIT: Now, GOTO and CALL commands may be simulated in the NotBatch.txt file!!! See this post.
Antonio
Just use:
type mybat.txt | cmd
Breaking it down...
type mybat.txt reads mybat.txt as a text file and prints the contents. The | says capture anything getting printed by the command on its left and pass it as an input to the command on its right. Then cmd (as you can probably guess) interprets any input it receives as commands and executes them.
In case you were wondering... you can replace cmd with bash to run on Linux.
in my case, to make windows run files without extension (only for *.cmd, *.exe) observed, i have missed pathext variable (in system varailbles) to include .cmd. Once added i have no more to run file.cmd than simply file.
environment variables --> add/edit system variable to include .cmd;.exe (ofcourse your file should be in path)
It could be possible yes, but probably nor in an easy way =) cause first of all.. security.
I try to do the same thing some year ago, and some month ago, but i found no solution about it.. you could try to do
execu.cmd
type toLaunch.txt >> bin.cmd
call bin.cmd
pause > nul
exit
then in toLaunch.txt put
#echo off
echo Hello!
pause > nul
exit
just as example, it will "compile" the code, then it will execute the "output" file, that is just "parse"
instead of parsed you could also just rename use and maybe put an auto rename inside the script using inside toLaunch.txt
ren %0 %0.txt
hope it helped!
It is possible at some degree. You'll need an admin permissions to run assoc and ftype commands. Also a 'caller' script that will use your code:
Lets say the extension you want is called .scr.
Then execute this script as admin:
#echo off
:: requires Admin permissions
:: allows a files with .scr (in this case ) extension to act like .bat/.cmd files.
:: Will create a 'caller.bat' associated with the extension
:: which will create a temp .bat file on each call (you can consider this as cheating)
:: and will call it.
:: Have on mind that the %0 argument will be lost.
rem :: "installing" a caller.
if not exist "c:\scrCaller.bat" (
echo #echo off
echo copy "%%~nx1" "%%temp%%\%%~nx1.bat" /Y ^>nul
echo "%%temp%%\%%~nx1.bat" %%*
) > c:\scrCaller.bat
rem :: associating file extension
assoc .scr=scrfile
ftype scrfile=c:\scrCaller "%%1" %%*
You even will be able to use GOTO and CALL and the other tricks you know. The only limitation is that the the %0 argument will be lost ,tough it can be hardcoded while creating the temp file.
As a lot of languages compile an .exe file for example I think this a legit approach.
If you want variables to be exported to the calling batch file, you could use
for /F "tokens=*" %%g in (file.txt) do (%%g)
This metod has several limitations (don't use :: for comments), but its perfect for configuration files.
Example:
rem Filename: "foo.conf"
rem
set option1=true
set option2=false
set option3=true
#echo off
for /F "tokens=*" %%g in (foo.conf) do (%%g)
echo %option1%
echo %option2%
echo %option3%
pause

String processing using Batch Script

I'm currently creating a batch script that has to loop through the lines in a file, checking for some string, and if theres a match prefix that string with a '#' (comment it out).
I'm perfectly new to batch script, all I got this far is:
for /f %%j in (CMakeLists.txt) do (
if "%%j"=="Extensions_AntTweakBar" (
echo lol1
)
if "%%j"=="Extensions_Inspection" (
echo lol2
)
if "%%j"=="Extensions_InspectionBar" (
echo lol3
)
)
So my current issue is, I don't know how to operate on string within batch scripts. If someone could help me out that would be appreciated :)
You can just use the text you want to append followed by your variable generally.
C:\>set MY_VAR=Hello world!
C:\>echo #%MY_VAR%
#Hello world!
C:\>set MY_VAR=#%MY_VAR%
C:\>echo %MY_VAR%
#Hello world!
If you're just doing echo, that's fine. echo #%%j will do what you need.
But if you want to set the line to a variable, you have to enable delayed expansion. Add setlocal ENABLEDELAYEDEXPANSION to the top of your file and then surround your variables with ! instead of %. For example (and notice that I've added delims= to put the entire line in %%j instead of the first word on the line):
#echo off
setlocal ENABLEDELAYEDEXPANSION
set LINE=
for /f "delims=" %%j in (CMakeLists.txt) do (
set LINE=%%j
if "%%j"=="Extensions AntTweakBar" (
set LINE=#%%j
)
if "%%j"=="Extensions Inspection" (
set LINE=#%%j
)
if "%%j"=="Extensions InspectionBar" (
set LINE=#%%j
)
echo !LINE!
)
Given this input file:
Extensions AntTweakBar
some text
Extensions Inspection
Extensions What?
some more text
Extensions InspectionBar
Extensions InspectionBar this line doesn't match because delims= takes all text
even more text
The above script produces this output:
C:\>comment.bat
#Extensions AntTweakBar
some text
#Extensions Inspection
Extensions What?
some more text
#Extensions InspectionBar
Extensions InspectionBar this line doesn't match because delims= takes all text
even more text
And of course removing #echo off will help you debug problems.
But all that being said, you're about at the limit of what you can accomplish with batch string processing. If you still want to use batch commands, you may need to start writing lines to temporary files and using findstr with a regex.
Without a better understanding of what you want inside your loop or what your CMakeLists.txt file looks like, try this on for starters:
FINDSTR "SOMETHING" %%J && ECHO #%%J || ECHO %%J
The && makes the second command (the ECHO) conditional on the first command exiting without an error state, and the || is like a logical OR and it runs when the first one doesn't.
Really, for modifying the internals of a text file you are probably going to be much better off using either sed or awk - win32 binaries can be found in the UnxUtils project.

Resources