stella 0.6.0 → 0.7.0.002
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.
- data/CHANGES.txt +7 -15
- data/LICENSE.txt +1 -1
- data/README.rdoc +93 -63
- data/Rakefile +32 -42
- data/bin/stella +138 -0
- data/examples/basic/listing_ids.csv +7 -0
- data/examples/basic/plan.rb +71 -0
- data/lib/stella/cli.rb +66 -0
- data/lib/stella/client.rb +199 -0
- data/lib/stella/config.rb +87 -0
- data/lib/stella/data/http/body.rb +15 -0
- data/lib/stella/data/http/request.rb +116 -0
- data/lib/stella/data/http/response.rb +92 -0
- data/lib/stella/data/http.rb +2 -257
- data/lib/stella/data.rb +85 -0
- data/lib/stella/dsl.rb +5 -0
- data/lib/stella/engine/functional.rb +39 -0
- data/lib/stella/engine/load.rb +106 -0
- data/lib/stella/engine.rb +55 -0
- data/lib/stella/exceptions.rb +15 -0
- data/lib/stella/guidelines.rb +18 -0
- data/lib/stella/mixins.rb +2 -0
- data/lib/stella/stats.rb +3 -7
- data/lib/stella/testplan/stats.rb +26 -0
- data/lib/stella/testplan/usecase.rb +67 -0
- data/lib/stella/testplan.rb +95 -220
- data/lib/{util → stella/utils}/httputil.rb +0 -0
- data/lib/stella/utils.rb +126 -0
- data/lib/stella/version.rb +15 -0
- data/lib/stella.rb +58 -104
- data/lib/threadify.rb +0 -6
- data/stella.gemspec +43 -49
- data/support/example_webapp.rb +246 -0
- data/support/useragents.txt +75 -0
- metadata +68 -32
- data/bin/example_test.rb +0 -82
- data/bin/example_webapp.rb +0 -63
- data/lib/logger.rb +0 -79
- data/lib/stella/clients.rb +0 -161
- data/lib/stella/command/base.rb +0 -20
- data/lib/stella/command/form.rb +0 -36
- data/lib/stella/command/get.rb +0 -44
- data/lib/stella/common.rb +0 -53
- data/lib/stella/crypto.rb +0 -88
- data/lib/stella/data/domain.rb +0 -82
- data/lib/stella/environment.rb +0 -66
- data/lib/stella/functest.rb +0 -105
- data/lib/stella/loadtest.rb +0 -186
- data/lib/stella/testrunner.rb +0 -64
- data/lib/storable.rb +0 -280
- data/lib/timeunits.rb +0 -65
- data/tryouts/drb/drb_test.rb +0 -65
- data/tryouts/drb/open4.rb +0 -19
- data/tryouts/drb/slave.rb +0 -27
- data/tryouts/oo_tryout.rb +0 -30
data/lib/stella/data/http.rb
CHANGED
@@ -1,259 +1,4 @@
|
|
1
1
|
|
2
|
-
|
3
|
-
require 'util/httputil'
|
4
|
-
require 'base64'
|
2
|
+
module Stella::Data::HTTP; end
|
5
3
|
|
6
|
-
|
7
|
-
|
8
|
-
# TODO: Implement HTTPHeaders. We should be printing untouched headers.
|
9
|
-
# HTTPUtil should split the HTTP event lines and that's it. Replace
|
10
|
-
# parse_header_body with split_header_body
|
11
|
-
class HTTPHeaders < Storable
|
12
|
-
attr_reader :raw_data
|
13
|
-
|
14
|
-
def to_s
|
15
|
-
@raw_data
|
16
|
-
end
|
17
|
-
|
18
|
-
end
|
19
|
-
|
20
|
-
class HTTPBody < Storable
|
21
|
-
field :content_type
|
22
|
-
field :form_param
|
23
|
-
field :content
|
24
|
-
|
25
|
-
def has_content?
|
26
|
-
!@content.nil?
|
27
|
-
end
|
28
|
-
|
29
|
-
end
|
30
|
-
|
31
|
-
class HTTPRequest < Storable
|
32
|
-
# A string representing a raw HTTP request
|
33
|
-
attr_reader :raw_data
|
34
|
-
|
35
|
-
# A hash containing blocks to be executed depending on the HTTP response status.
|
36
|
-
# The hash keys are numeric HTTP Status Codes.
|
37
|
-
#
|
38
|
-
# 200 => { ... }
|
39
|
-
# 304 => { ... }
|
40
|
-
# 500 => { ... }
|
41
|
-
#
|
42
|
-
attr_accessor :response_handler
|
43
|
-
|
44
|
-
field :name
|
45
|
-
field :stella_id
|
46
|
-
field :unique_id
|
47
|
-
field :time => DateTime
|
48
|
-
field :client_ip
|
49
|
-
field :server_ip
|
50
|
-
field :header
|
51
|
-
field :uri
|
52
|
-
field :params
|
53
|
-
field :body
|
54
|
-
field :http_method
|
55
|
-
field :http_version
|
56
|
-
|
57
|
-
|
58
|
-
def has_body?
|
59
|
-
!@body.nil? && !@body.empty?
|
60
|
-
end
|
61
|
-
def has_request?
|
62
|
-
false
|
63
|
-
end
|
64
|
-
|
65
|
-
def initialize (uri_str, method="GET", version="1.1")
|
66
|
-
@uri = (uri_str.is_a? String) ? URI.parse(uri_str) : uri
|
67
|
-
@http_method = method
|
68
|
-
@http_version = version
|
69
|
-
@headers = {}
|
70
|
-
@params = {}
|
71
|
-
@response_handler = {}
|
72
|
-
@time = Time.now
|
73
|
-
@stella_id = Stella::Crypto.sign(time.to_i.to_s, "#{@http_method}/#{@uri}/#{@params}")
|
74
|
-
@unique_id = nil
|
75
|
-
@body = HTTPBody.new
|
76
|
-
end
|
77
|
-
|
78
|
-
def set_unique_id(seasoning=rand)
|
79
|
-
@unique_id = Stella::Crypto.sign(rand.to_s + seasoning.to_s, "#{@http_method}/#{@uri}/#{@params}")
|
80
|
-
end
|
81
|
-
|
82
|
-
|
83
|
-
def from_raw(raw_data=nil)
|
84
|
-
@raw_data = raw_data
|
85
|
-
@http_method, @http_version, @uri, @header, @body = self.parse(@raw_data)
|
86
|
-
@time = DateTime.now
|
87
|
-
end
|
88
|
-
|
89
|
-
def self.parse(raw)
|
90
|
-
return unless raw
|
91
|
-
HTTPUtil::parse_http_request(raw, @uri.host, @uri.port)
|
92
|
-
end
|
93
|
-
|
94
|
-
|
95
|
-
def add_header(*args)
|
96
|
-
name, value = (args[0].is_a? Hash) ? args[0].to_a.flatten : args
|
97
|
-
@headers[name.to_s] ||= []
|
98
|
-
@headers[name.to_s] << value
|
99
|
-
end
|
100
|
-
def add_param(*args)
|
101
|
-
name, value = (args[0].is_a? Hash) ? args[0].to_a.flatten : args
|
102
|
-
|
103
|
-
# BUG: This auto-array shit is causing a problem where the one request
|
104
|
-
# will set the param and then next will set it again and it becomes
|
105
|
-
# an array.
|
106
|
-
#if @params[name.to_s] && !@params[name.to_s].is_a?(Array)
|
107
|
-
# @params[name.to_s] = [@params[name.to_s]]
|
108
|
-
#else
|
109
|
-
# @params[name.to_s] = ""
|
110
|
-
#end
|
111
|
-
|
112
|
-
@params[name.to_s] = value.to_s
|
113
|
-
end
|
114
|
-
|
115
|
-
def add_response_handler(*args, &b)
|
116
|
-
args << 200 if args.empty?
|
117
|
-
args.each do |status|
|
118
|
-
@response_handler[status] = b
|
119
|
-
end
|
120
|
-
end
|
121
|
-
|
122
|
-
# +content+ can be literal content or a file path
|
123
|
-
def add_body(content, form_param=nil, content_type=nil)
|
124
|
-
@body = Stella::Data::HTTPBody.new
|
125
|
-
|
126
|
-
@body.form_param = form_param if form_param
|
127
|
-
@body.content_type = content_type if content_type
|
128
|
-
|
129
|
-
if File.exists?(content)
|
130
|
-
@body.content = File.new(content)
|
131
|
-
@body.content_type ||= "application/x-www-form-urlencoded"
|
132
|
-
else
|
133
|
-
@body.content = content
|
134
|
-
end
|
135
|
-
|
136
|
-
end
|
137
|
-
|
138
|
-
|
139
|
-
def body
|
140
|
-
return nil unless @body
|
141
|
-
@body
|
142
|
-
#(!header || header[:Content_Type] || header[:Content_Type] !~ /text/) ? Base64.encode64(@body) : @body
|
143
|
-
end
|
144
|
-
|
145
|
-
|
146
|
-
def headers
|
147
|
-
return [] unless header
|
148
|
-
headers = []
|
149
|
-
header.each_pair do |n,v|
|
150
|
-
headers << [n.to_s.gsub('_', '-'), v[0]]
|
151
|
-
end
|
152
|
-
headers
|
153
|
-
end
|
154
|
-
|
155
|
-
def inspect
|
156
|
-
str = "%s %s HTTP/%s" % [http_method, uri.to_s, http_version]
|
157
|
-
str << $/ + headers.join($/) unless headers.empty?
|
158
|
-
str << $/ + $/ + body.to_s if body
|
159
|
-
str
|
160
|
-
end
|
161
|
-
|
162
|
-
def to_s
|
163
|
-
str = "%s: %s %s HTTP/%s" % [time.strftime(NICE_TIME_FORMAT), http_method, uri.to_s, http_version]
|
164
|
-
str
|
165
|
-
end
|
166
|
-
|
167
|
-
def cookies
|
168
|
-
return [] if !header.is_a?(Hash) || header[:Cookie].empty?
|
169
|
-
header[:Cookie]
|
170
|
-
end
|
171
|
-
|
172
|
-
end
|
173
|
-
|
174
|
-
class HTTPResponse < Storable
|
175
|
-
attr_reader :raw_data
|
176
|
-
|
177
|
-
field :time => DateTime
|
178
|
-
field :client_ip => String
|
179
|
-
field :server_ip => String
|
180
|
-
field :header => String
|
181
|
-
field :body => String
|
182
|
-
field :status => String
|
183
|
-
field :message => String
|
184
|
-
field :http_version => String
|
185
|
-
|
186
|
-
def initialize(raw_data=nil)
|
187
|
-
@raw_data = raw_data
|
188
|
-
parse(@raw_data)
|
189
|
-
end
|
190
|
-
|
191
|
-
def parse(raw)
|
192
|
-
return unless raw
|
193
|
-
@status, @http_version, @message, @header, @body = HTTPUtil::parse_http_response(raw)
|
194
|
-
end
|
195
|
-
|
196
|
-
def has_body?
|
197
|
-
!@body.nil? && !@body.empty?
|
198
|
-
end
|
199
|
-
def has_request?
|
200
|
-
false
|
201
|
-
end
|
202
|
-
def has_response?
|
203
|
-
false
|
204
|
-
end
|
205
|
-
|
206
|
-
|
207
|
-
def body
|
208
|
-
return nil unless @body
|
209
|
-
#TODO: Move to HTTPResponse::Body.to_s
|
210
|
-
if is_binary?
|
211
|
-
"[skipping binary content]"
|
212
|
-
elsif is_gzip?
|
213
|
-
#require 'zlib'
|
214
|
-
#Zlib::Inflate.inflate(@body)
|
215
|
-
"[skipping gzip content]"
|
216
|
-
else
|
217
|
-
@body
|
218
|
-
end
|
219
|
-
end
|
220
|
-
|
221
|
-
def headers
|
222
|
-
headers = []
|
223
|
-
header.each_pair do |n,v|
|
224
|
-
headers << [n.to_s.gsub('_', '-'), v[0]]
|
225
|
-
end
|
226
|
-
headers
|
227
|
-
end
|
228
|
-
|
229
|
-
def is_binary?
|
230
|
-
(!is_text?) == true
|
231
|
-
end
|
232
|
-
|
233
|
-
def is_text?
|
234
|
-
(!header[:Content_Type].nil? && (header[:Content_Type][0].is_a? String) && header[:Content_Type][0][/text/] != nil)
|
235
|
-
end
|
236
|
-
|
237
|
-
def is_gzip?
|
238
|
-
(!header[:Content_Encoding].nil? && (header[:Content_Encoding][0].is_a? String) && header[:Content_Encoding][0][/gzip/] != nil)
|
239
|
-
end
|
240
|
-
|
241
|
-
def inspect
|
242
|
-
str = "HTTP/%s %s (%s)" % [@http_version, @status, @message]
|
243
|
-
str << $/ + headers.join($/)
|
244
|
-
str << $/ + $/ + body if body
|
245
|
-
str
|
246
|
-
end
|
247
|
-
|
248
|
-
def to_s
|
249
|
-
str = "%s: HTTP/%s %s (%s)" % [time.strftime(NICE_TIME_FORMAT), @http_version, @status, @message]
|
250
|
-
str
|
251
|
-
end
|
252
|
-
|
253
|
-
|
254
|
-
def cookies
|
255
|
-
return [] unless header.is_a?(Array) && !header[:Set_Cookie].empty?
|
256
|
-
header[:Set_Cookie]
|
257
|
-
end
|
258
|
-
end
|
259
|
-
end
|
4
|
+
Stella::Utils.require_glob(STELLA_LIB_HOME, 'stella', 'data', 'http', '*.rb')
|
data/lib/stella/data.rb
ADDED
@@ -0,0 +1,85 @@
|
|
1
|
+
|
2
|
+
module Stella::Data
|
3
|
+
|
4
|
+
module Helpers
|
5
|
+
|
6
|
+
|
7
|
+
def random(input=nil)
|
8
|
+
|
9
|
+
Proc.new do
|
10
|
+
value = case input.class.to_s
|
11
|
+
when "Symbol"
|
12
|
+
resource(input)
|
13
|
+
when "Array"
|
14
|
+
input
|
15
|
+
when "Range"
|
16
|
+
input.to_a
|
17
|
+
when "Fixnum"
|
18
|
+
Stella::Utils.strand( input )
|
19
|
+
when "NilClass"
|
20
|
+
Stella::Utils.strand( rand(100) )
|
21
|
+
end
|
22
|
+
Stella.ld "RANDVALUES: #{input} #{value.inspect}"
|
23
|
+
value = value[ rand(value.size) ] if value.is_a?(Array)
|
24
|
+
Stella.ld "SELECTED: #{value}"
|
25
|
+
value
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def sequential(input=nil)
|
30
|
+
digest = input.gibbler
|
31
|
+
Proc.new do
|
32
|
+
value = case input.class.to_s
|
33
|
+
when "Symbol"
|
34
|
+
ret = resource(input)
|
35
|
+
ret
|
36
|
+
when "Array"
|
37
|
+
input
|
38
|
+
when "Range"
|
39
|
+
input.to_a
|
40
|
+
end
|
41
|
+
Stella.ld "SEQVALUES: #{input} #{value.inspect}"
|
42
|
+
@sequential_offset ||= {}
|
43
|
+
@sequential_offset[digest] ||= 0
|
44
|
+
if value.is_a?(Array)
|
45
|
+
size = value[ @sequential_offset[digest] ].size
|
46
|
+
value = value[ @sequential_offset[digest] ]
|
47
|
+
@sequential_offset[digest] += 1
|
48
|
+
@sequential_offset[digest] = 0 if @sequential_offset[digest] > size
|
49
|
+
end
|
50
|
+
Stella.ld "SELECTED: #{value}"
|
51
|
+
value
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
def rsequential(input=nil)
|
56
|
+
digest = input.gibbler
|
57
|
+
Proc.new do
|
58
|
+
value = case input.class.to_s
|
59
|
+
when "Symbol"
|
60
|
+
ret = resource(input)
|
61
|
+
ret
|
62
|
+
when "Array"
|
63
|
+
input
|
64
|
+
when "Range"
|
65
|
+
input.to_a
|
66
|
+
end
|
67
|
+
Stella.ld "RSEQVALUES: #{input} #{value.inspect}"
|
68
|
+
@rsequential_offset ||= {}
|
69
|
+
@rsequential_offset[digest] ||= value.size-1 rescue 1
|
70
|
+
if value.is_a?(Array)
|
71
|
+
size = value[ @rsequential_offset[digest] ].size
|
72
|
+
value = value[ @rsequential_offset[digest] ]
|
73
|
+
@rsequential_offset[digest] -= 1
|
74
|
+
@rsequential_offset[digest] = size if @rsequential_offset[digest] < 0
|
75
|
+
end
|
76
|
+
Stella.ld "SELECTED: #{value}"
|
77
|
+
value
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
end
|
82
|
+
|
83
|
+
end
|
84
|
+
|
85
|
+
Stella::Utils.require_glob(STELLA_LIB_HOME, 'stella', 'data', '*.rb')
|
data/lib/stella/dsl.rb
ADDED
@@ -0,0 +1,39 @@
|
|
1
|
+
|
2
|
+
module Stella::Engine
|
3
|
+
module Functional
|
4
|
+
extend Stella::Engine::Base
|
5
|
+
extend self
|
6
|
+
|
7
|
+
def run(plan, opts={})
|
8
|
+
opts = {
|
9
|
+
:hosts => [],
|
10
|
+
:benchmark => false,
|
11
|
+
:repetitions => 1
|
12
|
+
}.merge! opts
|
13
|
+
Stella.ld "OPTIONS: #{opts.inspect}"
|
14
|
+
Stella.li2 "Hosts: " << opts[:hosts].join(', ') if !opts[:hosts].empty?
|
15
|
+
|
16
|
+
client = Stella::Client.new opts[:hosts].first
|
17
|
+
client.add_observer(self)
|
18
|
+
client.enable_benchmark_mode if opts[:benchmark]
|
19
|
+
|
20
|
+
plan.usecases.each_with_index do |uc,i|
|
21
|
+
desc = (uc.desc || "Usecase ##{i+1}")
|
22
|
+
Stella.li ' %-65s '.att(:reverse).bright % [desc]
|
23
|
+
Stella.rescue { client.execute uc }
|
24
|
+
end
|
25
|
+
|
26
|
+
Drydock::Screen.flush
|
27
|
+
end
|
28
|
+
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
__END__
|
33
|
+
|
34
|
+
|
35
|
+
$ stella verify -p examples/basic/plan.rb http://localhost:3114
|
36
|
+
$ stella load -p examples/basic/plan.rb http://localhost:3114
|
37
|
+
$ stella remote-load -p examples/basic/plan.rb http://localhost:3114
|
38
|
+
$ stella remote-verify -p examples/basic/plan.rb http://localhost:3114
|
39
|
+
|
@@ -0,0 +1,106 @@
|
|
1
|
+
|
2
|
+
module Stella::Engine
|
3
|
+
module Load
|
4
|
+
extend Stella::Engine::Base
|
5
|
+
extend self
|
6
|
+
|
7
|
+
def run(plan, opts={})
|
8
|
+
opts = {
|
9
|
+
:hosts => [],
|
10
|
+
:users => 1,
|
11
|
+
:time => nil,
|
12
|
+
:benchmark => false,
|
13
|
+
:repetitions => 1
|
14
|
+
}.merge! opts
|
15
|
+
opts[:users] = plan.usecases.size if opts[:users] < plan.usecases.size
|
16
|
+
opts[:users] = 1000 if opts[:users] > 1000
|
17
|
+
|
18
|
+
Stella.ld "OPTIONS: #{opts.inspect}"
|
19
|
+
Stella.li2 "Hosts: " << opts[:hosts].join(', ')
|
20
|
+
|
21
|
+
packages = build_thread_package plan, opts
|
22
|
+
Drydock::Screen.flush
|
23
|
+
|
24
|
+
Thread.ify packages, :threads => opts[:users] do |package|
|
25
|
+
(1..opts[:repetitions]).to_a.each do |rep|
|
26
|
+
# We store client specific data in the usecase
|
27
|
+
# so we clone it here so each thread is unique.
|
28
|
+
Stella.rescue { package.client.execute package.usecase }
|
29
|
+
Drydock::Screen.flush
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
Drydock::Screen.flush
|
34
|
+
end
|
35
|
+
|
36
|
+
protected
|
37
|
+
class ThreadPackage
|
38
|
+
attr_accessor :index
|
39
|
+
attr_accessor :client
|
40
|
+
attr_accessor :usecase
|
41
|
+
def initialize(i, c, u)
|
42
|
+
@index, @client, @usecase = i, c, u
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
def build_thread_package(plan, opts)
|
47
|
+
packages, pointer = Array.new(opts[:users]), 0
|
48
|
+
plan.usecases.each_with_index do |usecase,i|
|
49
|
+
|
50
|
+
count = case opts[:users]
|
51
|
+
when 0..9
|
52
|
+
if (opts[:users] % plan.usecases.size > 0)
|
53
|
+
raise Stella::Testplan::WackyRatio, "User count does not match usecase count evenly"
|
54
|
+
else
|
55
|
+
(opts[:users] / plan.usecases.size)
|
56
|
+
end
|
57
|
+
else
|
58
|
+
(opts[:users] * usecase.ratio).to_i
|
59
|
+
end
|
60
|
+
|
61
|
+
Stella.ld "THREAD PACKAGE: #{usecase.desc} #{pointer} #{(pointer+count)} #{count}"
|
62
|
+
# Fill the thread_package with the contents of the block
|
63
|
+
packages.fill(pointer, count) do |index|
|
64
|
+
Stella.li2 "Creating client ##{index+1} "
|
65
|
+
client = Stella::Client.new opts[:hosts].first, index+1
|
66
|
+
client.add_observer(self)
|
67
|
+
client.enable_benchmark_mode if opts[:benchmark]
|
68
|
+
ThreadPackage.new(index+1, client, usecase.clone)
|
69
|
+
end
|
70
|
+
pointer += count
|
71
|
+
end
|
72
|
+
packages
|
73
|
+
end
|
74
|
+
|
75
|
+
def update_send_request(client_id, usecase, meth, uri, req, params, counter)
|
76
|
+
|
77
|
+
end
|
78
|
+
|
79
|
+
def update_receive_response(client_id, usecase, meth, uri, req, params, container)
|
80
|
+
desc = "#{usecase.desc} > #{req.desc}"
|
81
|
+
Stella.li ' Client%-3s %3d %-6s %-45s %s' % [client_id, container.status, req.http_method, desc, uri]
|
82
|
+
end
|
83
|
+
|
84
|
+
def update_execute_response_handler(client_id, req, container)
|
85
|
+
end
|
86
|
+
|
87
|
+
def update_error_execute_response_handler(client_id, ex, req, container)
|
88
|
+
end
|
89
|
+
|
90
|
+
def update_request_error(client_id, usecase, meth, uri, req, params, ex)
|
91
|
+
desc = "#{usecase.desc} > #{req.desc}"
|
92
|
+
Stella.le ' Client%-3s %-45s %s' % [client_id, desc, ex.message]
|
93
|
+
end
|
94
|
+
|
95
|
+
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
__END__
|
100
|
+
|
101
|
+
|
102
|
+
$ stella verify -p examples/basic/plan.rb http://localhost:3114
|
103
|
+
$ stella load -p examples/basic/plan.rb http://localhost:3114
|
104
|
+
$ stella remote-load -p examples/basic/plan.rb http://localhost:3114
|
105
|
+
$ stella remote-verify -p examples/basic/plan.rb http://localhost:3114
|
106
|
+
|
@@ -0,0 +1,55 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Stella::Engine
|
4
|
+
module Base
|
5
|
+
extend self
|
6
|
+
def run
|
7
|
+
raise "override the run method"
|
8
|
+
end
|
9
|
+
|
10
|
+
def update(*args)
|
11
|
+
what, *args = args
|
12
|
+
Stella.ld "OBSERVER UPDATE: #{what}"
|
13
|
+
if !respond_to?("update_#{what}")
|
14
|
+
Stella.ld "NO UPDATE HANDLER FOR: #{what}"
|
15
|
+
else
|
16
|
+
Stella.rescue {
|
17
|
+
self.send("update_#{what}", *args)
|
18
|
+
}
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
def update_send_request(client_id, usecase, meth, uri, req, params, counter)
|
23
|
+
notice = "repeat: #{counter-1}" if counter > 1
|
24
|
+
Stella.li2 ' ' << " %-46s %16s ".att(:reverse) % [req.desc, notice]
|
25
|
+
end
|
26
|
+
|
27
|
+
def update_receive_response(client_id, usecase, meth, uri, req, params, container)
|
28
|
+
Stella.li ' %-59s %3d' % [uri, container.status]
|
29
|
+
Stella.li2 " Method: " << req.http_method
|
30
|
+
Stella.li2 " Params: " << params.inspect
|
31
|
+
Stella.li3 $/, " Headers:"
|
32
|
+
container.headers.all.each do |pair|
|
33
|
+
Stella.li3 " %s: %s" % pair
|
34
|
+
end
|
35
|
+
Stella.li3 $/, " Content:"
|
36
|
+
Stella.li3 container.body.empty? ? ' [empty]' : container.body
|
37
|
+
Stella.li2 $/
|
38
|
+
end
|
39
|
+
|
40
|
+
def update_execute_response_handler(client_id, req, container)
|
41
|
+
end
|
42
|
+
|
43
|
+
def update_error_execute_response_handler(client_id, ex, req, container)
|
44
|
+
Stella.le ex.message
|
45
|
+
end
|
46
|
+
|
47
|
+
def update_request_error(client_id, usecase, meth, uri, req, params, ex)
|
48
|
+
desc = "#{usecase.desc} > #{req.desc}"
|
49
|
+
Stella.le ' Client%-3s %-45s %s' % [client_id, desc, ex.message]
|
50
|
+
end
|
51
|
+
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
Stella::Utils.require_glob(STELLA_LIB_HOME, 'stella', 'engine', '*.rb')
|
@@ -0,0 +1,18 @@
|
|
1
|
+
|
2
|
+
|
3
|
+
module Stella
|
4
|
+
module Guidelines
|
5
|
+
extend self
|
6
|
+
AFE = "Always fail early"
|
7
|
+
ABA = "Always be accurate"
|
8
|
+
CBC = "Consistency before cuteness"
|
9
|
+
NDP = "No defensive programming"
|
10
|
+
def inspect
|
11
|
+
all = Stella::Guidelines.constants
|
12
|
+
g = all.collect { |c| '%s="%s"' % [c, const_get(c)] }
|
13
|
+
%q{#<Stella::Guidelines:0x%s %s>} % [self.object_id, g.join(' ')]
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
p Stella::Guidelines if __FILE__ == $0
|
data/lib/stella/stats.rb
CHANGED
@@ -1,5 +1,4 @@
|
|
1
1
|
|
2
|
-
|
3
2
|
module Stella
|
4
3
|
# Based on Mongrel::Stats, Copyright (c) 2005 Zed A. Shaw
|
5
4
|
class Stats
|
@@ -17,12 +16,9 @@ class Stats
|
|
17
16
|
|
18
17
|
# Resets the internal counters so you can start sampling again.
|
19
18
|
def reset
|
20
|
-
@sum = 0.0
|
21
|
-
@sumsq = 0.0
|
19
|
+
@n, @sum, @sumsq = 0.0, 0.0, 0.0
|
22
20
|
@last_time = Time.new
|
23
|
-
@
|
24
|
-
@min = 0.0
|
25
|
-
@max = 0.0
|
21
|
+
@min, @max = 0.0, 0.0
|
26
22
|
end
|
27
23
|
|
28
24
|
# Adds a sampling to the calculations.
|
@@ -81,4 +77,4 @@ class Stats
|
|
81
77
|
@last_time = now
|
82
78
|
end
|
83
79
|
end
|
84
|
-
end
|
80
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
|
2
|
+
module Stella
|
3
|
+
class Testplan
|
4
|
+
|
5
|
+
class Stats
|
6
|
+
include Gibbler::Complex
|
7
|
+
attr_reader :requests
|
8
|
+
|
9
|
+
def initialize
|
10
|
+
@requests = OpenStruct.new
|
11
|
+
reset
|
12
|
+
end
|
13
|
+
|
14
|
+
def total_requests
|
15
|
+
@requests.successful + @requests.failed
|
16
|
+
end
|
17
|
+
|
18
|
+
def reset
|
19
|
+
@requests.successful = 0
|
20
|
+
@requests.failed = 0
|
21
|
+
end
|
22
|
+
|
23
|
+
end
|
24
|
+
|
25
|
+
end
|
26
|
+
end
|