akephalos 0.0.1 → 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore CHANGED
@@ -1,2 +1,4 @@
1
+ .rvmrc
2
+ burn
1
3
  pkg
2
4
  tags
@@ -0,0 +1,18 @@
1
+ 0.0.3
2
+ =======================================================================================
3
+ * DRb server should never shut down prematurely -- missing methods, 500 errors,
4
+ even java errors (NPE error from bad javascript).
5
+
6
+ 0.0.2 - 10 May 2010
7
+ =======================================================================================
8
+
9
+ - Ensure users cannot accidently call non-existant methods on DRb objects
10
+ - Refactor akephalos classes to expose HTMLUnit behavior, instead of shipping
11
+ objects directly to remote process.
12
+
13
+
14
+ 0.0.1 - 03 May 2010
15
+ =======================================================================================
16
+ - DRb server starts automatically when needed
17
+ - DRb objects are undumped, and references are kept on the server
18
+ - All capybara provided specs pass.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.1
1
+ 0.0.2
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{akephalos}
8
- s.version = "0.0.1"
8
+ s.version = "0.0.2"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Bernerd Schaefer"]
12
- s.date = %q{2010-05-05}
12
+ s.date = %q{2010-05-10}
13
13
  s.default_executable = %q{akephalos}
14
14
  s.description = %q{}
15
15
  s.email = %q{bj.schaefer@gmail.com}
