Find text within string line - batch-file

I have a text file, that has some text with this syntax:
mytextfile.txt:
websiteurl1 username1 password1
websiteurl2 username2 password2
websiteurl3 username3 password3
And so on....
And I'd like to be able to find username and password strings by pointing the websiteurl, so let's say I tell the batch file,
find websiteurl3, it should print the username3 and password3
and I was able to write a "FOR LOOP" but I am not sure how to use the syntax of the loop, as my code finds only the last line always, here is what I have:
FOR /F "tokens=2,3 delims= " %%A IN (URL.txt) DO IF EXIST URL.txt (set WEBUserName1=%%A) && (SET WEBUserPass1=%%B)
pause
echo Username:"%WEBUserName1%"
echo Password:"%WEBUserPass1%"
pause
exit
I know the loop is looking on the "URL.txt" for the tokens 2 and 3, and then sets the variables accordingly, what I'd like to know, is how I can use the loop, or if needed, any other command to be able to:
Find the "URL.txt file
Then find the specific string, in this case, the first word of the specified string line
Then find tokens 2 and 3 of that string line.

And I'd like to be able to find username and password strings
Use the following batch file.
test.cmd:
#echo off
setlocal enabledelayedexpansion
for /f "tokens=2,3" %%a in ('type mytextfile.txt ^| findstr "%1"') do (
echo Username:"%%a"
echo Password:"%%b"
pause
exit
)
endlocal
Notes:
Pass the website URL string as a parameter to the batch file.
findstr is used to find the matching line from the file, so we only need to parse a single line using for /f.
Example usage and output:
F:\test>type mytextfile.txt
websiteurl1 username1 password1
websiteurl2 username2 password2
websiteurl3 username3 password3
F:\test>test websiteurl3
Username:"username3"
Password:"password3"
Press any key to continue . . .
Further Reading
An A-Z Index of the Windows CMD command line - An excellent reference for all things Windows cmd line related.
findstr - Search for strings in files.
for /f - Loop command against the results of another command.
type - Display the contents of one or more text files.

bad way, but this too work:
#echo off
setlocal
set srch_site=websiteurl2
FOR /F "tokens=1,2,3 delims= " %%A IN (URL.txt) DO (
IF EXIST URL.txt (
if "%%A"=="%srch_site%" (
(set WEBUserName1=%%B) && (SET WEBUserPass1=%%C)&goto:stdout
)
)
)
:stdout
pause
echo Username:"%WEBUserName1%"
echo Password:"%WEBUserPass1%"
pause
exit

May I offer you a different approach?
The code below get all usernames and passwords and store they in two vectors:
#echo off
setlocal EnableDelayedExpansion
for /F "tokens=1-3" %%A in (URL.txt) do set "User[%%A]=%%B" & set "Pass[%%A]=%%C"
After that, you may test if the username and password of a certain site was given this way:
set "site=websiteurl3"
if defined User[%site%] echo The site "%site%" have username and password
... or display their values this way:
echo Username:"!User[%site%]!"
echo Password:"!Pass[%site%]!"
You may review a detailed explanation of array management in Batch files at this post.

You get the last line, because you process the whole file. Filter your textfile and process only that one line:
set "site=websiteurl2"
FOR /F "tokens=2,3 delims= " %%A IN ('find "%site%" URL.txt') DO (
set "usr=%%A"
set "pwd=%%B"
)
echo %usr%, %pwd%

Related

Batch Script To Fetch Website and Parse String

