Skip to content

Instantly share code, notes, and snippets.

@ktat
Created May 31, 2011 09:15
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save ktat/1000223 to your computer and use it in GitHub Desktop.
Save ktat/1000223 to your computer and use it in GitHub Desktop.
WebSocket perl client(AE)
#!/usr/bin/perl
use utf8;
use strict;
use warnings;
use AnyEvent;
use Protocol::WebSocket::Frame;
use Protocol::WebSocket::Handshake::Client;
use IO::Socket;
use constant {READ => 0, WRITE => 1};
$| = 1;
run();
sub run {
my $cv = AE::cv;
my $s = IO::Socket::INET->new(PeerAddr => '127.0.0.1', PeerPort => 50000, Proto => 'tcp', Blocking => 0);
if (not $s or not $s->connected) {
client_exit();
}
my $hc = Protocol::WebSocket::Handshake::Client->new(url => 'ws://127.0.0.1:50000/');
# handshare request
$s->syswrite($hc->to_string);
my (@messages, $wsr, $wsw, $stdin);
my $finish = sub { undef $stdin; undef $wsr; undef $wsw; $cv->send; client_exit($s) };
local @SIG{qw/INT TERM ALRM/} = ($finish) x 3;
$stdin = AE::io *STDIN, READ, sub {
my $line = <STDIN>;
unless ($line) {
$finish->();
} else {
chomp $line;
push @messages, Encode::decode('utf8', $line)
}
};
$wsw = AE::io $s, WRITE, sub {
if ($s->connected) {
while (my $msg = shift @messages) {
$s->syswrite(Protocol::WebSocket::Frame->new($msg)->to_string);
}
} else {
$finish->();
}
};
# parse server response
my $frame_chunk = '';
until ($hc->is_done) {
$s->sysread(my $buf, 1024);
if ($buf) {
if ($buf =~ s{(\x00.+)$}{}) {
$frame_chunk = $1;
}
print $buf;
$hc->parse($buf);
if ($hc->error) {
warn $hc->error;
$finish->();
}
}
}
my $frame = Protocol::WebSocket::Frame->new();
$frame->append($frame_chunk) if $frame_chunk;
$wsr = AE::io $s, READ, sub {
$s->sysread(my $buf, 100);
$frame->append($buf);
while (my $msg = $frame->next) {
print Encode::encode('utf8', $msg), "\n";
}
};
$cv->recv;
client_exit($s);
}
sub client_exit {
my $s = shift;
close $s if $s;
exit;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment