batch script to add number to a string in loop - batch-file

i need to generate list of dummy users. no of users will be provided as a input.. like 5 or 500 or 5000.
all i want is to have a standard text like usr and append a number and generate the list like usr1, usr2, usr3 etc. I thought i can do this in batch file quickly. but stuck with loop and appending the number to the string.. can some help?
#echo OFF
SETLOCAL ENABLEDELAYEDEXPANSION
set /p numb="Enter how many users to be generated "
set numb2=0
set x=0
set name1=tstusr
set name1=tstusr
set name2=%name1%
for /l %%x in (1,1,%numb%) do (
echo %%x
set numb2=%%x
set name1=tstusr
set name2=%name1%%numb2%
echo %name1%
echo %name2%
)

with a slight modification of your code...
#echo OFF
SETLOCAL ENABLEDELAYEDEXPANSION
set /p numb="Enter how many users to be generated "
set numb2=0
set x=0
set name1=tstusr
set name1=tstusr
set name2=%name1%
for /l %%x in (1,1,%numb%) do (
echo %%x
set numb2=%%x
set name1=tstusr
set name2=!name1!!numb2!
echo !name1!
echo !name2!
)
endlocal

#ECHO OFF
SETLOCAL ENABLEDELAYEDEXPANSION
set /p numb="Enter how many users to be generated "
>q28342811.txt ECHO tstusr%random%
:loop
set "name=tstusr%random%"
FINDSTR /x "%name%" q28342811.txt >NUL
IF ERRORLEVEL 1 SET /a numb -=1&>>q28342811.txt ECHO %name%
IF %numb% gtr 1 GOTO loop
TYPE q28342811.txt
GOTO :EOF
Produces q28342811.txt
generate a random username to the output file, then repeat the operation numb-1 times, checking that the new candidate doesn't already exist in the file first.

Related

Using multiple for loops in a batch

