如何访问子进程的 STDIN?

发布于 2024-11-18 14:12:40 字数 134 浏览 2 评论 0原文

我想运行命令:

nc localhost 9998

然后我希望我的脚本监视文件并在文件更改时将文件内容回显到该子进程。

我无法制定重定向方案。如何访问子进程的STDIN?

I want to run the command:

nc localhost 9998

Then I want my script to monitor a file and echo the contents of the file to this sub process whenever the file changes.

I can't work out the re-direction scheme. How can get access to the STDIN of the subprocess?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

你好,陌生人 2024-11-25 14:12:40

怎么样

tail -f $file |nc localhost 9998

编辑

:既然你已经有一个缓冲区,那么你可以尝试这样的事情:

while [ 1 ]; do
    # Your stuff here.
    buf=yourfunctionhere
    buffer=$buffer$buf

    if [ ! -z $buffer ]; then
        echo $buffer |nc localhost 9998
        # Empty buffer on success.
        if [ $? -eq 0 ]; then
            buffer="";
        fi
    fi
done

How about

tail -f $file |nc localhost 9998

Edit:

Since you already have a buffer, then you can try something like this:

while [ 1 ]; do
    # Your stuff here.
    buf=yourfunctionhere
    buffer=$buffer$buf

    if [ ! -z $buffer ]; then
        echo $buffer |nc localhost 9998
        # Empty buffer on success.
        if [ $? -eq 0 ]; then
            buffer="";
        fi
    fi
done
生死何惧 2024-11-25 14:12:40
mkfifo X
some_program <X >output &
create_input >X

some_program 将阻止读取 X,直到 create_input 对其进行写入。

mkfifo X
some_program <X >output &
create_input >X

some_program will block reading X until create_input writes to it.

善良天后 2024-11-25 14:12:40

我认为可以接受的两个解决方案:

1)使用 coprocess,这样我们就可以通过 COPROC[0/1] 数组访问 coprocess 命令创建的进程的 stdin 和 stdout。

2)我最终所做的是将我的应用程序分成两个代码块,如下所示。第一个块写入标准输出,然后通过管道传输到第二个块的标准输入。当第二个代码块中的 netcat 出现问题时,这为我提供了一种干净的方法来缓冲数据:(

{ while true;
  write to STDOUT; } |
{ while true
  nc localhost 9998 }

实际上,该脚本要复杂得多,因为当 netcat 无法连接时,第二个命令提供到磁盘缓冲,但是使用管道提供缓冲,以便当网络问题中断 netcat 时数据不会丢失)

Two solutions that I found acceptable:

1) use coprocess, this way we have access to stdin and stdout of the process created by the coprocess command via the COPROC[0/1] array.

2) What I ultimately did is separate my application into two code blocks as shown below. The first block writes to stdout, that is then piped to the stdin of the second block. This gives me a clean way to buffer data when there are issues with netcat in the second code block:

{ while true;
  write to STDOUT; } |
{ while true
  nc localhost 9998 }

(in actuality the script is far more complex as the second command provides to-disk buffering when netcat is unable to connect, but the use of the pipe provides buffering so that data isn't lost when a network issue interrupts netcat)

温暖的光 2024-11-25 14:12:40

我找到了使用 diff 和简单的 bash 脚本的解决方案。

以下脚本执行 cat $file > $namedpipe 当文件更改时。这是我制作的脚本 check-file.sh

#!/bin/bash

file=$1

tmp=`mktemp`
cp "$file" "$tmp"
namedpipe=`mktemp`
rm -rf $namedpipe
mkfifo $namedpipe

function cleanup() {
    echo "end of program"
    rm -rf $tmp
    rm -rf $namedpipe
    exit 1;
}

trap cleanup SIGINT
tail -f $namedpipe 2> /dev/null | netcat localhost 9998 &
while true; do
    diff=$(diff "$file" "$tmp")
    if [ ! -z "$diff" ]; then
        cat $file > $namedpipe
        cp $file $tmp
    fi
    sleep 1
done

该脚本将文件名作为输入。例如,在您的环境中尝试以下命令(运行 netcat -l 9998):

touch /tmp/test
bash check-file.sh /tmp/test &
echo "change 1" > /tmp/test
sleep 1
echo "change 2" > /tmp/test
sleep 1
echo "change 3" > /tmp/test

注意:临时文件会被陷阱清理,因此您可以优雅地中断此脚本。

I found a solution using diff and a simple bash script.

The following script execute cat $file > $namedpipe when file change. This is the script I made check-file.sh:

#!/bin/bash

file=$1

tmp=`mktemp`
cp "$file" "$tmp"
namedpipe=`mktemp`
rm -rf $namedpipe
mkfifo $namedpipe

function cleanup() {
    echo "end of program"
    rm -rf $tmp
    rm -rf $namedpipe
    exit 1;
}

trap cleanup SIGINT
tail -f $namedpipe 2> /dev/null | netcat localhost 9998 &
while true; do
    diff=$(diff "$file" "$tmp")
    if [ ! -z "$diff" ]; then
        cat $file > $namedpipe
        cp $file $tmp
    fi
    sleep 1
done

This script take as an input the name of a file. For example try these commands in your environment (whit netcat -l 9998 running):

touch /tmp/test
bash check-file.sh /tmp/test &
echo "change 1" > /tmp/test
sleep 1
echo "change 2" > /tmp/test
sleep 1
echo "change 3" > /tmp/test

Note: The temp file get cleaned up by the trap, so you can interrupt this script gracefuly.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文