From: Eric Wong Date: Thu, 26 Sep 2024 00:55:03 +0000 (+0000) Subject: www: load CSS files in same dir if @import is in use X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=869bd64e57850806ce2e4a1ecd72560238fe9237;p=thirdparty%2Fpublic-inbox.git www: load CSS files in same dir if @import is in use In case user-supplied CSS uses @import statements, load any other unspecified CSS files in that directory to ensure they can be accessed by clients. --- diff --git a/lib/PublicInbox/WWW.pm b/lib/PublicInbox/WWW.pm index 6f7c30b93..65f95eb85 100644 --- a/lib/PublicInbox/WWW.pm +++ b/lib/PublicInbox/WWW.pm @@ -13,6 +13,7 @@ package PublicInbox::WWW; use strict; use v5.10.1; +use autodie qw(chdir opendir); use PublicInbox::Config; use PublicInbox::Git; use PublicInbox::Hval; @@ -593,6 +594,7 @@ sub stylesheets_prepare ($$) { my $stylesheets = $self->{pi_cfg}->{css} || []; my $links = []; my $inline_ok = 1; + my (%css_dir, @css_dir); foreach my $s (@$stylesheets) { my $attr = {}; @@ -606,8 +608,9 @@ sub stylesheets_prepare ($$) { if (defined $attr->{href}) { $inline_ok = 0; } else { - my $fn = $_; - my ($key) = (m!([^/]+?)(?:\.css)?\z!i); + my ($fn, $dir, $key); + $fn = $_; + ($dir, $key) = (m!\A(?:(.+?)/)?([^/]+?)(?:\.css)?\z!i); if ($key !~ /\A[a-zA-Z0-9_\-\.]+\z/) { warn "ignoring $fn, non-ASCII word character\n"; next; @@ -617,6 +620,8 @@ sub stylesheets_prepare ($$) { ($local, $ctime) = @$rec; } elsif (open(my $fh, '<', $fn)) { ($local, $ctime) = _read_css $fh, $mini, $fn; + $local =~ /\@import\b/ && !$css_dir{$dir}++ and + push @css_dir, $dir; $css_map->{$key} = [ $local, $ctime ]; } else { warn "failed to open $fn: $!\n"; @@ -661,6 +666,31 @@ sub stylesheets_prepare ($$) { } else { $self->{-style_inline} = $buf; } + # load potentially imported CSS files in known CSS directories + if (@css_dir && !$self->{-css_dir}) { + opendir my $cwddh, '.'; + for my $d (@css_dir) { + CORE::opendir my $dh, $d or do { + warn "W: opendir($d): $!"; + next; + }; + chdir $dh; + my @css = grep /\.css\z/i, readdir $dh; + for my $fn (@css) { + my ($key) = ($fn =~ m!([^/]+?)(?:\.css)?\z!i); + next if $css_map->{$key}; + -f $fn or next; + # no warning for autoloaded CSS + open my $fh, '<', $fn or next; + -T $fh or next; + my ($local, $ctime) = + _read_css $fh, $mini, "$d/$fn"; + $css_map->{$key} = [ $local, $ctime ]; + } + chdir $cwddh; + } + $self->{-css_dir} = \@css_dir; + } $css_map; }