class DeviceDetector::Device

Constants

DEVICE_BRANDS

github.com/matomo-org/device-detector/blob/75d88bbefb0182f9207c9f48dc39b1bc8c7cc43f/Parser/Device/AbstractDeviceParser.php#L83-L1951

DEVICE_NAMES

order is relevant for testing with fixtures github.com/matomo-org/device-detector/blob/75d88bbefb0182f9207c9f48dc39b1bc8c7cc43f/Parser/Device/AbstractDeviceParser.php#L59-L74

Public Instance Methods

brand() click to toggle source
# File lib/device_detector/device.rb, line 1913
def brand
  return regex_meta[:brand] if regex_meta[:brand] == 'Sony Ericsson'

  brand = regex_meta[:regex_name] || regex_meta[:brand] || vendor_fragment.name || fix_for_x_music
  return if brand == 'Unknown'

  brand
end
known?() click to toggle source
# File lib/device_detector/device.rb, line 1897
def known?
  regex_meta.any?
end
name() click to toggle source
# File lib/device_detector/device.rb, line 1901
def name
  ModelExtractor.new(user_agent, regex_meta).call
end
type() click to toggle source
# File lib/device_detector/device.rb, line 1905
def type
  if hbbtv? || shelltv?
    'tv'
  else
    regex_meta[:device]
  end
end

Private Instance Methods

filenames() click to toggle source

The order of files needs to be the same as the order of device parser classes used in the piwik project.

# File lib/device_detector/device.rb, line 1934
def filenames
  [
    'device/televisions.yml',
    'device/shell_tv.yml',
    'device/notebooks.yml',
    'device/consoles.yml',
    'device/car_browsers.yml',
    'device/cameras.yml',
    'device/portable_media_player.yml',
    'device/mobiles.yml'
  ]
end
fix_for_x_music() click to toggle source
# File lib/device_detector/device.rb, line 1924
def fix_for_x_music
  user_agent&.include?('X-music Ⅲ') ? 'OneClick' : nil
end
hbbtv?() click to toggle source
# File lib/device_detector/device.rb, line 1987
def hbbtv?
  @regex_hbbtv ||= build_regex('HbbTV/([1-9]{1}(?:\.[0-9]{1}){1,2})')
  user_agent =~ @regex_hbbtv
end
matching_regex() click to toggle source
# File lib/device_detector/device.rb, line 1947
def matching_regex
  from_cache([self.class.name, user_agent]) do
    regex_list = hbbtv? ? regexes_for_hbbtv : regexes_other
    regex_list = shelltv? ? regexes_for_shelltv : regex_list

    regex = regex_find(user_agent, regex_list)
    if regex && regex[:models]
      model_regex = regex[:models].find { |m| user_agent =~ m[:regex] }
      if model_regex
        regex = regex.merge({
                              regex_model: model_regex[:regex],
                              model: model_regex[:model],
                              brand: model_regex[:brand]
                            })
        regex[:brand] = DEVICE_BRANDS[regex[:brand]] if DEVICE_BRANDS.key?(regex[:brand])
        regex[:device] = model_regex[:device] if model_regex.key?(:device)
        regex.delete(:models)
      end
    end
    regex
  end
end
parse_regexes(path, raw_regexes) click to toggle source
# File lib/device_detector/device.rb, line 2009
def parse_regexes(path, raw_regexes)
  raw_regexes.map do |brand, meta|
    raise "invalid device spec: #{meta.inspect}" unless meta[:regex].is_a? String

    meta[:regex] = build_regex(meta[:regex])
    if meta.key?(:models)
      meta[:models].each do |model|
        raise "invalid model spec: #{model.inspect}" unless model[:regex].is_a? String

        model[:regex] = build_regex(model[:regex])
        model[:brand] = brand.to_s unless model[:brand]
      end
    end
    meta[:path] = path
    meta
  end
end
regex_find(user_agent, regex_list) click to toggle source

Finds the first match of the string in a list of regexes. Handles exception with special characters caused by bug in Ruby regex @param user_agent [String] User Agent string @param regex_list [Array<Regex>] List of regexes

@return [MatchData, nil] MatchData if string matches any regexp, nil otherwise

# File lib/device_detector/device.rb, line 1976
def regex_find(user_agent, regex_list)
  regex_list.find { |r| user_agent =~ r[:regex] }
rescue RegexpError
  # Bug in ruby regex and special characters, retry with clean
  # https://bugs.ruby-lang.org/issues/13671
  user_agent = user_agent.encode(
    ::Encoding::ASCII, invalid: :replace, undef: :replace, replace: ''
  )
  regex_list.find { |r| user_agent =~ r[:regex] }
end
regexes_for_hbbtv() click to toggle source
# File lib/device_detector/device.rb, line 1997
def regexes_for_hbbtv
  regexes.select { |r| r[:path] == :'device/televisions.yml' }
end
regexes_for_shelltv() click to toggle source
# File lib/device_detector/device.rb, line 2001
def regexes_for_shelltv
  regexes.select { |r| r[:path] == :'device/shell_tv.yml' }
end
regexes_other() click to toggle source
# File lib/device_detector/device.rb, line 2005
def regexes_other
  regexes.reject { |r| r[:path] == :'device/televisions.yml' }
end
shelltv?() click to toggle source
# File lib/device_detector/device.rb, line 1992
def shelltv?
  @regex_shelltv ||= build_regex('[a-z]+[ _]Shell[ _]\w{6}')
  user_agent =~ @regex_shelltv
end
vendor_fragment() click to toggle source
# File lib/device_detector/device.rb, line 1928
def vendor_fragment
  ::DeviceDetector::VendorFragment.new(user_agent)
end