browscap 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,109 @@
1
+ require 'inifile'
2
+
3
+ class Browscap
4
+ def initialize(filename = 'browscap.ini')
5
+ @@user_agent_properties ||= {}
6
+ @@user_agent_regexps ||= {}
7
+ @@match_cache ||= {}
8
+
9
+ if @@user_agent_properties.empty? || @@user_agent_regexps.empty?
10
+ ini = IniFile.load(filename)
11
+
12
+ # Remote meta sections
13
+ ini.delete_section '*'
14
+ ini.delete_section 'GJK_Browscap_Version'
15
+
16
+ # Create a list of non-parent sections
17
+ child_sections = ini.sections.dup
18
+ ini.sections.each do |section|
19
+ child_sections.delete ini[section]["Parent"]
20
+ end
21
+
22
+ # Populate user_agent_properties and user_agent_regexps
23
+ child_sections.each do |section|
24
+ properties = _get_browser_props(ini, section)
25
+
26
+ browser = Browser.new
27
+ browser.browser = properties['Browser']
28
+ browser.version = properties['Version']
29
+ browser.major_ver = properties['MajorVer'].to_i
30
+ browser.minor_ver = properties['MinorVer'].to_i
31
+ browser.platform = properties['Platform']
32
+ browser.alpha = properties['Alpha'].downcase == 'true'
33
+ browser.beta = properties['Beta'].downcase == 'true'
34
+ browser.win16 = properties['Win16'].downcase == 'true'
35
+ browser.win32 = properties['Win32'].downcase == 'true'
36
+ browser.win64 = properties['Win64'].downcase == 'true'
37
+ browser.frames = properties['Frames'].downcase == 'true'
38
+ browser.iframes = properties['IFrames'].downcase == 'true'
39
+ browser.tables = properties['Tables'].downcase == 'true'
40
+ browser.cookies = properties['Cookies'].downcase == 'true'
41
+ browser.background_sounds = properties['BackgroundSounds'].downcase == 'true'
42
+ browser.javascript = properties['JavaScript'].downcase == 'true'
43
+ browser.vbscript = properties['VBScript'].downcase == 'true'
44
+ browser.java_applets = properties['JavaApplets'].downcase == 'true'
45
+ browser.activex_controls = properties['ActiveXControls'].downcase == 'true'
46
+ browser.is_banned = properties['isBanned'].downcase == 'true'
47
+ browser.is_mobile_device = properties['isMobileDevice'].downcase == 'true'
48
+ browser.is_syndication_reader = properties['isSyndicationReader'].downcase == 'true'
49
+ browser.crawler = properties['Crawler'].downcase == 'true'
50
+ browser.css_version = properties['CssVersion'].to_i
51
+ browser.supports_css = properties['supportsCSS'].downcase == 'true'
52
+ browser.aol_version = properties['aolVersion'].to_i
53
+ browser.aol = properties['AOL'].downcase == 'true'
54
+
55
+ @@user_agent_properties[section] = browser
56
+
57
+ # Convert .ini file regexp syntax into ruby regexp syntax
58
+ regexp = section.dup
59
+ regexp.gsub! /([\^\$\(\)\[\]\.\-])/, "\\\\\\1"
60
+ regexp.gsub! "?", "."
61
+ regexp.gsub! "*", ".*?"
62
+
63
+ @@user_agent_regexps[section] = Regexp.new("^%s$" % regexp)
64
+ end
65
+ end
66
+ end
67
+
68
+ # Looks up the given user agent string and returns a dictionary containing information on this browser or bot.
69
+ def query(user_agent)
70
+ section = _match(user_agent)
71
+ @@user_agent_properties[section]
72
+ end
73
+
74
+ def _match(user_agent)
75
+ return @@match_cache[user_agent] if @@match_cache[user_agent]
76
+
77
+ matching_section = ''
78
+
79
+ @@user_agent_regexps.each do |section, regexp|
80
+ # Find the longest regexp that matches the given user_agent_string. The length check is needed since multiple reg-exps may match the user_agent_string.
81
+ if regexp.match(user_agent) && section.length > matching_section.length
82
+ matching_section = section
83
+ end
84
+ end
85
+
86
+ @@match_cache[user_agent] = matching_section
87
+ matching_section
88
+ end
89
+
90
+ # Recursively traverses the properties tree (based on 'parent' attribute of each section) and
91
+ # returns a dictionary of all browser properties for the given section name. The properties lower
92
+ # in the tree override those higher in the tree.
93
+ def _get_browser_props(ini, section)
94
+ data = {}
95
+
96
+ if parent = ini[section]["Parent"]
97
+ data.merge! _get_browser_props(ini, parent)
98
+ end
99
+
100
+ data.merge! ini[section]
101
+ data
102
+ end
103
+ end
104
+
105
+ class Browser
106
+ attr_accessor :browser, :version, :major_ver, :minor_ver, :platform, :alpha, :beta, :win16, :win32, :win64,
107
+ :frames, :iframes, :tables, :cookies, :background_sounds, :javascript, :vbscript, :java_applets, :activex_controls,
108
+ :is_banned, :is_mobile_device, :is_syndication_reader, :crawler, :css_version, :supports_css, :aol_version, :aol
109
+ end
@@ -0,0 +1,75 @@
1
+ require 'browscap'
2
+
3
+ describe Browscap do
4
+ before(:each) do
5
+ @browscap = Browscap.new
6
+ end
7
+
8
+ it "should detect Konqueror 3.5 on Linux" do
9
+ konq35 = @browscap.query "Mozilla/5.0 (compatible; Konqueror/3.5; Linux; X11; de) KHTML/3.5.2 (like Gecko) Kubuntu 6.06 Dapper"
10
+ konq35.browser.should == 'Konqueror'
11
+ konq35.version.should == '3.5'
12
+ konq35.platform.should == 'Linux'
13
+ end
14
+
15
+ it "should detect Firefox 1.5 on Linux" do
16
+ ff15 = @browscap.query "Mozilla/5.0 (X11; U; Linux i686; de; rv:1.8.0.5) Gecko/20060731 Ubuntu/dapper-security Firefox/1.5.0.5"
17
+ ff15.browser.should == 'Firefox'
18
+ ff15.version.should == '1.5'
19
+ ff15.platform.should == 'Linux'
20
+ end
21
+
22
+ it "should detect Mozilla 1.7 on Linux" do
23
+ moz17 = @browscap.query "Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.7.12) Gecko/20060216 Debian/1.7.12-1.1ubuntu2"
24
+ moz17.browser.should == 'Mozilla'
25
+ moz17.version.should == '1.7'
26
+ moz17.platform.should == 'Linux'
27
+ end
28
+
29
+ it "should detect Firefox 1.5 on Linux (2)" do
30
+ ff15 = @browscap.query "Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.8.0.5) Gecko/20060731 Ubuntu/dapper-security Epiphany/2.14 Firefox/1.5.0.5"
31
+ ff15.browser.should == 'Firefox'
32
+ ff15.version.should == '1.5'
33
+ ff15.platform.should == 'Linux'
34
+ end
35
+
36
+ it "should detect Opera 9.0 on Linux" do
37
+ opera90 = @browscap.query "Opera/9.00 (X11; Linux i686; U; en)"
38
+ opera90.browser.should == 'Opera'
39
+ opera90.version.should == '9.0'
40
+ opera90.platform.should == 'Linux'
41
+ end
42
+
43
+ it "shouldn't detect Kazehakase" do
44
+ @browscap.query("Mozilla/5.0 (X11; Linux i686; U;) Gecko/20051128 Kazehakase/0.3.3 Debian/0.3.3-1").should be_nil
45
+ end
46
+
47
+ it "should detect Galeon 1.3 on Linux" do
48
+ galeon13 = @browscap.query "Mozilla/5.0 (X11; U; Linux i386) Gecko/20063102 Galeon/1.3test"
49
+ galeon13.browser.should == 'Galeon'
50
+ galeon13.version.should == '1.3'
51
+ galeon13.platform.should == 'Linux'
52
+ end
53
+
54
+ it "should detect MSIE 6.0 on Windows 98" do
55
+ ie6 = @browscap.query "Mozilla/4.0 (compatible; MSIE 6.0; Windows 98)"
56
+ ie6.browser.should == 'IE'
57
+ ie6.version.should == '6.0'
58
+ ie6.platform.should == 'Win98'
59
+ end
60
+
61
+ it "should detect Wget as crawler" do
62
+ wget = @browscap.query "Wget/1.10.2"
63
+ wget.crawler.should == true
64
+ end
65
+
66
+ it "should detect Googlebot as crawler" do
67
+ google = @browscap.query "Mozilla/5.0 (compatible; Googlebot/2.1; +http://www.google.com/bot.html)"
68
+ google.crawler.should == true
69
+ end
70
+
71
+ it "should detect Yahoo! bot as crawler" do
72
+ yahoo = @browscap.query "Mozilla/5.0 (compatible; Yahoo! Slurp; http://help.yahoo.com/help/us/ysearch/slurp)"
73
+ yahoo.crawler.should == true
74
+ end
75
+ end
metadata ADDED
@@ -0,0 +1,75 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: browscap
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Matt
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2009-10-29 00:00:00 -04:00
13
+ default_executable:
14
+ dependencies: []
15
+
16
+ description: Uses the browscap.ini file in Ruby.
17
+ email: hotiby@gmail.com
18
+ executables: []
19
+
20
+ extensions: []
21
+
22
+ extra_rdoc_files:
23
+ - README.rdoc
24
+ - lib/Manifest
25
+ - lib/browscap-0.1.0.gem
26
+ - lib/browscap.gemspec
27
+ - lib/browscap.ini
28
+ - lib/browscap.rb
29
+ - lib/spec/browscap_spec.rb
30
+ files:
31
+ - README.rdoc
32
+ - Rakefile
33
+ - lib/Manifest
34
+ - lib/browscap-0.1.0.gem
35
+ - lib/browscap.gemspec
36
+ - lib/browscap.ini
37
+ - lib/browscap.rb
38
+ - lib/spec/browscap_spec.rb
39
+ - Manifest
40
+ - browscap.gemspec
41
+ has_rdoc: true
42
+ homepage: http://github.com/lfittl/browscap
43
+ licenses: []
44
+
45
+ post_install_message:
46
+ rdoc_options:
47
+ - --line-numbers
48
+ - --inline-source
49
+ - --title
50
+ - Browscap
51
+ - --main
52
+ - README.rdoc
53
+ require_paths:
54
+ - lib
55
+ required_ruby_version: !ruby/object:Gem::Requirement
56
+ requirements:
57
+ - - ">="
58
+ - !ruby/object:Gem::Version
59
+ version: "0"
60
+ version:
61
+ required_rubygems_version: !ruby/object:Gem::Requirement
62
+ requirements:
63
+ - - ">="
64
+ - !ruby/object:Gem::Version
65
+ version: "1.2"
66
+ version:
67
+ requirements: []
68
+
69
+ rubyforge_project: browscap
70
+ rubygems_version: 1.3.5
71
+ signing_key:
72
+ specification_version: 3
73
+ summary: Uses the browscap.ini file in Ruby.
74
+ test_files: []
75
+