Class: Consently::Consent

Inherits:
Object
  • Object
show all
Defined in:
lib/consently/consent.rb

Overview

What the visitor has agreed to, as read from the cookie.

The cookie is deliberately tiny and readable by JavaScript - the banner writes it in the browser and the server only reads it, so a page rendered after the choice can emit the real tags instead of blocked ones.

{"v":1,"c":["analytics"],"t":"2026-08-12T10:00:00Z"}

Constant Summary collapse

NECESSARY =
:necessary

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(categories: [], version: nil, recorded_at: nil, given: true) ⇒ Consent

Returns a new instance of Consent.



41
42
43
44
45
46
# File 'lib/consently/consent.rb', line 41

def initialize(categories: [], version: nil, recorded_at: nil, given: true)
  @categories = Array(categories).map(&:to_sym).freeze
  @version = version
  @recorded_at = recorded_at
  @given = given
end

Instance Attribute Details

#categoriesObject (readonly)

Returns the value of attribute categories.



12
13
14
# File 'lib/consently/consent.rb', line 12

def categories
  @categories
end

#recorded_atObject (readonly)

Returns the value of attribute recorded_at.



12
13
14
# File 'lib/consently/consent.rb', line 12

def recorded_at
  @recorded_at
end

#versionObject (readonly)

Returns the value of attribute version.



12
13
14
# File 'lib/consently/consent.rb', line 12

def version
  @version
end

Class Method Details

Never raises: a cookie can be truncated, hand-edited or left over from an older format, and none of that should take a page down.



20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
# File 'lib/consently/consent.rb', line 20

def self.from_cookie(raw, version:)
  return none if raw.blank?

  data = begin
    JSON.parse(raw.to_s)
  rescue JSON::ParserError
    nil
  end
  return none unless data.is_a?(Hash)

  # A consent given against an older policy version counts as no consent:
  # the banner asks again and nothing runs in the meantime.
  return none unless data["v"].to_s == version.to_s

  new(
    categories: Array(data["c"]).map { |category| category.to_s.to_sym },
    version: data["v"],
    recorded_at: data["t"]
  )
end

.noneObject



14
15
16
# File 'lib/consently/consent.rb', line 14

def self.none
  new(given: false)
end

Instance Method Details

#given?Boolean

Returns:

  • (Boolean)


48
49
50
# File 'lib/consently/consent.rb', line 48

def given?
  @given
end

#granted?(category) ⇒ Boolean

Necessary tags are the ones the site cannot work without, so they never wait for a click.

Returns:

  • (Boolean)


54
55
56
# File 'lib/consently/consent.rb', line 54

def granted?(category)
  category.to_sym == NECESSARY || categories.include?(category.to_sym)
end

#to_hObject



58
59
60
# File 'lib/consently/consent.rb', line 58

def to_h
  { "v" => version, "c" => categories.map(&:to_s), "t" => recorded_at }
end