Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Echo to screen and file

186 views
Skip to first unread message

Scion

unread,
Aug 27, 2010, 7:25:30 AM8/27/10
to
Hi all,

I have a couple of batch files that output to the screen and also to a text
file.
This is done with two seperate commands each time.

e.g.

echo Processing %1
echo Processing %1 >result.txt

Is there a neat way of echoing to screen and file in one go?


Scion

unread,
Aug 27, 2010, 7:26:49 AM8/27/10
to

Of course subsequent echos to file need to append:

echo Done processing %1
echo Done processing %1 >>result.txt


foxidrive

unread,
Aug 27, 2010, 8:44:25 AM8/27/10
to

A TEE filter is one way. Here are some batch file TEE filter idea but
you can find TEE filters on the net too. Not all are compatible with NT
versions fo Windows.


:: tee.bat - idea from Joachim Hofmann
:: Syntax: TEE logfilename.log dos_command_to_capture
:: Example: tee logfile.log COPY "c:\myfolder\*.txt" "d:\backup\"
:: tee "My log.log" dir c:\*.sys /b
@ECHO OFF
set logfile="%~1"
if exist %logfile% del %logfile%
set "var=%*"
set "var=%var:*.log =%"
set "var=%var:*.log" =%"
for /F "tokens=1* delims=]" %%a IN (
'%var% 2^>^&1^|find /v /n ""'
) DO (
set /p"=%%b"<nul
echo.
set /p"=%%b"<nul>>%logfile%
echo.>>%logfile%
)
pause

From Tom Lavadas

@echo off
> TFILTER.VBS echo. sLogName="Logfile.log" ' default name
>>TFILTER.VBS echo. if WSH.Arguments.Count^>0 then sLogName=WSH.Arguments(0)
>>TFILTER.VBS echo. with CreateObject("Scripting.FileSystemObject")_
>>TFILTER.VBS echo. .OpenTextFile(sLogName, 8, true)
>>TFILTER.VBS echo. .WriteLine Now
>>TFILTER.VBS echo. Do Until WSH.StdIn.AtEndOfStream
>>TFILTER.VBS echo. str = WSH.StdIn.ReadLine
>>TFILTER.VBS echo. wsh.echo str : .WriteLine str
>>TFILTER.VBS echo. Loop
>>TFILTER.VBS echo. end with ' FSO

(echo === Started ====
copy *.bat "c:\folder" /y
echo ====text here=== )|cscript //nologo TFILTER.VBS MyLogFile.txt

del TFILTER.VBS

From William Allan:

Pipes in Windows NT/2000/XP operate to memory, and don't wait for
the completion of the input-side process. This means you can pipe
the output of your Batch file to a T-filter created in WSH with a
simple VBScript file. For example, create the following T-filter in
a plain text VBS file:

Lines that don't begin with two spaces have wrapped accidentally
====Begin cut-and-paste (omit this line)
Set StdIn = WScript.StdIn
Set StdOut = WScript.StdOut
Set Args=WScript.Arguments
LogFile=Args(0)
Set fso = CreateObject("Scripting.FileSystemObject")
Set LogFile= fso.CreateTextFile(Args(0))

LogFile.WriteLine Date & " " & Time

Do While Not StdIn.AtEndOfStream
str = StdIn.ReadLine
StdOut.WriteLine str
LogFile.WriteLine str
Loop

LogFile.Close

====End cut-and-paste (omit this line)
For study/demo use. Cut-and-paste as VBScript (.VBS) text file.
Batch file troubleshooting: http://www.allenware.com/find?UsualSuspects

With that file cut-and-paste as, say TFILTER.VBS, run your
Batch file with a pipe to the filter executed with CSCRIPT and
add the logfile name you require as a parameter.

Something like this:

MyBatchFile.bat | cscript//nologo TFILTER.VBS MyLogFile.txt

The output of the Batch file is displayed line-by-line and
simultaneously captured to MyLogFile.txt line-by-line.

Note: You must execute the TFILTER.VBS with CSCRIPT and
not WSCRIPT (STDIN and STDOUT are not available via WSCRIPT).

This technique avoids the use of third-party utilities. You could
create the TFILTER.VBS initially on-the-fly in the Batch file, and
delete it when the Batch file finishes. If you do, remember the
need to escape & characters with ^, thus: ^& when ECHO-ing them.

===[paste]===


--
Regards,
Mic

Timo Salmi

unread,
Aug 27, 2010, 10:55:56 AM8/27/10
to
On 27.08.2010 14:25 Scion <a...@b.invalid> wrote:
> I have a couple of batch files that output to the screen and also to a text
> file.
> Is there a neat way of echoing to screen and file in one go?

94} Can I send the script's output both to the screen and a log file?
http://www.netikka.net/tsneti/info/tscmd094.htm

All the best, Timo

--
Prof. Timo Salmi mailto:t...@uwasa.fi ftp & http://garbo.uwasa.fi/
Hpage: http://www.uwasa.fi/laskentatoimi/english/personnel/salmitimo/
Department of Accounting and Finance, University of Vaasa, Finland
Useful CMD script tricks http://www.netikka.net/tsneti/info/tscmd.php

Scion

unread,
Aug 27, 2010, 11:44:28 AM8/27/10
to


Thanks for the replies, they all look a bit more complex than what I was
looking for. I want to keep it simple, and all within a batch file.

Perhaps I'll just call a sub that outputs the text once to screen and once
to the file:

call :op Output text to display on screen and copy to file.
call :op Second line of output text.
.
.
.
goto :EOF

:op
echo %*
echo %* >> res.txt
goto :EOF


01MDM

unread,
Aug 28, 2010, 1:06:40 AM8/28/10
to
> Is there a neat way of echoing to screen and file in one go?

Use some of *tee.exe program. For example http://www.commandline.co.uk/mtee/

Timo Salmi

unread,
Aug 28, 2010, 1:19:37 PM8/28/10
to
On 27.08.2010 18:44 Scion wrote:

> Scion wrote:
>> I have a couple of batch files that output to the screen and also to
>> a text file.

> Thanks for the replies, they all look a bit more complex than what I was

> looking for. I want to keep it simple, and all within a batch file.
>
> Perhaps I'll just call a sub that outputs the text once to screen and once
> to the file:

It is one option. Unfortunately, it is not always quite as simple as one
thinks, because there can be subtle file handle pitfalls in the
subroutine method. For more on that, you may wish to see
http://www.netikka.net/tsneti/info/tscmd094.htm#handle

> call :op Output text to display on screen and copy to file.
> call :op Second line of output text.
> .

> goto :EOF
>
> :op
> echo %*
> echo %* >> res.txt
> goto :EOF

All the best, Timo

ImpalerCore

unread,
Aug 30, 2010, 9:24:04 AM8/30/10
to

I have a 'tee.cmd' in my old batch library on sourceforge. The
project is 'blip', short for 'Batch Library In Progress'.

Best regards,
John D.

FileGod

unread,
Aug 31, 2010, 2:25:23 PM8/31/10
to

>e.g.

Yes, it can be done in one line using the symbol &, I hope this
helps.
echo Processing %1 & echo Processing %1 >result.txt

http://www.filegod.netfirms.com

Scion

unread,
Sep 3, 2010, 11:08:48 AM9/3/10
to
Timo Salmi wrote:
> On 27.08.2010 18:44 Scion wrote:
>> Scion wrote:
>>> I have a couple of batch files that output to the screen and also to
>>> a text file.
>
>> Thanks for the replies, they all look a bit more complex than what I
>> was looking for. I want to keep it simple, and all within a batch
>> file. Perhaps I'll just call a sub that outputs the text once to screen
>> and once to the file:
>
> It is one option. Unfortunately, it is not always quite as simple as
> one thinks, because there can be subtle file handle pitfalls in the
> subroutine method. For more on that, you may wish to see
> http://www.netikka.net/tsneti/info/tscmd094.htm#handle
>
>> call :op Output text to display on screen and copy to file.
>> call :op Second line of output text.
>> .
>> goto :EOF
>>
>> :op
>> echo %*
>> echo %* >> res.txt
>> goto :EOF
>
> All the best, Timo

That's an interesting article - I had no idea about the numerical characters
being mistaken for file handles - there isn't usually a requirement to
escape these when Echoing is there?
Perhaps I need to work out a way of replacing numbers with escaped numbers
within the subroutine...I don't want to have to remember to escape them
every time I call the sub.


Scion

unread,
Sep 3, 2010, 11:09:43 AM9/3/10
to


Hmmm.... I wanted to avoid having to edit text twice (possibility of errors)
so that's not a solution for me this time.
Thanks anyway.


foxidrive

unread,
Sep 3, 2010, 11:40:50 AM9/3/10
to

A solution for the end of line numbers issue is either leave a space
before the redirection characters (which is included in the output file)

echo %* >>res.txt

Or place the redirection at the start of the line.

>>res.txt echo %*

--
Regards,
Mic

Timo Salmi