I tried searching but couldn't find anything specific to what I need.
So I want to fetch, maybe use curl for Windows, the guid string generated by this website without having to save the html file first. The sources are more or less like this:
<input name="YourGuidLabel" type="text" id="YourGuidLabel" onclick="this.focus(); this.select();" readonly="readonly" class="guidinput" value="852dd74c-4249-4390-85d3-6e9e2116ef2b" /></p>
What I want is this one: 852dd74c-4249-4390-85d3-6e9e2116ef2b. The string is then stored into a variable and echoed to view it.
In linux terminal I can do it in this simple way:
curl -s "https://www.guidgen.com/" | grep -o 'me="YourGuid.*value=.*/>' | cut -d '"' -f14
Does this thing by being able to use a batch file?.
This can do the trick with a batch file on Windows using a PowerShell Command and set it as variable with for /f .. do loop :
#echo off
Title Extract GUID Value from Input Field from site https://www.guidgen.com
#For /f %%a in ('Powershell -C "$(IWR https://www.guidgen.com -UseBasicParsing).InputFields.value"') do Set "GUID=%%a"
Echo GUID=%GUID%
pause
#ECHO OFF
SETLOCAL
rem The following settings for the source directory and filename are names
rem that I use for testing and deliberately include names which include spaces to make sure
rem that the process works using such names. These will need to be changed to suit your situation.
SET "sourcedir=u:\your files"
SET "filename1=%sourcedir%\q74909468.txt"
FOR /f "usebackqdelims=" %%e IN ("%filename1%") DO SET "html=%%e"
SET "html=%html:"=%"
SET "html=%html:<=%"
SET "html=%html:>=%"
SET "html=%html:)=%"
SET "html=%html:(=%"
SET "html=%html:;=%"
FOR %%e IN (%html%) DO if "%%e" neq "//p" SET "guid=%%e"
ECHO GUID=%guid%
GOTO :EOF
Always verify against a test directory before applying to real data.
Note that if the filename does not contain separators like spaces, then both usebackq and the quotes around %filename1% can be omitted.
You haven't told us where the html is located - I've presumed a file.
Sadly "more or less like" is not specific enough to generate a reliable solution.
Read the file line to a variable, html
Remove all " < > ) ( ; from that variable.
process the result, assigning each token in turn to guid, unless the token is //p
Assumes the required string is that string which precedes //p which is the last string in the (original text - deleted character set)
The following idea not using PowerShell may also perform the task you've laid out in your question.
#Echo Off & SetLocal EnableExtensions DisableDelayedExpansion
Set "value=" & For /F Delims^=^ EOL^= %%G In ('%SystemRoot%\System32\curl.exe -s "https://www.guidgen.com" ^| %SystemRoot%\System32\findstr.exe /RIC:" value=\"[0123456789abcdef][0123456789abcdef]*-[0123456789abcdef][0123456789abcdef]*-[0123456789abcdef][0123456789abcdef]*-[0123456789abcdef][0123456789abcdef]*-[0123456789abcdef][0123456789abcdef]*\""') Do (Set "value=%%G" & SetLocal EnableDelayedExpansion & For /F Delims^=^"^= %%H In ("!value:* value=!") Do EndLocal & Set "value=%%H")
If Defined value Echo %value% & Pause

Combine lines in text file using batch

I want to make a program that takes the content of the second line of a text file and puts it on the first. (It doesn't matter if the second doesn't get edited)
for /f "tokens=1" %%t in (file.txt) do set string1=%%t
for /f "tokens=2" %%t in (file.txt) do set string2=%%t
echo %string1%%string2%>file.txt
I have two issues hat I can't seem to be able to fix.
One: the loops only include the first word of each line in the variables.
Two: Echo doesn't replace the first line of the file with the variables given and instead writes ECHO command deactivated (I have the French version of Windows 10 and simply translated what got written in the file, the text in English Windows version might be slightly different, but you get the idea)
If you have any suggestions, I would appreciate if you explain what the code you provide does (I always like to learn)
Your question is not clear and can be understood in several different ways. Anyway, this management is simpler with no for command:
#echo off
setlocal EnableDelayedExpansion
< file.txt (
rem Takes the content of the first line
set /P "line1="
rem Takes the content of the second line and puts it on the first
set /P "line2="
echo !line1!!line2!
rem It doesn't matter if the second line doesn't get edited
echo !line2!
rem Copy the rest of lines
findstr "^"
) > output.txt
move /Y output.txt file.txt
The FOR command uses a space as a delimiter by default. So you have to tell it to not use any delimiters with the DELIMS option. Also, you should be able to do this with a single FOR /F command. Just hold the previous line in a variable.
#ECHO OFF
setlocal enabledelayedexpansion
set "line1="
(for /f "delims=" %%G in (file.txt) do (
IF NOT DEFINED line1 (
set "line1=%%G"
) else (
echo !line1!%%G
set "line1="
)
)
REM If there are an odd amount of lines, line1 will still be defined.
IF DEFINED line1 echo !line1!
)>File2.txt
EDIT: I think I completely misunderstood your question. Once you clarify your question I will repost a code solution if needed.
Use skip to omit the first line and write the 2nd line twice. In general an edit of a file implies a rewrite to a new file and possibly a rename to retain the old file name.
:: Q:\Test\2018\07\25\SO_51508268.cmd
#Echo off
Set "flag="
( for /f "usebackq skip=1 delims=" %%A in ("file1.txt") Do (
If not defined flag (
Echo=%%A
Set flag=true
)
Echo=%%A
)
) >file2.txt
Del file1.txt
Ren file2.txt file1.txt
After running the batch a file1.txt with initially numbered lines 1..5 looks like this:
> type file1.txt
2
2
3
4
5

Extract the sub string from end offline to a special character in batch file

HI i am trying to get the sub string ZoomIn10X,ZoomIn20X,ZoomIn30X etc, from a file which contain following lines below and out put that to another file
Job Name : STANALONE/1234/JobId/Date/ZoomIn10X
Job Name : STANALONE/1234/JobId/Date/ZoomIn20X
Job Name : STANALONE/JobId/Date/ZoomIn30X
Job Name : STANALONE/1234/JobId/Date/ZoomIn40X
Job Name : STANALONE/1234/Date/ZoomIn10X
i Have tried
for /F "tokens=*" %%A in (input.txt) do (
echo %%A r "/" "\n" %%A | tail -1 >> output.txt
)
but its not working as properly.Can you please help
on unix, with perl
perl -pe 's#.*/##' input.txt
see perl -h for options and perlop regex for more details.
habitually substitute expressions are written with a / forward slash delimiter but any other character can be used as in sed. here using # to avoid escaping /.
or with shell language bash (slower because of bash read)
while read -r line; do
echo "${line##*/}"
done <input.txt
see bash variable expansion. here ## to remove the longest prefix.
>output.txt (for /f "delims=" %%a in (input.txt) do echo %%~nxa)
Given the input lines, and handling them as paths+files references (yes, they are not, but can be handled as if they were), using the for replaceable parameter modifiers (see for /?) we request the name and extension of the file being referenced. All the output of the for execution is redirected to output.txt.
[W:\44365640]:# type go.cmd
#echo off
setlocal enableextensions disabledelayedexpansion
>output.txt (for /f "delims=" %%a in (input.txt) do echo %%~nxa)
[W:\44365640]:# type input.txt
Job Name : STANALONE/1234/JobId/Date/ZoomIn10X
Job Name : STANALONE/1234/JobId/Date/ZoomIn20X
Job Name : STANALONE/JobId/Date/ZoomIn30X
Job Name : STANALONE/1234/JobId/Date/ZoomIn40X
Job Name : STANALONE/1234/Date/ZoomIn10X
[W:\44365640]:# go
[W:\44365640]:# type output.txt
ZoomIn10X
ZoomIn20X
ZoomIn30X
ZoomIn40X
ZoomIn10X
[W:\44365640]:#
Using awk you could define / as field separator and output the last field:
$ awk -F/ '{print $NF}' input.txt
ZoomIn10X
ZoomIn20X
ZoomIn30X
ZoomIn40X
ZoomIn10X
Solution outputs the last field of every line, including the empty lines you had between the data lines. If you need to filter the output somehow, please update the requirements to the OP.
I think the others answers are not using batch only syntax.
The following solution should work if you have the input.txt file as you have written (I have added even option to use the solution as variable):
EDIT:
Added comments for the script:
#ECHO OFF
SETLOCAL ENABLEDELAYEDEXPANSION
REM your input.txt file looks like this
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn10X
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn20X
REM Job Name : STANALONE/JobId/Date/ZoomIn30X
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn40X
REM Job Name : STANALONE/1234/Date/ZoomIn10X
REM if you wished to use variable
REM SET final_name=""
FOR /F "tokens=2 delims=:" %%A IN (input.txt) DO (
SET temp_var=%%A
FOR /F "tokens=4 delims=/" %%B IN ("!temp_var!") DO (
SET temp_var_B=%%B
IF "!temp_var_B!" EQU "Date" (
FOR /F "tokens=5 delims=^/" %%C IN ("!temp_var!") DO (
ECHO %%C >> output.txt
REM if you wished to use variable
REM SET final_name=!final_name!,%%C
)
) ELSE (
ECHO %%B >> output.txt
REM if you wished to use variable
REM SET final_name=!final_name!,%%B
)
)
)
ECHO All collected variables: !final_name!
ENDLOCAL
This is somewhat inefficient solution, much better you can find below, but collects also variables. It uses the fact that you can split string multiple times and if you have different string length you can still extract it based on the string, if it is the same, like in your case a "Date". First FOR splits the string based on ":" character and the other FORs based on "/" char. There are two FORs as you have different length of the extracted string.
EDIT :
I think I was too quick to find a solution. When I thought about it I recognized it as very "crude" solution. I'll also comment it better as I have posted only the code.
The more efficient solution:
#ECHO OFF
SETLOCAL ENABLEDELAYEDEXPANSION
REM your input.txt file looks like this
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn10X
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn20X
REM Job Name : STANALONE/JobId/Date/ZoomIn30X
REM Job Name : STANALONE/1234/JobId/Date/ZoomIn40X
REM Job Name : STANALONE/1234/Date/ZoomIn10X
FOR /F "tokens=2 delims=:" %%A IN (input.txt) DO (
SET var=%%A
IF EXIST input.txt (
ECHO !var:~-9! >> output.txt
) ELSE (
ECHO !var:~-9! > output.txt
)
)
ENDLOCAL
Description:
First comes the FOR /F with "tokens=2" (takes a second part) and "delims=:" uses a ":" as delimiter.
The core of the solution uses the fact that you have at the end constant size string (9 characters to be exact) which you want to extract - !var:~-9!. Uses expanded variable and takes 9 characters from the end of the string which was selected with the FOR statement.
The solution needs to have the SETLOCAL ENABLEDELAYEDEXPANSION there as it uses the expansion.
There is also a IF EXISTS clause so it will create a new file every time you run it. That is not a vital part of the script and you may comment it out.

Cannot echo in the same line in Batch script

I have txt files that contain several lines and I need to create a log out of them to store in a log the following information:
File Name
Last modified
Count of lines containing the word "valid"
I've put together a .bat file but it splits the output in two lines.
type nul > FilesReceived.txt & for %f in (*.log) do (
find /c "valid" %f & echo(%~tf)>> LogsReceived.txt
)
With type nul I clear the contents of the FilesReceived.txt file. Then I loop through the files of type log.
Then I count lines that contain the word valid with find /c and I also echo the last modified time stamp.
However the output looks like:
---------- transaction_20160505_1005A.log: 6492
10/06/2016 04:37 p.m.
I don't know what's generating those dashes. Ultimately I'd like to have one line per log file as follows:
transaction_20012B.log: 6492 10/06/2016 04:37 p.m.
Hope you guys can help me.
Thanks,
Bruce
find prints the dashes if it processes a file. It doesn't, when processing from STDIN (type file.ext /c |find "string" prints the count only).
There is a trick to write without linefeed: <nul set /p"=Hello"
If you can live with another order, it's quite easy to assemble it::
#echo off
for %%f in (*.bat) do (
<nul set /p "=%%f %%~tf "
type %%f|find /c "echo"
)
If you want to keep your order it's a little bit more complicated: you can't force find to write without linefeed, so you have to use a trick (another for):
#echo off
(for %%f in (*.txt) do (
<nul set /p "=%%f: "
for /f %%i in ('type %%f^|find /c "valid"') do (<nul set /p "=%%i ")
echo %%~tf
))>LogsReceived.txt
You may get the output of find command via another for and put it at any place you wish:
#echo off
(for %%f in (*.log) do (
for /F %%c in ('find /c "valid" ^< %%f') do echo %%f: %%c %%~tf
)) > LogsReceived.txt

Echo information in quotes on a line containing a specific string?

If I had a text file that was a list of things in the following format:
Thing1 "Description of Thing1"
Thing2 "Description of Thing2"
etc.
How would I use a batch file to echo only the information contained in the quotes for any given thing?
Edit: Per the answer, I've tried the following:
for /f "tokens=1*" %%a in (G:\Games\Console\Emulators\MAME\listfull.txt) do if "%%a"=="%%~nf" set gamename=%%~b
echo !gamename!
if !count!==1 echo|set /P=", "!gamename!": [#name: "%%~nf", #path: "%%~dpf"]" >> "G:\Games\Console\Utilities\Lists\MAME_%%d.txt"
It almost totally works; if the description contains an &, symbol, however, "echo !gamename!" works while the next line doesn't and spits out that "&' isn't a command. (I have to use the echo|set to produce lines that don't have a carriage return.)
Edit2: The only solution I've found is to add an ^ before every & in whatever text file I'm reading the descriptions from. Not an ideal workaround, but...
set "search=Thing2"
for /f "tokens=1*" %%a in (textfile.txt) do if "%%a"=="%search%" echo %%~b
If all this script does is outputs the information for any given thing, then you could change search to %~1 and just input the value when calling the script.
for /f "tokens=1*" %%a in (textfile.txt) do if "%%a"=="%~1" echo %%~b
for /f "tokens=1*" %%a in (file.txt) do echo(%%~b

Resources