# Copyright (c) 2022 Contrast Security, Inc. See https://www.contrastsecurity.com/enduser-terms-0317a for more details. # frozen_string_literal: true module Contrast module Agent module Assess module Rule module Response # This rule checks if the HTTP Headers include HSTS header and ensures that the max-age value # is set to a value greater than 0. class HSTSHeader < BaseRule def rule_id 'hsts-header-missing' end protected HEADER_KEY = 'Strict-Transport-Security' HEADER_KEY_SYM = HEADER_KEY.to_sym MAX_AGE = 'max-age' MAX_AGE_SYM = MAX_AGE.to_sym # Rules discern which responses they can/should analyze. # # @param response [Contrast::Agent::Response] the response of the application def analyze_response? response super && response.headers.cs__is_a?(Hash) end # Determine if the Response violates the Rule or not. If it does, return the evidence that proves it so. # # @param response [Contrast::Agent::Response] the response of the application # @return [Hash, nil] return string # representation of the max_age def violated? response headers = response.headers target = headers[HEADER_KEY] || headers[HEADER_KEY_SYM] # this rule is safe by default if no target => no evidence # if the property max_age is not positive or absent then the rule is violated return unless target max_age = target[MAX_AGE] || target[MAX_AGE_SYM] return if max_age.to_i.positive? evidence max_age end # returns evidence that the max_age is negative or absent # # @param max_age [String] String representation of the max-age value to which the header is set # @return [Hash] return string representation of # the max_age def evidence max_age { data: max_age.to_s } end end end end end end end