Skip to content

Instantly share code, notes, and snippets.

@jmaslak
Last active January 11, 2023 05:15
Show Gist options
  • Save jmaslak/ba3cbfe1abd13b76ac906cfaeb0f62e9 to your computer and use it in GitHub Desktop.
Save jmaslak/ba3cbfe1abd13b76ac906cfaeb0f62e9 to your computer and use it in GitHub Desktop.
#!/usr/bin/env raku
use v6.d;
use Cro::HTTP::Server;
use Cro::HTTP::Router;
my $application = route {
get -> {
content 'text/html', 'Hello World';
}
}
# Basically a copy of Cro::TCP::Listener, but doesn't bother with
# allowing nodelay to be set and grabs the port number with a nest of
# tap and supplier.
class NuListener does Cro::Source {
has Str $.host = 'localhost';
has Cro::Port $.port is required;
method produces() { Cro::TCP::ServerConnection }
method incoming() {
my $listen-socket = IO::Socket::Async.listen($!host, $!port);
my $supplier = Supplier::Preserving.new();
my $tap = $listen-socket.tap( { $supplier.emit($_) } );
$!port = $tap.socket-port.result;
supply {
whenever $supplier.Supply() -> $socket {
emit Cro::TCP::ServerConnection.new(:$socket);
}
}
}
}
my Cro::Service $service = Cro::HTTP::Server.new(
:host('localhost'), :port(0), :$application
);
# Swap out the TCP component...
$service.components[0] = NuListener.new(:host('localhost'), :port(0));
$service.start;
my $ephemeral-port = $service.components[0].port;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment