holoserve 0.4.0 → 0.4.1

Sign up to get free protection for your applications and to get access to all the features.
data/README.rdoc CHANGED
@@ -130,6 +130,8 @@ The request/response pair file should have the following format.
130
130
  imports:
131
131
  - path: "test_fixture.users.0"
132
132
  as: "json.user"
133
+ transitions:
134
+ session_one: "existing"
133
135
  "user_one == :missing":
134
136
  json:
135
137
  message: "user not found"
@@ -170,3 +172,6 @@ are posted and the second one reacts on the transmission of <tt>username=one</tt
170
172
  If the state includes <tt>user_one == :existing</tt>, the first response would return the complete user object encoded
171
173
  as json, while the second one would reply the message "invalid password". In the state includes
172
174
  <tt>user_one == :missing</tt>, both requests would be replied with the message "user not found".
175
+
176
+ The <tt>transitions</tt> part of the response allows you set the successor state. If a response is selected, the
177
+ corresponding transitions will be evaluated.
data/bin/holoserve CHANGED
@@ -14,6 +14,9 @@ OptionParser.new do |parser|
14
14
  parser.on("-P", "--port PORT", Integer, "The port holoserve should listen to.") do |value|
15
15
  options[:port] = value
16
16
  end
17
+ parser.on("-l", "--log-file FILE", "The file where the messages go to.") do |value|
18
+ options[:log_filename] = value
19
+ end
17
20
  parser.on("-f", "--fixture-files PATTERN", "Load the specified fixture files on startup.") do |value|
18
21
  options[:fixture_file_pattern] = value
19
22
  end
data/bin/test.log ADDED
@@ -0,0 +1,4 @@
1
+ [690:INFO] 2012-04-02 21:19:51 :: Starting server on 0.0.0.0:4250 in production mode. Watch out for stones.
2
+ [708:INFO] 2012-04-02 21:20:17 :: Starting server on 0.0.0.0:4250 in production mode. Watch out for stones.
3
+ [712:INFO] 2012-04-02 21:20:24 :: Starting server on 0.0.0.0:4250 in production mode. Watch out for stones.
4
+ [724:INFO] 2012-04-02 21:20:33 :: Starting server on 0.0.0.0:4250 in production mode. Watch out for stones.
@@ -33,7 +33,7 @@ class Holoserve::Fixture::Importer
33
33
  end
34
34
 
35
35
  def merge
36
- @result = Holoserve::Tool::Merger.new(@result, hash_without_imports).result
36
+ @result = Holoserve::Tool::Merger.new(@result, hash_without_imports, :fusion).result
37
37
  end
38
38
 
39
39
  def hash_without_imports
@@ -8,7 +8,7 @@ module Holoserve::Interface::Control::State
8
8
  use Goliath::Rack::Params
9
9
 
10
10
  def response(environment)
11
- state.merge! params
11
+ state.merge! Holoserve::Tool::Hash::KeySymbolizer.new(params).hash
12
12
  logger.info "set state to '#{state.inspect}'"
13
13
  respond_json_acknowledgement
14
14
  end
@@ -7,7 +7,7 @@ class Holoserve::Response::Combiner
7
7
 
8
8
  def response
9
9
  @responses.inject @default do |result, response|
10
- Holoserve::Tool::Merger.new(result, response).result
10
+ Holoserve::Tool::Merger.new(result, response, :fusion).result
11
11
  end
12
12
  end
13
13
 
@@ -3,7 +3,8 @@ class Holoserve::Response::Selector
3
3
 
4
4
  class Sandbox
5
5
 
6
- def initialize(state)
6
+ def initialize(state, logger)
7
+ @logger = logger
7
8
  state.each do |resource, value|
8
9
  define_singleton_method resource.to_sym do
9
10
  value ? value.to_sym : nil
@@ -11,11 +12,16 @@ class Holoserve::Response::Selector
11
12
  end
12
13
  end
13
14
 
15
+ def method_missing(method_name, *arguments, &block)
16
+ @logger.warn "tried to use undefined state key '#{method_name}'"
17
+ nil
18
+ end
19
+
14
20
  end
15
21
 
16
22
  def initialize(responses, state, logger)
17
23
  @responses, @logger = responses, logger
18
- @sandbox = Sandbox.new state
24
+ @sandbox = Sandbox.new state, logger
19
25
  end
20
26
 
21
27
  def default_response
@@ -36,17 +36,19 @@ class Holoserve::Tool::DataPath
36
36
  path = @path ? @path.split(PATH_SEPARATOR) : [ ]
37
37
  return Holoserve::Tool::Merger.new(@data, value).result if path.empty?
38
38
 
39
- result = selected = clone @data
39
+ result = selected = clone(@data)
40
40
  key = parse_key path.shift
41
41
 
42
42
  while path.length > 0
43
43
  break unless selected.respond_to?(:[])
44
44
 
45
- selected[key] ||= { }
45
+ selected[key] ||= path.first.to_s == "@" ? [ ] : { }
46
46
  selected = selected[key]
47
47
  key = parse_key path.shift
48
48
  end
49
49
 
50
+ key = selected.length if key.to_s == "@"
51
+
50
52
  selected[key] = value
51
53
  result
52
54
  end
@@ -1,8 +1,10 @@
1
1
 
2
2
  class Holoserve::Tool::Merger
3
3
 
4
- def initialize(hash_or_array_one, hash_or_array_two)
5
- @hash_or_array_one, @hash_or_array_two = hash_or_array_one, hash_or_array_two
4
+ attr_accessor :mode
5
+
6
+ def initialize(hash_or_array_one, hash_or_array_two, mode = :union)
7
+ @hash_or_array_one, @hash_or_array_two, @mode = hash_or_array_one, hash_or_array_two, mode
6
8
  end
7
9
 
8
10
  def result
@@ -20,24 +22,32 @@ class Holoserve::Tool::Merger
20
22
  def merged_hash
21
23
  result = { }
22
24
  (@hash_or_array_one.keys + @hash_or_array_two.keys).uniq.each do |key|
23
- value_one, value_two = @hash_or_array_one[key],@hash_or_array_two[key]
25
+ value_one, value_two = @hash_or_array_one[key], @hash_or_array_two[key]
24
26
  result[key] = if values_mergeable?(value_one, value_two)
25
- self.class.new(value_one, value_two).result
27
+ self.class.new(value_one, value_two, @mode).result
26
28
  else
27
- value_two || value_one
29
+ @hash_or_array_two.has_key?(key) ? value_two : value_one
28
30
  end
29
31
  end
30
32
  result
31
33
  end
32
34
 
33
35
  def merged_array
36
+ send :"#{@mode}_array"
37
+ end
38
+
39
+ def fusion_array
40
+ @hash_or_array_one + @hash_or_array_two
41
+ end
42
+
43
+ def union_array
34
44
  result = Array.new [ @hash_or_array_one.length, @hash_or_array_two.length ].max
35
45
  result.each_index do |index|
36
46
  value_one, value_two = @hash_or_array_one[index], @hash_or_array_two[index]
37
47
  result[index] = if values_mergeable?(value_one, value_two)
38
- self.class.new(value_one, value_two).result
48
+ self.class.new(value_one, value_two, @mode).result
39
49
  else
40
- value_two || value_one
50
+ index < @hash_or_array_two.length ? value_two : value_one
41
51
  end
42
52
  end
43
53
  result
data/lib/holoserve.rb CHANGED
@@ -14,7 +14,7 @@ class Holoserve
14
14
  def initialize(options = { })
15
15
  @port = options[:port] || 4250
16
16
  @pid_filename = options[:pid_filename] || File.expand_path(File.join(File.dirname(__FILE__), "..", "holoserve.pid"))
17
- @log_filename = options[:log_filename] || File.expand_path(File.join(File.dirname(__FILE__), "..", "holoserve.log"))
17
+ @log_filename = options[:log_filename]
18
18
  @fixture_file_pattern = options[:fixture_file_pattern]
19
19
  @pair_file_pattern = options[:pair_file_pattern]
20
20
  @state = options[:state] || { }
@@ -52,7 +52,7 @@ class Holoserve
52
52
  private
53
53
 
54
54
  def initialize_logger
55
- @logger = Logger.new @log_filename
55
+ @logger = Logger.new(@log_filename ? @log_filename : $stdout)
56
56
  end
57
57
 
58
58
  def load_pairs
@@ -64,13 +64,13 @@ class Holoserve
64
64
 
65
65
  runner = Goliath::Runner.new [
66
66
  "-P", @pid_filename,
67
- "-l", @log_filename,
67
+ @log_filename ? [ "-l", @log_filename ] : "-s",
68
68
  "-e", "production",
69
69
  "-p", @port.to_s,
70
- daemonize ? "-d" : "-s"
71
- ], nil
70
+ daemonize ? "-d" : nil
71
+ ].flatten.compact, nil
72
72
  runner.options[:pairs] = @pairs
73
- runner.options[:state] = @state
73
+ runner.options[:state] = Tool::Hash::KeySymbolizer.new(@state).hash
74
74
  runner.api = Interface.new
75
75
  runner.app = Goliath::Rack::Builder.build Interface, runner.api
76
76
  runner.run
@@ -40,6 +40,25 @@ describe Holoserve::Fixture::Importer do
40
40
  subject.result.should == { :test => 1 }
41
41
  end
42
42
 
43
+ it "should return a hash with imported fixtures at a new target array" do
44
+ subject.hash = {
45
+ :imports => [
46
+ { :path => "one.first", :as => "test.@" }
47
+ ]
48
+ }
49
+ subject.result.should == { :test => [ 1 ] }
50
+ end
51
+
52
+ it "should return a hash with imported fixtures at an existing target array" do
53
+ subject.hash = {
54
+ :imports => [
55
+ { :path => "one.second", :as => "test.@" }
56
+ ],
57
+ :test => [ 1 ]
58
+ }
59
+ subject.result.should == { :test => [ 2, 1 ] }
60
+ end
61
+
43
62
  it "should return a hash with imported and white-list filtered fixtures" do
44
63
  subject.hash = {
45
64
  :imports => [
@@ -82,6 +82,18 @@ describe Holoserve::Tool::DataPath do
82
82
  subject.store("value").should == { :test => "value", :another => { :test => "value" } }
83
83
  end
84
84
 
85
+ it "should store the given value at the specified path and place it in a new array" do
86
+ subject.path = "test.@"
87
+ subject.data = { }.freeze
88
+ subject.store("value").should == { :test => [ "value" ] }
89
+ end
90
+
91
+ it "should store the given value at the specified path and place it in an existing array" do
92
+ subject.path = "test.@"
93
+ subject.data = { :test => [ 1 ] }.freeze
94
+ subject.store(2).should == { :test => [ 1, 2 ] }
95
+ end
96
+
85
97
  end
86
98
 
87
99
  end
@@ -17,6 +17,17 @@ describe Holoserve::Tool::Merger do
17
17
 
18
18
  end
19
19
 
20
+ context "of two hashes with boolean values" do
21
+
22
+ let(:argument_one) { { :one => false, :two => true } }
23
+ let(:argument_two) { { :one => true, :two => false } }
24
+
25
+ it "should merge hashes with boolean values" do
26
+ subject.result.should == { :one => true, :two => false }
27
+ end
28
+
29
+ end
30
+
20
31
  context "of two nested hashes" do
21
32
 
22
33
  let(:argument_one) { { :test => { :regular =>"value", :nested => "value" } } }
@@ -56,6 +67,21 @@ describe Holoserve::Tool::Merger do
56
67
 
57
68
  end
58
69
 
70
+ context "of two arrays in fusion mode" do
71
+
72
+ before :each do
73
+ subject.mode = :fusion
74
+ end
75
+
76
+ let(:argument_one) { [ 1 ] }
77
+ let(:argument_two) { [ 2, 3 ] }
78
+
79
+ it "should combine all arrays" do
80
+ subject.result.should == [ 1, 2, 3 ]
81
+ end
82
+
83
+ end
84
+
59
85
  end
60
86
 
61
87
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: holoserve
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.4.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,11 +9,11 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-03-13 00:00:00.000000000 Z
12
+ date: 2012-04-05 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: goliath
16
- requirement: &70166500305240 !ruby/object:Gem::Requirement
16
+ requirement: &70271201827600 !ruby/object:Gem::Requirement
17
17
  none: false
18
18
  requirements:
19
19
  - - ! '>='
@@ -21,10 +21,10 @@ dependencies:
21
21
  version: '0'
22
22
  type: :runtime
23
23
  prerelease: false
24
- version_requirements: *70166500305240
24
+ version_requirements: *70271201827600
25
25
  - !ruby/object:Gem::Dependency
26
26
  name: rake
27
- requirement: &70166500304380 !ruby/object:Gem::Requirement
27
+ requirement: &70271205878240 !ruby/object:Gem::Requirement
28
28
  none: false
29
29
  requirements:
30
30
  - - ! '>='
@@ -32,10 +32,10 @@ dependencies:
32
32
  version: '0'
33
33
  type: :development
34
34
  prerelease: false
35
- version_requirements: *70166500304380
35
+ version_requirements: *70271205878240
36
36
  - !ruby/object:Gem::Dependency
37
37
  name: rdoc
38
- requirement: &70166500303920 !ruby/object:Gem::Requirement
38
+ requirement: &70271201838000 !ruby/object:Gem::Requirement
39
39
  none: false
40
40
  requirements:
41
41
  - - ! '>='
@@ -43,10 +43,10 @@ dependencies:
43
43
  version: '0'
44
44
  type: :development
45
45
  prerelease: false
46
- version_requirements: *70166500303920
46
+ version_requirements: *70271201838000
47
47
  - !ruby/object:Gem::Dependency
48
48
  name: cucumber
49
- requirement: &70166500303360 !ruby/object:Gem::Requirement
49
+ requirement: &70271201834120 !ruby/object:Gem::Requirement
50
50
  none: false
51
51
  requirements:
52
52
  - - ! '>='
@@ -54,10 +54,10 @@ dependencies:
54
54
  version: '0'
55
55
  type: :development
56
56
  prerelease: false
57
- version_requirements: *70166500303360
57
+ version_requirements: *70271201834120
58
58
  - !ruby/object:Gem::Dependency
59
59
  name: rspec
60
- requirement: &70166500302680 !ruby/object:Gem::Requirement
60
+ requirement: &70271201831820 !ruby/object:Gem::Requirement
61
61
  none: false
62
62
  requirements:
63
63
  - - ! '>='
@@ -65,10 +65,10 @@ dependencies:
65
65
  version: '0'
66
66
  type: :development
67
67
  prerelease: false
68
- version_requirements: *70166500302680
68
+ version_requirements: *70271201831820
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: transport
71
- requirement: &70166500294600 !ruby/object:Gem::Requirement
71
+ requirement: &70271205892940 !ruby/object:Gem::Requirement
72
72
  none: false
73
73
  requirements:
74
74
  - - ! '>='
@@ -76,10 +76,10 @@ dependencies:
76
76
  version: '0'
77
77
  type: :development
78
78
  prerelease: false
79
- version_requirements: *70166500294600
79
+ version_requirements: *70271205892940
80
80
  - !ruby/object:Gem::Dependency
81
81
  name: oauth
82
- requirement: &70166500293740 !ruby/object:Gem::Requirement
82
+ requirement: &70271205890640 !ruby/object:Gem::Requirement
83
83
  none: false
84
84
  requirements:
85
85
  - - ! '>='
@@ -87,7 +87,7 @@ dependencies:
87
87
  version: '0'
88
88
  type: :development
89
89
  prerelease: false
90
- version_requirements: *70166500293740
90
+ version_requirements: *70271205890640
91
91
  description: This tool can be used to fake webservice APIs for testing proposals.
92
92
  email: philipp.bruell@skrill.com
93
93
  executables:
@@ -100,6 +100,7 @@ files:
100
100
  - LICENSE
101
101
  - Rakefile
102
102
  - bin/holoserve
103
+ - bin/test.log
103
104
  - lib/holoserve/fixture/importer.rb
104
105
  - lib/holoserve/fixture.rb
105
106
  - lib/holoserve/interface/control/bucket.rb
@@ -147,7 +148,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
147
148
  version: '0'
148
149
  segments:
149
150
  - 0
150
- hash: -1981031091455740716
151
+ hash: -4367529671340100891
151
152
  required_rubygems_version: !ruby/object:Gem::Requirement
152
153
  none: false
153
154
  requirements: