RoadRunner 3.3.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.
data/LICENSE ADDED
@@ -0,0 +1,3 @@
1
+ == RoadRunner
2
+
3
+ Put appropriate LICENSE for your project here.
data/README ADDED
@@ -0,0 +1,3 @@
1
+ == RoadRunner
2
+
3
+ You should document your project here.
@@ -0,0 +1,46 @@
1
+ #
2
+ # To change this template, choose Tools | Templates
3
+ # and open the template in the editor.
4
+
5
+
6
+ require 'rubygems'
7
+ require 'rake'
8
+ require 'rake/clean'
9
+ require 'rake/gempackagetask'
10
+ require 'rake/rdoctask'
11
+ require 'rake/testtask'
12
+
13
+ spec = Gem::Specification.new do |s|
14
+ s.name = 'RoadRunner'
15
+ s.version = '3.3.1'
16
+ s.has_rdoc = false
17
+ s.extra_rdoc_files = ['README', 'LICENSE']
18
+ s.summary = 'RoadRunner是LoadRunner的Ruby简易实现'
19
+ s.description = s.summary
20
+ s.author = 'CharlesCui'
21
+ s.email = 'zheng.cuizh@gmail.com'
22
+ # s.executables = ['your_executable_here']
23
+ s.files = %w(LICENSE README Rakefile) + Dir.glob("{bin,lib,spec,test}/**/*")
24
+ s.require_path = "lib"
25
+ s.bindir = "bin"
26
+ end
27
+
28
+ Rake::GemPackageTask.new(spec) do |p|
29
+ p.gem_spec = spec
30
+ p.need_tar = true
31
+ p.need_zip = true
32
+ end
33
+
34
+ Rake::RDocTask.new do |rdoc|
35
+ files =['README', 'LICENSE', 'lib/**/*.rb']
36
+ rdoc.rdoc_files.add(files)
37
+ rdoc.main = "README" # page to start on
38
+ rdoc.title = "RoadRunner Docs"
39
+ rdoc.rdoc_dir = 'doc/rdoc' # rdoc output folder
40
+ rdoc.options << '--line-numbers'
41
+ end
42
+
43
+ Rake::TestTask.new do |t|
44
+ t.test_files = FileList['test/**/*.rb']
45
+ end
46
+
@@ -0,0 +1,13 @@
1
+ #Here is LR Action function
2
+
3
+ module RoadRunnerModule
4
+ def action(&blk)
5
+
6
+ if block_given?
7
+ @actBlk=blk
8
+ else
9
+ raise ArgumentError, "no block"
10
+ end
11
+
12
+ end
13
+ end
@@ -0,0 +1,51 @@
1
+ #
2
+
3
+ module RoadRunnerModule
4
+
5
+ module Dbhelper
6
+
7
+ def migrate(tables)
8
+ tables.each do |table|
9
+ case table
10
+ when "scenarios" then
11
+ unless ActiveRecord::Base.connection.tables.include?(table.to_s) then
12
+ ActiveRecord::Base.connection.create_table(table.to_sym) do |t|
13
+ t.column :name, :string, :limit => 256
14
+ t.column :create_at,:string, :limit => 32
15
+ t.column :script, :string,:limit => 10240
16
+ t.column :author, :string, :default => 'Anonymous'
17
+ t.column :author, :tps, :int
18
+ t.column :desc, :string
19
+ end
20
+ end
21
+
22
+ when "transactions" then
23
+ unless ActiveRecord::Base.connection.tables.include?(table.to_s) then
24
+ ActiveRecord::Base.connection.create_table(table.to_sym) do |t|
25
+ t.column :name,:string,:limit => 256
26
+ t.column :scenario_id,:string,:limit => 256
27
+ t.column :success_rate,:string, :limit => 8
28
+ t.column :create_at,:string, :limit => 32
29
+
30
+ end
31
+ end
32
+
33
+ when "records" then
34
+ unless ActiveRecord::Base.connection.tables.include?(table.to_s) then
35
+ ActiveRecord::Base.connection.create_table(table.to_sym) do |t|
36
+ t.column :cost, :string, :limit => 32
37
+ t.column :ts, :string, :limit => 32
38
+ t.column :seq, :int
39
+ t.column :stats,:int
40
+ t.column :transaction_id,:string,:limit => 256
41
+ t.column :create_at,:string, :limit => 32
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+
48
+ module_function :migrate
49
+ end
50
+
51
+ end
@@ -0,0 +1,13 @@
1
+ #Here is LR End function
2
+
3
+ module RoadRunnerModule
4
+ def ended(&blk)
5
+
6
+ if block_given?
7
+ @endBlk=blk
8
+ else
9
+ raise ArgumentError, "no block"
10
+ end
11
+
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ #Here is LR init function
2
+
3
+ module RoadRunnerModule
4
+ def init(&blk)
5
+
6
+ if block_given?
7
+ @initBlk=blk
8
+ else
9
+ raise ArgumentError, "no block"
10
+ end
11
+
12
+ end
13
+ end
@@ -0,0 +1,10 @@
1
+ class Scenario < ActiveRecord::Base
2
+ has_many :transactions
3
+ end
4
+ class Transaction < ActiveRecord::Base
5
+ belongs_to :scenario
6
+ has_many :records
7
+ end
8
+ class Record < ActiveRecord::Base
9
+ belongs_to :transaction
10
+ end
@@ -0,0 +1,100 @@
1
+ #After roadRunner.run() executed,
2
+ #execute roadRunner.report() show the Performance report
3
+
4
+ module RoadRunnerModule
5
+
6
+ def report(label='',width=0)
7
+ p " Wait for moment,the report is collecting......"
8
+ content = if @rep
9
+ @succRates = getSuccessRate @transactions
10
+ <<-DOC
11
+ #{"Performance Reports".center(50, '*')}
12
+ #{label.ljust(width)}
13
+ #{Benchmark::Tms::CAPTION}
14
+ #{@rep.format}
15
+ #{'--'*32}
16
+ The Virtual User is #{@users}.
17
+ Total Execute #{@iterations*@users} Action(s).
18
+ Total Cost #{@rep.real} Second(s).
19
+ This Scenario's TPS : #{@tps}.
20
+ The longest action cost #{@longest || 0} seconds.
21
+ #{'Transaction Report'.center(50, '-')}
22
+ #{@transactions.inject("") { |str,k|
23
+ str += "#{k[0].to_s} : count => #{k[1].size} time(s) , cost => #{k[1].inject(0){|c,v|c+=v[:cost].to_f}.to_s[0..3]} sec(s) , success rate => #{@succRates[k[0]]}\n "
24
+ }.gsub(/\n$/,'')}
25
+ #{'--'*32}
26
+ User defined params as below:
27
+ #{@global}
28
+ #{"End of Reports".center(50, '*')}
29
+ DOC
30
+ else
31
+ "None Report before RoadRunner run."
32
+ end
33
+ puts content
34
+ self.log.info content
35
+ end
36
+
37
+ def save_report(opts={:author=>'Anonymous',:script=>""})
38
+
39
+ p " Saving report to database......"
40
+ opts={:author=>'Anonymous',:script=>""}.merge opts
41
+ if @data_write then
42
+ unless opts[:name] then
43
+ self.log.warn "scenario name may be needed."
44
+ require 'uuidtools' unless defined?UUID
45
+ # scenario || UUID.random_create.to_s is for debug
46
+ opts[:name] = opts[:name] || UUID.random_create.to_s
47
+ self.log.info "scenario is created as #{opts[:name]}"
48
+ end
49
+ # => scenario = Scenario.find_or_create_by_name(opts.merge({:create_at=>Time.now})).shift
50
+ scenario = Scenario.find_or_create_by_name(opts.merge({:create_at=>Time.now}))
51
+ scenario.tps+=@iterations*@users/@rep.real
52
+
53
+ # => if opts[:script] is set as <your script>.rb 's path
54
+ # => opts[:script] = __FILE__
55
+ # => then scenario.script will be set.
56
+ if FileTest.exist?(opts[:script]) then
57
+ scenario.script = ""
58
+ IO.foreach(opts[:script]){|x|scenario.script << x}
59
+ end
60
+
61
+ @succRates = @succRates || (getSuccessRate @transactions)
62
+ # k is transaction name ,
63
+ # v is reports in every transaction.
64
+ @transactions.each do |k,v|
65
+ transaction = Transaction.new({:name=>k,:create_at=>Time.now,:success_rate=>@succRates[k]})
66
+ v.each_index do |id|
67
+ transaction.records << Record.new(v[id].merge({:seq=>id,:ts=>v[id][:create_at].to_f-@strat_time.to_f}))
68
+ self.log.debug "v[#{id}] = #{v[id].inspect}"
69
+ end
70
+ scenario.transactions << transaction
71
+ end
72
+ begin
73
+ scenario.save!
74
+ p " Saved OK!"
75
+ rescue =>e
76
+ self.log.error e
77
+ p e
78
+ end
79
+ self.log.info "records has saved in DB."
80
+ else
81
+ p ' Error:You didn\'t connect any database.'
82
+ self.log.error 'You didn\'t connect any database.'
83
+ end
84
+ end
85
+
86
+ def getSuccessRate(transactions)
87
+ result = {}
88
+ transactions.each do |h|
89
+ success,faile = 0,0
90
+ h[1].each do |r|
91
+ r[:stats]==0?success+=1:faile+=1
92
+ end
93
+ result[h[0]]=success.to_f/(success+faile)
94
+ end
95
+ result
96
+ end
97
+
98
+ private :getSuccessRate
99
+
100
+ end
@@ -0,0 +1,113 @@
1
+ # Author : zheng.cuizh@gmail.com
2
+ # RoadRunner named lik LoadRunner which is a industry performance test tool of HP.
3
+ # I'm happy to user LR and Ruby,
4
+ # so i coded the RoadRunner.
5
+ # Using RR,you'll find somethings similar to LR.
6
+
7
+ $:.unshift File.dirname(__FILE__)
8
+ require 'rubygems'
9
+ require 'benchmark'
10
+ require 'logger'
11
+ require 'pp'
12
+
13
+ require 'init'
14
+ require 'action'
15
+ require 'ended'
16
+ require 'run'
17
+ require 'report'
18
+ require 'rrhelper'
19
+
20
+ class RoadRunner
21
+
22
+ include RoadRunnerModule
23
+ attr :iterations, true
24
+ attr :users,true
25
+ attr :global,true
26
+ attr :iterationId
27
+ attr :record
28
+ attr :userId
29
+ attr :mode,true
30
+ attr :log
31
+ attr :tps
32
+ alias_method :g,:global
33
+ alias_method :g=,:global=
34
+
35
+ def initialize(opts={})
36
+ # => DEBUG < INFO < WARN < ERROR < FATAL < UNKNOWN
37
+ opts = {:out=>"roadrunner_stdout.log",:frequency=>'daily',:size=>1048576,:level=>Logger::ERROR}.merge opts
38
+ @users,@iterations,@longest,@userId,@iterationId=1,1,0,0,0
39
+ @initBlk,@actBlk,@endBlk=proc{},proc{},proc{}
40
+ @global,@transactions={},{}
41
+ @log=Logger.new(opts[:out],opts[:frequency],opts[:size])
42
+ @log.level=opts[:level]
43
+ # => mode : sequence,thread
44
+ @mode='sequence'
45
+
46
+ if block_given? then
47
+ require 'active_record'
48
+ require 'db'
49
+
50
+ session = {}
51
+ _session = yield session
52
+ session = _session if session == {}
53
+
54
+ begin
55
+ ActiveRecord::Base.establish_connection(
56
+ #
57
+ # === session defined in block :
58
+ #
59
+ # :adapter=>session[:adapter],
60
+ # :encoding=>session[:encoding],
61
+ # :database=>session[:database],
62
+ # :username=>session[:username],
63
+ # :password=>session[:password],
64
+ # :host=>session[:host]
65
+ #
66
+ session
67
+ )
68
+ self.log.info "connect db ok."
69
+ rescue =>ex
70
+ self.log.error "adapter:#{session[:adapter]}.connect db faile."
71
+ end
72
+
73
+ default_report_table = %w"scenarios transactions records"
74
+
75
+ unless @data_write = default_report_table.inject(true){|r,t| r = r && ActiveRecord::Base.connection.tables.include?(t)} then
76
+ self.log.warn "table rreports doesn't defined and will be created."
77
+ Dbhelper::migrate default_report_table
78
+ if @data_write = default_report_table.inject(true){|r,t| r = r && ActiveRecord::Base.connection.tables.include?(t)} then
79
+ self.log.info "create table #{default_report_table.inspect} successful."
80
+ else
81
+ self.log.error "create table #{default_report_table.inspect} fail."
82
+ end
83
+ end
84
+ require 'model' unless defined? Scenario
85
+ self.log.debug 'model Rreport is reqruired.'
86
+ end
87
+ end
88
+
89
+ def transaction(name,&blk)
90
+ @transactions[name] || @transactions[name] = []
91
+ status = "AUTO"
92
+ # => Status is the last expression in the action block
93
+ rcost = Benchmark::realtime{status = yield} if block_given?
94
+ # => status's value is:
95
+ # => 0=>success
96
+ # => -1=>faile
97
+ case status
98
+ when false,'false','-1',-1 then status = -1
99
+ else status = 0
100
+ end
101
+ # {:stats=>status,:cost=>rcost,:create_at=>Time.now} is one record
102
+ @transactions[name] << {:stats=>status,:cost=>rcost,:create_at=>Time.now}
103
+ # => the below sentence cost a lot of system resource
104
+ # => if you run for production result,keep it annotated!!!
105
+ # self.log.debug @transactions[name].inspect
106
+ rcost
107
+ end
108
+
109
+ def method_missing(name,*args,&blk)
110
+ self.transaction(name.to_s,&blk)
111
+ end
112
+
113
+ end
@@ -0,0 +1,168 @@
1
+ # Logfile created on Mon May 25 14:25:28 +0800 2009 by /
2
+ connect db ok.
3
+ ***************Performance Reports****************
4
+
5
+ user system total real
6
+
7
+ 43.328000 7.657000 50.985000 ( 75.508000)
8
+
9
+ ----------------------------------------------------------------
10
+ The Virtual User is 10.
11
+ Total Execute 500 Action(s).
12
+ Total Cost 75.5080001354218 Second(s).
13
+ This Scenario's TPS : 6.62181489515366.
14
+ The longest action cost 3.24900007247925 seconds.
15
+ ----------------Transaction Report----------------
16
+ Action : count => 500 time(s) , cost => 73.0 sec(s) , success rate => 1.0
17
+ homepage : count => 500 time(s) , cost => 29.6 sec(s) , success rate => 1.0
18
+ auto : count => 500 time(s) , cost => 37.9 sec(s) , success rate => 1.0
19
+
20
+ ----------------------------------------------------------------
21
+ User defined params as below:
22
+
23
+ ******************End of Reports******************
24
+
25
+ connect db ok.
26
+ connect db ok.
27
+ ***************Performance Reports****************
28
+
29
+ user system total real
30
+
31
+ 11.859000 2.828000 14.687000 ( 21.623000)
32
+
33
+ ----------------------------------------------------------------
34
+ The Virtual User is 10.
35
+ Total Execute 100 Action(s).
36
+ Total Cost 21.6230001449585 Second(s).
37
+ This Scenario's TPS : 4.62470514404152.
38
+ The longest action cost 3.125 seconds.
39
+ ----------------Transaction Report----------------
40
+ Action : count => 100 time(s) , cost => 21.5 sec(s) , success rate => 1.0
41
+ homepage : count => 100 time(s) , cost => 8.67 sec(s) , success rate => 1.0
42
+ auto : count => 100 time(s) , cost => 12.4 sec(s) , success rate => 1.0
43
+
44
+ ----------------------------------------------------------------
45
+ User defined params as below:
46
+
47
+ ******************End of Reports******************
48
+
49
+ I, [2009-05-25T14:38:06.388000 #3748] INFO -- : ***************Performance Reports****************
50
+
51
+ user system total real
52
+
53
+ 14.266000 0.015000 14.281000 ( 14.342000)
54
+
55
+ ----------------------------------------------------------------
56
+ The Virtual User is 10.
57
+ Total Execute 1000 Action(s).
58
+ Total Cost 14.3420000076294 Second(s).
59
+ This Scenario's TPS : 69.7252823503025.
60
+ The longest action cost 0.0320000648498535 seconds.
61
+ ----------------Transaction Report----------------
62
+ Action : count => 1000 time(s) , cost => 5.90 sec(s) , success rate => 1.0
63
+
64
+ ----------------------------------------------------------------
65
+ User defined params as below:
66
+ deep1000pi3140.59265383977
67
+ ******************End of Reports******************
68
+
69
+ I, [2009-05-25T16:57:12.328000 #4264] INFO -- : ***************Performance Reports****************
70
+
71
+ user system total real
72
+
73
+ 14.188000 0.016000 14.204000 ( 14.318000)
74
+
75
+ ----------------------------------------------------------------
76
+ The Virtual User is 10.
77
+ Total Execute 1000 Action(s).
78
+ Total Cost 14.3180000782013 Second(s).
79
+ This Scenario's TPS : 69.8421563443395.
80
+ The longest action cost 0.0320000648498535 seconds.
81
+ ----------------Transaction Report----------------
82
+ Action : count => 1000 time(s) , cost => 5.21 sec(s) , success rate => 1.0
83
+
84
+ ----------------------------------------------------------------
85
+ User defined params as below:
86
+ deep1000pi3140.59265383977
87
+ ******************End of Reports******************
88
+
89
+ I, [2009-05-25T16:59:11.609000 #4884] INFO -- : ***************Performance Reports****************
90
+
91
+ user system total real
92
+
93
+ 14.235000 0.032000 14.267000 ( 14.334000)
94
+
95
+ ----------------------------------------------------------------
96
+ The Virtual User is 10.
97
+ Total Execute 1000 Action(s).
98
+ Total Cost 14.3339998722076 Second(s).
99
+ This Scenario's TPS : 69.7641976360633.
100
+ The longest action cost 1 seconds.
101
+ ----------------Transaction Report----------------
102
+ Action : count => 1000 time(s) , cost => 5.38 sec(s) , success rate => 1.0
103
+
104
+ ----------------------------------------------------------------
105
+ User defined params as below:
106
+ deep1000pi3140.59265383977
107
+ ******************End of Reports******************
108
+
109
+ I, [2009-05-25T17:00:02.113000 #5796] INFO -- : ***************Performance Reports****************
110
+
111
+ user system total real
112
+
113
+ 4.906000 0.000000 4.906000 ( 4.955000)
114
+
115
+ ----------------------------------------------------------------
116
+ The Virtual User is 10.
117
+ Total Execute 1000 Action(s).
118
+ Total Cost 4.95499992370605 Second(s).
119
+ This Scenario's TPS : 201.816350231557.
120
+ The longest action cost 1 seconds.
121
+ ----------------Transaction Report----------------
122
+ Action : count => 1000 time(s) , cost => 4.90 sec(s) , success rate => 0.0
123
+
124
+ ----------------------------------------------------------------
125
+ User defined params as below:
126
+ deep1000pi3140.59265383977
127
+ ******************End of Reports******************
128
+
129
+ I, [2009-05-25T17:00:22.402000 #4628] INFO -- : ***************Performance Reports****************
130
+
131
+ user system total real
132
+
133
+ 4.906000 0.000000 4.906000 ( 4.908000)
134
+
135
+ ----------------------------------------------------------------
136
+ The Virtual User is 10.
137
+ Total Execute 1000 Action(s).
138
+ Total Cost 4.90799999237061 Second(s).
139
+ This Scenario's TPS : 203.748981571818.
140
+ The longest action cost 1 seconds.
141
+ ----------------Transaction Report----------------
142
+ Action : count => 1000 time(s) , cost => 4.86 sec(s) , success rate => 1.0
143
+
144
+ ----------------------------------------------------------------
145
+ User defined params as below:
146
+ deep1000pi3140.59265383977
147
+ ******************End of Reports******************
148
+
149
+ I, [2009-05-25T17:01:05.497000 #5828] INFO -- : ***************Performance Reports****************
150
+
151
+ user system total real
152
+
153
+ 14.297000 0.047000 14.344000 ( 14.381000)
154
+
155
+ ----------------------------------------------------------------
156
+ The Virtual User is 10.
157
+ Total Execute 1000 Action(s).
158
+ Total Cost 14.3810000419617 Second(s).
159
+ This Scenario's TPS : 69.5361933858664.
160
+ The longest action cost 1 seconds.
161
+ ----------------Transaction Report----------------
162
+ Action : count => 1000 time(s) , cost => 5.82 sec(s) , success rate => 1.0
163
+
164
+ ----------------------------------------------------------------
165
+ User defined params as below:
166
+ deep1000pi3140.59265383977
167
+ ******************End of Reports******************
168
+