0

私は、KDEでよりうまく機能するPerlスクリプトを作成しようとしていますkwrited。これは、私が知る限り、ptsに接続され、KDEシステムトレイ通知を介して受信したすべての行に「KDE書き込みデーモン」というタイトルを付けます。 。

残念ながら、行ごとに個別の通知を行うため、通常の古い書き込みで複数行のメッセージがシステムトレイにスパム送信され、 wallを使用すると、何らかの理由でメッセージの最後の行全体が切断されます。1行のメッセージも消え去ります。

また、シッククライアントを使用するLANを介してブロードキャストできるようにすることも望んでいました。それを始める前に(もちろんSSHが必要です)、SSHなしのバージョンを作成して動作することを確認しました。残念ながら、そうではありません。

perl ./write.pl "Testing 1 2 3"

ここで、以下はの内容です./write.pl

#!/usr/bin/perl

use strict;
use warnings;

my $message = "";
my $device = "";
my $possibledevice = '`w -hs | grep "/usr/bin/kwrited"`'; #Where is kwrited?
$possibledevice =~ s/^[^\t][\t]//;
$possibledevice =~ s/[\t][^\t][\t ]\/usr\/bin\/kwrited$//;
$possibledevice = '/dev/'.$possibledevice;
unless ($possibledevice eq "") {
    $device = $possibledevice;
}

if ($ARGV[0] ne "") {
    $message = $ARGV[0];
    $device = $ARGV[1];
}
else {
    $device = $ARGV[0] unless $ARGV[0] eq "";
    while (<STDIN>) {
        chomp;
        $message .= <STDIN>;
    }
}

if ($message ne "") {
    system "echo \'$message\' > $device";
}
else {
    print "Error: empty message"
}

次のエラーが発生します。

$ perl write.pl "Testing 1 2 3"
Use of uninitialized value $device in concatenation (.) or string at write.pl line 29.
sh: -c: line 0: syntax error near unexpected token `newline'
sh: -c: line 0: `echo 'foo' > '

$possibledeviceどういうわけか、 kwritedがに接続されている/dev/pts/0場合、以下が完全に機能するため、処理中の正規表現やバッククォートエスケープが正しく機能していません。

$ perl write.pl "Testing 1 2 3" /dev/pts/0
4

2 に答える 2

4

コマンドライン引数(文字列 " Testing 1 2 3")を1つだけ指定します。

したがって、$ARGV[1]は未定義です。

したがって$device、内部のロジックのためにundefですif ($ARGV[0] ne "")

したがって、シェルのechoコマンドは何もリダイレクトせず( " echo something >")、シェルは文句を言います(そして、そこから "undefined $ device" Perl警告が発生します)。

デバイスを「1」にする場合は、perl write.pl Testing 1 2 3コマンドラインで引数文字列()の引用符を外します。

また、ファイルハンドルに「$message」を書き込んだり印刷したりするためのファイルとして$deviceを開くことを検討してください。これはもう少し慣用的なPerlであり、Perlからシェルへの遷移/引用などに起因する問題が発生しにくくなっています...

于 2010-06-06T19:11:32.917 に答える
0

1つの問題は'、試行されたシステムコールの周りです。Perlでは一重引用符内で補間は行われません。

単純なケースを見ると:

#!/usr/bin/perl

use strict;
use warnings;


my $possibledevice = '`w -hs | grep "/usr/bin/kwrited"`'; #Where is kwrited?
print $possibledevice;

出力は次のとおりです。

`w -hs | grep "/usr/bin/kwrited"`

したがって、シェル呼び出しは発生しません。修正は、シェル呼び出しを次のようなものに変更することです。

my $possibledevice = `w -hs | grep \"/usr/bin/kwrited\"`; #shud b there...
#or
my $possibledevice = qx$w -hs | grep \"/usr/bin/kwrited\"$; #alternate form

perlopまたはperldocの演算子のようなさまざまな引用についてはこちらをご覧ください

ここにバッククォート、システム、シェルのチュートリアルがあります

于 2010-06-06T18:54:50.620 に答える