This is an automated email from the ASF dual-hosted git repository.
sebb pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/whimsy.git
The following commit(s) were added to refs/heads/master by this push:
new c982ab75 Tweak CSP checking
c982ab75 is described below
commit c982ab754699ba5d6c38353f6e4a514003283d46
Author: Sebb <[email protected]>
AuthorDate: Thu Oct 30 22:36:46 2025 +0000
Tweak CSP checking
---
lib/whimsy/sitestandards.rb | 63 +++++++++++++++++++++++++++++++++------------
1 file changed, 47 insertions(+), 16 deletions(-)
diff --git a/lib/whimsy/sitestandards.rb b/lib/whimsy/sitestandards.rb
index f678dd4a..8266b904 100644
--- a/lib/whimsy/sitestandards.rb
+++ b/lib/whimsy/sitestandards.rb
@@ -141,10 +141,10 @@ module SiteStandards
CHECK_DOC => 'Projects SHOULD add a copy of their logo to
https://www.apache.org/logos/ to be included in ASF homepage.',
},
- 'csp' => { # Custom: CSP must follow standards
- CHECK_TEXT => 'Non-standard CSP',
+ 'csp_check' => { # Custom: CSP must follow standards
+ CHECK_TEXT => 'Non-default CSP',
CHECK_CAPTURE => nil,
- CHECK_VALIDATE => :CSP,
+ CHECK_VALIDATE => %r{OK},
CHECK_TYPE => 'message',
CHECK_POLICY => 'https://infra.apache.org/tools/csp.html',
CHECK_DOC => 'Websites must not replace the default
Content-Security-Policy',
@@ -238,7 +238,8 @@ module SiteStandards
worker-src 'self' data: blob:;
EOD
- NON_PMC = <<-EOD.strip.gsub("\n",'').gsub(/ +/, ' ')
+ # CSP for main website
+ WWW_CSP = <<-EOD.strip.gsub("\n",'').gsub(/ +/, ' ')
default-src 'self' data: 'unsafe-inline'
https://www.apachecon.com/ https://analytics.apache.org/
http://analytics.apache.org/
https://www.youtube-nocookie.com https://www.youtube.com;
@@ -252,22 +253,51 @@ module SiteStandards
DEFAULT_CSP_RE = %r{^#{DEFAULT_CSP}$}
- def CSP(site, key)
- squashed = site&.gsub(/ +/, ' ') # data might be missing
- return true if squashed == NON_PMC
- if squashed =~ DEFAULT_CSP_RE
- # custom = $1
- # $stderr.puts [key, custom].inspect if custom.size > 1
- return true
- end
- return false
- end
-
def _validate(site, match, key)
- return method(match).call(site, key) if match.is_a? Symbol
+ # return method(match).call(site, key) if match.is_a? Symbol
return site =~ match
end
+ # For possible later use:
+ # def parse_csp(csp)
+ # ret={}
+ # csp.chomp(';').split(';').each do |part|
+ # words = part.strip.split
+ # key = words.shift
+ # ret[key] = Set.new(words)
+ # end
+ # return ret
+ # end
+
+ # process csp entries to return
+ # - exact match
+ # - has overrides
+ # - invalid
+ def process_csp(sites)
+ sites.each do |site, data|
+ csp = data.fetch('csp', '')
+ squashed = csp.gsub(/ +/, ' ')
+ m = DEFAULT_CSP_RE.match(squashed)
+ if m # the syntax of the CSP appears to be OK
+ extras = m.captures.uniq
+ if extras.size == 1
+ extra1 = extras.first
+ if extra1 == ''
+ data['csp_check'] = 'OK'
+ else
+ data['csp_check'] = "Extras: #{extra1}"
+ end
+ else
+ data['csp_check'] = "Mixed Extras - should not happen: #{extras}"
+ end
+ elsif data['nonpmc'] and data['uri'] =~
%r{^https://(www\.)?apache\.org/} and squashed == WWW_CSP
+ data['csp_check'] = 'OK'
+ else # did not match
+ data['csp_check'] = "Invalid: #{squashed}"
+ end
+ end
+ end
+
# Analyze data returned from site-scan.rb by using checks[CHECK_VALIDATE]
regex
# If value =~ CHECK_VALIDATE, SITE_PASS
# If value is present (presumably from CHECK_TEXT|CAPTURE), then SITE_WARN
@@ -277,6 +307,7 @@ module SiteStandards
# @return [overall counts, description of statuses, success listings]
# called by site_or_pod.rb
def analyze(sites, checks)
+ process_csp sites
success = Hash.new { |h, k| h[k] = Hash.new(&h.default_proc) }
counts = Hash.new { |h, k| h[k] = Hash.new(&h.default_proc) }
checks.each do |nam, check_data|