domreactor-redglass 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. data/lib/domreactor-redglass.rb +128 -0
  2. metadata +142 -0
@@ -0,0 +1,128 @@
1
+ require 'json'
2
+ require 'rest-client'
3
+ require 'zip/zip'
4
+
5
+ module DomReactorRedGlass
6
+
7
+ REQUIRED_ARCHIVE_FILES = %w(dom.json metadata.json screenshot.png source.html)
8
+ REQUIRED_BASELINE_BROWSER_CONFIG_KEYS = [:name, :version, :platform]
9
+ DOMREACTOR_INIT_CHAIN_REACTION_URL = 'http://domreactor.com/api/v1/chain_reactions'
10
+
11
+ def create_chain_reaction(api_token, archive_location, config)
12
+ detect_archive_location archive_location
13
+ detect_min_archive_quota archive_location
14
+ detect_baseline_browser archive_location, config
15
+ id = init_chain_reaction(api_token, archive_location, config)[:chain_reaction][:id]
16
+ api_url = config[:api_url] || DOMREACTOR_INIT_CHAIN_REACTION_URL
17
+ post_url = "#{api_url}/#{id}"
18
+ archive_files = zip_archives archive_location
19
+ post_archives(api_token, post_url, archive_files)
20
+ end
21
+
22
+ def detect_archive_location(archive_location)
23
+ unless File.directory?(archive_location)
24
+ raise 'A valid archive location is required.'
25
+ end
26
+ end
27
+
28
+ def detect_min_archive_quota(archive_location)
29
+ raise 'At least two valid page archives are required.' unless sum_archive_count(archive_location) >= 2
30
+ end
31
+
32
+ def sum_archive_count(archive_location)
33
+ archive_count = 0
34
+ Dir.foreach(archive_location) do |file|
35
+ next if file == '.' or file == '..'
36
+ archive_count += 1 if is_valid_page_archive? "#{archive_location}/#{file}"
37
+ end
38
+ archive_count
39
+ end
40
+
41
+ def is_valid_page_archive?(file)
42
+ is_valid = false
43
+ if File.directory? file
44
+ dir_files = Dir.entries(file).delete_if {|name| name == '.' || name == '..'}
45
+ is_valid = true if dir_files == REQUIRED_ARCHIVE_FILES
46
+ end
47
+ is_valid
48
+ end
49
+
50
+ def detect_baseline_browser(archive_location, config)
51
+ unless config[:baseline_browser] && is_valid_baseline_browser_config?(config[:baseline_browser])
52
+ raise 'A valid baseline_browser configuration is required.'
53
+ end
54
+ unless has_baseline_archive?(archive_location, config)
55
+ raise 'A page archive that corresponds to the baseline browser configuration is required.'
56
+ end
57
+ end
58
+
59
+ def is_valid_baseline_browser_config?(baseline_browser_config)
60
+ baseline_browser_config.keys == REQUIRED_BASELINE_BROWSER_CONFIG_KEYS
61
+ end
62
+
63
+ def has_baseline_archive?(archive_location, config)
64
+ found_archive = false
65
+ Dir.foreach(archive_location) do |file|
66
+ next if file == '.' or file == '..'
67
+ path = "#{archive_location}/#{file}"
68
+ if is_valid_page_archive? path
69
+ if parse_json_file("#{path}/metadata.json")[:browser] == config[:baseline_browser]
70
+ found_archive = true
71
+ break
72
+ end
73
+ end
74
+ end
75
+ found_archive
76
+ end
77
+
78
+ def init_chain_reaction(api_token, archive_location, config)
79
+ payload = {
80
+ auth_token: api_token,
81
+ analysis_only: true,
82
+ threshold: config[:threshold] || 0.04,
83
+ baseline_browser: config[:baseline_browser],
84
+ archive_count: sum_archive_count(archive_location)
85
+ }.to_json
86
+ api_url = config[:api_url] || DOMREACTOR_INIT_CHAIN_REACTION_URL
87
+ response = RestClient.post(api_url, payload, content_type: 'application/json') do |response|
88
+ unless response.code == 200 && response.body.match(/chain_reaction/)
89
+ raise "ChainReaction initialization failed with code #{response.code} : #{response.body}"
90
+ end
91
+ response
92
+ end
93
+ JSON.parse(response, symbolize_names: true)
94
+ end
95
+
96
+ def zip_archives(archive_location)
97
+ zip_files = []
98
+ Dir.foreach(archive_location) do |file|
99
+ next if file == '.' or file == '..'
100
+ path = "#{archive_location}/#{file}"
101
+ if is_valid_page_archive? path
102
+ zip_file = "#{path}.zip"
103
+ zip_files << zip_file
104
+ Zip::ZipFile.open(zip_file, Zip::ZipFile::CREATE) do |zipfile|
105
+ REQUIRED_ARCHIVE_FILES.each do |filename|
106
+ zipfile.add(filename, path + '/' + filename)
107
+ end
108
+ end
109
+ end
110
+ end
111
+ zip_files
112
+ end
113
+
114
+ def post_archives(api_token, post_url, zip_files)
115
+ zip_files.each do |file|
116
+ payload = {
117
+ auth_token: api_token,
118
+ file: File.new(file, 'rb')
119
+ }
120
+ RestClient.put(post_url, payload)
121
+ end
122
+ end
123
+
124
+ def parse_json_file(path)
125
+ json_str = File.open(path, 'rb') {|f| f.read}
126
+ JSON.parse(json_str, symbolize_names: true)
127
+ end
128
+ end
metadata ADDED
@@ -0,0 +1,142 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: domreactor-redglass
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Frank O'Hara
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2013-05-27 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rest-client
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: json
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ! '>='
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
38
+ type: :runtime
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ! '>='
44
+ - !ruby/object:Gem::Version
45
+ version: '0'
46
+ - !ruby/object:Gem::Dependency
47
+ name: rubyzip
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
54
+ type: :runtime
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ - !ruby/object:Gem::Dependency
63
+ name: red-glass
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ! '>='
68
+ - !ruby/object:Gem::Version
69
+ version: 0.1.1
70
+ type: :runtime
71
+ prerelease: false
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: 0.1.1
78
+ - !ruby/object:Gem::Dependency
79
+ name: rspec
80
+ requirement: !ruby/object:Gem::Requirement
81
+ none: false
82
+ requirements:
83
+ - - ! '>='
84
+ - !ruby/object:Gem::Version
85
+ version: '0'
86
+ type: :development
87
+ prerelease: false
88
+ version_requirements: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ! '>='
92
+ - !ruby/object:Gem::Version
93
+ version: '0'
94
+ - !ruby/object:Gem::Dependency
95
+ name: selenium-webdriver
96
+ requirement: !ruby/object:Gem::Requirement
97
+ none: false
98
+ requirements:
99
+ - - ! '>='
100
+ - !ruby/object:Gem::Version
101
+ version: '0'
102
+ type: :development
103
+ prerelease: false
104
+ version_requirements: !ruby/object:Gem::Requirement
105
+ none: false
106
+ requirements:
107
+ - - ! '>='
108
+ - !ruby/object:Gem::Version
109
+ version: '0'
110
+ description: Send RedGlass page archives to DomReactor for automated layout analysis.
111
+ email:
112
+ - frankj.ohara@gmail.com
113
+ executables: []
114
+ extensions: []
115
+ extra_rdoc_files: []
116
+ files:
117
+ - lib/domreactor-redglass.rb
118
+ homepage: https://github.com/bimech/domreactor-redglass
119
+ licenses: []
120
+ post_install_message:
121
+ rdoc_options: []
122
+ require_paths:
123
+ - lib
124
+ required_ruby_version: !ruby/object:Gem::Requirement
125
+ none: false
126
+ requirements:
127
+ - - ! '>='
128
+ - !ruby/object:Gem::Version
129
+ version: '0'
130
+ required_rubygems_version: !ruby/object:Gem::Requirement
131
+ none: false
132
+ requirements:
133
+ - - ! '>='
134
+ - !ruby/object:Gem::Version
135
+ version: '0'
136
+ requirements: []
137
+ rubyforge_project:
138
+ rubygems_version: 1.8.24
139
+ signing_key:
140
+ specification_version: 3
141
+ summary: DomReactor plugin for RedGlass.
142
+ test_files: []