]> Sergey Matveev's repositories - public-inbox.git/commitdiff
wwwstatic: do not open() files for HEAD requests
authorEric Wong <e@80x24.org>
Wed, 1 Jan 2020 10:38:57 +0000 (10:38 +0000)
committerEric Wong <e@80x24.org>
Wed, 1 Jan 2020 19:10:59 +0000 (19:10 +0000)
open() is a much more expensive syscall than stat(),
so avoid it

lib/PublicInbox/WwwStatic.pm

index c605e64f51b1aa3af868eaad4493e3d62830f7ff..093a79200c8ac580494b925524286ebc520e0e26 100644 (file)
@@ -51,7 +51,9 @@ sub prepare_range {
                if ($len <= 0) {
                        $code = 416;
                } else {
-                       sysseek($in, $beg, SEEK_SET) or return r(500);
+                       if ($in) {
+                               sysseek($in, $beg, SEEK_SET) or return r(500);
+                       }
                        push @$h, qw(Accept-Ranges bytes Content-Range);
                        push @$h, "bytes $beg-$end/$size";
 
@@ -70,8 +72,13 @@ sub response {
        my ($env, $h, $path, $type) = @_;
        return r(404) unless -f $path && -r _; # just in case it's a FIFO :P
 
-       open my $in, '<', $path or return;
-       my $size = -s $in;
+       my ($size, $in);
+       if ($env->{REQUEST_METHOD} eq 'HEAD') {
+               $size = -s _;
+       } else { # GET, callers should've already filtered out other methods
+               open $in, '<', $path or return r(403);
+               $size = -s $in;
+       }
        my $mtime = time2str((stat(_))[9]);
 
        if (my $ims = $env->{HTTP_IF_MODIFIED_SINCE}) {
@@ -86,13 +93,13 @@ sub response {
                return $code if ref($code);
        }
        push @$h, 'Content-Length', $len, 'Last-Modified', $mtime;
-       my $body = bless {
+       my $body = $in ? bless {
                initial_rd => 65536,
                len => $len,
                in => $in,
                path => $path,
                env => $env,
-       }, __PACKAGE__;
+       }, __PACKAGE__ : [];
        [ $code, $h, $body ];
 }