FOR command (batch) wont accept extensions - batch-file

This for command will not accept the file extension. All i get is that it cant find "myth." Any ideas?
Code:
#echo off
goto s2
:s
for /f %%h in (\\WTAB-14R2S02\Users\100048201\Documents\Chat\Program_Files\last\%un%.last) do (
set currentchannel=%%h
)
pause
title /%currentchannel%
cls
ECHO ---------------Chat Messages---------------
TYPE \\WTAB-14R2s02\Users\100048201\Documents\Chat\Program_Files\channels\%currentchannel%.channel
ping localhost -n 2 >nul
goto s
:s2
set un=myth
goto s

set un=myth
^ there is a space here
The space at the end is included in the variable value. Remove it or still better use quotes to prevent this problem
set "un=myth"
Or, if the space is really needed (and it will still be better to use quotes to better see it in the code), then you need to include the quotes to the file reference in for /f command
for /f "usebackq" %%h in (
"\\WTAB-14R2S02\Users\100048201\Documents\Chat\Program_Files\last\%un%.last"
) do (
...
Note that usebackq has been included to avoid the quoted file being treated as a direct string to be processed.

Related

how to add new lines to windows hosts with a batch file

i know this was already discussed but i didn't find what i needed.
I need to add new lines at the end of the hosts window file but,
first i need to check if these lines already exist and than adding them.
I tried this:
set "list=examp.com=examp2.com=examp3.com"
SET NEWLINE=^0.0.0.0
for %%a in (%list%) do (
FINDSTR /I %%a %WINDIR%\system32\drivers\etc\hosts)
IF %ERRORLEVEL% NEQ 0 (ECHO %NEWLINE% %%a>>%WINDIR%\System32\drivers\etc\hosts)
pause
but the result in hosts is just 1 line like this:
0.0.0.0 %a
I also want to know if it's possible to change this:
set "list=examp.com=examp2.com=examp3.com"
with another code that will take variables from a txt file.
Your code is not quite as bad as Mofi would suggest. Although it's quite uncommon to use an equal sign as a delimiter for a for loop, it is nevertheless legal syntax. The largest two problems I see are that you're closing your for loop at the end of your findstr statement; and, assuming you fix that, %ERRORLEVEL% would need its expansion delayed. Or you could use the if errorlevel syntax of the if statement (see help if in a cmd console for full details`). Or even better, use conditional execution.
Here's an example using conditional execution. This example also opens your HOSTS file for appending one time, rather than one time for each loop iteration -- a subtle efficiency improvement, true, but a worthwhile habit to practice when writing files with a loop. And because HOSTS by default has attributes set to prevent writing, I stored and removed the read-only / system / hidden / etc. attributes of the hosts file, appended the changes to the file, then restored the attributes back the way they were before.
#echo off & setlocal
set "hosts=%WINDIR%\system32\drivers\etc\hosts"
set "list=examp.com=examp2.com=examp3.com"
SET "NEWLINE=0.0.0.0"
for /f "delims=" %%I in ('attrib "%hosts%"') do set "raw=%%~I"
setlocal enabledelayedexpansion
for /L %%I in (0,1,18) do if not "!raw:~%%I,1!"==" " set "attrs=!attrs!+!raw:~%%I,1! "
endlocal & set "attrs=%attrs%"
attrib -h -s -r -o -i -x -p -u "%hosts%"
>>"%hosts%" (
for %%a in (%list%) do (
>NUL 2>NUL find /I "%%a" "%hosts%" || echo(%NEWLINE% %%a
)
)
attrib %attrs% "%hosts%"

Batch read file that contains greater / lower than signs / carets

Alright, so I'm trying to read all lines from a text file. My current way is:
FOR /F "delims=0123456789 tokens=1,*" %%F IN ('find /v /n "" ^< myFile.bat') DO (
SET line = %%G
:: ^ Syntax errors at this line
SET line=!line:~1!
:: Yes, I have delayed expansions enabled due to a lot of fors and ifs needed
)
Basically the input file is another batch file which also contains the exact same code as above and other code with <, >, ^ etc. Once I read a line, it's basically impossible to use %%G as it will expand to stuff like:
SET line=ECHO Hello >> someFile
or
SET line=FOR /L %%G IN (1,1,5) ( SET "line=ECHO Hello %%G" & call :something & >nul SET /P =. )
Which will obviously not work. I've tried many workarounds (all have failed), including:
SET line="%%G
Which (most of the time) works, but from there using is with basically anything is near-impossible, even with something like:
:fixLine
SET line=%line:^=^^^^%
SET line=%line:<=^^^<%
SET line=%line:>=^^^>%
SET line=%line:'=^^^'%
SET line=%line:~2%
GOTO :returnFixLine
But all methods fail in some case or another. How can I read a file containing a batch script from another batch script, including special characters?
EDIT:
Doing
SET "line=%%G"
won't work, as %%G can contain quotes, and even if it doesn't, carets are still special in quotes:
SET "line=ECHO ^<Hello^>"
will turn into
SET "line=ECHO <Hello>"
Also, lines containing exclamation marks will get expanded too.
The first problems are the spaces in set line = %%G, as you set the variable line<space> instead of line.
And you prefix to the content a space.
You should use set line=%%G instead, but even that produces sometimes problems, when spaces are behind the %%G they are appended.
The best way is to use the extended SET syntax set "line=%%G".
Btw. There exists only one special charcter which can fail with a FOR-parameter expansion, that is the exclamation mark when delayed expansion is enabled.
The solution is to toggle delayed expansion.
setlocal DisableDelayedExpansion
FOR /F "delims= tokens=*" %%F IN ('find /v /n "" ^< myFile.bat') DO (
SET "line=%%F"
setlocal EnableDelayedExpansion
SET "line=!line:*]=!"
echo(Testoutput: !line!
endlocal
)

how to set a variable for the value of " ping 8.8.8.8 | find /c "TTL=" " [duplicate]

This question already has answers here:
Assign output of a program to a variable using a MS batch file
(12 answers)
Closed 9 months ago.
I'm trying to assign the output of a command to a variable - as in, I'm trying to set the current flash version to a variable. I know this is wrong, but this is what I've tried:
set var=reg query hklm\SOFTWARE\Macromedia\FlashPlayer\CurrentVersion>
or
reg query hklm\SOFTWARE\Macromedia\FlashPlayer\CurrentVersion >> set var
Yeah, as you can see I'm a bit lost. Any and all help is appreciated!
A method has already been devised, however this way you don't need a temp file.
for /f "delims=" %%i in ('command') do set output=%%i
However, I'm sure this has its own exceptions and limitations.
This post has a method to achieve this
from (zvrba)
You can do it by redirecting the output to a file first. For example:
echo zz > bla.txt
set /p VV=<bla.txt
echo %VV%
You can't assign a process output directly into a var, you need to parse the output with a For /F loop:
#Echo OFF
FOR /F "Tokens=2,*" %%A IN (
'Reg Query "HKEY_CURRENT_USER\Software\Macromedia\FlashPlayer" /v "CurrentVersion"'
) DO (
REM Set "Version=%%B"
Echo Version: %%B
)
Pause&Exit
http://ss64.com/nt/for_f.html
PS: Change the reg key used if needed.
Okay here some more complex sample for the use of For /F
:: Main
#prompt -$G
call :REGQUERY "Software\Classes\CLSID\{3E6AE265-3382-A429-56D1-BB2B4D1D}"
#goto :EOF
:REGQUERY
:: Checks HKEY_LOCAL_MACHINE\ and HKEY_CURRENT_USER\
:: for the key and lists its content
#call :EXEC "REG QUERY HKCU\%~1"
#call :EXEC "REG QUERY "HKLM\%~1""
#goto :EOF
:EXEC
#set output=
#for /F "delims=" %%i in ('%~1 2^>nul') do #(
set output=%%i
)
#if not "%output%"=="" (
echo %1 -^> %output%
)
#goto :EOF
I packed it into the sub function :EXEC so all of its nasty details of implementation doesn't litters the main script.
So it got some kinda some batch tutorial.
Notes 'bout the code:
the output from the command executed via call :EXEC command is stored in %output%. Batch cmd doesn't cares about scopes so %output% will be also available in the main script.
the # the beginning is just decoration and there to suppress echoing the command line. You may delete them all and just put some #echo off at the first line is really dislike that. However like this I find debugging much more nice.
Decoration Number two is prompt -$G. It's there to make command prompt look like this ->
I use :: instead of rem
the tilde(~) in %~1 is to remove quotes from the first argument
2^>nul is there to suppress/discard stderr error output. Normally you would do it via 2>nul. Well the ^ the batch escape char is there avoids to early resolving the redirector(>). There's some simulare use a little later in the script: echo %1 -^>... so there ^ makes it possible the output a '>' via echo what else wouldn't have been possible.
even if the compare at #if not "%output%"==""looks like in most common programming languages - it's maybe different that you expected (if you're not used to MS-batch). Well remove the '#' at the beginning. Study the output. Change it tonot %output%==""-rerun and consider why this doesn't work. ;)
This is work for me
#FOR /f "delims=" %i in ('reg query hklm\SOFTWARE\Macromedia\FlashPlayer\CurrentVersion') DO set var=%i
echo %var%

Edit html file in batch file

I have a script in which I read html files which I want to edit. Here I paste the code which calls :remove_redundant_columns subroutine.
It should remove the spaces/white spaces from begin of each line and remove from html file. Only problem is that it adds extra text like = to lines which are almost empty, just have few tabs.
The html file which I downloaded is from hidemyass.com/proxy-list/1
call parse_proxy.bat remove_redundant_columns !FILENAME!
exit /b
:remove_redundant_columns
REM Remove whitespaces from begin of lines and <span></span>
FOR /f "tokens=*" %%t in (%1) do (
SET S=%%t
SET S=!S:^<span^>^</span^>=!
if NOT "!S!"=="" >>$tmp$ echo !S!
)
del %1
REN $tmp$ %1
exit /b
If you believe, that's your only problem... You need to check, if your variable S contains content.
That's required, as substitution on an undefined variable will not produce an undefined/empty variable, the new content will be the substitution text.
:remove_redundant_columns
REM Remove whitespaces from begin of lines and <span></span>
FOR /f "tokens=*" %%t in (%1) do (
SET S=%%t
if defined S (
SET S=!S:^<span^>^</span^>=!
>>$tmp$ echo !S!
)
)
As dbenham stated, you got many other problems,
and one additional problem is the echo !S! command itself.
ECHO has some nasty side effects on different content.
If the content is empty (or only spaces) then it will print it's currently state
ECHO IS OFF
If the content is OFF or ON it will NOT be echoed, it will only change the state.
And if the content is /? it will echo the help instead of /?.
To solve this you could simply change ECHO !S! to ECHO(!S! and all problems are gone.
jeb already solved your = problem (once the extra IF DEFINED check is added to his answer). But you may have at least one other problem.
I agree with Joey that you should not be using batch to manipulate HTML like this. But, if you really want to...
Your potential problem is that HTML usually has ! characters sprinkled within. Your code uses delayed expansion, but that causes corruption of FOR variable expansion when it contains ! character(s). The solution is to toggle delayed expansion on and off within your loop.
:remove_redundant_columns
setlocal disableDelayedExpansion
REM Remove whitespaces from begin of lines and <span></span>
(
FOR /f "usebackq eol= tokens=*" %%t in ("%~1") do (
SET S=%%t
setlocal enableDelayedExpansion
if defined S SET "S=!S:<span></span>=!"
for /f "eol= tokens=*" %%S in ("!S!") do if "%%S" neq "" echo %%S
endlocal
)
) >>$tmp$
move /y $tmp$ "%~1"
exit /b
Other minor changes that were made to the code:
The search and replace can be simplified by using quotes so that special chars don't need to be escaped.
You can replace DEL and REN with a single MOVE.
Redirection is more efficient (faster) if you redirect once using an outer set of parentheses
You may need to search a file name that has spaces and or special characters, in which case you will need to quote the name. But that requires the FOR /F "USEBACKQ" option.
EDIT
Modified code to strip leading spaces after <span></span> has been replaced to eliminate potential of a line containing nothing but spaces and/or tabs.
Also set EOL to space to prevent stripping of lines beginning with ;

BAT-file: FOR %%x variable incorrect expansion

I have bat-script with following code:
FOR /F "tokens=1,2 delims==" %%g in ("%CFGFILE%") do (
SET firstChar=%%g
SET firstChar=!firstChar:~1,1!
if /I "!firstChar!"=="#" (
echo %%g>>"%INSTALL_PATH%\tmp.cfg"
)else (
if /I "%%g"=="document.folder" (
SET path_written=TRUE
echo %%g=%DOC_FOLDER%>>"%INSTALL_PATH%\tmp.cfg"
)else (
rem next line is buggy
echo %%g=%%h>>"%INSTALL_PATH%\tmp.cfg"
)
)
)
The point is parsing cfg-file %CFGFILE% contents and copying every string without changes to new config-file, except only one string starting with "document.folder". This line must be changed. Problem is that the line after "next line is buggy" comment gives "c:\program files\myApp\original.cfg=" which is content of %CFGFILE% variable plus equals sign. Is this a bug or i've done something wrong? Is this connected with %%x variables visibility?
You have mis-identified the source of the problem! :-)
Your problem is in the very first line - your FOR statement is processing a string, not a file, because the IN() clause is enclosed by double quotes. If you want the IN() clause to be treated as a quoted file name, then you need to add USEBACKQ to your FOR options.
FOR /F "usebackq tokens=1,2 delims==" %%g in ("%CFGFILE%") do (
Just a heads up - even after the fix above, your code will not give the correct results if any of the following conditions appear
If any line contains ! then expansion of %%g or %%h will be corrupted because delayed expansion is enabled
Commented # line will be incomplete if the original contained =
Your normal lines will not be complete if there is a 2nd = in the original
My suggestion:
Use FART...
http://sourceforge.net/projects/fart-it/

Resources