unread,
Sep 3, 2010, 2:31:40 PM9/3/10
to
On 03.09.2010 18:40 foxidrive <foxi...@gotcha.woohoo.invalid> wrote:
> On 4/09/2010 01:08, Scion wrote:
>> Timo Salmi wrote:
>>> On 27.08.2010 18:44 Scion wrote:
>>>> Scion wrote:
>>>> file. Perhaps I'll just call a sub that outputs the text once to screen
>>>> and once to the file:

>>> It is one option. Unfortunately, it is not always quite as simple as
>>> one thinks, because there can be subtle file handle pitfalls in the
>>> subroutine method. For more on that, you may wish to see

> A solution for the end of line numbers issue is either leave a space

> before the redirection characters (which is included in the output file)
> echo %* >>res.txt
> Or place the redirection at the start of the line.
> >>res.txt echo %*

Yes, true. Unfortunately, even that (better) solution breaks down with
some poison characters in the passed text like &
The batch-subroutine method of teeing simply is subject to pitfalls.

foxidrive

unread,
Sep 3, 2010, 3:22:17 PM9/3/10
to
On 4/09/2010 04:31, Timo Salmi wrote:
> On 03.09.2010 18:40 foxidrive <foxi...@gotcha.woohoo.invalid> wrote:
>> On 4/09/2010 01:08, Scion wrote:
>>> Timo Salmi wrote:
>>>> On 27.08.2010 18:44 Scion wrote:
>>>>> Scion wrote:
>>>>> file. Perhaps I'll just call a sub that outputs the text once to
>>>>> screen
>>>>> and once to the file:
>
>>>> It is one option. Unfortunately, it is not always quite as simple as
>>>> one thinks, because there can be subtle file handle pitfalls in the
>>>> subroutine method. For more on that, you may wish to see
>
>> A solution for the end of line numbers issue is either leave a space
>> before the redirection characters (which is included in the output file)
>> echo %* >>res.txt
>> Or place the redirection at the start of the line.
>> >>res.txt echo %*
>
> Yes, true. Unfortunately, even that (better) solution breaks down with
> some poison characters in the passed text like &
> The batch-subroutine method of teeing simply is subject to pitfalls.

There is one robust method of echoing text characters though, Timo.

I believe that only % has issues with this and they will merely be
truncated and not cause an error.


@echo off
call :subroutine "%&!><?*|"
goto :eof

:subroutine
for /f "delims=" %%a in ("%~1") do >>file.txt echo %%a


--
Regards,
Mic

Timo Salmi

unread,
Sep 4, 2010, 1:57:01 AM9/4/10
to
On 03.09.2010 22:22 foxidrive <foxi...@gotcha.woohoo.invalid> wrote:
> There is one robust method of echoing text characters though, Timo.
>
> I believe that only % has issues with this and they will merely be
> truncated and not cause an error.
>
>
> @echo off
> call :subroutine "%&!><?*|"
> goto :eof
>
> :subroutine
> for /f "delims=" %%a in ("%~1") do >>file.txt echo %%a

Good! I have incorporated the discussed into
http://www.netikka.net/tsneti/info/tscmd094.htm#handle

I'm_HERE

unread,
Sep 4, 2010, 5:28:44 AM9/4/10
to
--------------8<----------------
@echo off
Set "$_=%%&!><?*|^"
call :subroutine
goto :eof

:subroutine
for /f "tokens=1*delims==" %%a in ('set $_') do echo %%b >> nee.txt
goto:eof
--------------8<----------------

foxidrive

unread,
Sep 4, 2010, 7:27:56 AM9/4/10
to
On 4/09/2010 19:28, I'm_HERE wrote:
> --------------8<----------------
> @echo off
> Set "$_=%%&!><?*|^"
> call :subroutine
> goto :eof
>
> :subroutine
> for /f "tokens=1*delims==" %%a in ('set $_') do >>tee.txt echo %%b
> goto:eof
> --------------8<----------------

That's good. As long as there are doubled percent characters and there
are no mismatched single percent characters, it's as robust as batch can
make it.


Just for the record Delayed expansion damages the ! and ^ characters in
the example.

@echo off
setlocal enabledelayedexpansion
Set "$_=%%&!><?*|^abc"
call :subroutine
goto :eof

:subroutine
for /f "tokens=1*delims==" %%a in ('set $_') do >>tee.txt echo %%b
goto:eof

--
Regards,
Mic

Frank P. Westlake

unread,
Sep 4, 2010, 9:07:01 AM9/4/10
to
"foxidrive" news:4C822D3...@gotcha.woohoo.invalid...

> That's good. As long as there are doubled percent characters and
> there are no mismatched single percent characters, it's as robust as
> batch can make it.

