App-DubiousHTTP
view release on metacpan or search on metacpan
lib/App/DubiousHTTP/Tests/Common.pm view on Meta::CPAN
"<script src=/ping.js></script><script>ping_back('/ping?BAD:$spec')</script><body style='background: #e30e2c;'><div style='text-align:center'>HTML</div></body>" ]
},
'warn.html' => sub {
my $spec = shift;
return [ "Content-type: text/html\r\n",
"<script src=/ping.js></script><script>ping_back('/ping?WARN:$spec')</script><body style='background: #e7d82b'><div style='text-align:center'>HTML</div></body>" ]
},
# we hide javascript behind GIF87a to work around content filters :)
'ok.js' => sub {
my $spec = shift;
return [ "Content-type: application/javascript\n",
"GIF87a=1;try { document.getElementById('$spec').style.backgroundColor = '#00e800'; } catch(e) {} ping_back('/ping?OK:$spec');" ]
},
'bad.js' => sub {
my $spec = shift;
return [ "Content-type: application/javascript\r\n",
"GIF87a=1;try { document.getElementById('$spec').style.backgroundColor = '#e30e2c'; } catch(e) {} ping_back('/ping?BAD:$spec');" ]
},
'warn.js' => sub {
my $spec = shift;
return [ "Content-type: application/javascript\r\n",
"GIF87a=1;try { document.getElementById('$spec').style.backgroundColor = '#e7d82b'; } catch(e) {} ping_back('/ping?WARN:$spec');" ]
},
'ping' => [ "Content-type: text/plain\r\n", "pong" ],
'ping.js' => [
"Content-type: application/javascript\r\n".
"Expires: Tue, 30 Jul 2033 20:04:02 GMT\r\n",
<<'PING_JS' ],
GIF87a=1;
function ping_back(url) {
var xmlHttp = null;
try { xmlHttp = new XMLHttpRequest(); }
catch(e) {
try { xmlHttp = new ActiveXObject("Microsoft.XMLHTTP"); }
catch(e) {
try { xmlHttp = new ActiveXObject("Msxml2.XMLHTTP"); }
catch(e) { xmlHttp = null; }
}
}
if (xmlHttp) {
xmlHttp.open('GET', url, true);
xmlHttp.send(null);
}
}
PING_JS
'set_success.js' => sub {
my $spec = shift;
return [ "Content-type: application/javascript\n", "set_success('$spec','js');" ]
},
'parent_set_success.html' => sub {
my $spec = shift;
return [ "Content-type: text/html\n", "<script>parent.set_success('$spec','html');</script>" ]
},
'stylesheet.css' => [
"Content-type: text/css\r\n".
"Expires: Tue, 30 Jul 2033 20:04:02 GMT\r\n",
<<'STYLESHEET' ],
body { max-width: 55em; line-height: 140%; margin-left: 2em; }
ul { list-style-type: square; padding-left: 2em; }
h1 { font-variant: small-caps; font-size: x-large; }
h2,h3 { font-size: large; }
.runtest { text-align: right; margin-right: 5em; margin-top: 2em; }
.runtest a {
text-decoration: none;
background-color: #bfbfbf;
color: #333333;
padding: 4px 6px;
white-space: nowrap;
}
#test_novirus a { background-color: #70e270; padding: 8px 10px; }
#test_virus a { background-color: #ff4d4d; padding: 8px 10px; }
h1,h2,h3 { border: 1px; border-style: solid; padding: 5px 10px 5px 10px; }
h1 { color: #000; background: #eee; padding-top: 10px; padding-bottom: 10px; }
h2 { color: #444; background: #eee; }
h3 { color: #444; background: #fff; }
h2,h3 { margin-top: 2em; }
* { font-size: medium; font-family: Verdana,sans-serif; }
pre { font-family: Monospace,monospace; }
.button {
text-decoration: none;
background-color: #EEEEEE;
color: #333333;
padding: 2px 6px 2px 6px;
border-top: 1px solid #CCCCCC;
border-right: 1px solid #333333;
border-bottom: 1px solid #333333;
border-left: 1px solid #CCCCCC;
white-space: nowrap;
}
STYLESHEET
# give the bots something to play with
'robots.txt' => [
"Content-type: text/plain\r\n",
"User-Agent: *\nDisallow: /have-fun-looking-for-goodies/\n"
],
# and a nice favicon
'favicon.ico' => [ "Content-type: image/vnd.microsoft.icon\r\n", decode_base64(<<'FAVICON') ],
AAABAAEAEBAQAAEABAAoAQAAFgAAACgAAAAQAAAAIAAAAAEABAAAAAAAgAAAAAAAAAAAAAAAEAAA
AAAAAAAAAAAASB3MAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAERAAAAAAAAAREAAAAAAAABAQAAAAAAARER
EQAAAAARAAABEAAAAAAAAAAAAAAAAAERAAAAAAAAABAAAAAAAAAAAAAAAAAAAQAAAQAAAAAREAAR
EAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD//wAA//8AAP4/AAD+PwAA/r8AAPgPAADz5wAA//8A
AP4/AAD/fwAA//8AAPvvAADxxwAA//8AAP//AAD//wAA
FAVICON
);
my %cache;
sub content {
my ($page,$spec) = @_;
$page =~s{^/+}{};
if (my $e = $cache{$page}) {
return @$e;
}
my ($hdr,$data,$bad);
if ( $basedir && -f "$basedir/$page" && open( my $fh,'<',"$basedir/$page" )) {
$data = do { local $/; <$fh> };
if ($data =~s{\A((?:\w+(?:-\w*)*:.*\r?\n){1,10})\r?\n}{}) {
# assume header + body
( $hdr = $1 ) =~s{\r?\n}{\r\n}g;
$bad = $1 if $hdr =~s{^X-Virus:[ \t]*(.*\S)[ \t]*\r?\n}{}mi;
# check if we have a brotli compressed version
if (open($fh,'<',"$basedir/$page.brotli")
and my $brotli = do { local $/; <$fh> }) {
# remove optional header
$brotli =~s{\A((?:\w+(?:-\w*)*:.*\r?\n){1,10})\r?\n}{};
bro_compress($data,$brotli);
}
} else {
$hdr =
$page =~m{\.js$} ? "Content-type: application/javascript\r\n" :
$page =~m{\.css$} ? "Content-type: text/css\r\n" :
$page =~m{\.html?$} ? "Content-type: text/html\r\n" :
$page =~m{\.(gif|png|jpeg)$} ? "Content-type: image/$1\r\n" :
"Content-type: application/octet-stream\r\n";
( run in 0.725 second using v1.01-cache-2.11-cpan-5735350b133 )