@@ -17,17 +17,18 @@ Gem::Specification.new do |s|
17
17
  s.files = [
18
18
  ".gitignore",
19
19
  "Rakefile",
20
+ "TODO.txt",
20
21
  "VERSION",
21
22
  "akephalos.gemspec",
22
23
  "bin/akephalos",
23
24
  "lib/akephalos.rb",
24
25
  "lib/akephalos/capybara.rb",
26
+ "lib/akephalos/client.rb",
25
27
  "lib/akephalos/cucumber.rb",
26
28
  "lib/akephalos/htmlunit.rb",
27
- "lib/akephalos/htmlunit/html_element.rb",
28
- "lib/akephalos/htmlunit/html_page.rb",
29
- "lib/akephalos/htmlunit/html_select.rb",
30
- "lib/akephalos/htmlunit/web_client.rb",
29
+ "lib/akephalos/node.rb",
30
+ "lib/akephalos/page.rb",
31
+ "lib/akephalos/remote_client.rb",
31
32
  "lib/akephalos/server.rb",
32
33
  "spec/driver/akephalos_driver_spec.rb",
33
34
  "spec/session/akephalos_session_spec.rb",
@@ -5,7 +5,9 @@ raise "Usage: akephalos socket_file" unless ARGV[0]
5
5
  require 'pathname'
6
6
 
7
7
  root = Pathname(__FILE__).expand_path.dirname.parent
8
+ lib = root + 'lib'
8
9
  jruby = root + "src/jruby-complete-1.4.0.jar"
9
- server = root + "lib/akephalos/server"
10
+ server = 'akephalos/server'
10
11
 
11
- exec "java -Xmx2048M -jar #{jruby} -r#{server} -e 'Akephalos::Server.start!(#{ARGV[0].inspect})'"
12
+ command = %Q(java -Xmx2048M -jar #{jruby} -I#{lib} -r #{server} -e 'Akephalos::Server.start!(%s)')
13
+ exec command % ARGV[0].inspect
@@ -1,8 +1,11 @@
1
+ require 'java' if RUBY_PLATFORM == 'java'
1
2
  require 'capybara'
2
3
 
3
4
  module Akephalos
5
+ BIN_DIR = Pathname(__FILE__).expand_path.dirname.parent + 'bin'
4
6
  end
5
7
 
8
+ require 'akephalos/client'
6
9
  require 'akephalos/capybara'
7
10
 
8
11
  if Object.const_defined? :Cucumber
@@ -6,41 +6,36 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
6
6
  name = name.to_s
7
7
  case name
8
8
  when 'checked'
9
- node.isChecked
9
+ node.checked?
10
10
  else
11
11
  node[name.to_s]
12
12
  end
13
13
  end
14
14
 
15
15
  def text
16
- node.asText
16
+ node.text
17
17
  end
18
18
 
19
19
  def value
20
20
  if tag_name == "select" && self[:multiple]
21
- values = []
22
- results = node.getSelectedOptions
23
- while (i ||= 0) < results.size
24
- values << results[i].asText
25
- i += 1
26
- end
27
- values
21
+ node.selected_options.map { |option| option.text }
28
22
  elsif tag_name == "select"
29
- node.getSelectedOptions.first.asText
23
+ selected_option = node.selected_options.first
24
+ selected_option ? selected_option.text : nil
30
25
  else
31
- super
26
+ self[:value]
32
27
  end
33
28
  end
34
29
 
35
30
  def set(value)
36
31
  if tag_name == 'textarea'
37
- node.setText(value.to_s)
32
+ node.value = value.to_s
38
33
  elsif tag_name == 'input' and type == 'radio'
39
- node.click
34
+ click
40
35
  elsif tag_name == 'input' and type == 'checkbox'
41
- node.click
36
+ click
42
37
  elsif tag_name == 'input'
43
- node.setValueAttribute(value.to_s)
38
+ node.value = value.to_s
44
39
  end
45
40
  end
46
41
 
@@ -48,13 +43,7 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
48
43
  result = node.select_option(option)
49
44
 
50
45
  if result == nil
51
- options = []
52
- results = node.getOptions
53
- while (i ||= 0) < results.size
54
- options << results[i].asText
55
- i += 1
56
- end
57
- options = options.join(", ")
46
+ options = node.options.map(&:text).join(", ")
58
47
  raise Capybara::OptionNotFound, "No such option '#{option}' in this select box. Available options: #{options}"
59
48
  else
60
49
  result
@@ -69,13 +58,7 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
69
58
  result = node.unselect_option(option)
70
59
 
71
60
  if result == nil
72
- options = []
73
- results = node.getOptions
74
- while (i ||= 0) < results.size
75
- options << results[i].asText
76
- i += 1
77
- end
78
- options = options.join(", ")
61
+ options = node.options.map(&:text).join(", ")
79
62
  raise Capybara::OptionNotFound, "No such option '#{option}' in this select box. Available options: #{options}"
80
63
  else
81
64
  result
@@ -87,17 +70,17 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
87
70
  end
88
71
 
89
72
  def tag_name
90
- node.getNodeName
73
+ node.tag_name
91
74
  end
92
75
 
93
76
  def visible?
94
- node.isDisplayed
77
+ node.visible?
95
78
  end
96
79
 
97
80
  def drag_to(element)
98
- node.fire_event('mousedown')
99
- element.node.fire_event('mousemove')
100
- element.node.fire_event('mouseup')
81
+ trigger('mousedown')
82
+ element.trigger('mousemove')
83
+ element.trigger('mouseup')
101
84
  end
102
85
 
103
86
  def click
@@ -107,13 +90,7 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
107
90
  private
108
91
 
109
92
  def all_unfiltered(selector)
110
- nodes = []
111
- results = node.getByXPath(selector)
112
- while (i ||= 0) < results.size
113
- nodes << Node.new(driver, results[i])
114
- i += 1
115
- end
116
- nodes
93
+ node.find(selector).map { |node| Node.new(driver, node) }
117
94
  end
118
95
 
119
96
  def type
@@ -124,28 +101,7 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
124
101
  attr_reader :app, :rack_server
125
102
 
126
103
  def self.driver
127
- if RUBY_PLATFORM == "java"
128
- require '/usr/local/projects/personal/htmlunit-ruby/jruby'
129
- @driver ||= WebClient.new
130
- else
131
- @driver ||= begin
132
- socket_file = "/tmp/akephalos.#{Process.pid}.sock"
133
- uri = "drbunix://#{socket_file}"
134
-
135
- server = fork do
136
- exec("#{Pathname(__FILE__).dirname.parent.parent + 'bin/akephalos'} #{socket_file}")
137
- end
138
-
139
- DRb.start_service
140
-
141
- sleep 1 until File.exists?(socket_file)
142
-
143
- client_class = DRbObject.new_with_uri(uri)
144
-
145
- at_exit { Process.kill(:INT, server); File.unlink(socket_file) }
146
- client_class
147
- end
148
- end
104
+ @driver ||= Akephalos::Client.new
149
105
  end
150
106
 
151
107
  def initialize(app)
@@ -171,13 +127,7 @@ class Capybara::Driver::Akephalos < Capybara::Driver::Base
171
127
  end
172
128
 
173
129
  def find(selector)
174
- nodes = []
175
- results = page.find(selector)
176
- while (i ||= 0) < results.size
177
- nodes << Node.new(self, results[i])
178
- i += 1
179
- end
180
- nodes
130
+ page.find(selector).map { |node| Node.new(self, node) }
181
131
  end
182
132
 
183
133
  def evaluate_script(script)
@@ -0,0 +1,28 @@
1
+ if RUBY_PLATFORM != "java"
2
+ require 'akephalos/remote_client'
3
+ Akephalos::Client = Akephalos::RemoteClient
4
+ else
5
+ require 'akephalos/htmlunit'
6
+ require 'akephalos/page'
7
+ require 'akephalos/node'
8
+
9
+ module Akephalos
10
+ class Client
11
+ def initialize
12
+ @_client = WebClient.new
13
+ @_client.setCssErrorHandler(com.gargoylesoftware.htmlunit.SilentCssErrorHandler.new)
14
+ end
15
+
16
+ def visit(url)
17
+ @page = Page.new(@_client.getPage(url))
18
+ end
19
+
20
+ def page
21
+ if @page != (page = @_client.getCurrentWindow.getEnclosedPage)
22
+ @page = Page.new(page)
23
+ end
24
+ @page
25
+ end
26
+ end
27
+ end
28
+ end
@@ -21,17 +21,8 @@ require "xml-apis-1.3.04.jar"
21
21
  logger = org.apache.commons.logging.LogFactory.getLog('com.gargoylesoftware.htmlunit')
22
22
  logger.getLogger().setLevel(java.util.logging.Level::SEVERE)
23
23
 
24
- java_import 'java.io.StringWriter'
25
- java_import 'java.io.PrintWriter'
26
24
  java_import "com.gargoylesoftware.htmlunit.WebClient"
27
- java_import "com.gargoylesoftware.htmlunit.html.HtmlPage"
28
- java_import "com.gargoylesoftware.htmlunit.html.HtmlSubmitInput"
29
25
 
30
26
  com.gargoylesoftware.htmlunit.BrowserVersion.setDefault(
31
27
  com.gargoylesoftware.htmlunit.BrowserVersion::FIREFOX_3
32
28
  )
33
-
34
- require Pathname(__FILE__).dirname + "htmlunit/html_element"
35
- require Pathname(__FILE__).dirname + "htmlunit/html_page"
36
- require Pathname(__FILE__).dirname + "htmlunit/html_select"
37
- require Pathname(__FILE__).dirname + "htmlunit/web_client"
@@ -0,0 +1,68 @@
1
+ module Akephalos
2
+ class Node
3
+ def initialize(node)
4
+ @_node = node
5
+ end
6
+
7
+ def checked?
8
+ @_node.isChecked
9
+ end
10
+
11
+ def text
12
+ @_node.asText
13
+ end
14
+
15
+ def [](name)
16
+ @_node.hasAttribute(name.to_s) ? @_node.getAttribute(name.to_s) : nil
17
+ end
18
+
19
+ def value=(value)
20
+ case tag_name
21
+ when "textarea"
22
+ @_node.setText(value)
23
+ when "input"
24
+ @_node.setValueAttribute(value)
25
+ end
26
+ end
27
+
28
+ def select_option(option)
29
+ opt = @_node.getOptions.detect { |o| o.asText == option }
30
+
31
+ opt && opt.setSelected(true)
32
+ end
33
+
34
+ def unselect_option(option)
35
+ opt = @_node.getOptions.detect { |o| o.asText == option }
36
+
37
+ opt && opt.setSelected(false)
38
+ end
39
+
40
+ def options
41
+ @_node.getOptions.map { |node| Node.new(node) }
42
+ end
43
+
44
+ def selected_options
45
+ @_node.getSelectedOptions.map { |node| Node.new(node) }
46
+ end
47
+
48
+ def fire_event(name)
49
+ @_node.fireEvent(name)
50
+ end
51
+
52
+ def tag_name
53
+ @_node.getNodeName
54
+ end
55
+
56
+ def visible?
57
+ @_node.isDisplayed
58
+ end
59
+
60
+ def click
61
+ @_node.click
62
+ end
63
+
64
+ def find(selector)
65
+ @_node.getByXPath(selector).map { |node| Node.new(node) }
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,34 @@
1
+ module Akephalos
2
+ class Page
3
+ def initialize(page)
4
+ @nodes = []
5
+ @_page = page
6
+ end
7
+
8
+ def find(selector)
9
+ nodes = @_page.getByXPath(selector).map { |node| Node.new(node) }
10
+ @nodes << nodes
11
+ nodes
12
+ end
13
+
14
+ def modified_source
15
+ @_page.asXml
16
+ end
17
+
18
+ def source
19
+ @_page.getWebResponse.getContentAsString
20
+ end
21
+
22
+ def current_url
23
+ @_page.getWebResponse.getRequestSettings.getUrl.toString
24
+ end
25
+
26
+ def execute_script(script)
27
+ @_page.executeJavaScript(script).getJavaScriptResult
28
+ end
29
+
30
+ def ==(other)
31
+ @_page == other
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,21 @@
1
+ module Akephalos
2
+ class RemoteClient
3
+ @socket_file = "/tmp/akephalos.#{Process.pid}.sock"
4
+
5
+ def self.start!
6
+ remote_client = fork do
7
+ exec("#{Akephalos::BIN_DIR + 'akephalos'} #{@socket_file}")
8
+ end
9
+
10
+ sleep 1 until File.exists?(@socket_file)
11
+
12
+ at_exit { Process.kill(:INT, remote_client); File.unlink(@socket_file) }
13
+ end
14
+
15
+ def self.new
16
+ start!
17
+ DRb.start_service
18
+ DRbObject.new_with_uri("drbunix://#{@socket_file}")
19
+ end
20
+ end
21
+ end
@@ -1,6 +1,12 @@
1
1
  require "pathname"
2
2
  require "drb/drb"
3
- require Pathname(__FILE__).expand_path.dirname + "htmlunit"
3
+ require "akephalos/client"
4
+
5
+ class NameError::Message
6
+ def _dump
7
+ to_s
8
+ end
9
+ end
4
10
 
5
11
  [
6
12
  java.net.URL,
@@ -17,34 +23,10 @@ require Pathname(__FILE__).expand_path.dirname + "htmlunit"
17
23
  com.gargoylesoftware.htmlunit.WebRequestSettings
18
24
  ].each { |klass| klass.send(:include, DRbUndumped) }
19
25
 
20
- class WebClient
21
- def page
22
- @page = getCurrentWindow.getEnclosedPage
23
- end
24
- end
25
-
26
- class HtmlPage
27
- def find(selector)
28
- @present_nodes = getByXPath(selector).to_a
29
- (@nodes ||= []).push(*@present_nodes)
30
- @present_nodes
31
- end
32
- end
33
-
34
- class HtmlSubmitInput
35
- def click
36
- super
37
- rescue => e
38
- puts e
39
- puts e.backtrace.join("\n")
40
- end
41
- end
42
-
43
26
  module Akephalos
44
27
  class Server
45
28
  def self.start!(socket_file)
46
- client = WebClient.new
47
- client.setCssErrorHandler(com.gargoylesoftware.htmlunit.SilentCssErrorHandler.new)
29
+ client = Client.new
48
30
  DRb.start_service("drbunix://#{socket_file}", client)
49
31
  DRb.thread.join
50
32
  end
metadata CHANGED
@@ -5,8 +5,8 @@ version: !ruby/object:Gem::Version
5
5
  segments:
6
6
  - 0
7
7
  - 0
8
- - 1
9
- version: 0.0.1
8
+ - 2
9
+ version: 0.0.2
10
10
  platform: ruby
11
11
  authors:
12
12
  - Bernerd Schaefer
@@ -14,7 +14,7 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-05-05 00:00:00 -05:00
17
+ date: 2010-05-10 00:00:00 -05:00
18
18
  default_executable: akephalos
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
@@ -68,17 +68,18 @@ extra_rdoc_files: []
68
68
  files:
69
69
  - .gitignore
70
70
  - Rakefile
71
+ - TODO.txt
71
72
  - VERSION
72
73
  - akephalos.gemspec
73
74
  - bin/akephalos
74
75
  - lib/akephalos.rb
75
76
  - lib/akephalos/capybara.rb
77
+ - lib/akephalos/client.rb
76
78
  - lib/akephalos/cucumber.rb
77
79
  - lib/akephalos/htmlunit.rb
78
- - lib/akephalos/htmlunit/html_element.rb
79
- - lib/akephalos/htmlunit/html_page.rb
80
- - lib/akephalos/htmlunit/html_select.rb
81
- - lib/akephalos/htmlunit/web_client.rb
80
+ - lib/akephalos/node.rb
81
+ - lib/akephalos/page.rb
82
+ - lib/akephalos/remote_client.rb
82
83
  - lib/akephalos/server.rb
83
84
  - spec/driver/akephalos_driver_spec.rb
84
85
  - spec/session/akephalos_session_spec.rb
@@ -1,11 +0,0 @@
1
- module Akephalos
2
- module Htmlunit
3
- module HtmlElement
4
- def [](name)
5
- hasAttribute(name.to_s) ? getAttribute(name.to_s) : nil
6
- end
7
-
8
- com.gargoylesoftware.htmlunit.html.HtmlElement.send(:include, self)
9
- end
10
- end
11
- end
@@ -1,28 +0,0 @@
1
- module Akephalos
2
- module Htmlunit
3
- module HtmlPage
4
-
5
- def modified_source
6
- asXml
7
- end
8
-
9
- def source
10
- getWebResponse.getContentAsString
11
- end
12
-
13
- def current_url
14
- getWebResponse.getRequestSettings.getUrl.toString
15
- end
16
-
17
- def find(selector)
18
- getByXPath(selector)
19
- end
20
-
21
- def execute_script(script)
22
- executeJavaScript(script).getJavaScriptResult
23
- end
24
-
25
- com.gargoylesoftware.htmlunit.html.HtmlPage.send(:include, self)
26
- end
27
- end
28
- end
@@ -1,19 +0,0 @@
1
- module Akephalos
2
- module Htmlunit
3
- module HtmlSelect
4
- def select_option(option)
5
- opt = getOptions.detect { |o| o.asText == option }
6
-
7
- opt && opt.setSelected(true)
8
- end
9
-
10
- def unselect_option(option)
11
- opt = getOptions.detect { |o| o.asText == option }
12
-
13
- opt && opt.setSelected(false)
14
- end
15
-
16
- com.gargoylesoftware.htmlunit.html.HtmlSelect.send(:include, self)
17
- end
18
- end
19
- end
@@ -1,16 +0,0 @@
1
- module Akephalos
2
- module Htmlunit
3
- module WebClient
4
-
5
- def visit(url)
6
- getPage(url)
7
- end
8
-
9
- def page
10
- getCurrentWindow.getEnclosedPage
11
- end
12
-
13
- com.gargoylesoftware.htmlunit.WebClient.send(:include, self)
14
- end
15
- end
16
- end