module Calligraphy::Rails::WebDavPreconditions

Provides methods to handle checking and validating WebDAV request preconditions.

Private Instance Methods

check_preconditions() click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 10
def check_preconditions
  return true unless request.headers['If'].present?

  evaluate_if_header
end
conditions_hash() click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 47
def conditions_hash
  {
    dav_no_lock: nil,
    etag: nil,
    lock_token: nil,
    resource: nil
  }
end
evaluate_etag_condition(conditions) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 102
def evaluate_etag_condition(conditions)
  validators = [@resource.etag, '']
  validate_etag validators, conditions[:etag]
end
evaluate_if_header() click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 16
def evaluate_if_header
  conditions_met = false
  condition_lists = if_conditions

  condition_lists.each do |list|
    conditions = parse_preconditions list

    conditions_met = evaluate_preconditions conditions
    break if conditions_met
  end

  conditions_met
end
evaluate_preconditions(conditions) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 80
def evaluate_preconditions(conditions)
  conditions_met = true

  if conditions[:etag]
    conditions_met = false unless evaluate_etag_condition conditions
  end

  conditions_met = false if conditions[:dav_no_lock]
  conditions_met
end
if_conditions() click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 30
def if_conditions
  if request.headers['If'][0] == '<'
    request.headers['If'].split Calligraphy::TAGGED_LIST_REGEX
  else
    request.headers['If'].split Calligraphy::UNTAGGAGED_LIST_REGEX
  end
end
match_dav_no_lock(list) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 56
def match_dav_no_lock(list)
  return nil unless list =~ Calligraphy::DAV_NO_LOCK_REGEX

  list =~ Calligraphy::DAV_NOT_NO_LOCK_REGEX ? nil : true
end
parse_preconditions(list) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 38
def parse_preconditions(list)
  conditions = conditions_hash
  conditions[:dav_no_lock] = match_dav_no_lock list
  conditions[:resource] = scan_for_resource list
  conditions[:lock_token] = scan_for_lock_token list
  conditions[:etag] = scan_for_etag list
  conditions
end
scan_for_etag(list) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 74
def scan_for_etag(list)
  return nil unless list =~ Calligraphy::ETAG_IF_REGEX

  list.scan(Calligraphy::ETAG_IF_REGEX).flatten[0]
end
scan_for_lock_token(list) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 68
def scan_for_lock_token(list)
  return nil unless list =~ Calligraphy::LOCK_TOKEN_REGEX

  list.scan(Calligraphy::LOCK_TOKEN_REGEX).flatten[0]
end
scan_for_resource(list) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 62
def scan_for_resource(list)
  return nil unless list =~ Calligraphy::RESOURCE_REGEX

  list.scan(Calligraphy::RESOURCE_REGEX).flatten[0]
end
target_resource(conditions) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 91
def target_resource(conditions)
  if conditions[:resource]
    @resource_class.new(
      resource: conditions[:resource],
      mount: @resource.mount_point
    )
  else
    @resource
  end
end
validate_etag(etag_validators, validate_against) click to toggle source
# File lib/calligraphy/rails/web_dav_preconditions.rb, line 107
def validate_etag(etag_validators, validate_against)
  cache_key = ActiveSupport::Cache.expand_cache_key etag_validators

  validate_against == "W/\"#{Digest::MD5.hexdigest(cache_key)}\""
end