jmeter-reports 0.0.1alpha

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1 @@
1
+ jmeter-reports*.gem
@@ -0,0 +1,4 @@
1
+ language: ruby
2
+ rvm:
3
+ - 1.9.3
4
+ - 1.8.7
data/Gemfile ADDED
@@ -0,0 +1,8 @@
1
+ source :rubygems
2
+
3
+ gem 'rake'
4
+
5
+ group :test do
6
+ gem 'minitest'
7
+ gem 'minitest-colorize'
8
+ end
@@ -0,0 +1,15 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ minitest (2.12.1)
5
+ minitest-colorize (0.0.4)
6
+ minitest (~> 2.0)
7
+ rake (10.0.2)
8
+
9
+ PLATFORMS
10
+ ruby
11
+
12
+ DEPENDENCIES
13
+ minitest
14
+ minitest-colorize
15
+ rake
data/LICENSE ADDED
@@ -0,0 +1,13 @@
1
+ DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
2
+ Version 2, December 2004
3
+
4
+ Copyright (C) 2012 Marcos Hack <marcoshack@gmail.com>
5
+
6
+ Everyone is permitted to copy and distribute verbatim or modified
7
+ copies of this license document, and changing it is allowed as long
8
+ as the name is changed.
9
+
10
+ DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
11
+ TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
12
+
13
+ 0. You just DO WHAT THE FUCK YOU WANT TO.
@@ -0,0 +1,10 @@
1
+ == JMeter Reports {<img src="https://travis-ci.org/marcoshack/jmeter-reports.png?branch=master" alt="Build Status" />}[https://travis-ci.org/marcoshack/jmeter-reports]
2
+
3
+ Basic tools for JMeter reports processing.
4
+
5
+ Right now it supports only CSV summary reports processing to show:
6
+
7
+ * Test execution time
8
+ * Average request throughput
9
+ * Number of requests/errors for each request and/or transaction
10
+ * 90 and 95 response time percentiles
@@ -0,0 +1,19 @@
1
+ #!/usr/bin/env rake
2
+
3
+ begin
4
+ require 'bundler/setup'
5
+ rescue LoadError
6
+ puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
7
+ end
8
+
9
+ require 'rake'
10
+ require 'rake/testtask'
11
+
12
+ Rake::TestTask.new do |t|
13
+ t.libs << "test"
14
+ t.libs << "lib"
15
+ t.test_files = FileList['test/**/test_*.rb', 'test/**/*_spec.rb']
16
+ t.verbose = false
17
+ end
18
+
19
+ task :default => :test
@@ -0,0 +1,22 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ $:.push File.join(File.dirname(__FILE__), '..'), File.join(File.dirname(__FILE__), '..','lib')
4
+ require 'jmeter/reports'
5
+
6
+ if ARGV[0] == nil || ARGV[0].empty?
7
+ puts "Usage: #{File.basename(__FILE__)} <report_file>"
8
+ exit 1
9
+ end
10
+
11
+ begin
12
+ report = Jmeter::SummaryReport::Report.create(ARGV[0])
13
+ puts "Test time: #{report.elapsed} secs"
14
+ puts "Average throughput: #{report.avg_throughput} RPS"
15
+ puts "Test plan:"
16
+ report.items.each do |item|
17
+ puts "\t#{item.text_summary}"
18
+ end
19
+ rescue Exception => e
20
+ puts e.message
21
+ exit 1
22
+ end
@@ -0,0 +1,21 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+
5
+ Gem::Specification.new do |gem|
6
+ gem.name = "jmeter-reports"
7
+ gem.version = "0.0.1alpha"
8
+ gem.authors = ["Marcos Hack"]
9
+ gem.email = ["marcos.hack@gmail.com"]
10
+ gem.description = %q{JMeter Reports}
11
+ gem.summary = %q{Basic tools for JMeter reports processing.}
12
+ gem.homepage = "https://github.com/marcoshack/jmeter-reports"
13
+
14
+ gem.files = `git ls-files`.split($/)
15
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
16
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
17
+ gem.require_paths = ["lib"]
18
+
19
+ gem.add_development_dependency "rake"
20
+ gem.add_development_dependency "minitest", "~> 3"
21
+ end
@@ -0,0 +1,3 @@
1
+ require 'jmeter/summary_report/report'
2
+ require 'jmeter/summary_report/report_item'
3
+ require 'jmeter/summary_report/result_line'
@@ -0,0 +1,52 @@
1
+ module Jmeter
2
+ module SummaryReport
3
+ class Report
4
+ CSV_HEADER = "timeStamp,elapsed,label,responseCode,responseMessage,threadName,"+
5
+ "dataType,success,bytes,grpThreads,allThreads,URL,Latency\n"
6
+
7
+ def initialize
8
+ @items = {}
9
+ @req_count = 0
10
+ end
11
+
12
+ def self.create(summary_report_file_path)
13
+ report = Report.new
14
+ csv_report = File.open(summary_report_file_path,'r')
15
+
16
+ unless csv_report.readline == CSV_HEADER
17
+ raise Exception.new("Invalid CSV report: #{summary_report_file_path}")
18
+ end
19
+
20
+ csv_report.each_line do |line|
21
+ next if line.start_with?("timeStamp,") # ignore header
22
+ report.add(ResultLine.parse(line))
23
+ end
24
+ return report
25
+ end
26
+
27
+ def add(line)
28
+ @items[line.label] = ReportItem.new(line.label) if @items[line.label].nil?
29
+ @items[line.label].add(line)
30
+ @req_count += 1
31
+ @start = line.timestamp if @start.nil? || line.timestamp < @start
32
+ @end = line.timestamp if @end.nil? || line.timestamp > @end
33
+ end
34
+
35
+ def elapsed_in_ms
36
+ @end - @start
37
+ end
38
+
39
+ def elapsed
40
+ (self.elapsed_in_ms / 1000.0).ceil
41
+ end
42
+
43
+ def avg_throughput
44
+ @req_count / self.elapsed
45
+ end
46
+
47
+ def items
48
+ @items.values
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,42 @@
1
+ module Jmeter
2
+ module SummaryReport
3
+ class ReportItem
4
+ def initialize(label)
5
+ @label = label
6
+ @items = []
7
+ @error_count = 0
8
+ end
9
+
10
+ def add(item)
11
+ @error_count += 1 if item.error?
12
+ @items << item.elapsed
13
+ end
14
+
15
+ def size
16
+ @items.size
17
+ end
18
+
19
+ def errors
20
+ @error_count
21
+ end
22
+
23
+ def error_rate
24
+ @error_count / self.size.to_f
25
+ end
26
+
27
+ def text_summary
28
+ sorted_items = @items.sort
29
+ p90 = sorted_items[(self.size * 0.90).round]
30
+ p95 = sorted_items[(self.size * 0.95).round]
31
+ err_rate = round(self.error_rate, 3) * 100
32
+ "#{@label}: #{self.size}/#{self.errors} reqs/err(#{round(self.error_rate, 3)}%), " +
33
+ "90% <= #{p90}ms, 95% <= #{p95}ms"
34
+ end
35
+
36
+ private
37
+ def round(float_number, dec)
38
+ (float_number * 10**dec).to_i / (10**dec).to_f
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,32 @@
1
+ # Representation of a summary report result line.
2
+ #
3
+ # Header:
4
+ # timeStamp,elapsed,label,responseCode,responseMessage,threadName,dataType,
5
+ # success,bytes,grpThreads,allThreads,URL,Latency
6
+ #
7
+ # Line example:
8
+ # 1355164382383,97,Tela de Login,200,"Number of samples in transaction : 1,
9
+ # number of failing samples : 0",Thread Group 1-1,,true,5168,1,1,null,0
10
+ #
11
+ module Jmeter
12
+ module SummaryReport
13
+ class ResultLine
14
+ attr_accessor :timestamp, :elapsed, :label, :error, :latency
15
+
16
+ def self.parse(line)
17
+ t,e,l,rc,rm,_,_,s,_,_,_,_,lt = line.split(",")
18
+ res = Jmeter::SummaryReport::ResultLine.new
19
+ res.timestamp = t.to_i
20
+ res.elapsed = e.to_i
21
+ res.label = l
22
+ res.error = (s == "false" ? true : false)
23
+ res.latency = lt.to_i
24
+ return res
25
+ end
26
+
27
+ def error?
28
+ self.error
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,10 @@
1
+ timeStamp,elapsed,label,responseCode,responseMessage,threadName,dataType,success,bytes,grpThreads,allThreads,URL,Latency
2
+ 1355230052183,75,GET retrieve_gui,200,OK,Thread Group 1-1,text,true,5168,1,1,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2820887356_2820887356&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=3887356&provedores=facebook%2Ctwitter%2Cgoogle,74
3
+ 1355230052256,72,GET retrieve_gui,200,OK,Thread Group 1-3,text,true,5168,3,3,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2464809911_2464809911&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=8771784&provedores=facebook%2Ctwitter%2Cgoogle,70
4
+ 1355230052460,65,GET retrieve_gui,200,OK,Thread Group 1-5,text,true,5168,5,5,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2880723472_2880723472&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=9723472&provedores=facebook%2Ctwitter%2Cgoogle,64
5
+ 1355230053060,71,GET retrieve_gui,200,OK,Thread Group 1-6,text,true,5168,6,6,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2808390679_2808390679&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=9390679&provedores=facebook%2Ctwitter%2Cgoogle,69
6
+ 1355230053262,66,GET retrieve_gui,200,OK,Thread Group 1-7,text,true,5168,7,7,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2692773635_2692773635&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=1773635&provedores=facebook%2Ctwitter%2Cgoogle,65
7
+ 1355230053660,73,GET retrieve_gui,200,OK,Thread Group 1-8,text,true,5168,8,8,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery2625634952_2625634952&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=6634952&provedores=facebook%2Ctwitter%2Cgoogle,71
8
+ 1355230054465,68,GET retrieve_gui,200,OK,Thread Group 1-9,text,true,5168,9,9,http://stage.id.abril.com.br/widgets/login/retrieve_gui?callback=AbrilIdJQuery1205134350_1205134350&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=8134350&provedores=facebook%2Ctwitter%2Cgoogle,67
9
+ 1355230054867,434,POST execute,200,OK,Thread Group 1-5,text,true,1468,10,10,http://stage.id.abril.com.br/widgets/login/execute,434
10
+ 1355230054902,27,GET retrieve_success_gui,200,OK,Thread Group 1-5,text,true,2084,10,10,http://stage.id.abril.com.br/widgets/login/retrieve_success_gui?callback=AbrilIdJQuery2880723472_2880723472&application_login=PLAYBOY&current_instance_id=aiwwidgets&current_box_id=abril-id-load_test-login&confirmation_url=http://example.com/&_=9723472,27
@@ -0,0 +1,2 @@
1
+ require 'minitest/autorun'
2
+ require 'minitest/colorize'
@@ -0,0 +1,25 @@
1
+ require File.expand_path('helper', File.dirname(__FILE__))
2
+ require 'jmeter/reports'
3
+
4
+ class TestSummaryReport < MiniTest::Unit::TestCase
5
+ def setup
6
+ fixture = File.expand_path('fixtures/summary_report.csv', File.dirname(__FILE__))
7
+ @report = Jmeter::SummaryReport::Report.create(fixture)
8
+ end
9
+
10
+ def test_report_items
11
+ assert_equal 3, @report.items.size
12
+ end
13
+
14
+ def test_avg_throughput
15
+ assert_equal 3, @report.avg_throughput
16
+ end
17
+
18
+ def test_elapsed_in_ms
19
+ assert_equal 2719, @report.elapsed_in_ms
20
+ end
21
+
22
+ def test_elapsed
23
+ assert_equal 3, @report.elapsed
24
+ end
25
+ end
metadata ADDED
@@ -0,0 +1,98 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: jmeter-reports
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1alpha
5
+ prerelease: 5
6
+ platform: ruby
7
+ authors:
8
+ - Marcos Hack
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-12-11 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rake
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :development
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: minitest
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ~>
36
+ - !ruby/object:Gem::Version
37
+ version: '3'
38
+ type: :development
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: '3'
46
+ description: JMeter Reports
47
+ email:
48
+ - marcos.hack@gmail.com
49
+ executables:
50
+ - jmeter-reports
51
+ extensions: []
52
+ extra_rdoc_files: []
53
+ files:
54
+ - .gitignore
55
+ - .travis.yml
56
+ - Gemfile
57
+ - Gemfile.lock
58
+ - LICENSE
59
+ - README.rdoc
60
+ - Rakefile
61
+ - bin/jmeter-reports
62
+ - jmeter-reports.gemspec
63
+ - lib/jmeter/reports.rb
64
+ - lib/jmeter/summary_report/report.rb
65
+ - lib/jmeter/summary_report/report_item.rb
66
+ - lib/jmeter/summary_report/result_line.rb
67
+ - test/fixtures/summary_report.csv
68
+ - test/helper.rb
69
+ - test/test_summary_report.rb
70
+ homepage: https://github.com/marcoshack/jmeter-reports
71
+ licenses: []
72
+ post_install_message:
73
+ rdoc_options: []
74
+ require_paths:
75
+ - lib
76
+ required_ruby_version: !ruby/object:Gem::Requirement
77
+ none: false
78
+ requirements:
79
+ - - ! '>='
80
+ - !ruby/object:Gem::Version
81
+ version: '0'
82
+ required_rubygems_version: !ruby/object:Gem::Requirement
83
+ none: false
84
+ requirements:
85
+ - - ! '>'
86
+ - !ruby/object:Gem::Version
87
+ version: 1.3.1
88
+ requirements: []
89
+ rubyforge_project:
90
+ rubygems_version: 1.8.23
91
+ signing_key:
92
+ specification_version: 3
93
+ summary: Basic tools for JMeter reports processing.
94
+ test_files:
95
+ - test/fixtures/summary_report.csv
96
+ - test/helper.rb
97
+ - test/test_summary_report.rb
98
+ has_rdoc: