Created
August 26, 2014 01:31
-
-
Save hoelzro/671912c49b0efcc8d2aa to your computer and use it in GitHub Desktop.
HTTP User Agent Example
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#| Abstract representation of an HTTP connection | |
role HTTPConnection { | |
method send(Buf $bytes) { ... } | |
} | |
# Stub classes that are HTTPConnections, just to illustrate the kind of things | |
# you could do. They will probably wrap each other, something like this: | |
# | |
# SSLConnection.new(ConnectProxyConnection.new(:host<...>, :port(...))); | |
#| Raw TCP connection; useful for direct http:// URLs | |
class RawConnection does HTTPConnection { ... } | |
#| HTTP over SSL; useful for https:// | |
class SSLConnection does HTTPConnection { ... } | |
#| Useful if you need to go over a SOCKS proxy | |
class SOCKSConnection does HTTPConnection { ... } | |
#| Go over a network proxy using the CONNECT verb | |
class ConnectProxyConnection does HTTPConnection { ... } | |
#| Go over an HTTP proxy without using CONNECT | |
class ProxyConnection does HTTPConnection { ... } | |
class ConnectionManager { | |
#| Returns an HTTPConnection object appropriate for C<$req>. | |
method connect(Request $req) returns HTTPConnection { | |
... | |
} | |
} | |
# The UserAgent itself | |
class UserAgent { | |
has $.connection-manager is rw handles 'connect' = ConnectionManager.new; # this could be a different object (you could even provide a fake one for testing) | |
method send-request(Request $req) { | |
self.*before-request($req); | |
my $conn = $.connect($req); | |
my $res = $conn.send($req.Buf); | |
$res = Response.parse($res); | |
self.*after-request($req, $res); | |
$res | |
} | |
method GET($url) { | |
$.send-request(Request.new(:method<GET>, :$url)) | |
} | |
} | |
# An example middleware | |
role CookieBehavior { | |
method before-request(Request $req) { | |
# XXX insert cookies for domain | |
} | |
method after-request(Request $, Response $res) { | |
# XXX store cookies for domain | |
} | |
} | |
# Another middleware | |
role AuthBasicBehavior { | |
method before-request(Request $req) { | |
# XXX insert username/password into $req | |
} | |
} | |
# Example: | |
my $ua = UserAgent.new does (CookieBehavior, AuthBasicBehavior); # there would probably be some internal sugar for this in UserAgent |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment