Martin
Martin

Reputation: 10878

Buffer output before piping it

I need to write a batch file that is piping the output of SQLCMD to an application that will modify the tables on which the SQLCMD is reading from:

sqlcmd -E -h-1 -S . -d Database -i Script.sql|ModifyApplication.exe

Unfortunately the command from above does run into a dead lock. So I modified the batch script to look like that:

sqlcmd -E -h-1 -S . -d Database -i Script.sql>tmp.txt
type tmp.txt|ModifyApplication.exe

This works - but it's ugly because it needs to write to the file system and if for some reason the SQLCMD fails to write the file then the old file from the previous run will be piped into ModifyApplication.exe.

It would be ideal if I could just buffer all the data from the sqlcmd into the memory before piping it to ModifyApplication.exe like so:

sqlcmd -E -h-1 -S . -d Database -i Script.sql|Buffer.exe|ModifyApplication.exe

Is there a "Buffer.exe"-like command in windows?

Upvotes: 0

Views: 298

Answers (4)

Aacini
Aacini

Reputation: 67236

You may try my PIPE.COM program. Create it this way:

@ECHO off
if not exist pipe.com call :DefinePipe
sqlcmd -E -h-1 -S . -d Database -i Script.sql|pipe|ModifyApplication.exe

goto :EOF

:DefinePipe
setlocal DisableDelayedExpansion
set pipe=´)€ì!Í!ŠÐŠà€Ä!€ü.t2€ü+u!:æu8²A€ê!´#€ì!Í!².€ê!´#€ì!Í!²+€ê!´#€ì!Í!Šò€Æ!´,€ì!Í!"Àu°´LÍ!ëÒ
setlocal EnableDelayedExpansion
echo !pipe!>pipe.com
exit /B

You must be aware that my PIPE.COM insert a blank space in empty lines. However, I can modify that behavior if you not need it.

EDIT: Source code added, requested by Martin

The Batch file below create a simpler version of PIPE.COM that does not check for empty lines:

(
echo    A100
echo    mov     ah,8            ;AH = CONSOLE_INPUT_WITHOUT_ECHO
echo    int     21H             ;get next char. in AL
echo    mov     dl,al           ;pass it to DL
echo    mov     ah,2            ;AH = VIDEO_OUTPUT
echo    int     21H             ;show the char. in the screen
echo    mov     ah,0B           ;AH = CHECK_KEYBOARD_STATUS
echo    int     21H             ;get key status in AL: 0=no more keys
echo    cmp     al,0            ;is there another key?
echo    jne     100             ;yes: go back for it
echo    mov     ah,4C           ;AH = TERMINATE_PROGRAM
echo    int     21H             ;terminate this program
echo/
echo    RCX
echo    16
echo    W
echo    Q
) | DEBUG PIPE.COM

To get basic help on DEBUG use, type DEBUG then ? then Q. If you have not DEBUG.COM program, you may get it from this site

Upvotes: 1

PA.
PA.

Reputation: 29369

even if sqlcmd "fails to write to the file system", the > operator would erase the previous tmp.txt so it wil not reuse "the old file from the previous run". However, you can always make sure that this would not be the case by inserting a del tmp.txt command prior to the sqlcmd execution.

Upvotes: 0

Martin
Martin

Reputation: 10878

As nos suggested I wrote one:

using System;
using System.Collections.Generic;

namespace Buffer
{
    class Program
    {
        static void Main(string[] args)
        {
            foreach(string line in new List<string>(GetLines()))
            {
                Console.WriteLine(line); 
            }
        }

        static IEnumerable<string> GetLines()
        {
            string line;
            while (!string.IsNullOrEmpty(line = Console.ReadLine()))
            {
                yield return line;
            }
        }
    }
}

Upvotes: 0

nos
nos

Reputation: 229244

There is no such standard utility. You should write one, it's a rather simple thing to create.

Upvotes: 0

Related Questions