Module: Tsscmp

Defined in:
lib/tsscmp.rb,
lib/tsscmp/version.rb

Constant Summary collapse

VERSION =
'0.1.4'

Class Method Summary collapse

Class Method Details

.compare(a, b) ⇒ Object

Constant time string comparison.

Returns true if the two arguments have same value, otherwise false.

Raises:

  • (TypeError)


14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
# File 'lib/tsscmp.rb', line 14

def compare(a, b) # rubocop:disable Naming/MethodParameterName
  return false if a.nil? || b.nil?

  # assume the arguments is String
  raise TypeError unless a.is_a?(String) || b.is_a?(String)
  return false unless a.size == b.size

  key = SecureRandom.random_bytes(32)
  ah = OpenSSL::HMAC.hexdigest('sha256', key, a)
  bh = OpenSSL::HMAC.hexdigest('sha256', key, b)

  # Implementation Note:
  # `&& a == b` is a very very conservative comparison.
  # In my opnion, `ah == bh` is enough to compare securely although several other implementations use
  # the strictly method such as:
  #  - https://github.com/rails/rails/blob/v5.2.3/activesupport/lib/active_support/security_utils.rb#L27
  #  - https://github.com/suryagh/tsscmp/blob/v1.0.6/lib/index.js#L35
  # So, as of the present time, I add `&& a == b`.
  ah == bh && a == b
end