Below is the code I am working on
setlocal enabledelayedexpansion
echo on
IF NOT EXIST "D:\Deployments\Parameter_Build*.txt" (
exit
)
set SCRIPTDIRECTORY=D:\Deployments\
PUSHD %SCRIPTDIRECTORY%
FOR %%A in (Parameter_Build*.txt) DO (
echo %%A
set ANT_HOME=C:\tibco\ant\apache-ant-1.9.13
set string=
set /p string=< D:\Deployments\%%A
echo string is !string!
echo before for loop
call :myInnerloop !string!
)
POPD
GOTO:EOF
rem *************************************************************
:myInnerloop
FOR /F "tokens=2,4,6,8,10 delims==:" %%G IN ("!string!") DO (
echo inside for loop
set COMPONENTDIR="D:\kpn_eai\EAI_FIXED\branches\kpn_eai_fixed\fixed\components"
set CONFIGDIR="D:\kpn_eai\EAI_FIXED\branches\kpn_eai_fixed\fixed\configuration\components"
set ADAPTER=%%K
echo %%G %%H %%I %%J %%K
echo value taken from file is !string! >> D:\Deployments\logs\Deployment-%%J.log 2>&1
svn update !COMPONENTDIR!\!ADAPTER! >> D:\Deployments\logs\Deployment-%%J.log 2>&1
svn update !CONFIGDIR!\!ADAPTER! >> D:\Deployments\logs\Deployment-%%J.log 2>&1
echo Starting with deployment with parameters %%G %%H %%I >> D:\Deployments\logs\Deployment-%%J.log 2>&1
%ANT_HOME%\bin\xanteai deploy %%G %%H %%I >> D:\Deployments\logs\Deployment-%%J.log 2>&1
echo Deployment completed >> D:\Deployments\logs\Deployment-%%J.log 2>&1
move D:\Deployments\Parameter_Build-%%J.txt D:\Deployments\archive\Parameter_Build-%%J.txt
RENAME D:\Deployments\logs\Deployment.txt Deployment-%%J.log
)
:next
GOTO:EOF
endlocal
Parameter_Build file contains text in below format :-
Environment=:Domain=:Component=xyz.zip|abc.zip|jkl.zip|efg.zip:Build=160:Adapter=xyz|abc|jkl|efg
Here I am trying to perform deployment for each Component
Component=xyz.zip|abc.zip|jkl.zip|efg.zip
by taking SVN update for each Adapter
xyz|abc|jkl|efg
I need to separate Component and Adapter consecutively and pass it to deploy command one by one. Also before triggering deployment I need to use each components respective adapter for taking SVN update (for eg: If component xyz.zip is triggered for deployment Adapter xyz should get updated first by SVN Update utility)
This creates the variables a[0], a[1], ... a[n]
#echo off
setlocal EnableDelayedExpansion
set "var=xyz|abc|jkl|efg"
set cnt=0
set "a[0]=%var:|="&set /a cnt+=1&set "a[!cnt!]=%"
echo cnt=!cnt!
set a[
Output:
cnt=3
a[0]=xyz
a[1]=abc
a[2]=jkl
a[3]=efg
Explanation
The code simply replaces all occurences of the delimiter with "&set /a cnt+=1&set "a[!cnt!]=.
That looks strange but as example it looks like
set "a[0]=xyz" & set /a cnt+=1 & set "a[!cnt!]=abc" & set /a cnt+=1 & set "a[!cnt!]=jkl" & set /a cnt+=1 & set "a[!cnt!]=efg"
When unrolled to multiple lines it looks like
set "a[0]=xyz"
set /a cnt+=1
set "a[!cnt!]=abc"
set /a cnt+=1
set "a[!cnt!]=jkl"
set /a cnt+=1
set "a[!cnt!]=efg"
In other words, it creates several commands per one delimiter.
This technic can be used even with string delimiters like <->
set "a[0]=%var:<->=...
Thanks to #Aacini, who introduced this technic, see split string into substrings based on delimiter
I still don't understand what you really want to do, but perhaps this may help you:
#echo off
setlocal
set "Component=xyz.zip|abc.zip|jkl.zip|efg.zip"
for %%a in ("%Component:|=" "%") do (
echo With extension: %%~a
echo Without extension: %%~Na
)
EDIT: New method added
Please, review this code:
#echo off
setlocal EnableDelayedExpansion
rem Parameter_Build file contains text in below format :-
rem Environment=:Domain=:Component=xyz.zip|abc.zip|jkl.zip|efg.zip:Build=160:Adapter=xyz|abc|jkl|efg
rem Read the file:
set /P "line=" < Parameter_Build.txt
echo Line read:
echo !line!
rem Separate variables:
set "%line::=" & set "%"
rem Separate Component and Adapter in *matching* parts
set cnt=1
set "Component[1]=%Component:|=" & set /A cnt+=1 & set "Component[!cnt!]=%"
set cnt=1
set "Adapter[1]=%Adapter:|=" & set /A cnt+=1 & set "Adapter[!cnt!]=%"
rem Ok:
for /L %%i in (1,1,%cnt%) do echo Component[%%i]=!Component[%%i]!, Adapter[%%i]=!Adapter[%%i]!
Output example:
Line read:
Environment=:Domain=:Component=xyz.zip|abc.zip|jkl.zip|efg.zip:Build=160:Adapter=xyz|abc|jkl|efg
Component[1]=xyz.zip, Adapter[1]=xyz
Component[2]=abc.zip, Adapter[2]=abc
Component[3]=jkl.zip, Adapter[3]=jkl
Component[4]=efg.zip, Adapter[4]=efg

Creating a list of files and contents

Trying to create a sort of vault. I have several .txt files with the account names containing the amount inside.
echo ______________________>current.txt
::this bit just resets the file ^^
setlocal enabledelayedexpansion
set Counter=1
for /f %%x in (list.txt) do (
set "Line_!Counter!=%%x"
set "temp=%%x"
set /p amountIn=<%%x.txt
set /a Counter+=1
echo %temp% vault contains>>current.txt
)
When I run this I just get " Vault contains " in current.txt. and no errors inside the CMD.
To clarify, Current.txt is my output file that i want the list in, list.txt is a list of the bank accounts, and the directory has all of the bank accounts with numbers in them.
As in my comment:
Echo ______________________>current.txt
SetLocal EnableDelayedExpansion
Set "Counter=1"
For /F %%A In (list.txt) Do (
Set "Line_!Counter!=%%A"
Set "_tmp=%%A"
Set /P "amountIn="<%%A.txt
Set /A Counter +=1
>>current.txt Echo !_tmp! vault contains !amountIn!
)
Or:
SetLocal EnableDelayedExpansion
Set "Counter=0"
(
For /F %%A In (list.txt) Do (
Set /A Counter +=1
Set "Line_!Counter!=%%A"
Set /P "amountIn="<%%A.txt
Echo %%A vault contains !amountIn!
)
)>current.txt

Windows Batch read a file, parse and output

I'm 90% of the way there on a Windows Batch file.
It takes 2 input parameters, input and output files.
It then reads in the input file, and substrings certain lines into arrays (Well line 2 onwards).
Then we come to a loop for outputting.
With delayed expansion on my counter for going through the array doesn't update unless I use !counter2!, %counter2% doesn't work.
Using !arrayname[!counter2!]! doesn't work.
Here is the code as it stands.
#Echo off
if [%1] == [] goto usage
if [%2] == [] goto usage
echo start time : %time%>logfile.log
set input_file=%1
set output_file=%2
if exist %output_file% del %output_file%
Echo Start reading %input_file%>> logfile.log
setLocal EnableDelayedExpansion
set /a counter=1
for /F "tokens=* delims=" %%a in ('type %input_file%') DO (
::echo !counter!
if "!counter!"=="1" set header=%%a
if not "!counter!"=="1" (
set data[!counter!]=%%a
set line=%%a
set jobnumber[!counter!]=!line:~0,7!
set docnumber[!counter!]=!line:~7,5!
set pagecount[!counter!]=!line:~12,2!
set customernumber[!counter!]=!line:~14,20!
set presort[!counter!]=0000
set postcode[!counter!]=0000
set inserts[!counter!]=!line:~36,11!
set filler[!counter!]=000000
set address[!counter!]=!line:~58,350!
set filler2[!counter!]=" "
set endline[!counter!]=X
)
set /a counter=counter+1
)
Echo Start writing %output_file%>> logfile.log
for /L %%G in (2,1,%counter%) DO (
set counter2=%%G
echo !counter2!
echo !jobnumber[%counter2%]!!docnumber[%counter2%]!!pagecount[%counter2%]!!customernumber[%counter2%]!!presort[%counter2%]!!postcode[%counter2%]!!inserts[%counter2%]!!filler[%counter2%]!!address[%counter2%]!!filler2[%counter2%]!!endline[%counter2%]!>>%output_file%
)
echo end time : %time%>>logfile.log
pause
goto :eof
:usage
echo Usage: blah.bat input_filename output_filename
pause
goto :eof
It is the echo !jobnumber[%counter2%]! where things are not being resolved.
The echo !counter2! works fine.
Before you ask, Yes I know this could be done better and easier in C# or another programming language, However I am tasked with doing it in a windows batch file.
Thanks in advance for any help provided.
Tel
Try with:
for /L %%G in (2,1,%counter%) DO (
set counter2=%%G
echo !counter2!
echo !jobnumber[%%G]!!docnumber[%%G]!!pagecount[%%G]!!customernumber[%%G]!!presort[%%G]!!postcode[%%G]!!inserts[%%G]!!filler[%%G]!!address[%%G]!!filler2[%%G]!!endline[%%G]!>>%output_file%
)
You are not changing the value of the coutner2 so you don't need it and you can directly use %%G.
Though if you need changes in counter2 you'll have to wrap it again in for loop and to use its tokens.

Search random line

I got 2 files bot.bat
#echo off & setlocal EnableDelayedExpansion
:botconfig
set botname=Unknow
set botcity=unknow
set botadress=unknow
set botage=unknow
for /f "delims=*" %%x in (botfeel.txt) do set botfeel=%%x
:askme
set /p how=
echo I feel %botfeel%
goto askme
and botfeel.txt
good
bad
sick
What i want is instead of showing just "i feel sick" it shows randomly one of the 3 words in botfeel.txt
Make your batch file look like this:
#echo off
:botconfig
set botname=Unknow
set botcity=unknow
set botadress=unknow
set botage=unknow
:askme
set /p how=
SET /a line=%RANDOM% * 3 / 32768
if %line%==0 goto firstline
for /F "skip=%line% delims=" %%i in (botfeel.txt) do set "botfeel=%%i"&goto nextline
:nextline
echo I feel %botfeel%
goto askme
:firstline
set /p botfeel= <botfeel.txt
goto nextline

Batch File - loop incrementing count in value not displaying correctly

I'm trying to read a file and output the lines of data into registry keys. The data collection works, but I don't understand the syntax required to increment the string values in the last loop.
#echo OFF
SETLOCAL DisableDelayedExpansion
FOR /F "usebackq skip=1 delims=" %%a in (`"findstr /n ^^ C:\GetSID.txt"`) do (
set "var=%%a"
SETLOCAL EnableDelayedExpansion
set "var=!var:*:=!" This removes the prefix
echo(!var:~76,63!>>C:\SIDoutput.txt
goto :EndLoop
)
:EndLoop
set /p SID= <C:\users\paintic\SIDoutput.txt
set KEY_NAME="HKEY_USERS\!SID!\Software\Microsoft\Windows NT\CurrentVersion\PrinterPorts"
set Counter=1
for /f %%x in (C:\users\paintic\Networkprinters.txt) do (
set "Line_!Counter!=%%x"
set /a Counter+=1
if !Counter!==3 (Echo %line_counter%)
)
set /a counter2=!counter!-3
set counter=1
The part below is what I can't get to work. I'm trying to write LINE_1, LINE_2 and LINE_3 values from the previous loop to increment via the loop below. So VALUENAME should equal LINE_1, TYPE should = LINE_2's value and DATA should = LINE_3 on the first run and keep going up by 1 until the loop finishes (end of the file read)
`for /L %%i in (1,1,%counter2%) do (
set ValueName=%Line_!counter!%
set /a counter+=1
set Type=%Line_!counter!%
set /a Counter+=1
set Data=%Line_!counter!%
set /a Counter+=1
echo !ValueName!
echo !Type!
echo !Data!
REG ADD %KEY_NAME% /v !ValueName! /t !Type! /d !Data! /f
)
ENDLOCAL
Pause`
On searching for errors in batch file it is always helpful to use in first line #echo on or remove #echo off or comment this line with rem to see what cmd.exe really executes.
Command line interpreter fails on lines with set VariableName=%Line_!counter!% as the interpreter does not know what to expand first. I think it is not possible to create dynamically the name of an environment variable and reference next the value of this environment variable. This approach most likely does not work ever.
However, what you want to achieve can be done much easier directly in second loop as the following example demonstrates:
#echo off
setlocal EnableDelayedExpansion
rem Create data for demo example.
set "KEY_NAME=HKEY_USERS\S-1-5-20\Software\Microsoft\Windows NT\CurrentVersion\PrinterPorts"
echo TestValue>"%TEMP%\Networkprinters.txt"
echo REG_SZ>>"%TEMP%\Networkprinters.txt"
echo Sample Data>>"%TEMP%\Networkprinters.txt"
echo AnotherValue>>"%TEMP%\Networkprinters.txt"
echo REG_DWORD>>"%TEMP%\Networkprinters.txt"
echo ^1>>"%TEMP%\Networkprinters.txt"
rem Now the loop follows which reads the data from the file line
rem by line and build the line for using command "reg.exe" to
rem add the data to registry of the user with the defined SID.
set Counter=1
for /f "usebackq delims=" %%x in ("%TEMP%\Networkprinters.txt") do (
if "!Counter!"=="1" (
set "ValueName=%%x"
) else if "!Counter!"=="2" (
set "ValueType=%%x"
) else (
set "ValueData=%%x"
rem Echo the command instead of really executing "reg.exe".
echo reg.exe ADD %KEY_NAME% /v "!ValueName!" /t !ValueType! /d "!ValueData!" /f
set Counter=0
)
set /a Counter+=1
)
rem Delete the text file created for demo example.
del "%TEMP%\Networkprinters.txt"
endlocal
This solution is much easier than what you have tried and can be maybe even more simplified.

Resources