Regarding text which is entered into the script, percent signs must be
doubled by definition. Also, since the text is being entered by the
script writer it is probably known by that script writer if delayed
expansion is enabled and characters can be escaped if necessary ("^!",
"^^"). If it is not known if delayed expansion is enabled then it can be
tested by the script and special characters can be handled accordingly.
I've done this in some of the scripts I posted here and as I recall it
all characters could be correctly ECHOed.

Regarding text which is read from a file, percent signs need no special
treatment. I don't recall if "!" and "^" require special treatment.

Frank


Message has been deleted

I'm_HERE

unread,
Sep 4, 2010, 9:37:38 AM9/4/10
to
-----------------------------------8<-------------------------
@echo off
call :subroutine "%%%%&!><?*|^abc"

setlocal enabledelayedexpansion
echo !#_!
pause
goto :eof

:subroutine
Set "$_=%~1"
for /f "tokens=1*delims==" %%a in ('set $_') do set "#_=%%b"
endlocal & set "#_=%#_:^^=^%" & goto:eof

----------------------------------8<------------------------

I'm_HERE

unread,
Sep 4, 2010, 9:54:22 AM9/4/10
to
or
------------------------8<-----------------------------

@echo off

Set "$h=%%&!><?*|^abc"
call :con $h
Call :fil $h
pause
goto :eof


:con
setlocal enabledelayedexpansion
echo !%~1!
endlocal & goto :eof

:fil
setlocal enabledelayedexpansion
echo:!%~1!>>tee.txt
endlocal & goto :eof

-----------------------8<------------------------------

foxidrive

unread,
Sep 4, 2010, 12:02:37 PM9/4/10
to
On 4/09/2010 23:54, I'm_HERE wrote:
> or
> ------------------------8<-----------------------------
>
> @echo off
>
> Set "$h=%%&!><?*|^abc"
> call :con $h
> Call :fil $h
> pause
> goto :eof
>
>
> :con
> setlocal enabledelayedexpansion
> echo !%~1!
> endlocal& goto :eof

>
> :fil
> setlocal enabledelayedexpansion
> echo:!%~1!>>tee.txt
> endlocal& goto :eof
>
> -----------------------8<------------------------------


That is exceptionally robust. well done.

Timo, please include this in your write up. Percent signs are the only
characters that need matched pairs and doubling.

This technique is worth noting because it could be used in other places.


@echo off

Set "$h=^^^!!!%%&!><?*|^abc!123"
call :tee $h
pause
goto :eof

:tee
setlocal enabledelayedexpansion
echo !%~1!


echo:!%~1!>>tee.txt
endlocal & goto :eof


--
Regards,
Mic

foxidrive

unread,
Sep 4, 2010, 11:59:42 AM9/4/10
to
On 4/09/2010 23:54, I'm_HERE wrote:
> or
> ------------------------8<-----------------------------
>
> @echo off
>
> Set "$h=%%&!><?*|^abc"
> call :con $h
> Call :fil $h
> pause
> goto :eof
>
>
> :con
> setlocal enabledelayedexpansion
> echo !%~1!
> endlocal& goto :eof

>
> :fil
> setlocal enabledelayedexpansion
> echo:!%~1!>>tee.txt
> endlocal& goto :eof
>
> -----------------------8<------------------------------


That is exceptionally robust. well done.

Timo, please include this in your write up. Percent signs are the only
characters that need matched pairs and doubling.

This technique is worth noting because it could be used in other places.


@echo off

Set "$h=^^^!!!%%&!><?*|^abc!123"
call :tee $h
pause
goto :eof

:tee
setlocal enabledelayedexpansion
echo !%~1!

echo:!%~1!>>tee.txt
endlocal & goto :eof


--
Regards,
Mic

Timo Salmi

unread,
Sep 4, 2010, 12:43:31 PM9/4/10
to
On 04.09.2010 18:59 foxidrive wrote:
> On 4/09/2010 23:54, I'm_HERE wrote:
>> or

>> :fil


>> setlocal enabledelayedexpansion
>> echo:!%~1!>>tee.txt
>> endlocal& goto :eof

> That is exceptionally robust. well done.


>
> Timo, please include this in your write up. Percent signs are the only
> characters that need matched pairs and doubling.

I've included links to this thread. While useful, interesting and
instructive, let's bear in mind the point that compared to using a "tee"
these solutions are, more or less, esoteric.

foxidrive

unread,
Sep 4, 2010, 12:57:40 PM9/4/10
to
On 5/09/2010 02:43, Timo Salmi wrote:

> While useful, interesting and
> instructive, let's bear in mind the point that compared to using a "tee"
> these solutions are, more or less, esoteric.

Yes, I would use a real tee filter... but that's the lure of a batch
file - to do what you can with a limited instruction set. :)


--
Regards,
Mic

0 new messages