diff --git a/coverage/index.html b/coverage/index.html index c3569aa..c0f3e57 100644 --- a/coverage/index.html +++ b/coverage/index.html @@ -148,7 +148,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:34 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:49 -0500 2008 with rcov 0.8.1.2


@@ -159,9 +159,9 @@ - -
Name
TOTAL2947 + 2962 2564 + 2575 @@ -186,11 +186,11 @@ - - -
98.9%  
lib/flog.rb 516 + 519 425 + 427
95.7% +
95.8%   - -
@@ -267,9 +267,9 @@
spec/flog_spec.rb 1103 + 1115 906 + 915 diff --git a/coverage/lib-flog_rb.html b/coverage/lib-flog_rb.html index 4e60ae1..f422ff1 100644 --- a/coverage/lib-flog_rb.html +++ b/coverage/lib-flog_rb.html @@ -553,7 +553,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:34 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:49 -0500 2008 with rcov 0.8.1.2


Code reported as executed by Ruby looks like this...
@@ -571,11 +571,11 @@
     
   
- - -
100.0%  
lib/flog.rb 516 + 519 425 + 427 - -
95.7% +
95.8%  
@@ -711,409 +711,412 @@ 111 process Sexp.from_array(sexp).first 112 end 113 -114 def add_to_score(name) -115 @calls["#{class_name}##{method_name}"][name] += SCORES[name] * @multiplier -116 end -117 -118 def average -119 return 0 if calls.size == 0 -120 total / calls.size -121 end -122 -123 def penalize_by(bonus) -124 @multiplier += bonus -125 yield -126 @multiplier -= bonus -127 end -128 -129 def analyze_list(exp) -130 process exp.shift until exp.empty? -131 end -132 -133 def set_class(name) -134 @class_stack.unshift name -135 yield -136 @class_stack.shift -137 end -138 -139 def class_name -140 @class_stack.first || @@no_class -141 end -142 -143 def set_method(name) -144 @method_stack.unshift name -145 yield -146 @method_stack.shift -147 end -148 -149 def method_name -150 @method_stack.first || @@no_method -151 end -152 -153 def reset -154 @totals = @total_score = nil -155 @multiplier = 1.0 -156 @calls = Hash.new { |h,k| h[k] = Hash.new 0 } -157 end -158 -159 def total -160 totals unless @total_score # calculates total_score as well +114 def collect_blame(filename) +115 end +116 +117 def add_to_score(name) +118 @calls["#{class_name}##{method_name}"][name] += SCORES[name] * @multiplier +119 end +120 +121 def average +122 return 0 if calls.size == 0 +123 total / calls.size +124 end +125 +126 def penalize_by(bonus) +127 @multiplier += bonus +128 yield +129 @multiplier -= bonus +130 end +131 +132 def analyze_list(exp) +133 process exp.shift until exp.empty? +134 end +135 +136 def set_class(name) +137 @class_stack.unshift name +138 yield +139 @class_stack.shift +140 end +141 +142 def class_name +143 @class_stack.first || @@no_class +144 end +145 +146 def set_method(name) +147 @method_stack.unshift name +148 yield +149 @method_stack.shift +150 end +151 +152 def method_name +153 @method_stack.first || @@no_method +154 end +155 +156 def reset +157 @totals = @total_score = nil +158 @multiplier = 1.0 +159 @calls = Hash.new { |h,k| h[k] = Hash.new 0 } +160 end 161 -162 @total_score -163 end +162 def total +163 totals unless @total_score # calculates total_score as well 164 -165 def score_method(tally) -166 a, b, c = 0, 0, 0 -167 tally.each do |cat, score| -168 case cat -169 when :assignment then a += score -170 when :branch then b += score -171 else c += score -172 end -173 end -174 Math.sqrt(a*a + b*b + c*c) -175 end -176 -177 def record_method_score(method, score) -178 @totals ||= Hash.new(0) -179 @totals[method] = score -180 end -181 -182 def increment_total_score_by(amount) -183 @total_score ||= 0 -184 @total_score += amount -185 end -186 -187 def summarize_method(meth, tally) -188 return if options[:methods] and meth =~ /##{@@no_method}$/ -189 score = score_method(tally) -190 record_method_score(meth, score) -191 increment_total_score_by score -192 end -193 -194 def totals -195 unless @totals then -196 @total_score = 0 -197 @totals = Hash.new(0) -198 calls.each {|meth, tally| summarize_method(meth, tally) } -199 end -200 @totals -201 end -202 -203 def output_summary(io) -204 io.puts "Total Flog = %.1f (%.1f flog / method)\n" % [total, average] -205 end -206 -207 def output_method_details(io, class_method, call_list) -208 return 0 if options[:methods] and class_method =~ /##{@@no_method}/ -209 -210 total = totals[class_method] -211 io.puts "%s: (%.1f)" % [class_method, total] -212 -213 call_list.sort_by { |k,v| -v }.each do |call, count| -214 io.puts " %6.1f: %s" % [count, call] -215 end -216 -217 total -218 end +165 @total_score +166 end +167 +168 def score_method(tally) +169 a, b, c = 0, 0, 0 +170 tally.each do |cat, score| +171 case cat +172 when :assignment then a += score +173 when :branch then b += score +174 else c += score +175 end +176 end +177 Math.sqrt(a*a + b*b + c*c) +178 end +179 +180 def record_method_score(method, score) +181 @totals ||= Hash.new(0) +182 @totals[method] = score +183 end +184 +185 def increment_total_score_by(amount) +186 @total_score ||= 0 +187 @total_score += amount +188 end +189 +190 def summarize_method(meth, tally) +191 return if options[:methods] and meth =~ /##{@@no_method}$/ +192 score = score_method(tally) +193 record_method_score(meth, score) +194 increment_total_score_by score +195 end +196 +197 def totals +198 unless @totals then +199 @total_score = 0 +200 @totals = Hash.new(0) +201 calls.each {|meth, tally| summarize_method(meth, tally) } +202 end +203 @totals +204 end +205 +206 def output_summary(io) +207 io.puts "Total Flog = %.1f (%.1f flog / method)\n" % [total, average] +208 end +209 +210 def output_method_details(io, class_method, call_list) +211 return 0 if options[:methods] and class_method =~ /##{@@no_method}/ +212 +213 total = totals[class_method] +214 io.puts "%s: (%.1f)" % [class_method, total] +215 +216 call_list.sort_by { |k,v| -v }.each do |call, count| +217 io.puts " %6.1f: %s" % [count, call] +218 end 219 -220 def output_details(io, max = nil) -221 my_totals = totals -222 current = 0 -223 calls.sort_by { |k,v| -my_totals[k] }.each do |class_method, call_list| -224 current += output_method_details(io, class_method, call_list) -225 break if max and current >= max -226 end -227 end -228 -229 def report(io = $stdout) -230 output_summary(io) -231 return if options[:score] -232 -233 if options[:all] -234 output_details(io) -235 else -236 output_details(io, total * THRESHOLD) -237 end -238 ensure -239 reset -240 end -241 -242 ############################################################ -243 # Process Methods: +220 total +221 end +222 +223 def output_details(io, max = nil) +224 my_totals = totals +225 current = 0 +226 calls.sort_by { |k,v| -my_totals[k] }.each do |class_method, call_list| +227 current += output_method_details(io, class_method, call_list) +228 break if max and current >= max +229 end +230 end +231 +232 def report(io = $stdout) +233 output_summary(io) +234 return if options[:score] +235 +236 if options[:all] +237 output_details(io) +238 else +239 output_details(io, total * THRESHOLD) +240 end +241 ensure +242 reset +243 end 244 -245 def process_alias(exp) -246 process exp.shift -247 process exp.shift -248 add_to_score :alias -249 s() -250 end -251 -252 def process_and(exp) -253 add_to_score :branch -254 penalize_by 0.1 do -255 process exp.shift # lhs -256 process exp.shift # rhs -257 end -258 s() -259 end -260 -261 def process_attrasgn(exp) -262 add_to_score :assignment -263 process exp.shift # lhs -264 exp.shift # name -265 process exp.shift # rhs -266 s() -267 end -268 -269 def process_attrset(exp) -270 add_to_score :assignment -271 raise exp.inspect -272 s() -273 end -274 -275 def process_block(exp) -276 penalize_by 0.1 do -277 analyze_list exp -278 end -279 s() -280 end -281 -282 # [:block_pass, [:lit, :blah], [:fcall, :foo]] -283 def process_block_pass(exp) -284 arg = exp.shift -285 call = exp.shift -286 -287 add_to_score :block_pass -288 -289 case arg.first -290 when :lvar, :dvar, :ivar, :cvar, :self, :const, :nil then -291 # do nothing -292 when :lit, :call then -293 add_to_score :to_proc_normal -294 when :iter, :and, :case, :else, :if, :or, :rescue, :until, :when, :while then -295 add_to_score :to_proc_icky! -296 else -297 raise({:block_pass => [arg, call]}.inspect) -298 end -299 -300 process arg -301 process call +245 ############################################################ +246 # Process Methods: +247 +248 def process_alias(exp) +249 process exp.shift +250 process exp.shift +251 add_to_score :alias +252 s() +253 end +254 +255 def process_and(exp) +256 add_to_score :branch +257 penalize_by 0.1 do +258 process exp.shift # lhs +259 process exp.shift # rhs +260 end +261 s() +262 end +263 +264 def process_attrasgn(exp) +265 add_to_score :assignment +266 process exp.shift # lhs +267 exp.shift # name +268 process exp.shift # rhs +269 s() +270 end +271 +272 def process_attrset(exp) +273 add_to_score :assignment +274 raise exp.inspect +275 s() +276 end +277 +278 def process_block(exp) +279 penalize_by 0.1 do +280 analyze_list exp +281 end +282 s() +283 end +284 +285 # [:block_pass, [:lit, :blah], [:fcall, :foo]] +286 def process_block_pass(exp) +287 arg = exp.shift +288 call = exp.shift +289 +290 add_to_score :block_pass +291 +292 case arg.first +293 when :lvar, :dvar, :ivar, :cvar, :self, :const, :nil then +294 # do nothing +295 when :lit, :call then +296 add_to_score :to_proc_normal +297 when :iter, :and, :case, :else, :if, :or, :rescue, :until, :when, :while then +298 add_to_score :to_proc_icky! +299 else +300 raise({:block_pass => [arg, call]}.inspect) +301 end 302 -303 s() -304 end +303 process arg +304 process call 305 -306 def process_call(exp) -307 penalize_by 0.2 do -308 recv = process exp.shift -309 end -310 name = exp.shift -311 penalize_by 0.2 do -312 args = process exp.shift -313 end -314 -315 add_to_score name -316 -317 s() -318 end +306 s() +307 end +308 +309 def process_call(exp) +310 penalize_by 0.2 do +311 recv = process exp.shift +312 end +313 name = exp.shift +314 penalize_by 0.2 do +315 args = process exp.shift +316 end +317 +318 add_to_score name 319 -320 def process_case(exp) -321 add_to_score :branch -322 process exp.shift # recv -323 penalize_by 0.1 do -324 analyze_list exp -325 end -326 s() -327 end -328 -329 def process_class(exp) -330 set_class exp.shift do -331 penalize_by 1.0 do -332 supr = process exp.shift -333 end -334 analyze_list exp -335 end -336 s() -337 end -338 -339 def process_dasgn_curr(exp) -340 add_to_score :assignment -341 exp.shift # name -342 process exp.shift # assigment, if any -343 s() -344 end -345 -346 def process_defn(exp) -347 set_method exp.shift do -348 analyze_list exp -349 end -350 s() -351 end -352 -353 def process_defs(exp) -354 process exp.shift -355 set_method exp.shift do -356 analyze_list exp -357 end -358 s() -359 end -360 -361 # TODO: it's not clear to me whether this can be generated at all. -362 def process_else(exp) -363 add_to_score :branch -364 penalize_by 0.1 do -365 analyze_list exp -366 end -367 s() -368 end -369 -370 def process_iasgn(exp) -371 add_to_score :assignment -372 exp.shift # name -373 process exp.shift # rhs -374 s() -375 end -376 -377 def process_if(exp) -378 add_to_score :branch -379 process exp.shift # cond -380 penalize_by 0.1 do -381 process exp.shift # true -382 process exp.shift # false -383 end -384 s() -385 end -386 -387 def process_iter(exp) -388 context = (self.context - [:class, :module, :scope]) -389 if context.uniq.sort_by {|s|s.to_s} == [:block, :iter] then -390 recv = exp.first -391 if recv[0] == :call and recv[1] == nil and recv.arglist[1] and [:lit, :str].include? recv.arglist[1][0] then -392 msg = recv[2] -393 submsg = recv.arglist[1][1] -394 set_method submsg do -395 set_class msg do -396 analyze_list exp -397 end -398 end -399 return s() -400 end -401 end -402 -403 add_to_score :branch -404 -405 process exp.shift # no penalty for LHS -406 -407 penalize_by 0.1 do -408 analyze_list exp -409 end -410 -411 s() -412 end +320 s() +321 end +322 +323 def process_case(exp) +324 add_to_score :branch +325 process exp.shift # recv +326 penalize_by 0.1 do +327 analyze_list exp +328 end +329 s() +330 end +331 +332 def process_class(exp) +333 set_class exp.shift do +334 penalize_by 1.0 do +335 supr = process exp.shift +336 end +337 analyze_list exp +338 end +339 s() +340 end +341 +342 def process_dasgn_curr(exp) +343 add_to_score :assignment +344 exp.shift # name +345 process exp.shift # assigment, if any +346 s() +347 end +348 +349 def process_defn(exp) +350 set_method exp.shift do +351 analyze_list exp +352 end +353 s() +354 end +355 +356 def process_defs(exp) +357 process exp.shift +358 set_method exp.shift do +359 analyze_list exp +360 end +361 s() +362 end +363 +364 # TODO: it's not clear to me whether this can be generated at all. +365 def process_else(exp) +366 add_to_score :branch +367 penalize_by 0.1 do +368 analyze_list exp +369 end +370 s() +371 end +372 +373 def process_iasgn(exp) +374 add_to_score :assignment +375 exp.shift # name +376 process exp.shift # rhs +377 s() +378 end +379 +380 def process_if(exp) +381 add_to_score :branch +382 process exp.shift # cond +383 penalize_by 0.1 do +384 process exp.shift # true +385 process exp.shift # false +386 end +387 s() +388 end +389 +390 def process_iter(exp) +391 context = (self.context - [:class, :module, :scope]) +392 if context.uniq.sort_by {|s|s.to_s} == [:block, :iter] then +393 recv = exp.first +394 if recv[0] == :call and recv[1] == nil and recv.arglist[1] and [:lit, :str].include? recv.arglist[1][0] then +395 msg = recv[2] +396 submsg = recv.arglist[1][1] +397 set_method submsg do +398 set_class msg do +399 analyze_list exp +400 end +401 end +402 return s() +403 end +404 end +405 +406 add_to_score :branch +407 +408 process exp.shift # no penalty for LHS +409 +410 penalize_by 0.1 do +411 analyze_list exp +412 end 413 -414 def process_lasgn(exp) -415 add_to_score :assignment -416 exp.shift # name -417 process exp.shift # rhs -418 s() -419 end -420 -421 def process_lit(exp) -422 value = exp.shift -423 case value -424 when 0, -1 then -425 # ignore those because they're used as array indicies instead of first/last -426 when Integer then -427 add_to_score :lit_fixnum -428 when Float, Symbol, Regexp, Range then -429 # do nothing -430 else -431 raise value.inspect -432 end -433 s() -434 end -435 -436 def process_masgn(exp) -437 add_to_score :assignment -438 process exp.shift # lhs -439 process exp.shift # rhs -440 s() -441 end -442 -443 def process_module(exp) -444 set_class exp.shift do -445 analyze_list exp -446 end -447 s() -448 end -449 -450 def process_or(exp) -451 add_to_score :branch -452 penalize_by 0.1 do -453 process exp.shift # lhs -454 process exp.shift # rhs -455 end -456 s() -457 end -458 -459 def process_rescue(exp) -460 add_to_score :branch -461 penalize_by 0.1 do -462 analyze_list exp -463 end -464 s() -465 end -466 -467 def process_sclass(exp) -468 penalize_by 0.5 do -469 recv = process exp.shift -470 analyze_list exp -471 end -472 -473 add_to_score :sclass -474 s() -475 end -476 -477 def process_super(exp) -478 add_to_score :super -479 analyze_list exp -480 s() -481 end -482 -483 def process_until(exp) -484 add_to_score :branch -485 penalize_by 0.1 do -486 process exp.shift # cond -487 process exp.shift # body -488 end -489 exp.shift # pre/post -490 s() -491 end -492 -493 def process_when(exp) -494 add_to_score :branch -495 penalize_by 0.1 do -496 analyze_list exp -497 end -498 s() -499 end -500 -501 def process_while(exp) -502 add_to_score :branch -503 penalize_by 0.1 do -504 process exp.shift # cond -505 process exp.shift # body -506 end -507 exp.shift # pre/post -508 s() -509 end -510 -511 def process_yield(exp) -512 add_to_score :yield -513 analyze_list exp -514 s() -515 end -516 end +414 s() +415 end +416 +417 def process_lasgn(exp) +418 add_to_score :assignment +419 exp.shift # name +420 process exp.shift # rhs +421 s() +422 end +423 +424 def process_lit(exp) +425 value = exp.shift +426 case value +427 when 0, -1 then +428 # ignore those because they're used as array indicies instead of first/last +429 when Integer then +430 add_to_score :lit_fixnum +431 when Float, Symbol, Regexp, Range then +432 # do nothing +433 else +434 raise value.inspect +435 end +436 s() +437 end +438 +439 def process_masgn(exp) +440 add_to_score :assignment +441 process exp.shift # lhs +442 process exp.shift # rhs +443 s() +444 end +445 +446 def process_module(exp) +447 set_class exp.shift do +448 analyze_list exp +449 end +450 s() +451 end +452 +453 def process_or(exp) +454 add_to_score :branch +455 penalize_by 0.1 do +456 process exp.shift # lhs +457 process exp.shift # rhs +458 end +459 s() +460 end +461 +462 def process_rescue(exp) +463 add_to_score :branch +464 penalize_by 0.1 do +465 analyze_list exp +466 end +467 s() +468 end +469 +470 def process_sclass(exp) +471 penalize_by 0.5 do +472 recv = process exp.shift +473 analyze_list exp +474 end +475 +476 add_to_score :sclass +477 s() +478 end +479 +480 def process_super(exp) +481 add_to_score :super +482 analyze_list exp +483 s() +484 end +485 +486 def process_until(exp) +487 add_to_score :branch +488 penalize_by 0.1 do +489 process exp.shift # cond +490 process exp.shift # body +491 end +492 exp.shift # pre/post +493 s() +494 end +495 +496 def process_when(exp) +497 add_to_score :branch +498 penalize_by 0.1 do +499 analyze_list exp +500 end +501 s() +502 end +503 +504 def process_while(exp) +505 add_to_score :branch +506 penalize_by 0.1 do +507 process exp.shift # cond +508 process exp.shift # body +509 end +510 exp.shift # pre/post +511 s() +512 end +513 +514 def process_yield(exp) +515 add_to_score :yield +516 analyze_list exp +517 s() +518 end +519 end

Generated using the rcov code coverage analysis tool for Ruby version 0.8.1.2.

diff --git a/coverage/spec-flog_command_spec_rb.html b/coverage/spec-flog_command_spec_rb.html index dec4835..dd85edd 100644 --- a/coverage/spec-flog_command_spec_rb.html +++ b/coverage/spec-flog_command_spec_rb.html @@ -553,7 +553,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:34 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:49 -0500 2008 with rcov 0.8.1.2


Code reported as executed by Ruby looks like this...
@@ -598,358 +598,358 @@
       
-
  1 require File.dirname(__FILE__) + '/spec_helper.rb'
-  2 require 'flog'
-  3 
-  4 describe 'flog command' do
-  5   before :each do
-  6     @flog = stub('Flog', :flog_files => true, :report => true)
-  7     Flog.stubs(:new).returns(@flog)
-  8     self.stubs(:exit)
-  9     self.stubs(:puts)
- 10   end
- 11 
- 12   def run_command
- 13     eval File.read(File.join(File.dirname(__FILE__), *%w[.. bin flog]))
- 14   end
- 15   
- 16   describe 'when no command-line arguments are specified' do
- 17     before :each do
- 18       Object.send(:remove_const, :ARGV)
- 19       ARGV = []
- 20     end  
- 21   
- 22     it 'should run' do
- 23       lambda { run_command }.should_not raise_error(Errno::ENOENT)
- 24     end
- 25     
- 26     it 'should not alter the include path' do
- 27       @paths = $:.dup
- 28       run_command
- 29       $:.should == @paths
- 30     end
- 31 
- 32     it 'should create a Flog instance' do
- 33       Flog.expects(:new).returns(@flog)
- 34       run_command
- 35     end
- 36     
- 37     it 'should not have any options flags set' do
- 38       Flog.expects(:new).with({}).returns(@flog)
- 39       run_command
- 40     end
- 41     
- 42     it 'should call flog_files on the Flog instance' do
- 43       @flog.expects(:flog_files)
- 44       run_command
- 45     end
- 46     
- 47     it "should pass '-' (for the file path) to flog_files on the instance" do
- 48       @flog.expects(:flog_files).with(['-'])
- 49       run_command
- 50     end
- 51 
- 52     it 'should call report on the Flog instance' do
- 53       @flog.expects(:report)
- 54       run_command
- 55     end
- 56     
- 57     it 'should exit with status 0' do
- 58       self.expects(:exit).with(0)
- 59       run_command
- 60     end
- 61   end
- 62   
- 63   describe "when -a is specified on the command-line" do
- 64     before :each do
- 65       Object.send(:remove_const, :ARGV)
- 66       ARGV = ['-a']
- 67     end
- 68     
- 69     it 'should create a Flog instance' do
- 70       Flog.expects(:new).returns(@flog)
- 71       run_command
- 72     end
- 73     
- 74     it "should set the option to show all methods" do
- 75       Flog.expects(:new).with(:all => true).returns(@flog)      
- 76       run_command
- 77     end
- 78     
- 79     it 'should exit with status 0' do
- 80       self.expects(:exit).with(0)
- 81       run_command
- 82     end
- 83   end
- 84   
- 85   describe "when --all is specified on the command-line" do
- 86     before :each do
- 87       Object.send(:remove_const, :ARGV)
- 88       ARGV = ['--all']
- 89     end
- 90     
- 91     it 'should create a Flog instance' do
- 92       Flog.expects(:new).returns(@flog)
- 93       run_command
- 94     end
- 95     
- 96     it "should set the option to show all methods" do
- 97       Flog.expects(:new).with(:all => true).returns(@flog)      
- 98       run_command
- 99     end
-100     
-101     it 'should exit with status 0' do
-102       self.expects(:exit).with(0)
-103       run_command
-104     end
-105   end
-106   
-107   describe "when -s is specified on the command-line" do
-108     before :each do
-109       Object.send(:remove_const, :ARGV)
-110       ARGV = ['-s']
-111     end
-112     
-113     it 'should create a Flog instance' do
-114       Flog.expects(:new).returns(@flog)
-115       run_command
-116     end
-117 
-118     it "should set the option to show only the score" do
-119       Flog.expects(:new).with(:score => true).returns(@flog)      
-120       run_command
-121     end
-122         
-123     it 'should exit with status 0' do
-124       self.expects(:exit).with(0)
-125       run_command
-126     end
-127   end
-128   
-129   describe "when --score is specified on the command-line" do
-130     before :each do
-131       Object.send(:remove_const, :ARGV)
-132       ARGV = ['--score']
-133     end
-134     
-135     it 'should create a Flog instance' do
-136       Flog.expects(:new).returns(@flog)
-137       run_command
-138     end
-139     
-140     it "should set the option to show only the score" do
-141       Flog.expects(:new).with(:score => true).returns(@flog)      
-142       run_command
-143     end
-144     
-145     it 'should exit with status 0' do
-146       self.expects(:exit).with(0)
-147       run_command
-148     end
-149   end
-150   
-151   describe "when -m is specified on the command-line" do
-152     before :each do
-153       Object.send(:remove_const, :ARGV)
-154       ARGV = ['-m']
-155     end
-156     
-157     it 'should create a Flog instance' do
-158       Flog.expects(:new).returns(@flog)
-159       run_command
-160     end
-161     
-162     it "should set the option to report on methods only" do
-163       Flog.expects(:new).with(:methods => true).returns(@flog)      
-164       run_command
-165     end
-166     
-167     it 'should exit with status 0' do
-168       self.expects(:exit).with(0)
-169       run_command
-170     end
-171   end
-172 
-173   describe "when --methods-only is specified on the command-line" do
-174     before :each do
-175       Object.send(:remove_const, :ARGV)
-176       ARGV = ['--methods-only']
-177     end
-178     
-179     it 'should create a Flog instance' do
-180       Flog.expects(:new).returns(@flog)
-181       run_command
-182     end
-183 
-184     it "should set the option to report on methods only" do
-185       Flog.expects(:new).with(:methods => true).returns(@flog)      
-186       run_command
-187     end
-188         
-189     it 'should exit with status 0' do
-190       self.expects(:exit).with(0)
-191       run_command
-192     end
-193   end
-194 
-195   describe "when -v is specified on the command-line" do
-196     before :each do
-197       Object.send(:remove_const, :ARGV)
-198       ARGV = ['-v']
-199     end
-200     
-201     it 'should create a Flog instance' do
-202       Flog.expects(:new).returns(@flog)
-203       run_command
-204     end
-205     
-206     it "should set the option to be verbose" do
-207       Flog.expects(:new).with(:verbose => true).returns(@flog)      
-208       run_command
-209     end
-210     
-211     it 'should exit with status 0' do
-212       self.expects(:exit).with(0)
-213       run_command
-214     end
-215   end
-216 
-217   describe "when --verbose is specified on the command-line" do
-218     before :each do
-219       Object.send(:remove_const, :ARGV)
-220       ARGV = ['--verbose']
-221     end
-222     
-223     it 'should create a Flog instance' do
-224       Flog.expects(:new).returns(@flog)
-225       run_command
-226     end
-227     
-228     it "should set the option to be verbose" do
-229       Flog.expects(:new).with(:verbose => true).returns(@flog)      
-230       run_command
-231     end
-232     
-233     it 'should exit with status 0' do
-234       self.expects(:exit).with(0)
-235       run_command
-236     end
-237   end
-238 
-239   describe "when -h is specified on the command-line" do
-240     before :each do
-241       Object.send(:remove_const, :ARGV)
-242       ARGV = ['-h']
-243     end
-244     
-245     it "should display help information" do
-246       self.expects(:puts)
-247       run_command
-248     end
-249     
-250     it 'should not create a Flog instance' do
-251       Flog.expects(:new).never
-252       run_command
-253     end
-254     
-255     it 'should exit with status 0' do
-256       self.expects(:exit).with(0)
-257       run_command
-258     end
-259   end
-260   
-261   describe "when --help is specified on the command-line" do
-262     before :each do
-263       Object.send(:remove_const, :ARGV)
-264       ARGV = ['--help']
-265     end
-266     
-267     it "should display help information" do
-268       self.expects(:puts)
-269       run_command
-270     end
-271     
-272     it 'should not create a Flog instance' do
-273       Flog.expects(:new).never
-274       run_command
-275     end
-276     
-277     it 'should exit with status 0' do
-278       self.expects(:exit).with(0)
-279       run_command
-280     end
-281   end
-282   
-283   describe 'when -I is specified on the command-line' do
-284     before :each do
-285       Object.send(:remove_const, :ARGV)
-286       ARGV = ['-I /tmp,/etc']
-287     end
-288     
-289     before :each do
-290       @paths = $:.dup
-291     end
-292  
-293     it "should append each ':' separated path to $:" do
-294       run_command
-295       $:.should_not == @paths
-296     end
-297     
-298     it 'should create a Flog instance' do
-299       Flog.expects(:new).returns(@flog)
-300       run_command
-301     end
-302     
-303     it 'should exit with status 0' do
-304       self.expects(:exit).with(0)
-305       run_command
-306     end
-307   end
-308   
-309   describe 'when -b is specified on the command-line' do
-310     before :each do
-311       Object.send(:remove_const, :ARGV)
-312       ARGV = ['-b']
-313     end
-314 
-315     it 'should create a Flog instance' do
-316       Flog.expects(:new).returns(@flog)
-317       run_command
-318     end
-319     
-320     it "should set the option to provide 'blame' information" do
-321       Flog.expects(:new).with(:blame => true).returns(@flog)      
-322       run_command
-323     end
-324     
-325     it 'should exit with status 0' do
-326       self.expects(:exit).with(0)
-327       run_command
-328     end
-329   end
-330   
-331   describe 'when --blame is specified on the command-line' do
-332     before :each do
-333       Object.send(:remove_const, :ARGV)
-334       ARGV = ['--blame']
-335     end
-336 
-337     it 'should create a Flog instance' do
-338       Flog.expects(:new).returns(@flog)
-339       run_command
-340     end
-341     
-342     it "should set the option to provide 'blame' information" do
-343       Flog.expects(:new).with(:blame => true).returns(@flog)      
-344       run_command
-345     end
-346     
-347     it 'should exit with status 0' do
-348       self.expects(:exit).with(0)
-349       run_command
-350     end
-351   end
-352 end
+
  1 require File.dirname(__FILE__) + '/spec_helper.rb'
+  2 require 'flog'
+  3 
+  4 describe 'flog command' do
+  5   before :each do
+  6     @flog = stub('Flog', :flog_files => true, :report => true)
+  7     Flog.stubs(:new).returns(@flog)
+  8     self.stubs(:exit)
+  9     self.stubs(:puts)
+ 10   end
+ 11 
+ 12   def run_command
+ 13     eval File.read(File.join(File.dirname(__FILE__), *%w[.. bin flog]))
+ 14   end
+ 15   
+ 16   describe 'when no command-line arguments are specified' do
+ 17     before :each do
+ 18       Object.send(:remove_const, :ARGV)
+ 19       ARGV = []
+ 20     end  
+ 21   
+ 22     it 'should run' do
+ 23       lambda { run_command }.should_not raise_error(Errno::ENOENT)
+ 24     end
+ 25     
+ 26     it 'should not alter the include path' do
+ 27       @paths = $:.dup
+ 28       run_command
+ 29       $:.should == @paths
+ 30     end
+ 31 
+ 32     it 'should create a Flog instance' do
+ 33       Flog.expects(:new).returns(@flog)
+ 34       run_command
+ 35     end
+ 36     
+ 37     it 'should not have any options flags set' do
+ 38       Flog.expects(:new).with({}).returns(@flog)
+ 39       run_command
+ 40     end
+ 41     
+ 42     it 'should call flog_files on the Flog instance' do
+ 43       @flog.expects(:flog_files)
+ 44       run_command
+ 45     end
+ 46     
+ 47     it "should pass '-' (for the file path) to flog_files on the instance" do
+ 48       @flog.expects(:flog_files).with(['-'])
+ 49       run_command
+ 50     end
+ 51 
+ 52     it 'should call report on the Flog instance' do
+ 53       @flog.expects(:report)
+ 54       run_command
+ 55     end
+ 56     
+ 57     it 'should exit with status 0' do
+ 58       self.expects(:exit).with(0)
+ 59       run_command
+ 60     end
+ 61   end
+ 62   
+ 63   describe "when -a is specified on the command-line" do
+ 64     before :each do
+ 65       Object.send(:remove_const, :ARGV)
+ 66       ARGV = ['-a']
+ 67     end
+ 68     
+ 69     it 'should create a Flog instance' do
+ 70       Flog.expects(:new).returns(@flog)
+ 71       run_command
+ 72     end
+ 73     
+ 74     it "should set the option to show all methods" do
+ 75       Flog.expects(:new).with(:all => true).returns(@flog)      
+ 76       run_command
+ 77     end
+ 78     
+ 79     it 'should exit with status 0' do
+ 80       self.expects(:exit).with(0)
+ 81       run_command
+ 82     end
+ 83   end
+ 84   
+ 85   describe "when --all is specified on the command-line" do
+ 86     before :each do
+ 87       Object.send(:remove_const, :ARGV)
+ 88       ARGV = ['--all']
+ 89     end
+ 90     
+ 91     it 'should create a Flog instance' do
+ 92       Flog.expects(:new).returns(@flog)
+ 93       run_command
+ 94     end
+ 95     
+ 96     it "should set the option to show all methods" do
+ 97       Flog.expects(:new).with(:all => true).returns(@flog)      
+ 98       run_command
+ 99     end
+100     
+101     it 'should exit with status 0' do
+102       self.expects(:exit).with(0)
+103       run_command
+104     end
+105   end
+106   
+107   describe "when -s is specified on the command-line" do
+108     before :each do
+109       Object.send(:remove_const, :ARGV)
+110       ARGV = ['-s']
+111     end
+112     
+113     it 'should create a Flog instance' do
+114       Flog.expects(:new).returns(@flog)
+115       run_command
+116     end
+117 
+118     it "should set the option to show only the score" do
+119       Flog.expects(:new).with(:score => true).returns(@flog)      
+120       run_command
+121     end
+122         
+123     it 'should exit with status 0' do
+124       self.expects(:exit).with(0)
+125       run_command
+126     end
+127   end
+128   
+129   describe "when --score is specified on the command-line" do
+130     before :each do
+131       Object.send(:remove_const, :ARGV)
+132       ARGV = ['--score']
+133     end
+134     
+135     it 'should create a Flog instance' do
+136       Flog.expects(:new).returns(@flog)
+137       run_command
+138     end
+139     
+140     it "should set the option to show only the score" do
+141       Flog.expects(:new).with(:score => true).returns(@flog)      
+142       run_command
+143     end
+144     
+145     it 'should exit with status 0' do
+146       self.expects(:exit).with(0)
+147       run_command
+148     end
+149   end
+150   
+151   describe "when -m is specified on the command-line" do
+152     before :each do
+153       Object.send(:remove_const, :ARGV)
+154       ARGV = ['-m']
+155     end
+156     
+157     it 'should create a Flog instance' do
+158       Flog.expects(:new).returns(@flog)
+159       run_command
+160     end
+161     
+162     it "should set the option to report on methods only" do
+163       Flog.expects(:new).with(:methods => true).returns(@flog)      
+164       run_command
+165     end
+166     
+167     it 'should exit with status 0' do
+168       self.expects(:exit).with(0)
+169       run_command
+170     end
+171   end
+172 
+173   describe "when --methods-only is specified on the command-line" do
+174     before :each do
+175       Object.send(:remove_const, :ARGV)
+176       ARGV = ['--methods-only']
+177     end
+178     
+179     it 'should create a Flog instance' do
+180       Flog.expects(:new).returns(@flog)
+181       run_command
+182     end
+183 
+184     it "should set the option to report on methods only" do
+185       Flog.expects(:new).with(:methods => true).returns(@flog)      
+186       run_command
+187     end
+188         
+189     it 'should exit with status 0' do
+190       self.expects(:exit).with(0)
+191       run_command
+192     end
+193   end
+194 
+195   describe "when -v is specified on the command-line" do
+196     before :each do
+197       Object.send(:remove_const, :ARGV)
+198       ARGV = ['-v']
+199     end
+200     
+201     it 'should create a Flog instance' do
+202       Flog.expects(:new).returns(@flog)
+203       run_command
+204     end
+205     
+206     it "should set the option to be verbose" do
+207       Flog.expects(:new).with(:verbose => true).returns(@flog)      
+208       run_command
+209     end
+210     
+211     it 'should exit with status 0' do
+212       self.expects(:exit).with(0)
+213       run_command
+214     end
+215   end
+216 
+217   describe "when --verbose is specified on the command-line" do
+218     before :each do
+219       Object.send(:remove_const, :ARGV)
+220       ARGV = ['--verbose']
+221     end
+222     
+223     it 'should create a Flog instance' do
+224       Flog.expects(:new).returns(@flog)
+225       run_command
+226     end
+227     
+228     it "should set the option to be verbose" do
+229       Flog.expects(:new).with(:verbose => true).returns(@flog)      
+230       run_command
+231     end
+232     
+233     it 'should exit with status 0' do
+234       self.expects(:exit).with(0)
+235       run_command
+236     end
+237   end
+238 
+239   describe "when -h is specified on the command-line" do
+240     before :each do
+241       Object.send(:remove_const, :ARGV)
+242       ARGV = ['-h']
+243     end
+244     
+245     it "should display help information" do
+246       self.expects(:puts)
+247       run_command
+248     end
+249     
+250     it 'should not create a Flog instance' do
+251       Flog.expects(:new).never
+252       run_command
+253     end
+254     
+255     it 'should exit with status 0' do
+256       self.expects(:exit).with(0)
+257       run_command
+258     end
+259   end
+260   
+261   describe "when --help is specified on the command-line" do
+262     before :each do
+263       Object.send(:remove_const, :ARGV)
+264       ARGV = ['--help']
+265     end
+266     
+267     it "should display help information" do
+268       self.expects(:puts)
+269       run_command
+270     end
+271     
+272     it 'should not create a Flog instance' do
+273       Flog.expects(:new).never
+274       run_command
+275     end
+276     
+277     it 'should exit with status 0' do
+278       self.expects(:exit).with(0)
+279       run_command
+280     end
+281   end
+282   
+283   describe 'when -I is specified on the command-line' do
+284     before :each do
+285       Object.send(:remove_const, :ARGV)
+286       ARGV = ['-I /tmp,/etc']
+287     end
+288     
+289     before :each do
+290       @paths = $:.dup
+291     end
+292  
+293     it "should append each ':' separated path to $:" do
+294       run_command
+295       $:.should_not == @paths
+296     end
+297     
+298     it 'should create a Flog instance' do
+299       Flog.expects(:new).returns(@flog)
+300       run_command
+301     end
+302     
+303     it 'should exit with status 0' do
+304       self.expects(:exit).with(0)
+305       run_command
+306     end
+307   end
+308   
+309   describe 'when -b is specified on the command-line' do
+310     before :each do
+311       Object.send(:remove_const, :ARGV)
+312       ARGV = ['-b']
+313     end
+314 
+315     it 'should create a Flog instance' do
+316       Flog.expects(:new).returns(@flog)
+317       run_command
+318     end
+319     
+320     it "should set the option to provide 'blame' information" do
+321       Flog.expects(:new).with(:blame => true).returns(@flog)      
+322       run_command
+323     end
+324     
+325     it 'should exit with status 0' do
+326       self.expects(:exit).with(0)
+327       run_command
+328     end
+329   end
+330   
+331   describe 'when --blame is specified on the command-line' do
+332     before :each do
+333       Object.send(:remove_const, :ARGV)
+334       ARGV = ['--blame']
+335     end
+336 
+337     it 'should create a Flog instance' do
+338       Flog.expects(:new).returns(@flog)
+339       run_command
+340     end
+341     
+342     it "should set the option to provide 'blame' information" do
+343       Flog.expects(:new).with(:blame => true).returns(@flog)      
+344       run_command
+345     end
+346     
+347     it 'should exit with status 0' do
+348       self.expects(:exit).with(0)
+349       run_command
+350     end
+351   end
+352 end
 

Generated using the rcov code coverage analysis tool for Ruby version 0.8.1.2.

diff --git a/coverage/spec-flog_integration_spec_rb.html b/coverage/spec-flog_integration_spec_rb.html index 4b380dd..c30ee82 100644 --- a/coverage/spec-flog_integration_spec_rb.html +++ b/coverage/spec-flog_integration_spec_rb.html @@ -553,7 +553,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:35 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:50 -0500 2008 with rcov 0.8.1.2


Code reported as executed by Ruby looks like this...
@@ -598,946 +598,946 @@
       
-
  1 require File.dirname(__FILE__) + '/spec_helper.rb'
-  2 require 'flog'
-  3 require 'sexp_processor'
-  4 
-  5 describe Flog do
-  6   before :each do
-  7     @flog = Flog.new({})
-  8   end
-  9 
- 10   describe 'flog_files' do
- 11 
- 12     describe 'when given empty input' do
- 13       before :each do
- 14         @files = ['/empty/empty.rb']
- 15       end
- 16     
- 17       it 'should not fail when flogging the given input' do
- 18         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
- 19       end
- 20       
- 21       currently 'should report an overall flog score of 0' do
- 22         @flog.flog_files(fixture_files(@files))
- 23         @flog.total.should be_close(0.0, 0.0000000001)
- 24       end
- 25     end
- 26   
- 27     describe 'when given a simple file' do
- 28       before :each do
- 29         @files = ['/simple/simple.rb']
- 30         @calls = YAML.load(<<-YAML)
- 31         --- 
- 32         RailsClassMethods#generate: 
- 33           :save: 1.4
- 34           :assignment: 2.80000000000001
- 35           :spawn: 1.4
- 36         RailsClassMethods#exemplar_path: 
- 37           :join: 1.4
- 38         ClassMethods#generator_for: 
- 39           :is_a?: 2.8
- 40           :arity: 2.0
- 41           :assignment: 16.5
- 42           :respond_to?: 1.7
- 43           :first: 1.6
- 44           :branch: 19.0
- 45           :name: 2.0
- 46           :lit_fixnum: 0.45
- 47           :length: 1.8
- 48           :raise: 8.60000000000001
- 49           :include?: 1.8
- 50           :lambda: 1.8
- 51           :to_sym: 3.1
- 52           :[]: 16.1
- 53           :==: 1.6
- 54           :keys: 3.8
- 55           :record_generator_for: 5.00000000000001
- 56         ObjectDaddy#included: 
- 57           :extend: 5.6
- 58           :branch: 2.6
- 59           :sclass: 7.5
- 60           :alias_method: 8.4
- 61           :<: 1.4
- 62         ClassMethods#underscore: 
- 63           :gsub: 1.6
- 64           :downcase: 1.4
- 65         ClassMethods#gather_exemplars: 
- 66           :load: 1.5
- 67           :underscore: 1.6
- 68           :assignment: 4.40000000000001
- 69           :respond_to?: 1.4
- 70           :superclass: 5.50000000000001
- 71           :branch: 6.00000000000001
- 72           :name: 1.8
- 73           :gather_exemplars: 1.6
- 74           :exemplars_generated: 1.4
- 75           :exists?: 1.4
- 76           :join: 1.4
- 77           :dup: 1.6
- 78           :exemplar_path: 1.6
- 79           :generators: 1.9
- 80         ClassMethods#none: 
- 81           :protected: 2.6
- 82           :attr_accessor: 1.3
- 83           :attr_reader: 1.3
- 84         Foo#initialize: 
- 85           :super: 1.2
- 86         main#none: 
- 87           :assignment: 1.1
- 88           :attr_writer: 1.1
- 89           :branch: 5.60000000000001
- 90           :lit_fixnum: 0.275000000000001
- 91           :puts: 1.1
- 92           :alias: 2.20000000000001
- 93         ClassMethods#record_generator_for: 
- 94           :assignment: 1.4
- 95           :branch: 3.20000000000001
- 96           :raise: 1.5
- 97           :==: 1.4
- 98           :[]: 3.50000000000001
- 99           :generators: 3.50000000000001
-100         RailsClassMethods#validates_presence_of_with_object_daddy: 
-101           :is_a?: 1.4
-102           :assignment: 5.80000000000001
-103           :branch: 2.80000000000001
-104           :last: 1.6
-105           :dup: 1.4
-106           :pop: 1.5
-107           :each: 1.4
-108           :validates_presence_of_without_object_daddy: 1.4
-109         ClassMethods#presence_validated_attributes: 
-110           :merge: 1.5
-111           :presence_validated_attributes: 1.7
-112           :assignment: 4.30000000000001
-113           :respond_to?: 1.4
-114           :superclass: 3.50000000000001
-115           :branch: 1.4
-116         ClassMethods#spawn: 
-117           :presence_validated_attributes: 5.4
-118           :each_pair: 1.4
-119           :assignment: 35.3
-120           :generate: 1.7
-121           :class_name: 2.1
-122           :call: 1.8
-123           :reflect_on_all_associations: 1.8
-124           :branch: 24.0
-125           :constantize: 1.9
-126           :name: 3.9
-127           :gather_exemplars: 1.4
-128           :select: 1.6
-129           :-: 1.8
-130           :send: 5.4
-131           :to_a: 1.6
-132           :empty?: 1.5
-133           :new: 1.4
-134           :reject!: 1.7
-135           :next: 1.9
-136           :delete: 1.9
-137           :include?: 1.8
-138           :primary_key_name: 4.2
-139           :to_s: 5.7
-140           :each: 3.2
-141           :keys: 4.0
-142           :[]: 23.6
-143           :generators: 1.7
-144           :scope: 1.6
-145         RailsClassMethods#generate!: 
-146           :save!: 1.4
-147           :assignment: 2.80000000000001
-148           :spawn: 1.4
-149         YAML
-150         
-151         @totals = YAML.load(<<-YAML)
-152         --- 
-153         RailsClassMethods#generate: 3.95979797464467
-154         ObjectDaddy#included: 23.0471256342304
-155         ClassMethods#generator_for: 59.7115776043475
-156         RailsClassMethods#exemplar_path: 1.4
-157         ClassMethods#underscore: 3.00000000000001
-158         ClassMethods#none: 5.2
-159         ClassMethods#gather_exemplars: 23.8882816460289
-160         ClassMethods#record_generator_for: 10.4980950652964
-161         main#none: 7.37737249974544
-162         Foo#initialize: 1.2
-163         ClassMethods#spawn: 96.0108847995893
-164         ClassMethods#presence_validated_attributes: 9.27685291464731
-165         RailsClassMethods#validates_presence_of_with_object_daddy: 10.8245092267502
-166         RailsClassMethods#generate!: 3.95979797464467
-167         YAML
-168       end
-169     
-170       it 'should not fail when flogging the given input' do
-171         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
-172       end
-173 
-174       currently 'should report an overall flog score of 259.354295339925' do
-175         @flog.flog_files(fixture_files(@files))
-176         @flog.total.should be_close(259.354295339925, 0.0000000001)
-177       end
-178       
-179       currently 'should compute the same call data as flog-1.1.0' do
-180         @flog.flog_files(fixture_files(@files))
-181         @flog.calls.each_pair do |k,v|
-182           v.each_pair do |x, y|
-183             @calls[k][x].should be_close(y, 0.0000000001)
-184           end
-185         end
-186       end
-187 
-188       currently 'should compute the same totals data as flog-1.1.0' do
-189         @flog.flog_files(fixture_files(@files))        
-190         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
-191       end
-192     end
-193   
-194     describe 'when given a directory of files' do
-195       before :each do
-196         @files = ['/directory/']
-197         @calls = YAML.load(<<-YAML)
-198         --- 
-199         BotSender#validate: 
-200           :assignment: 1.3
-201         BotParserFormat#description: 
-202           :join: 1.3
-203           :branch: 1.2
-204           :empty?: 1.2
-205         BotParserFormat#initialize: 
-206           :assignment: 4.8
-207           :branch: 1.2
-208           :raise: 1.3
-209           :nil?: 1.2
-210         BotParser#parse: 
-211           :merge: 1.3
-212           :detect: 1.3
-213           :assignment: 6.7
-214           :branch: 3.9
-215           :empty?: 1.3
-216           :process: 1.4
-217           :formats: 1.5
-218         register_format#video: 
-219           :register_format: 1.2
-220           :assignment: 3.6
-221           :lit_fixnum: 1.05
-222           :[]: 3.6
-223         register_format#image: 
-224           :register_format: 1.2
-225           :assignment: 3.6
-226           :lit_fixnum: 1.05
-227           :[]: 3.6
-228         BotFilter#process: 
-229           :class: 1.6
-230           :options: 1.8
-231           :kinds: 1.4
-232           :assignment: 5.4
-233           :branch: 2.5
-234           :get: 1.8
-235           :process: 1.4
-236           :new: 1.6
-237           :each: 1.2
-238         BotFilter#register: 
-239           :<<: 1.8
-240         BotSender#deliver: 
-241           :respond_to?: 1.3
-242           :assignment: 2.7
-243           :send: 4.2
-244           :branch: 5.2
-245           :raise: 1.4
-246           :to_s: 1.5
-247           :to_sym: 1.3
-248           :[]: 4.5
-249         register_format#true_or_false: 
-250           :register_format: 1.2
-251           :assignment: 3.6
-252           :lit_fixnum: 0.35
-253           :[]: 1.2
-254         BotSender#none: 
-255           :assignment: 1.1
-256           :attr_reader: 1.2
-257         BotParser#clear_formats: 
-258           :assignment: 1.9
-259         BotSender#register: 
-260           :each_pair: 1.3
-261           :assignment: 6.90000000000001
-262           :branch: 1.3
-263         register_format#definition: 
-264           :register_format: 1.2
-265           :assignment: 3.6
-266           :lit_fixnum: 0.7
-267           :[]: 2.4
-268         register_format#link: 
-269           :register_format: 1.2
-270           :assignment: 3.6
-271           :lit_fixnum: 1.05
-272           :[]: 3.6
-273         BotParser#none: 
-274           :assignment: 1.2
-275           :sclass: 6.0
-276           :attr_reader: 1.8
-277         BotParser#register_format: 
-278           :<<: 1.9
-279           :new: 2.1
-280           :formats: 2.1
-281           :block_pass: 2.1
-282         BotSender#initialize: 
-283           :validate: 1.3
-284           :assignment: 2.6
-285           :[]: 1.3
-286         register_format#quote: 
-287           :register_format: 1.2
-288           :assignment: 3.6
-289           :lit_fixnum: 1.05
-290           :[]: 3.6
-291         BotFilter#register_filter: 
-292           :register: 1.8
-293           :load: 1.8
-294           :filter_path: 1.8
-295           :assignment: 1.8
-296           :exists?: 1.8
-297           :branch: 1.8
-298           :raise: 1.9
-299         BotSender#kinds: 
-300           :assignment: 1.4
-301           :sort_by: 1.3
-302           :branch: 1.3
-303           :to_s: 1.4
-304           :keys: 1.5
-305         main#none: 
-306           :require: 2.2
-307         BotFilter#new: 
-308           :locate_filters: 1.9
-309           :assignment: 3.6
-310           :send: 5.4
-311           :branch: 1.8
-312           :allocate: 1.8
-313         BotSender#new: 
-314           :kinds: 1.5
-315           :assignment: 2.6
-316           :send: 3.9
-317           :branch: 1.3
-318           :allocate: 1.3
-319           :raise: 1.4
-320           :include?: 1.3
-321           :[]: 4.7
-322         BotFilter#locate_filters: 
-323           :register_filter: 2.0
-324           :assignment: 2.0
-325           :branch: 5.5
-326           :each: 1.9
-327           :[]: 4.0
-328         BotFilter#get: 
-329           :gsub: 2.0
-330           :upcase: 2.1
-331           :assignment: 1.8
-332           :const_get: 1.8
-333           :branch: 2.0
-334           :to_sym: 1.8
-335           :to_s: 2.2
-336         BotParserFormat#none: 
-337           :attr_reader: 1.1
-338         BotFilter#filter_path: 
-339           :+: 2.0
-340           :dirname: 2.2
-341           :expand_path: 1.8
-342         BotParserFormat#process: 
-343           :merge: 1.2
-344           :call: 1.4
-345           :match: 1.2
-346           :format: 1.4
-347           :name: 1.4
-348           :assignment: 1.2
-349           :branch: 1.2
-350           :block: 1.6
-351         BotParser#formats: 
-352           :class: 1.5
-353           :formats: 1.3
-354         BotFilter#initialize: 
-355           :assignment: 2.4
-356         register_format#fact: 
-357           :register_format: 1.2
-358           :assignment: 3.6
-359           :lit_fixnum: 0.35
-360           :[]: 1.2
-361         BotFilter#none: 
-362           :sclass: 5.5
-363           :attr_reader: 1.1
-364         YAML
-365         
-366         @totals = YAML.load(<<-YAML)
-367         --- 
-368         BotFilter#register: 1.8
-369         BotFilter#process: 12.3308556069723
-370         register_format#image: 6.86895188511319
-371         register_format#video: 6.86895188511319
-372         BotParser#parse: 10.3121287811974
-373         BotParserFormat#initialize: 5.54346462061408
-374         BotParserFormat#description: 2.77308492477241
-375         BotSender#validate: 1.3
-376         register_format#true_or_false: 4.53017659699929
-377         BotSender#deliver: 15.3613150478727
-378         BotParser#clear_formats: 1.9
-379         BotSender#none: 1.62788205960997
-380         BotParser#none: 7.89176786277955
-381         register_format#link: 6.86895188511319
-382         register_format#definition: 5.60802995712398
-383         BotSender#register: 7.14072825417689
-384         BotParser#register_format: 8.2
-385         BotFilter#register_filter: 9.44933860119321
-386         register_format#quote: 6.86895188511319
-387         BotSender#initialize: 3.67695526217005
-388         BotFilter#new: 9.9503768772846
-389         main#none: 2.2
-390         BotSender#kinds: 4.61410879802373
-391         BotFilter#get: 10.2591422643416
-392         BotFilter#locate_filters: 9.83158176490437
-393         BotSender#new: 14.3965273590543
-394         BotFilter#filter_path: 6.0
-395         BotParserFormat#none: 1.1
-396         BotFilter#initialize: 2.4
-397         BotParser#formats: 2.8
-398         BotParserFormat#process: 8.37376856618333
-399         BotFilter#none: 6.6
-400         register_format#fact: 4.53017659699929
-401         YAML
-402       end
-403     
-404       it 'should not fail when flogging the given input' do
-405         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
-406       end
-407 
-408       currently 'should report an overall flog score of 209.977217342726' do
-409         @flog.flog_files(fixture_files(@files))
-410         @flog.total.should be_close(209.977217342726, 0.0000000001)        
-411       end
-412       
-413       currently 'should compute the same call data as flog-1.1.0' do
-414         @flog.flog_files(fixture_files(@files))
-415         @flog.calls.each_pair do |k,v|
-416           v.each_pair do |x, y|
-417             @calls[k][x].should be_close(y, 0.0000000001)
-418           end
-419         end
-420       end
-421 
-422       currently 'should compute the same totals data as flog-1.1.0' do
-423         @flog.flog_files(fixture_files(@files))
-424         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
-425       end
-426     end
-427   
-428     describe 'when given a collection of files' do
-429       before :each do
-430         @files = ['/collection/']  
-431         @calls = YAML.load(<<-YAML)
-432         --- 
-433         InstanceMethods#initialize_with_has_many_range_extension: 
-434           :returning: 1.3
-435           :initialize_without_has_many_range_extension: 1.5
-436           :macro: 1.90000000000001
-437           :add_has_many_range_extension: 1.70000000000001
-438           :branch: 2.80000000000001
-439           :puts: 6.00000000000002
-440           :==: 1.50000000000001
-441           :to_s: 1.70000000000001
-442         ClassMethods#calculate_with_range_restrictions: 
-443           :with_current_time_scope: 1.5
-444           :calculate_without_range_restrictions: 3.10000000000001
-445           :branch: 2.90000000000001
-446           :[]: 1.4
-447           :acts_as_range_configuration: 1.6
-448         InstanceMethods#contained_by?: 
-449           :to_range: 3.70000000000001
-450           :exclude_end?: 3.60000000000001
-451           :respond_to?: 1.3
-452           :last: 1.8
-453           :contained_by?: 1.5
-454           :branch: 18.5
-455           :>=: 1.9
-456           :acts_as_range_begin: 12.5
-457           :==: 3.20000000000001
-458           :include?: 2.90000000000001
-459           :acts_as_range_end: 14.4
-460           :<=: 1.9
-461         ClassMethods#sequentialized?: 
-462           :branch: 1.3
-463           :sequentialized_on: 1.3
-464         InstanceMethods#expired?: 
-465           :assignment: 1.3
-466           :branch: 1.3
-467           :now: 1.3
-468           :acts_as_range_end: 2.8
-469           :<=: 1.3
-470         ClassMethods#with_overlapping_scope: 
-471           :|: 3.00000000000001
-472           :with_containing_scope: 4.00000000000001
-473           :with_contained_scope: 1.8
-474           :flatten: 5.20000000000001
-475           :block_pass: 5.80000000000001
-476         ClassMethods#with_containing_scope: 
-477           :acts_as_range_begin_attr: 5.30000000000001
-478           :with_scope: 1.4
-479           :<<: 11.0
-480           :assignment: 4.20000000000001
-481           :join: 1.8
-482           :table_name: 10.6
-483           :branch: 2.80000000000001
-484           :acts_as_range_end_attr: 5.30000000000001
-485           :block_pass: 1.4
-486           :flatten: 1.4
-487           :nil?: 2.80000000000001
-488         ClassMethods#with_after_scope: 
-489           :acts_as_range_begin_attr: 3.20000000000001
-490           :with_scope: 1.4
-491           :table_name: 3.20000000000001
-492           :block_pass: 1.4
-493         InstanceMethods#overlapping?: 
-494           :is_a?: 1.4
-495           :first: 1.8
-496           :respond_to?: 1.3
-497           :last: 1.8
-498           :assignment: 3.20000000000001
-499           :contained_by?: 1.4
-500           :containing?: 7.80000000000002
-501           :branch: 11.3
-502           :acts_as_range_begin: 3.30000000000001
-503           :acts_as_range_end: 3.30000000000001
-504         ClassMethods#acts_as_date_range_sequentialize_class: 
-505           :acts_as_date_range_param_sequentialize_class: 1.4
-506           :acts_as_date_range_singleton_sequentialize_class: 1.4
-507           :branch: 1.3
-508           :flatten!: 1.3
-509           :==: 1.3
-510         ClassMethods#acts_as_date_range_param_sequentialize_class: 
-511           :validate_on_create: 1.3
-512           :add: 1.6
-513           :count: 1.7
-514           :>: 1.5
-515           :acts_as_range_begin_attr: 3.9
-516           :class: 3.8
-517           :extend: 2.6
-518           :errors: 1.8
-519           :assignment: 5.80000000000001
-520           :before_validation_on_create: 1.3
-521           :branch: 6.90000000000001
-522           :before_create: 1.3
-523           :now: 1.5
-524           :acts_as_range_begin: 6.00000000000001
-525           :to_sql: 4.2
-526           :acts_as_range_end_attr: 4.2
-527           :each: 1.5
-528           :expire: 1.6
-529           :find: 1.7
-530           :flatten: 3.8
-531           :to_attributes_for: 4.2
-532         InstanceMethods#destroy_without_callbacks: 
-533           :class: 3.8
-534           :default_timezone: 1.8
-535           :freeze: 1.3
-536           :new_record?: 1.3
-537           :update_all: 1.6
-538           :assignment: 1.6
-539           :send: 5.4
-540           :branch: 4.3
-541           :now: 3.6
-542           :acts_as_range_end_attr: 2.0
-543           :id: 2.0
-544           :utc: 1.7
-545           :==: 1.6
-546           :[]: 1.4
-547           :acts_as_range_configuration: 1.6
-548           :quote_value: 1.8
-549         ClassMethods#with_contained_scope: 
-550           :acts_as_range_begin_attr: 7.60000000000002
-551           :with_scope: 1.4
-552           :<<: 16.8
-553           :assignment: 4.20000000000001
-554           :join: 1.8
-555           :table_name: 15.2
-556           :branch: 4.40000000000001
-557           :acts_as_range_end_attr: 7.60000000000002
-558           :block_pass: 1.4
-559           :flatten: 1.4
-560           :nil?: 4.40000000000001
-561         ClassMethods#count_with_range_restrictions: 
-562           :count_without_range_restrictions: 3.10000000000001
-563           :with_current_time_scope: 1.5
-564           :branch: 2.90000000000001
-565           :[]: 1.4
-566           :acts_as_range_configuration: 1.6
-567         InstanceMethods#to_range: 
-568           :assignment: 2.60000000000001
-569           :acts_as_range_begin: 1.3
-570           :acts_as_range_end: 1.3
-571         ParamExtension#to_attributes_for: 
-572           :attributes: 1.7
-573           :assignment: 1.5
-574           :branch: 1.4
-575           :[]: 1.5
-576           :to_s: 1.7
-577           :collect: 1.4
-578         ClassMethods#with_current_time_scope: 
-579           :first: 3.3
-580           :respond_to?: 2.7
-581           :call: 2.7
-582           :with_overlapping_scope: 2.9
-583           :end_dated_association_date: 3.1
-584           :last: 3.3
-585           :assignment: 2.7
-586           :with_containing_scope: 2.9
-587           :branch: 2.7
-588           :block_pass: 5.80000000000001
-589         InstanceMethods#included: 
-590           :extend: 5.20000000000001
-591         DateRanged#current: 
-592           :containing: 1.1
-593           :now: 1.3
-594         ClassMethods#with_before_scope: 
-595           :with_scope: 1.4
-596           :table_name: 3.20000000000001
-597           :acts_as_range_end_attr: 3.20000000000001
-598           :block_pass: 1.4
-599         ClassMethods#remove_args: 
-600           :first: 1.5
-601           :>: 1.4
-602           :last: 2.0
-603           :<<: 1.4
-604           :extract_options_from_args!: 1.4
-605           :assignment: 2.90000000000001
-606           :branch: 2.80000000000001
-607           :length: 1.6
-608           :delete: 1.5
-609           :keys: 1.8
-610           :each: 1.4
-611         ClassMethods#add_args: 
-612           :merge: 1.6
-613           :<<: 1.4
-614           :extract_options_from_args!: 1.8
-615         InstanceMethods#before?: 
-616           :respond_to?: 1.3
-617           :branch: 3.90000000000001
-618           :<: 1.3
-619           :before?: 1.4
-620           :acts_as_range_begin: 1.6
-621           :acts_as_range_end: 2.80000000000001
-622         InstanceMethods#containing?: 
-623           :to_range: 8.50000000000001
-624           :is_a?: 1.4
-625           :exclude_end?: 6.30000000000001
-626           :>: 2.0
-627           :first: 4.00000000000001
-628           :respond_to?: 1.3
-629           :assignment: 3.20000000000001
-630           :last: 10.7
-631           :contained_by?: 1.4
-632           :branch: 28.0
-633           :acts_as_range_begin: 8.90000000000002
-634           :==: 5.90000000000001
-635           :include?: 5.20000000000001
-636           :acts_as_range_end: 13.1
-637           :<=: 3.70000000000001
-638         ClassMethods#acts_as_date_range: 
-639           :acts_as_range: 1.3
-640           :is_a?: 1.3
-641           :assignment: 1.3
-642           :acts_as_date_range?: 1.3
-643           :acts_as_date_range_configure_class: 1.3
-644           :branch: 2.6
-645           :update: 1.5
-646           :raise: 1.4
-647         InstanceMethods#limit_date_range: 
-648           :end_dated_association_date: 1.4
-649           :assignment: 6.9
-650           :branch: 1.4
-651           :yield: 1.4
-652           :new: 1.4
-653           :acts_as_range_begin: 1.4
-654           :acts_as_range_end: 1.4
-655         InstanceMethods#lifetime: 
-656           :>: 1.4
-657           :assignment: 1.3
-658           :branch: 5.4
-659           :now: 1.3
-660           :acts_as_range_begin: 4.6
-661           :acts_as_range_end: 3.2
-662           :distance_of_time_in_words: 1.3
-663           :nil?: 2.7
-664         ClassMethods#validates_interval: 
-665           :validation_method: 1.6
-666           :add: 1.80000000000001
-667           :errors: 2.00000000000001
-668           :evaluate_condition: 1.6
-669           :assignment: 9.30000000000003
-670           :send: 4.20000000000001
-671           :branch: 10.9
-672           :acts_as_range_begin: 1.70000000000001
-673           :acts_as_range_end: 1.70000000000001
-674           :each: 1.3
-675           :humanize: 2.60000000000001
-676           :to_s: 3.00000000000001
-677           :[]: 12.3
-678           :acts_as_range_configuration: 6.00000000000001
-679           :<=: 1.90000000000001
-680           :nil?: 3.70000000000001
-681         ClassMethods#acts_as_range: 
-682           :is_a?: 1.3
-683           :class_inheritable_reader: 1.3
-684           :assignment: 1.3
-685           :acts_as_range_configure_class: 1.3
-686           :branch: 2.60000000000001
-687           :update: 1.5
-688           :raise: 1.4
-689           :acts_as_range?: 1.3
-690         ParamExtension#to_sql: 
-691           :assignment: 1.7
-692           :join: 1.4
-693           :branch: 1.6
-694           :collect: 1.6
-695         ClassMethods#none: 
-696           :protected: 3.70000000000001
-697           :assignment: 1.4
-698           :branch: 2.70000000000001
-699           :[]: 1.5
-700           :to_sym: 1.7
-701           :acts_as_range_configuration: 1.7
-702           :define_method: 7.00000000000002
-703           :each: 1.3
-704         DateRange#included: 
-705           :respond_to?: 1.2
-706           :extend: 2.4
-707           :assignment: 1.4
-708           :branch: 2.6
-709           :now: 1.5
-710           :new: 1.4
-711           :attr: 1.9
-712           :sclass: 7.0
-713         DateRange#none: 
-714           :include: 2.2
-715         InstanceMethods#add_has_many_range_extension: 
-716           :options: 1.50000000000001
-717           :assignment: 6.00000000000002
-718           :push: 1.60000000000001
-719           :branch: 2.80000000000001
-720           :puts: 5.40000000000002
-721           :acts_as_range?: 1.3
-722           :include?: 1.50000000000001
-723           :[]: 5.20000000000002
-724           :klass: 3.00000000000001
-725           :flatten: 1.50000000000001
-726         Ranged#included: 
-727           :alias_method_chain: 1.3
-728           :branch: 1.2
-729           :send: 3.60000000000001
-730           :puts: 1.2
-731           :instance_eval: 6.00000000000002
-732         Range#included: 
-733           :respond_to?: 1.2
-734           :extend: 2.4
-735           :assignment: 1.4
-736           :branch: 2.6
-737           :now: 1.5
-738           :new: 1.4
-739           :attr: 1.9
-740           :sclass: 7.00000000000001
-741         InstanceMethods#include?: 
-742           :class: 3.2
-743           :branch: 5.40000000000001
-744           :id: 3.2
-745           :find: 2.8
-746         ClassMethods#acts_as_range?: 
-747           :included_modules: 1.5
-748           :include?: 1.3
-749         ClassMethods#acts_as_date_range_configure_class: 
-750           :acts_as_date_range_sequentialize_class: 1.4
-751           :assignment: 1.3
-752           :write_inheritable_attribute: 1.3
-753           :branch: 1.3
-754           :[]: 2.9
-755           :include: 2.6
-756         InstanceMethods#none: 
-757           :+: 3.8
-758           :class: 9.20000000000001
-759           :assignment: 5.60000000000001
-760           :private: 1.2
-761           :send: 43.2
-762           :branch: 8.00000000000001
-763           :alias_method: 4.80000000000001
-764           :to_s: 4.2
-765           :to_sym: 6.80000000000001
-766           :define_method: 28.0
-767           :each: 2.4
-768         Ranged#none: 
-769           :+: 1.7
-770           :assignment: 3.60000000000001
-771           :select: 1.2
-772           :send: 3.90000000000001
-773           :branch: 3.30000000000001
-774           :to_sym: 1.5
-775           :define_method: 5.50000000000002
-776           :each: 1.0
-777         ClassMethods#acts_as_range_configure_class: 
-778           :assignment: 3.20000000000001
-779           :write_inheritable_attribute: 1.3
-780           :alias_method_chain: 1.90000000000001
-781           :branch: 1.8
-782           :validates_interval: 1.3
-783           :to_sym: 2.1
-784           :each: 1.8
-785           :sclass: 6.50000000000002
-786           :include: 2.60000000000001
-787         ClassMethods#ranged_lookup: 
-788           :first: 1.5
-789           :respond_to?: 1.4
-790           :last: 1.5
-791           :assignment: 7.00000000000002
-792           :-: 1.7
-793           :branch: 2.80000000000001
-794           :to_a: 1.5
-795           :yield: 1.4
-796           :new: 3.80000000000001
-797           :acts_as_range_begin: 1.5
-798           :acts_as_range_end: 1.5
-799         ClassMethods#find_with_range_restrictions: 
-800           :find_without_range_restrictions: 9.80000000000002
-801           :with_current_time_scope: 1.5
-802           :remove_args: 7.50000000000002
-803           :with_before_scope: 1.5
-804           :extract_options_from_args!: 1.4
-805           :assignment: 12.8
-806           :with_containing_scope: 1.5
-807           :send: 5.40000000000001
-808           :with_after_scope: 1.5
-809           :branch: 19.7
-810           :dup: 1.4
-811           :ranged_lookup: 1.7
-812           :acts_as_range_configuration: 1.6
-813           :==: 1.7
-814           :each: 1.4
-815           :keys: 9.90000000000002
-816           :[]: 12.1
-817           :has_key?: 5.70000000000001
-818         InstanceMethods#after?: 
-819           :>: 1.3
-820           :respond_to?: 1.3
-821           :branch: 3.90000000000001
-822           :acts_as_range_begin: 2.80000000000001
-823           :after?: 1.4
-824           :acts_as_range_end: 1.6
-825         ClassMethods#acts_as_date_range_singleton_sequentialize_class: 
-826           :validate_on_create: 1.3
-827           :add: 1.6
-828           :count: 1.7
-829           :>: 1.5
-830           :acts_as_range_begin_attr: 3.7
-831           :class: 3.8
-832           :errors: 1.8
-833           :assignment: 5.8
-834           :before_validation_on_create: 1.3
-835           :branch: 6.90000000000001
-836           :before_create: 1.3
-837           :now: 1.5
-838           :acts_as_range_begin: 5.6
-839           :acts_as_range_end_attr: 3.8
-840           :each: 1.5
-841           :expire: 1.6
-842           :find: 1.7
-843         ClassMethods#acts_as_date_range?: 
-844           :included_modules: 1.5
-845           :include?: 1.3
-846         InstanceMethods#expire: 
-847           :second: 1.6
-848           :is_a?: 2.7
-849           :save!: 1.3
-850           :ago: 1.4
-851           :assignment: 4.2
-852           :-: 1.5
-853           :branch: 4.0
-854           :now: 1.3
-855           :lit_fixnum: 0.875
-856           :acts_as_range_end: 1.3
-857         ClassMethods#sequentialized_on: 
-858           :[]: 1.3
-859           :acts_as_range_configuration: 1.5
-860         YAML
-861         
-862         @totals = YAML.load(<<-YAML)
-863         --- 
-864         InstanceMethods#expired?: 5.70438427878067
-865         ClassMethods#sequentialized?: 1.83847763108502
-866         InstanceMethods#contained_by?: 52.0954892481106
-867         ClassMethods#calculate_with_range_restrictions: 8.13449445263812
-868         InstanceMethods#initialize_with_has_many_range_extension: 15.8492902049272
-869         InstanceMethods#destroy_without_callbacks: 31.238757977871
-870         ClassMethods#acts_as_date_range_param_sequentialize_class: 50.3140139523772
-871         ClassMethods#acts_as_date_range_sequentialize_class: 5.55427763079954
-872         InstanceMethods#overlapping?: 25.0267856505785
-873         ClassMethods#with_after_scope: 9.20000000000002
-874         ClassMethods#with_containing_scope: 41.3095630574811
-875         ClassMethods#with_overlapping_scope: 19.8
-876         InstanceMethods#included: 5.20000000000001
-877         ClassMethods#with_current_time_scope: 26.9716517847907
-878         ParamExtension#to_attributes_for: 6.62570750939099
-879         InstanceMethods#to_range: 3.67695526217005
-880         ClassMethods#count_with_range_restrictions: 8.13449445263812
-881         ClassMethods#with_contained_scope: 57.9202900545225
-882         InstanceMethods#lifetime: 15.5273951453552
-883         InstanceMethods#limit_date_range: 9.92824254337091
-884         ClassMethods#acts_as_date_range: 8.60581198958007
-885         InstanceMethods#containing?: 77.6916983982203
-886         InstanceMethods#before?: 9.2612094242599
-887         ClassMethods#add_args: 4.80000000000001
-888         ClassMethods#remove_args: 14.5688022843335
-889         ClassMethods#with_before_scope: 9.20000000000002
-890         DateRanged#current: 2.40000000000001
-891         DateRange#none: 2.2
-892         DateRange#included: 15.6805612144464
-893         ClassMethods#none: 17.171487996094
-894         ParamExtension#to_sql: 3.80131556174965
-895         ClassMethods#acts_as_range: 8.6058119895801
-896         ClassMethods#validates_interval: 47.6073523733468
-897         Range#included: 15.6805612144464
-898         Ranged#included: 12.1593585357124
-899         InstanceMethods#add_has_many_range_extension: 22.0190826330255
-900         InstanceMethods#include?: 10.6677082824757
-901         InstanceMethods#none: 104.05921391208
-902         ClassMethods#acts_as_date_range_configure_class: 8.40357066966181
-903         ClassMethods#acts_as_range?: 2.80000000000001
-904         InstanceMethods#expire: 13.3056613890479
-905         ClassMethods#acts_as_date_range?: 2.8
-906         ClassMethods#acts_as_date_range_singleton_sequentialize_class: 34.8846671189507
-907         InstanceMethods#after?: 9.2612094242599
-908         ClassMethods#find_with_range_restrictions: 69.6799110217573
-909         ClassMethods#ranged_lookup: 17.5065701952153
-910         ClassMethods#acts_as_range_configure_class: 17.8809954980141
-911         Ranged#none: 15.5849286170968
-912         ClassMethods#sequentialized_on: 2.8
-913         YAML
-914       end
-915 
-916       it 'should not fail when flogging the given input' do
-917         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
-918       end
-919 
-920       currently 'should report an overall flog score of 981.137760580242' do
-921         @flog.flog_files(fixture_files(@files))
-922         @flog.total.should be_close(981.137760580242, 0.0000000001)
-923       end
-924       
-925       currently 'should compute the same call data as flog-1.1.0' do
-926         @flog.flog_files(fixture_files(@files))
-927         @flog.calls.each_pair do |k,v|
-928           v.each_pair do |x, y|
-929             @calls[k][x].should be_close(y, 0.0000000001)
-930           end
-931         end
-932       end
-933 
-934       currently 'should compute the same totals data as flog-1.1.0' do
-935         @flog.flog_files(fixture_files(@files))
-936         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
-937       end
-938     end
-939   end
-940 end
+
  1 require File.dirname(__FILE__) + '/spec_helper.rb'
+  2 require 'flog'
+  3 require 'sexp_processor'
+  4 
+  5 describe Flog do
+  6   before :each do
+  7     @flog = Flog.new({})
+  8   end
+  9 
+ 10   describe 'flog_files' do
+ 11 
+ 12     describe 'when given empty input' do
+ 13       before :each do
+ 14         @files = ['/empty/empty.rb']
+ 15       end
+ 16     
+ 17       it 'should not fail when flogging the given input' do
+ 18         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
+ 19       end
+ 20       
+ 21       currently 'should report an overall flog score of 0' do
+ 22         @flog.flog_files(fixture_files(@files))
+ 23         @flog.total.should be_close(0.0, 0.0000000001)
+ 24       end
+ 25     end
+ 26   
+ 27     describe 'when given a simple file' do
+ 28       before :each do
+ 29         @files = ['/simple/simple.rb']
+ 30         @calls = YAML.load(<<-YAML)
+ 31         --- 
+ 32         RailsClassMethods#generate: 
+ 33           :save: 1.4
+ 34           :assignment: 2.80000000000001
+ 35           :spawn: 1.4
+ 36         RailsClassMethods#exemplar_path: 
+ 37           :join: 1.4
+ 38         ClassMethods#generator_for: 
+ 39           :is_a?: 2.8
+ 40           :arity: 2.0
+ 41           :assignment: 16.5
+ 42           :respond_to?: 1.7
+ 43           :first: 1.6
+ 44           :branch: 19.0
+ 45           :name: 2.0
+ 46           :lit_fixnum: 0.45
+ 47           :length: 1.8
+ 48           :raise: 8.60000000000001
+ 49           :include?: 1.8
+ 50           :lambda: 1.8
+ 51           :to_sym: 3.1
+ 52           :[]: 16.1
+ 53           :==: 1.6
+ 54           :keys: 3.8
+ 55           :record_generator_for: 5.00000000000001
+ 56         ObjectDaddy#included: 
+ 57           :extend: 5.6
+ 58           :branch: 2.6
+ 59           :sclass: 7.5
+ 60           :alias_method: 8.4
+ 61           :<: 1.4
+ 62         ClassMethods#underscore: 
+ 63           :gsub: 1.6
+ 64           :downcase: 1.4
+ 65         ClassMethods#gather_exemplars: 
+ 66           :load: 1.5
+ 67           :underscore: 1.6
+ 68           :assignment: 4.40000000000001
+ 69           :respond_to?: 1.4
+ 70           :superclass: 5.50000000000001
+ 71           :branch: 6.00000000000001
+ 72           :name: 1.8
+ 73           :gather_exemplars: 1.6
+ 74           :exemplars_generated: 1.4
+ 75           :exists?: 1.4
+ 76           :join: 1.4
+ 77           :dup: 1.6
+ 78           :exemplar_path: 1.6
+ 79           :generators: 1.9
+ 80         ClassMethods#none: 
+ 81           :protected: 2.6
+ 82           :attr_accessor: 1.3
+ 83           :attr_reader: 1.3
+ 84         Foo#initialize: 
+ 85           :super: 1.2
+ 86         main#none: 
+ 87           :assignment: 1.1
+ 88           :attr_writer: 1.1
+ 89           :branch: 5.60000000000001
+ 90           :lit_fixnum: 0.275000000000001
+ 91           :puts: 1.1
+ 92           :alias: 2.20000000000001
+ 93         ClassMethods#record_generator_for: 
+ 94           :assignment: 1.4
+ 95           :branch: 3.20000000000001
+ 96           :raise: 1.5
+ 97           :==: 1.4
+ 98           :[]: 3.50000000000001
+ 99           :generators: 3.50000000000001
+100         RailsClassMethods#validates_presence_of_with_object_daddy: 
+101           :is_a?: 1.4
+102           :assignment: 5.80000000000001
+103           :branch: 2.80000000000001
+104           :last: 1.6
+105           :dup: 1.4
+106           :pop: 1.5
+107           :each: 1.4
+108           :validates_presence_of_without_object_daddy: 1.4
+109         ClassMethods#presence_validated_attributes: 
+110           :merge: 1.5
+111           :presence_validated_attributes: 1.7
+112           :assignment: 4.30000000000001
+113           :respond_to?: 1.4
+114           :superclass: 3.50000000000001
+115           :branch: 1.4
+116         ClassMethods#spawn: 
+117           :presence_validated_attributes: 5.4
+118           :each_pair: 1.4
+119           :assignment: 35.3
+120           :generate: 1.7
+121           :class_name: 2.1
+122           :call: 1.8
+123           :reflect_on_all_associations: 1.8
+124           :branch: 24.0
+125           :constantize: 1.9
+126           :name: 3.9
+127           :gather_exemplars: 1.4
+128           :select: 1.6
+129           :-: 1.8
+130           :send: 5.4
+131           :to_a: 1.6
+132           :empty?: 1.5
+133           :new: 1.4
+134           :reject!: 1.7
+135           :next: 1.9
+136           :delete: 1.9
+137           :include?: 1.8
+138           :primary_key_name: 4.2
+139           :to_s: 5.7
+140           :each: 3.2
+141           :keys: 4.0
+142           :[]: 23.6
+143           :generators: 1.7
+144           :scope: 1.6
+145         RailsClassMethods#generate!: 
+146           :save!: 1.4
+147           :assignment: 2.80000000000001
+148           :spawn: 1.4
+149         YAML
+150         
+151         @totals = YAML.load(<<-YAML)
+152         --- 
+153         RailsClassMethods#generate: 3.95979797464467
+154         ObjectDaddy#included: 23.0471256342304
+155         ClassMethods#generator_for: 59.7115776043475
+156         RailsClassMethods#exemplar_path: 1.4
+157         ClassMethods#underscore: 3.00000000000001
+158         ClassMethods#none: 5.2
+159         ClassMethods#gather_exemplars: 23.8882816460289
+160         ClassMethods#record_generator_for: 10.4980950652964
+161         main#none: 7.37737249974544
+162         Foo#initialize: 1.2
+163         ClassMethods#spawn: 96.0108847995893
+164         ClassMethods#presence_validated_attributes: 9.27685291464731
+165         RailsClassMethods#validates_presence_of_with_object_daddy: 10.8245092267502
+166         RailsClassMethods#generate!: 3.95979797464467
+167         YAML
+168       end
+169     
+170       it 'should not fail when flogging the given input' do
+171         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
+172       end
+173 
+174       currently 'should report an overall flog score of 259.354295339925' do
+175         @flog.flog_files(fixture_files(@files))
+176         @flog.total.should be_close(259.354295339925, 0.0000000001)
+177       end
+178       
+179       currently 'should compute the same call data as flog-1.1.0' do
+180         @flog.flog_files(fixture_files(@files))
+181         @flog.calls.each_pair do |k,v|
+182           v.each_pair do |x, y|
+183             @calls[k][x].should be_close(y, 0.0000000001)
+184           end
+185         end
+186       end
+187 
+188       currently 'should compute the same totals data as flog-1.1.0' do
+189         @flog.flog_files(fixture_files(@files))        
+190         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
+191       end
+192     end
+193   
+194     describe 'when given a directory of files' do
+195       before :each do
+196         @files = ['/directory/']
+197         @calls = YAML.load(<<-YAML)
+198         --- 
+199         BotSender#validate: 
+200           :assignment: 1.3
+201         BotParserFormat#description: 
+202           :join: 1.3
+203           :branch: 1.2
+204           :empty?: 1.2
+205         BotParserFormat#initialize: 
+206           :assignment: 4.8
+207           :branch: 1.2
+208           :raise: 1.3
+209           :nil?: 1.2
+210         BotParser#parse: 
+211           :merge: 1.3
+212           :detect: 1.3
+213           :assignment: 6.7
+214           :branch: 3.9
+215           :empty?: 1.3
+216           :process: 1.4
+217           :formats: 1.5
+218         register_format#video: 
+219           :register_format: 1.2
+220           :assignment: 3.6
+221           :lit_fixnum: 1.05
+222           :[]: 3.6
+223         register_format#image: 
+224           :register_format: 1.2
+225           :assignment: 3.6
+226           :lit_fixnum: 1.05
+227           :[]: 3.6
+228         BotFilter#process: 
+229           :class: 1.6
+230           :options: 1.8
+231           :kinds: 1.4
+232           :assignment: 5.4
+233           :branch: 2.5
+234           :get: 1.8
+235           :process: 1.4
+236           :new: 1.6
+237           :each: 1.2
+238         BotFilter#register: 
+239           :<<: 1.8
+240         BotSender#deliver: 
+241           :respond_to?: 1.3
+242           :assignment: 2.7
+243           :send: 4.2
+244           :branch: 5.2
+245           :raise: 1.4
+246           :to_s: 1.5
+247           :to_sym: 1.3
+248           :[]: 4.5
+249         register_format#true_or_false: 
+250           :register_format: 1.2
+251           :assignment: 3.6
+252           :lit_fixnum: 0.35
+253           :[]: 1.2
+254         BotSender#none: 
+255           :assignment: 1.1
+256           :attr_reader: 1.2
+257         BotParser#clear_formats: 
+258           :assignment: 1.9
+259         BotSender#register: 
+260           :each_pair: 1.3
+261           :assignment: 6.90000000000001
+262           :branch: 1.3
+263         register_format#definition: 
+264           :register_format: 1.2
+265           :assignment: 3.6
+266           :lit_fixnum: 0.7
+267           :[]: 2.4
+268         register_format#link: 
+269           :register_format: 1.2
+270           :assignment: 3.6
+271           :lit_fixnum: 1.05
+272           :[]: 3.6
+273         BotParser#none: 
+274           :assignment: 1.2
+275           :sclass: 6.0
+276           :attr_reader: 1.8
+277         BotParser#register_format: 
+278           :<<: 1.9
+279           :new: 2.1
+280           :formats: 2.1
+281           :block_pass: 2.1
+282         BotSender#initialize: 
+283           :validate: 1.3
+284           :assignment: 2.6
+285           :[]: 1.3
+286         register_format#quote: 
+287           :register_format: 1.2
+288           :assignment: 3.6
+289           :lit_fixnum: 1.05
+290           :[]: 3.6
+291         BotFilter#register_filter: 
+292           :register: 1.8
+293           :load: 1.8
+294           :filter_path: 1.8
+295           :assignment: 1.8
+296           :exists?: 1.8
+297           :branch: 1.8
+298           :raise: 1.9
+299         BotSender#kinds: 
+300           :assignment: 1.4
+301           :sort_by: 1.3
+302           :branch: 1.3
+303           :to_s: 1.4
+304           :keys: 1.5
+305         main#none: 
+306           :require: 2.2
+307         BotFilter#new: 
+308           :locate_filters: 1.9
+309           :assignment: 3.6
+310           :send: 5.4
+311           :branch: 1.8
+312           :allocate: 1.8
+313         BotSender#new: 
+314           :kinds: 1.5
+315           :assignment: 2.6
+316           :send: 3.9
+317           :branch: 1.3
+318           :allocate: 1.3
+319           :raise: 1.4
+320           :include?: 1.3
+321           :[]: 4.7
+322         BotFilter#locate_filters: 
+323           :register_filter: 2.0
+324           :assignment: 2.0
+325           :branch: 5.5
+326           :each: 1.9
+327           :[]: 4.0
+328         BotFilter#get: 
+329           :gsub: 2.0
+330           :upcase: 2.1
+331           :assignment: 1.8
+332           :const_get: 1.8
+333           :branch: 2.0
+334           :to_sym: 1.8
+335           :to_s: 2.2
+336         BotParserFormat#none: 
+337           :attr_reader: 1.1
+338         BotFilter#filter_path: 
+339           :+: 2.0
+340           :dirname: 2.2
+341           :expand_path: 1.8
+342         BotParserFormat#process: 
+343           :merge: 1.2
+344           :call: 1.4
+345           :match: 1.2
+346           :format: 1.4
+347           :name: 1.4
+348           :assignment: 1.2
+349           :branch: 1.2
+350           :block: 1.6
+351         BotParser#formats: 
+352           :class: 1.5
+353           :formats: 1.3
+354         BotFilter#initialize: 
+355           :assignment: 2.4
+356         register_format#fact: 
+357           :register_format: 1.2
+358           :assignment: 3.6
+359           :lit_fixnum: 0.35
+360           :[]: 1.2
+361         BotFilter#none: 
+362           :sclass: 5.5
+363           :attr_reader: 1.1
+364         YAML
+365         
+366         @totals = YAML.load(<<-YAML)
+367         --- 
+368         BotFilter#register: 1.8
+369         BotFilter#process: 12.3308556069723
+370         register_format#image: 6.86895188511319
+371         register_format#video: 6.86895188511319
+372         BotParser#parse: 10.3121287811974
+373         BotParserFormat#initialize: 5.54346462061408
+374         BotParserFormat#description: 2.77308492477241
+375         BotSender#validate: 1.3
+376         register_format#true_or_false: 4.53017659699929
+377         BotSender#deliver: 15.3613150478727
+378         BotParser#clear_formats: 1.9
+379         BotSender#none: 1.62788205960997
+380         BotParser#none: 7.89176786277955
+381         register_format#link: 6.86895188511319
+382         register_format#definition: 5.60802995712398
+383         BotSender#register: 7.14072825417689
+384         BotParser#register_format: 8.2
+385         BotFilter#register_filter: 9.44933860119321
+386         register_format#quote: 6.86895188511319
+387         BotSender#initialize: 3.67695526217005
+388         BotFilter#new: 9.9503768772846
+389         main#none: 2.2
+390         BotSender#kinds: 4.61410879802373
+391         BotFilter#get: 10.2591422643416
+392         BotFilter#locate_filters: 9.83158176490437
+393         BotSender#new: 14.3965273590543
+394         BotFilter#filter_path: 6.0
+395         BotParserFormat#none: 1.1
+396         BotFilter#initialize: 2.4
+397         BotParser#formats: 2.8
+398         BotParserFormat#process: 8.37376856618333
+399         BotFilter#none: 6.6
+400         register_format#fact: 4.53017659699929
+401         YAML
+402       end
+403     
+404       it 'should not fail when flogging the given input' do
+405         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
+406       end
+407 
+408       currently 'should report an overall flog score of 209.977217342726' do
+409         @flog.flog_files(fixture_files(@files))
+410         @flog.total.should be_close(209.977217342726, 0.0000000001)        
+411       end
+412       
+413       currently 'should compute the same call data as flog-1.1.0' do
+414         @flog.flog_files(fixture_files(@files))
+415         @flog.calls.each_pair do |k,v|
+416           v.each_pair do |x, y|
+417             @calls[k][x].should be_close(y, 0.0000000001)
+418           end
+419         end
+420       end
+421 
+422       currently 'should compute the same totals data as flog-1.1.0' do
+423         @flog.flog_files(fixture_files(@files))
+424         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
+425       end
+426     end
+427   
+428     describe 'when given a collection of files' do
+429       before :each do
+430         @files = ['/collection/']  
+431         @calls = YAML.load(<<-YAML)
+432         --- 
+433         InstanceMethods#initialize_with_has_many_range_extension: 
+434           :returning: 1.3
+435           :initialize_without_has_many_range_extension: 1.5
+436           :macro: 1.90000000000001
+437           :add_has_many_range_extension: 1.70000000000001
+438           :branch: 2.80000000000001
+439           :puts: 6.00000000000002
+440           :==: 1.50000000000001
+441           :to_s: 1.70000000000001
+442         ClassMethods#calculate_with_range_restrictions: 
+443           :with_current_time_scope: 1.5
+444           :calculate_without_range_restrictions: 3.10000000000001
+445           :branch: 2.90000000000001
+446           :[]: 1.4
+447           :acts_as_range_configuration: 1.6
+448         InstanceMethods#contained_by?: 
+449           :to_range: 3.70000000000001
+450           :exclude_end?: 3.60000000000001
+451           :respond_to?: 1.3
+452           :last: 1.8
+453           :contained_by?: 1.5
+454           :branch: 18.5
+455           :>=: 1.9
+456           :acts_as_range_begin: 12.5
+457           :==: 3.20000000000001
+458           :include?: 2.90000000000001
+459           :acts_as_range_end: 14.4
+460           :<=: 1.9
+461         ClassMethods#sequentialized?: 
+462           :branch: 1.3
+463           :sequentialized_on: 1.3
+464         InstanceMethods#expired?: 
+465           :assignment: 1.3
+466           :branch: 1.3
+467           :now: 1.3
+468           :acts_as_range_end: 2.8
+469           :<=: 1.3
+470         ClassMethods#with_overlapping_scope: 
+471           :|: 3.00000000000001
+472           :with_containing_scope: 4.00000000000001
+473           :with_contained_scope: 1.8
+474           :flatten: 5.20000000000001
+475           :block_pass: 5.80000000000001
+476         ClassMethods#with_containing_scope: 
+477           :acts_as_range_begin_attr: 5.30000000000001
+478           :with_scope: 1.4
+479           :<<: 11.0
+480           :assignment: 4.20000000000001
+481           :join: 1.8
+482           :table_name: 10.6
+483           :branch: 2.80000000000001
+484           :acts_as_range_end_attr: 5.30000000000001
+485           :block_pass: 1.4
+486           :flatten: 1.4
+487           :nil?: 2.80000000000001
+488         ClassMethods#with_after_scope: 
+489           :acts_as_range_begin_attr: 3.20000000000001
+490           :with_scope: 1.4
+491           :table_name: 3.20000000000001
+492           :block_pass: 1.4
+493         InstanceMethods#overlapping?: 
+494           :is_a?: 1.4
+495           :first: 1.8
+496           :respond_to?: 1.3
+497           :last: 1.8
+498           :assignment: 3.20000000000001
+499           :contained_by?: 1.4
+500           :containing?: 7.80000000000002
+501           :branch: 11.3
+502           :acts_as_range_begin: 3.30000000000001
+503           :acts_as_range_end: 3.30000000000001
+504         ClassMethods#acts_as_date_range_sequentialize_class: 
+505           :acts_as_date_range_param_sequentialize_class: 1.4
+506           :acts_as_date_range_singleton_sequentialize_class: 1.4
+507           :branch: 1.3
+508           :flatten!: 1.3
+509           :==: 1.3
+510         ClassMethods#acts_as_date_range_param_sequentialize_class: 
+511           :validate_on_create: 1.3
+512           :add: 1.6
+513           :count: 1.7
+514           :>: 1.5
+515           :acts_as_range_begin_attr: 3.9
+516           :class: 3.8
+517           :extend: 2.6
+518           :errors: 1.8
+519           :assignment: 5.80000000000001
+520           :before_validation_on_create: 1.3
+521           :branch: 6.90000000000001
+522           :before_create: 1.3
+523           :now: 1.5
+524           :acts_as_range_begin: 6.00000000000001
+525           :to_sql: 4.2
+526           :acts_as_range_end_attr: 4.2
+527           :each: 1.5
+528           :expire: 1.6
+529           :find: 1.7
+530           :flatten: 3.8
+531           :to_attributes_for: 4.2
+532         InstanceMethods#destroy_without_callbacks: 
+533           :class: 3.8
+534           :default_timezone: 1.8
+535           :freeze: 1.3
+536           :new_record?: 1.3
+537           :update_all: 1.6
+538           :assignment: 1.6
+539           :send: 5.4
+540           :branch: 4.3
+541           :now: 3.6
+542           :acts_as_range_end_attr: 2.0
+543           :id: 2.0
+544           :utc: 1.7
+545           :==: 1.6
+546           :[]: 1.4
+547           :acts_as_range_configuration: 1.6
+548           :quote_value: 1.8
+549         ClassMethods#with_contained_scope: 
+550           :acts_as_range_begin_attr: 7.60000000000002
+551           :with_scope: 1.4
+552           :<<: 16.8
+553           :assignment: 4.20000000000001
+554           :join: 1.8
+555           :table_name: 15.2
+556           :branch: 4.40000000000001
+557           :acts_as_range_end_attr: 7.60000000000002
+558           :block_pass: 1.4
+559           :flatten: 1.4
+560           :nil?: 4.40000000000001
+561         ClassMethods#count_with_range_restrictions: 
+562           :count_without_range_restrictions: 3.10000000000001
+563           :with_current_time_scope: 1.5
+564           :branch: 2.90000000000001
+565           :[]: 1.4
+566           :acts_as_range_configuration: 1.6
+567         InstanceMethods#to_range: 
+568           :assignment: 2.60000000000001
+569           :acts_as_range_begin: 1.3
+570           :acts_as_range_end: 1.3
+571         ParamExtension#to_attributes_for: 
+572           :attributes: 1.7
+573           :assignment: 1.5
+574           :branch: 1.4
+575           :[]: 1.5
+576           :to_s: 1.7
+577           :collect: 1.4
+578         ClassMethods#with_current_time_scope: 
+579           :first: 3.3
+580           :respond_to?: 2.7
+581           :call: 2.7
+582           :with_overlapping_scope: 2.9
+583           :end_dated_association_date: 3.1
+584           :last: 3.3
+585           :assignment: 2.7
+586           :with_containing_scope: 2.9
+587           :branch: 2.7
+588           :block_pass: 5.80000000000001
+589         InstanceMethods#included: 
+590           :extend: 5.20000000000001
+591         DateRanged#current: 
+592           :containing: 1.1
+593           :now: 1.3
+594         ClassMethods#with_before_scope: 
+595           :with_scope: 1.4
+596           :table_name: 3.20000000000001
+597           :acts_as_range_end_attr: 3.20000000000001
+598           :block_pass: 1.4
+599         ClassMethods#remove_args: 
+600           :first: 1.5
+601           :>: 1.4
+602           :last: 2.0
+603           :<<: 1.4
+604           :extract_options_from_args!: 1.4
+605           :assignment: 2.90000000000001
+606           :branch: 2.80000000000001
+607           :length: 1.6
+608           :delete: 1.5
+609           :keys: 1.8
+610           :each: 1.4
+611         ClassMethods#add_args: 
+612           :merge: 1.6
+613           :<<: 1.4
+614           :extract_options_from_args!: 1.8
+615         InstanceMethods#before?: 
+616           :respond_to?: 1.3
+617           :branch: 3.90000000000001
+618           :<: 1.3
+619           :before?: 1.4
+620           :acts_as_range_begin: 1.6
+621           :acts_as_range_end: 2.80000000000001
+622         InstanceMethods#containing?: 
+623           :to_range: 8.50000000000001
+624           :is_a?: 1.4
+625           :exclude_end?: 6.30000000000001
+626           :>: 2.0
+627           :first: 4.00000000000001
+628           :respond_to?: 1.3
+629           :assignment: 3.20000000000001
+630           :last: 10.7
+631           :contained_by?: 1.4
+632           :branch: 28.0
+633           :acts_as_range_begin: 8.90000000000002
+634           :==: 5.90000000000001
+635           :include?: 5.20000000000001
+636           :acts_as_range_end: 13.1
+637           :<=: 3.70000000000001
+638         ClassMethods#acts_as_date_range: 
+639           :acts_as_range: 1.3
+640           :is_a?: 1.3
+641           :assignment: 1.3
+642           :acts_as_date_range?: 1.3
+643           :acts_as_date_range_configure_class: 1.3
+644           :branch: 2.6
+645           :update: 1.5
+646           :raise: 1.4
+647         InstanceMethods#limit_date_range: 
+648           :end_dated_association_date: 1.4
+649           :assignment: 6.9
+650           :branch: 1.4
+651           :yield: 1.4
+652           :new: 1.4
+653           :acts_as_range_begin: 1.4
+654           :acts_as_range_end: 1.4
+655         InstanceMethods#lifetime: 
+656           :>: 1.4
+657           :assignment: 1.3
+658           :branch: 5.4
+659           :now: 1.3
+660           :acts_as_range_begin: 4.6
+661           :acts_as_range_end: 3.2
+662           :distance_of_time_in_words: 1.3
+663           :nil?: 2.7
+664         ClassMethods#validates_interval: 
+665           :validation_method: 1.6
+666           :add: 1.80000000000001
+667           :errors: 2.00000000000001
+668           :evaluate_condition: 1.6
+669           :assignment: 9.30000000000003
+670           :send: 4.20000000000001
+671           :branch: 10.9
+672           :acts_as_range_begin: 1.70000000000001
+673           :acts_as_range_end: 1.70000000000001
+674           :each: 1.3
+675           :humanize: 2.60000000000001
+676           :to_s: 3.00000000000001
+677           :[]: 12.3
+678           :acts_as_range_configuration: 6.00000000000001
+679           :<=: 1.90000000000001
+680           :nil?: 3.70000000000001
+681         ClassMethods#acts_as_range: 
+682           :is_a?: 1.3
+683           :class_inheritable_reader: 1.3
+684           :assignment: 1.3
+685           :acts_as_range_configure_class: 1.3
+686           :branch: 2.60000000000001
+687           :update: 1.5
+688           :raise: 1.4
+689           :acts_as_range?: 1.3
+690         ParamExtension#to_sql: 
+691           :assignment: 1.7
+692           :join: 1.4
+693           :branch: 1.6
+694           :collect: 1.6
+695         ClassMethods#none: 
+696           :protected: 3.70000000000001
+697           :assignment: 1.4
+698           :branch: 2.70000000000001
+699           :[]: 1.5
+700           :to_sym: 1.7
+701           :acts_as_range_configuration: 1.7
+702           :define_method: 7.00000000000002
+703           :each: 1.3
+704         DateRange#included: 
+705           :respond_to?: 1.2
+706           :extend: 2.4
+707           :assignment: 1.4
+708           :branch: 2.6
+709           :now: 1.5
+710           :new: 1.4
+711           :attr: 1.9
+712           :sclass: 7.0
+713         DateRange#none: 
+714           :include: 2.2
+715         InstanceMethods#add_has_many_range_extension: 
+716           :options: 1.50000000000001
+717           :assignment: 6.00000000000002
+718           :push: 1.60000000000001
+719           :branch: 2.80000000000001
+720           :puts: 5.40000000000002
+721           :acts_as_range?: 1.3
+722           :include?: 1.50000000000001
+723           :[]: 5.20000000000002
+724           :klass: 3.00000000000001
+725           :flatten: 1.50000000000001
+726         Ranged#included: 
+727           :alias_method_chain: 1.3
+728           :branch: 1.2
+729           :send: 3.60000000000001
+730           :puts: 1.2
+731           :instance_eval: 6.00000000000002
+732         Range#included: 
+733           :respond_to?: 1.2
+734           :extend: 2.4
+735           :assignment: 1.4
+736           :branch: 2.6
+737           :now: 1.5
+738           :new: 1.4
+739           :attr: 1.9
+740           :sclass: 7.00000000000001
+741         InstanceMethods#include?: 
+742           :class: 3.2
+743           :branch: 5.40000000000001
+744           :id: 3.2
+745           :find: 2.8
+746         ClassMethods#acts_as_range?: 
+747           :included_modules: 1.5
+748           :include?: 1.3
+749         ClassMethods#acts_as_date_range_configure_class: 
+750           :acts_as_date_range_sequentialize_class: 1.4
+751           :assignment: 1.3
+752           :write_inheritable_attribute: 1.3
+753           :branch: 1.3
+754           :[]: 2.9
+755           :include: 2.6
+756         InstanceMethods#none: 
+757           :+: 3.8
+758           :class: 9.20000000000001
+759           :assignment: 5.60000000000001
+760           :private: 1.2
+761           :send: 43.2
+762           :branch: 8.00000000000001
+763           :alias_method: 4.80000000000001
+764           :to_s: 4.2
+765           :to_sym: 6.80000000000001
+766           :define_method: 28.0
+767           :each: 2.4
+768         Ranged#none: 
+769           :+: 1.7
+770           :assignment: 3.60000000000001
+771           :select: 1.2
+772           :send: 3.90000000000001
+773           :branch: 3.30000000000001
+774           :to_sym: 1.5
+775           :define_method: 5.50000000000002
+776           :each: 1.0
+777         ClassMethods#acts_as_range_configure_class: 
+778           :assignment: 3.20000000000001
+779           :write_inheritable_attribute: 1.3
+780           :alias_method_chain: 1.90000000000001
+781           :branch: 1.8
+782           :validates_interval: 1.3
+783           :to_sym: 2.1
+784           :each: 1.8
+785           :sclass: 6.50000000000002
+786           :include: 2.60000000000001
+787         ClassMethods#ranged_lookup: 
+788           :first: 1.5
+789           :respond_to?: 1.4
+790           :last: 1.5
+791           :assignment: 7.00000000000002
+792           :-: 1.7
+793           :branch: 2.80000000000001
+794           :to_a: 1.5
+795           :yield: 1.4
+796           :new: 3.80000000000001
+797           :acts_as_range_begin: 1.5
+798           :acts_as_range_end: 1.5
+799         ClassMethods#find_with_range_restrictions: 
+800           :find_without_range_restrictions: 9.80000000000002
+801           :with_current_time_scope: 1.5
+802           :remove_args: 7.50000000000002
+803           :with_before_scope: 1.5
+804           :extract_options_from_args!: 1.4
+805           :assignment: 12.8
+806           :with_containing_scope: 1.5
+807           :send: 5.40000000000001
+808           :with_after_scope: 1.5
+809           :branch: 19.7
+810           :dup: 1.4
+811           :ranged_lookup: 1.7
+812           :acts_as_range_configuration: 1.6
+813           :==: 1.7
+814           :each: 1.4
+815           :keys: 9.90000000000002
+816           :[]: 12.1
+817           :has_key?: 5.70000000000001
+818         InstanceMethods#after?: 
+819           :>: 1.3
+820           :respond_to?: 1.3
+821           :branch: 3.90000000000001
+822           :acts_as_range_begin: 2.80000000000001
+823           :after?: 1.4
+824           :acts_as_range_end: 1.6
+825         ClassMethods#acts_as_date_range_singleton_sequentialize_class: 
+826           :validate_on_create: 1.3
+827           :add: 1.6
+828           :count: 1.7
+829           :>: 1.5
+830           :acts_as_range_begin_attr: 3.7
+831           :class: 3.8
+832           :errors: 1.8
+833           :assignment: 5.8
+834           :before_validation_on_create: 1.3
+835           :branch: 6.90000000000001
+836           :before_create: 1.3
+837           :now: 1.5
+838           :acts_as_range_begin: 5.6
+839           :acts_as_range_end_attr: 3.8
+840           :each: 1.5
+841           :expire: 1.6
+842           :find: 1.7
+843         ClassMethods#acts_as_date_range?: 
+844           :included_modules: 1.5
+845           :include?: 1.3
+846         InstanceMethods#expire: 
+847           :second: 1.6
+848           :is_a?: 2.7
+849           :save!: 1.3
+850           :ago: 1.4
+851           :assignment: 4.2
+852           :-: 1.5
+853           :branch: 4.0
+854           :now: 1.3
+855           :lit_fixnum: 0.875
+856           :acts_as_range_end: 1.3
+857         ClassMethods#sequentialized_on: 
+858           :[]: 1.3
+859           :acts_as_range_configuration: 1.5
+860         YAML
+861         
+862         @totals = YAML.load(<<-YAML)
+863         --- 
+864         InstanceMethods#expired?: 5.70438427878067
+865         ClassMethods#sequentialized?: 1.83847763108502
+866         InstanceMethods#contained_by?: 52.0954892481106
+867         ClassMethods#calculate_with_range_restrictions: 8.13449445263812
+868         InstanceMethods#initialize_with_has_many_range_extension: 15.8492902049272
+869         InstanceMethods#destroy_without_callbacks: 31.238757977871
+870         ClassMethods#acts_as_date_range_param_sequentialize_class: 50.3140139523772
+871         ClassMethods#acts_as_date_range_sequentialize_class: 5.55427763079954
+872         InstanceMethods#overlapping?: 25.0267856505785
+873         ClassMethods#with_after_scope: 9.20000000000002
+874         ClassMethods#with_containing_scope: 41.3095630574811
+875         ClassMethods#with_overlapping_scope: 19.8
+876         InstanceMethods#included: 5.20000000000001
+877         ClassMethods#with_current_time_scope: 26.9716517847907
+878         ParamExtension#to_attributes_for: 6.62570750939099
+879         InstanceMethods#to_range: 3.67695526217005
+880         ClassMethods#count_with_range_restrictions: 8.13449445263812
+881         ClassMethods#with_contained_scope: 57.9202900545225
+882         InstanceMethods#lifetime: 15.5273951453552
+883         InstanceMethods#limit_date_range: 9.92824254337091
+884         ClassMethods#acts_as_date_range: 8.60581198958007
+885         InstanceMethods#containing?: 77.6916983982203
+886         InstanceMethods#before?: 9.2612094242599
+887         ClassMethods#add_args: 4.80000000000001
+888         ClassMethods#remove_args: 14.5688022843335
+889         ClassMethods#with_before_scope: 9.20000000000002
+890         DateRanged#current: 2.40000000000001
+891         DateRange#none: 2.2
+892         DateRange#included: 15.6805612144464
+893         ClassMethods#none: 17.171487996094
+894         ParamExtension#to_sql: 3.80131556174965
+895         ClassMethods#acts_as_range: 8.6058119895801
+896         ClassMethods#validates_interval: 47.6073523733468
+897         Range#included: 15.6805612144464
+898         Ranged#included: 12.1593585357124
+899         InstanceMethods#add_has_many_range_extension: 22.0190826330255
+900         InstanceMethods#include?: 10.6677082824757
+901         InstanceMethods#none: 104.05921391208
+902         ClassMethods#acts_as_date_range_configure_class: 8.40357066966181
+903         ClassMethods#acts_as_range?: 2.80000000000001
+904         InstanceMethods#expire: 13.3056613890479
+905         ClassMethods#acts_as_date_range?: 2.8
+906         ClassMethods#acts_as_date_range_singleton_sequentialize_class: 34.8846671189507
+907         InstanceMethods#after?: 9.2612094242599
+908         ClassMethods#find_with_range_restrictions: 69.6799110217573
+909         ClassMethods#ranged_lookup: 17.5065701952153
+910         ClassMethods#acts_as_range_configure_class: 17.8809954980141
+911         Ranged#none: 15.5849286170968
+912         ClassMethods#sequentialized_on: 2.8
+913         YAML
+914       end
+915 
+916       it 'should not fail when flogging the given input' do
+917         lambda { @flog.flog_files(fixture_files(@files)) }.should_not raise_error
+918       end
+919 
+920       currently 'should report an overall flog score of 981.137760580242' do
+921         @flog.flog_files(fixture_files(@files))
+922         @flog.total.should be_close(981.137760580242, 0.0000000001)
+923       end
+924       
+925       currently 'should compute the same call data as flog-1.1.0' do
+926         @flog.flog_files(fixture_files(@files))
+927         @flog.calls.each_pair do |k,v|
+928           v.each_pair do |x, y|
+929             @calls[k][x].should be_close(y, 0.0000000001)
+930           end
+931         end
+932       end
+933 
+934       currently 'should compute the same totals data as flog-1.1.0' do
+935         @flog.flog_files(fixture_files(@files))
+936         @flog.totals.each_pair {|k,v| v.should be_close(@totals[k], 0.0000000001) }
+937       end
+938     end
+939   end
+940 end
 

Generated using the rcov code coverage analysis tool for Ruby version 0.8.1.2.

diff --git a/coverage/spec-flog_spec_rb.html b/coverage/spec-flog_spec_rb.html index 08c64dd..42b5ac5 100644 --- a/coverage/spec-flog_spec_rb.html +++ b/coverage/spec-flog_spec_rb.html @@ -553,7 +553,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:36 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:51 -0500 2008 with rcov 0.8.1.2


Code reported as executed by Ruby looks like this...
@@ -571,9 +571,9 @@
     
   
spec/flog_spec.rb 1103 + 1115 906 + 915 @@ -598,1109 +598,1121 @@
100.0%  
-
   1 require File.dirname(__FILE__) + '/spec_helper.rb'
-   2 require 'flog'
-   3 require 'sexp_processor'
-   4 
-   5 describe Flog do
-   6   before :each do
-   7     @options = { }
-   8     @flog = Flog.new(@options)
-   9   end
-  10 
-  11   describe 'when initializing' do
-  12     it 'should require options arguments' do
-  13       lambda { Flog.new }.should raise_error(ArgumentError)
-  14     end
-  15     
-  16     it 'should not reference the parse tree' do
-  17       ParseTree.expects(:new).never
-  18       Flog.new(@options)
-  19     end
-  20   end
-  21   
-  22   describe 'after initializing' do
-  23     it 'should have options set' do
-  24       @flog.options.should == @options
-  25     end
-  26 
-  27     it 'should return an SexpProcessor' do
-  28       @flog.should be_a_kind_of(SexpProcessor)
-  29     end
-  30     
-  31     it 'should be initialized like all SexpProcessors' do
-  32       # less than ideal means of insuring the Flog instance was initialized properly, imo -RB
-  33       @flog.context.should == []  
-  34     end
-  35     
-  36     it 'should have no current class' do
-  37       @flog.class_name.should == :main
-  38     end
-  39     
-  40     it 'should have no current method' do
-  41       @flog.method_name.should == :none
-  42     end
-  43     
-  44     it 'should not have any calls yet' do
-  45       @flog.calls.should == {}
-  46     end
-  47     
-  48     it 'should have a means of accessing its parse tree' do
-  49       @flog.should respond_to(:parse_tree)
-  50     end
-  51     
-  52     it 'should not have any totals yet' do
-  53       @flog.totals.should == {}
-  54     end
-  55     
-  56     it 'should have a 0 total score' do
-  57       @flog.total.should == 0.0
-  58     end
-  59     
-  60     it 'should have a multiplier of 1' do
-  61       @flog.multiplier.should == 1.0
-  62     end
-  63     
-  64     currently "should have 'auto shift type' set to true" do
-  65       @flog.auto_shift_type.should be_true
-  66     end
-  67 
-  68     currently "should have 'require empty' set to false" do
-  69       @flog.require_empty.should be_false
-  70     end
-  71   end
-  72   
-  73   describe 'options' do
-  74     it 'should return the current options settings' do
-  75       @flog.should respond_to(:options)
-  76     end
-  77   end
-  78   
-  79   describe 'when accessing the parse tree' do
-  80     before :each do
-  81       @parse_tree = stub('parse tree')
-  82     end
-  83     
-  84     describe 'for the first time' do
-  85       it 'should create a new ParseTree' do
-  86         ParseTree.expects(:new)
-  87         @flog.parse_tree
-  88       end
-  89       
-  90       currently 'should leave newlines off when creating the ParseTree instance' do
-  91         ParseTree.expects(:new).with(false)
-  92         @flog.parse_tree
-  93       end
-  94       
-  95       it 'should return a ParseTree instance' do
-  96         ParseTree.stubs(:new).returns(@parse_tree)
-  97         @flog.parse_tree.should == @parse_tree
-  98       end
-  99     end
- 100     
- 101     describe 'after the parse tree has been initialized' do
- 102       it 'should not attempt to create a new ParseTree instance' do
- 103         @flog.parse_tree
- 104         ParseTree.expects(:new).never
- 105         @flog.parse_tree
- 106       end
- 107       
- 108       it 'should return a ParseTree instance' do
- 109         ParseTree.stubs(:new).returns(@parse_tree)
- 110         @flog.parse_tree
- 111         @flog.parse_tree.should == @parse_tree
- 112       end
- 113     end
- 114   end
- 115   
- 116   describe "when flogging a list of files" do
- 117     describe 'when no files are specified' do
- 118       currently 'should not raise an exception' do
- 119         lambda { @flog.flog_files }.should_not raise_error
- 120       end
- 121       
- 122       it 'should never call flog_file' do
- 123         @flog.expects(:flog_file).never
- 124         @flog.flog_files
- 125       end
- 126     end
- 127     
- 128     describe 'when files are specified' do
- 129       before :each do
- 130         @files = [1, 2, 3, 4]
- 131         @flog.stubs(:flog_file)
- 132       end
- 133       
- 134       it 'should do a flog for each individual file' do
- 135         @flog.expects(:flog_file).times(@files.size)
- 136         @flog.flog_files(@files)
- 137       end
- 138       
- 139       it 'should provide the filename when flogging a file' do
- 140         @files.each do |file|
- 141           @flog.expects(:flog_file).with(file)
- 142         end
- 143         @flog.flog_files(@files)          
- 144       end
- 145     end
- 146     
- 147     describe 'when flogging a single file' do
- 148       before :each do
- 149         @flog.stubs(:flog)
- 150       end
- 151       
- 152       describe 'when the filename is "-"' do
- 153         before :each do
- 154           @stdin = $stdin  # HERE: working through the fact that zenspider is using $stdin in the middle of the system
- 155           $stdin = stub('stdin', :read => 'data')
- 156         end
- 157 
- 158         after :each do
- 159           $stdin = @stdin
- 160         end
- 161         
- 162         describe 'when reporting blame information' do
- 163           before :each do
- 164             @flog = Flog.new(:blame => true)
- 165             @flog.stubs(:flog)
- 166           end
- 167           
- 168           it 'should fail' do
- 169             lambda { @flog.flog_file('-') }.should raise_error(RuntimeError)
- 170           end
- 171         end
- 172 
- 173         it 'should not raise an exception' do
- 174           lambda { @flog.flog_file('-') }.should_not raise_error
- 175         end
- 176 
- 177         it 'should read the data from stdin' do
- 178           $stdin.expects(:read).returns('data')
- 179           @flog.flog_file('-')
- 180         end
- 181         
- 182         it 'should flog the read data' do
- 183           @flog.expects(:flog).with('data', '-')
- 184           @flog.flog_file('-')
- 185         end
- 186         
- 187         describe 'when the verbose flag is on' do
- 188           before :each do
- 189             @flog = Flog.new(:verbose => true)
- 190           end
- 191           
- 192           it 'should note which file is being flogged' do
- 193             @flog.expects(:warn)
- 194             @flog.flog_file('-')
- 195           end
- 196         end
- 197         
- 198         describe 'when the verbose flag is off' do
- 199           before :each do
- 200             @flog = Flog.new({})
- 201           end
- 202           
- 203           it 'should not note which file is being flogged' do
- 204             @flog.expects(:warn).never
- 205             @flog.flog_file('-')
- 206           end          
- 207         end
- 208       end
- 209       
- 210       describe 'when the filename points to a directory' do
- 211         before :each do
- 212           @flog.stubs(:flog_directory)
- 213           @file = File.dirname(__FILE__)
- 214         end
- 215 
- 216         it 'should expand the files under the directory' do
- 217           @flog.expects(:flog_directory)
- 218           @flog.flog_file(@file)
- 219         end
- 220         
- 221         it 'should not read data from stdin' do
- 222           $stdin.expects(:read).never
- 223           @flog.flog_file(@file)          
- 224         end
- 225         
- 226         it 'should not flog any data' do
- 227           @flog.expects(:flog).never
- 228           @flog.flog_file(@file)
- 229         end
- 230       end
- 231       
- 232       describe 'when the filename points to a non-existant file' do
- 233         before :each do
- 234           @file = '/adfasdfasfas/fasdfaf-#{rand(1000000).to_s}'
- 235         end
- 236         
- 237         it 'should raise an exception' do
- 238           lambda { @flog.flog_file(@file) }.should raise_error(Errno::ENOENT)
- 239         end
- 240       end
- 241       
- 242       describe 'when the filename points to an existing file' do
- 243         before :each do
- 244           @file = __FILE__
- 245           File.stubs(:read).returns('data')
- 246         end
- 247         
- 248         it 'should read the contents of the file' do
- 249           File.expects(:read).with(@file).returns('data')
- 250           @flog.flog_file(@file)
- 251         end
- 252         
- 253         it 'should flog the contents of the file' do
- 254           @flog.expects(:flog).with('data', @file)
- 255           @flog.flog_file(@file)
- 256         end
- 257         
- 258         describe 'when the verbose flag is on' do
- 259           before :each do
- 260             @flog = Flog.new(:verbose => true)
- 261           end
- 262           
- 263           it 'should note which file is being flogged' do
- 264             @flog.expects(:warn)
- 265             @flog.flog_file(@file)
- 266           end
- 267         end
- 268         
- 269         describe 'when the verbose flag is off' do
- 270           before :each do
- 271             @flog = Flog.new({})
- 272           end
- 273           
- 274           it 'should not note which file is being flogged' do
- 275             @flog.expects(:warn).never
- 276             @flog.flog_file(@file)
- 277           end          
- 278         end
- 279       end
- 280     end
- 281   end
- 282 
- 283   describe 'when flogging a directory' do
- 284     before :each do
- 285       @files = ['a.rb', '/foo/b.rb', '/foo/bar/c.rb', '/foo/bar/baz/d.rb']
- 286       @dir = File.dirname(__FILE__)
- 287       Dir.stubs(:[]).returns(@files)
- 288     end
- 289     
- 290     it 'should get the list of ruby files under the directory' do
- 291       @flog.stubs(:flog_file)
- 292       Dir.expects(:[]).returns(@files)
- 293       @flog.flog_directory(@dir)
- 294     end
- 295     
- 296     it "should call flog_file once for each file in the directory" do
- 297       @files.each {|f| @flog.expects(:flog_file).with(f) }
- 298       @flog.flog_directory(@dir)
- 299     end
- 300   end
- 301 
- 302   describe 'when flogging a Ruby string' do
- 303     it 'should require both a Ruby string and a filename' do
- 304       lambda { @flog.flog('string') }.should raise_error(ArgumentError)
- 305     end
- 306     
- 307     describe 'when reporting blame information' do
- 308       before :each do
- 309         @flog = Flog.new(:blame => true)
- 310       end
- 311       
- 312       it 'should gather blame information for the file' do
- 313         @flog.expects(:collect_blame).with('filename')
- 314         @flog.flog('string', 'filename')
- 315       end
- 316     end
- 317     
- 318     describe 'when not reporting blame information' do
- 319       it 'should not gather blame information for the file' do
- 320         @flog.expects(:collect_blame).never 
- 321         @flog.flog('string', 'filename')
- 322       end
- 323     end
- 324     
- 325     describe 'when the string has a syntax error' do
- 326       before :each do
- 327         @flog.stubs(:warn)
- 328         @flog.stubs(:process_parse_tree).raises(SyntaxError.new("<% foo %>"))
- 329       end
- 330       
- 331       describe 'when the string has erb snippets' do
- 332         currently 'should warn about skipping' do
- 333           @flog.expects(:warn)
- 334           @flog.flog('string', 'filename')
- 335         end
- 336         
- 337         it 'should not raise an exception' do
- 338           lambda { @flog.flog('string', 'filename') }.should_not raise_error
- 339         end
- 340         
- 341         it 'should not process the failing code' do
- 342           @flog.expects(:process).never
- 343           @flog.flog('string', 'filename')
- 344         end
- 345       end
- 346       
- 347       describe 'when the string has no erb snippets' do
- 348         before :each do
- 349           @flog.stubs(:process_parse_tree).raises(SyntaxError)
- 350         end
- 351         
- 352         it 'should raise a SyntaxError exception' do
- 353           lambda { @flog.flog('string', 'filename') }.should raise_error(SyntaxError)
- 354         end
- 355         
- 356         it 'should not process the failing code' do
- 357           @flog.expects(:process).never
- 358           lambda { @flog.flog('string', 'filename') }
- 359         end
- 360       end
- 361     end
- 362     
- 363     describe 'when the string contains valid Ruby' do
- 364       before :each do
- 365         @flog.stubs(:process_parse_tree)
- 366       end
- 367       
- 368       it 'should process the parse tree for the string' do
- 369         @flog.expects(:process_parse_tree)
- 370         @flog.flog('string', 'filename')
- 371       end
- 372       
- 373       it 'should provide the string and the filename to the parse tree processor' do
- 374         @flog.expects(:process_parse_tree).with('string', 'filename')
- 375         @flog.flog('string', 'filename')
- 376       end
- 377     end
- 378   end
- 379   
- 380   describe 'when processing a ruby parse tree' do
- 381     before :each do
- 382       @flog.stubs(:process)
- 383       @sexp = stub('s-expressions')
- 384       @parse_tree = stub('parse tree', :parse_tree_for_string => @sexp)
- 385       ParseTree.stubs(:new).returns(@parse_tree)
- 386     end
- 387     
- 388     it 'should require both a ruby string and a filename' do
- 389       lambda { @flog.process_parse_tree('string') }.should raise_error(ArgumentError)
- 390     end
- 391     
- 392     it 'should compute the parse tree for the ruby string' do
- 393       Sexp.stubs(:from_array).returns(['1', '2'])
- 394       @parse_tree.expects(:parse_tree_for_string).returns(@sexp)
- 395       @flog.process_parse_tree('string', 'file')
- 396     end
- 397     
- 398     it 'should use both the ruby string and the filename when computing the parse tree' do
- 399       Sexp.stubs(:from_array).returns(['1', '2'])
- 400       @parse_tree.expects(:parse_tree_for_string).with('string', 'file').returns(@sexp)
- 401       @flog.process_parse_tree('string', 'file')      
- 402     end
- 403     
- 404     describe 'if the ruby string is valid' do
- 405       before :each do
- 406         @parse_tree = stub('parse tree', :parse_tree_for_string => @sexp)
- 407         @flog.stubs(:process)
- 408         @flog.stubs(:parse_tree).returns(@parse_tree)        
- 409       end
- 410       
- 411       it 'should convert the parse tree into a list of S-expressions' do
- 412         Sexp.expects(:from_array).with(@sexp).returns(['1', '2'])
- 413         @flog.process_parse_tree('string', 'file')
- 414       end
- 415       
- 416       it 'should process the list of S-expressions' do
- 417         @flog.expects(:process)
- 418         @flog.process_parse_tree('string', 'file')
- 419       end
- 420       
- 421       it 'should start processing at the first S-expression' do
- 422         Sexp.stubs(:from_array).returns(['1', '2'])
- 423         @flog.expects(:process).with('1')
- 424         @flog.process_parse_tree('string', 'file')        
- 425       end
- 426     end
- 427     
- 428     describe 'if the ruby string is invalid' do
- 429       before :each do
- 430         @parse_tree = stub('parse tree')
- 431         @flog.stubs(:parse_tree).returns(@parse_tree)        
- 432         @parse_tree.stubs(:parse_tree_for_string).raises(SyntaxError)
- 433       end
- 434       
- 435       it 'should fail' do
- 436         lambda { @flog.process_parse_tree('string', 'file') }.should raise_error(SyntaxError)
- 437       end
- 438       
- 439       it 'should not attempt to process the parse tree' do
- 440         @flog.expects(:process).never
- 441         lambda { @flog.process_parse_tree('string', 'file') }
- 442       end
- 443     end
- 444   end
- 445   
- 446   describe 'multiplier' do
- 447     it 'should be possible to determine the current value of the multiplier' do
- 448       @flog.should respond_to(:multiplier)
- 449     end
- 450   
- 451     it 'should be possible to set the current value of the multiplier' do
- 452       @flog.multiplier = 10
- 453       @flog.multiplier.should == 10
- 454     end
- 455   end
- 456   
- 457   describe 'class_stack' do
- 458     it 'should be possible to determine the current value of the class stack' do
- 459       @flog.should respond_to(:class_stack)
- 460     end
- 461   
- 462     it 'should be possible to set the current value of the class stack' do
- 463       @flog.class_stack = [ 'name' ]
- 464       @flog.class_stack.should == [ 'name' ]
- 465     end
- 466   end
- 467   
- 468   describe 'method_stack' do
- 469     it 'should be possible to determine the current value of the method stack' do
- 470       @flog.should respond_to(:method_stack)
- 471     end
- 472   
- 473     it 'should be possible to set the current value of the method stack' do
- 474       @flog.method_stack = [ 'name' ]
- 475       @flog.method_stack.should == [ 'name' ]
- 476     end
- 477   end
- 478   
- 479   describe 'when adding to the current flog score' do
- 480     before :each do
- 481       @flog.multiplier = 1
- 482       @flog.stubs(:class_name).returns('foo')
- 483       @flog.stubs(:method_name).returns('bar')
- 484       @flog.calls['foo#bar'] = { :alias => 0 }
- 485     end
- 486     
- 487     it 'should require an operation name' do
- 488       lambda { @flog.add_to_score() }.should raise_error(ArgumentError)
- 489     end
- 490     
- 491     it 'should update the score for the current class, method, and operation' do
- 492       @flog.add_to_score(:alias)
- 493       @flog.calls['foo#bar'][:alias].should_not == 0
- 494     end
- 495     
- 496     it 'should use the multiplier when updating the current call score' do
- 497       @flog.multiplier = 10
- 498       @flog.add_to_score(:alias)
- 499       @flog.calls['foo#bar'][:alias].should == 10*Flog::SCORES[:alias]
- 500     end
- 501   end
- 502   
- 503   describe 'when computing the average per-call flog score' do
- 504     it 'should not allow arguments' do
- 505       lambda { @flog.average('foo') }.should raise_error(ArgumentError)
- 506     end
- 507     
- 508     it 'should return the total flog score divided by the number of calls' do
- 509       @flog.stubs(:total).returns(100.0)
- 510       @flog.stubs(:calls).returns({ :bar => {}, :foo => {} })
- 511       @flog.average.should be_close(100.0/2, 0.00000000001)
- 512     end
- 513   end
- 514 
- 515   describe 'when recursively analyzing the complexity of code' do
- 516     it 'should require a complexity modifier value' do
- 517       lambda { @flog.penalize_by }.should raise_error(ArgumentError)
- 518     end
- 519     
- 520     it 'should require a block, for code to recursively analyze' do
- 521       lambda { @flog.penalize_by(42) }.should raise_error(LocalJumpError)
- 522     end
- 523     
- 524     it 'should recursively analyze the provided code block' do
- 525       @flog.penalize_by(42) do
- 526         @foo = true
- 527       end
- 528       
- 529       @foo.should be_true
- 530     end
- 531     
- 532     it 'should update the complexity multiplier when recursing' do
- 533       @flog.multiplier = 1
- 534       @flog.penalize_by(42) do
- 535         @flog.multiplier.should == 43
- 536       end
- 537     end
- 538     
- 539     it 'when it is done it should restore the complexity multiplier to its original value' do
- 540       @flog.multiplier = 1
- 541       @flog.penalize_by(42) do
- 542       end
- 543       @flog.multiplier.should == 1
- 544     end
- 545   end
- 546   
- 547   describe 'when computing complexity of all remaining opcodes' do
- 548     it 'should require a list of opcodes' do
- 549       lambda { @flog.analyze_list }.should raise_error(ArgumentError)
- 550     end
- 551     
- 552     it 'should process each opcode' do
- 553       @opcodes = [ :foo, :bar, :baz ]
- 554       @opcodes.each do |opcode|
- 555          @flog.expects(:process).with(opcode)
- 556       end
- 557       
- 558       @flog.analyze_list @opcodes
- 559     end
- 560   end
- 561   
- 562   describe 'when recording the current class being analyzed' do
- 563     it 'should require a class name' do
- 564       lambda { @flog.set_class }.should raise_error(ArgumentError)
- 565     end
- 566     
- 567     it 'should require a block during which the class name is in effect' do
- 568       lambda { @flog.set_class('name') }.should raise_error(LocalJumpError)
- 569     end
- 570     
- 571     it 'should recursively analyze the provided code block' do
- 572       @flog.set_class 'name' do
- 573         @foo = true
- 574       end
- 575       
- 576       @foo.should be_true
- 577     end
- 578     
- 579     it 'should update the class stack when recursing' do
- 580       @flog.class_stack = []
- 581       @flog.set_class 'name' do
- 582         @flog.class_stack.should == ['name']
- 583       end
- 584     end
- 585     
- 586     it 'when it is done it should restore the class stack to its original value' do
- 587       @flog.class_stack = []
- 588       @flog.set_class 'name' do
- 589       end
- 590       @flog.class_stack.should == []
- 591     end
- 592   end
- 593   
- 594   describe 'when looking up the name of the class currently under analysis' do
- 595     it 'should not take any arguments' do
- 596       lambda { @flog.class_name('foo') }.should raise_error(ArgumentError)
- 597     end
- 598     
- 599     it 'should return the most recent class entered' do
- 600       @flog.class_stack = [:foo, :bar, :baz]
- 601       @flog.class_name.should == :foo
- 602     end
- 603     
- 604     it 'should return the default class if no classes entered' do
- 605       @flog.class_stack = []
- 606       @flog.class_name.should == :main
- 607     end
- 608   end
- 609 
- 610   describe 'when recording the current method being analyzed' do
- 611     it 'should require a method name' do
- 612       lambda { @flog.set_method }.should raise_error(ArgumentError)
- 613     end
- 614     
- 615     it 'should require a block during which the class name is in effect' do
- 616       lambda { @flog.set_method('name') }.should raise_error(LocalJumpError)
- 617     end
- 618     
- 619     it 'should recursively analyze the provided code block' do
- 620       @flog.set_method 'name' do
- 621         @foo = true
- 622       end
- 623       
- 624       @foo.should be_true
- 625     end
- 626     
- 627     it 'should update the class stack when recursing' do
- 628       @flog.method_stack = []
- 629       @flog.set_method 'name' do
- 630         @flog.method_stack.should == ['name']
- 631       end
- 632     end
- 633     
- 634     it 'when it is done it should restore the class stack to its original value' do
- 635       @flog.method_stack = []
- 636       @flog.set_method 'name' do
- 637       end
- 638       @flog.method_stack.should == []
- 639     end
- 640   end
- 641 
- 642   describe 'when looking up the name of the method currently under analysis' do
- 643     it 'should not take any arguments' do
- 644       lambda { @flog.method_name('foo') }.should raise_error(ArgumentError)
- 645     end
- 646     
- 647     it 'should return the most recent class entered' do
- 648       @flog.method_stack = [:foo, :bar, :baz]
- 649       @flog.method_name.should == :foo
- 650     end
- 651     
- 652     it 'should return the default class if no classes entered' do
- 653       @flog.method_stack = []
- 654       @flog.method_name.should == :none
- 655     end
- 656   end
- 657   
- 658   describe 'when resetting state' do
- 659     it 'should not take any arguments' do
- 660       lambda { @flog.reset('foo') }.should raise_error(ArgumentError)
- 661     end
- 662     
- 663     it 'should clear any recorded totals data' do
- 664       @flog.totals['foo'] = 'bar'
- 665       @flog.reset
- 666       @flog.totals.should == {}
- 667     end
- 668         
- 669     it 'should clear the total score' do
- 670       # the only way I know to do this is to force the total score to be computed for actual code, then reset it
- 671       @flog.flog_files(fixture_files('/simple/simple.rb'))
- 672       @flog.reset
- 673       @flog.total.should == 0
- 674     end
- 675     
- 676     it 'should set the multiplier to 1.0' do
- 677       @flog.multiplier = 20.0
- 678       @flog.reset
- 679       @flog.multiplier.should == 1.0
- 680     end
- 681     
- 682     it 'should set clear any calls data' do
- 683       @flog.calls['foobar'] = 'yoda'
- 684       @flog.reset
- 685       @flog.calls.should == {}
- 686     end
- 687     
- 688     it 'should ensure that new recorded calls will get 0 counts without explicit initialization' do
- 689       @flog.reset
- 690       @flog.calls['foobar']['baz'] += 20
- 691       @flog.calls['foobar']['baz'].should == 20
- 692     end
- 693   end
- 694   
- 695   describe 'when retrieving the total score' do
- 696     it 'should take no arguments' do
- 697       lambda { @flog.total('foo') }.should raise_error(ArgumentError)
- 698     end
- 699     
- 700     it 'should return 0 if nothing has been analyzed' do
- 701       @flog.total.should == 0
- 702     end
- 703     
- 704     it 'should compute totals data when called the first time' do
- 705       @flog.expects(:totals)
- 706       @flog.total
- 707     end
- 708     
- 709     it 'should not recompute totals data when called after the first time' do
- 710       @flog.total
- 711       @flog.expects(:totals).never
- 712       @flog.total
- 713     end
- 714     
- 715     it 'should return the score from the analysis once files have been analyzed' do
- 716       @flog.flog_files(fixture_files('/simple/simple.rb'))
- 717       @flog.total.should_not == 0
- 718     end
- 719   end
- 720   
- 721   describe 'when computing a score for a method' do
- 722     it 'should require a hash of call tallies' do
- 723       lambda { @flog.score_method }.should raise_error(ArgumentError)
- 724     end
- 725     
- 726     it 'should return a score of 0 if no tallies are provided' do
- 727       @flog.score_method({}).should == 0.0
- 728     end
- 729     
- 730     it 'should compute the sqrt of summed squares for assignments, branches, and other tallies' do
- 731       @flog.score_method({
- 732         :assignment => 7,
- 733         :branch => 23,
- 734         :crap => 37
- 735       }).should be_close(Math.sqrt(7*7 + 23*23 + 37*37), 0.0000000001)
- 736     end
- 737   end
- 738   
- 739   describe 'when recording a total for a method' do
- 740     # guess what, @totals and @calls could be refactored to be first-class objects
- 741     it 'should require a method and a score' do
- 742       lambda { @flog.record_method_score('foo') }.should raise_error(ArgumentError)
- 743     end
- 744     
- 745     it 'should set the total score for the provided method' do
- 746       @flog.record_method_score('foo', 20)
- 747       @flog.totals['foo'].should == 20
- 748     end
- 749   end
- 750   
- 751   describe 'when updating the total flog score' do
- 752     it 'should require an amount to update by' do
- 753       lambda { @flog.increment_total_score_by }.should raise_error(ArgumentError)
- 754     end
- 755     
- 756     it 'should update the total flog score' do
- 757       @flog.increment_total_score_by 42
- 758       @flog.total.should == 42
- 759     end
- 760   end
- 761   
- 762   describe 'when compiling summaries for a method' do
- 763     before :each do
- 764       @tally = { :foo => 0.0 }
- 765       @method = 'foo'
- 766       @score = 42.0
- 767       
- 768       @flog.stubs(:score_method).returns(@score)
- 769       @flog.stubs(:record_method_score)
- 770       @flog.stubs(:increment_total_score_by)
- 771     end
- 772     
- 773     it 'should require a method name and a tally' do
- 774       lambda { @flog.summarize_method('foo') }.should raise_error(ArgumentError)
- 775     end
- 776     
- 777     it 'should compute a score for the method, based on the tally' do
- 778       @flog.expects(:score_method).with(@tally)
- 779       @flog.summarize_method(@method, @tally)
- 780     end
- 781     
- 782     it 'should record the score for the method' do
- 783       @flog.expects(:record_method_score).with(@method, @score)
- 784       @flog.summarize_method(@method, @tally)      
- 785     end
- 786     
- 787     it 'should update the overall flog score' do
- 788       @flog.expects(:increment_total_score_by).with(@score)
- 789       @flog.summarize_method(@method, @tally)            
- 790     end
- 791 
- 792     describe 'ignoring non-method code and given a non-method tally' do
- 793       it 'should not compute a score for the tally' do
- 794         @flog.expects(:score_method).never
- 795         @flog.summarize_method(@method, @tally)
- 796       end
- 797       
- 798       it 'should not record a score based on the tally' do
- 799         @flog.expects(:record_method_score).never
- 800         @flog.summarize_method(@method, @tally)      
- 801       end
- 802       
- 803       it 'should not update the overall flog score' do
- 804         @flog.expects(:increment_total_score_by).never
- 805         @flog.summarize_method(@method, @tally)            
- 806       end
- 807     end    
- 808   end
- 809   
- 810   describe 'when requesting totals' do
- 811     it 'should not accept any arguments' do
- 812       lambda { @flog.totals('foo') }.should raise_error(ArgumentError)
- 813     end
- 814     
- 815     describe 'when called the first time' do
- 816       it 'should access calls data' do
- 817         @flog.expects(:calls).returns({})
- 818         @flog.totals
- 819       end
- 820       
- 821       it "will compile a summary for each method from the method's tally" do
- 822         @calls = { :foo => 1.0, :bar => 2.0, :baz => 3.0 }
- 823         @flog.stubs(:calls).returns(@calls)
- 824         @calls.each do |meth, tally|
- 825           @flog.expects(:summarize_method).with(meth, tally)
- 826         end
- 827         @flog.totals
- 828       end
- 829       
- 830       it 'should return the totals data' do
- 831         @flog.totals.should == {}
- 832       end      
- 833     end
- 834     
- 835     describe 'when called after the first time' do
- 836       before :each do
- 837         @flog.totals
- 838       end
- 839       
- 840       it 'should not access calls data' do
- 841         @flog.expects(:calls).never
- 842         @flog.totals        
- 843       end
- 844       
- 845       it 'should not compile method summaries' do
- 846         @flog.expects(:summarize_method).never
- 847         @flog.totals
- 848       end
- 849       
- 850       it 'should return the totals data' do
- 851         @flog.totals.should == {}
- 852       end
- 853     end
- 854   end
- 855   
- 856   describe 'when producing a report summary' do
- 857     before :each do
- 858       @handle = stub('io handle)', :puts => nil)
- 859       @flog.stubs(:total).returns(@total_score = 42.0)
- 860       @flog.stubs(:average).returns(@average_score = 1.0)
- 861     end
- 862     
- 863     it 'should require an io handle' do
- 864       lambda { @flog.output_summary }.should raise_error(ArgumentError)
- 865     end
- 866 
- 867     it 'computes the total flog score' do
- 868       @flog.expects(:total).returns 42.0
- 869       @flog.output_summary(@handle)
- 870     end 
- 871     
- 872     it 'computes the average flog score' do
- 873       @flog.expects(:average).returns 1.0
- 874       @flog.output_summary(@handle)
- 875     end
- 876     
- 877     it 'outputs the total flog score to the handle' do
- 878       @handle.expects(:puts).with do |string|
- 879         string =~ Regexp.new(Regexp.escape("%.1f" % @total_score))
- 880       end
- 881       @flog.output_summary(@handle)
- 882     end
- 883     
- 884     it 'outputs the average flog score to the handle' do
- 885       @handle.expects(:puts).with do |string|
- 886         string =~ Regexp.new(Regexp.escape("%.1f" % @average_score))
- 887       end
- 888       @flog.output_summary(@handle)
- 889     end
- 890   end
- 891   
- 892   describe 'when producing a detailed call summary report' do
- 893     before :each do
- 894       @handle = stub('io handle)', :puts => nil)
- 895       @calls = { :foo => {}, :bar => {}, :baz => {} }
- 896       @totals = { :foo => 1, :bar => 2, :baz => 3 }
- 897       
- 898       @flog.stubs(:calls).returns(@calls)
- 899       @flog.stubs(:totals).returns(@totals)
- 900       @flog.stubs(:output_method_details).returns(5)
- 901     end
- 902     
- 903     it 'should require an i/o handle' do
- 904       lambda { @flog.output_details }.should raise_error(ArgumentError)
- 905     end
- 906     
- 907     it 'should allow a threshold on the amount of detail to report' do
- 908       lambda { @flog.output_details(@handle, 300) }.should_not raise_error(ArgumentError)
- 909     end
- 910       
- 911     it 'retrieves the set of total statistics' do
- 912       @flog.expects(:totals).returns(@totals)
- 913       @flog.output_details(@handle)
- 914     end
- 915     
- 916     it 'retrieves the set of call statistics' do
- 917       @flog.expects(:calls).returns({})
- 918       @flog.output_details(@handle)      
- 919     end
- 920 
- 921     it 'should output a method summary for each located method' do
- 922       @calls.each do |meth, list|
- 923         @flog.expects(:output_method_details).with(@handle, meth, list).returns(5)
- 924       end
- 925       @flog.output_details(@handle)
- 926     end
- 927     
- 928     describe 'if a threshold is provided' do
- 929       it 'should only output details for methods until the threshold is reached' do
- 930         @flog.expects(:output_method_details).with(@handle, :baz, {}).returns(5)
- 931         @flog.expects(:output_method_details).with(@handle, :bar, {}).returns(5)
- 932         @flog.expects(:output_method_details).with(@handle, :foo, {}).never
- 933         @flog.output_details(@handle, 10)
- 934       end
- 935     end
- 936     
- 937     describe 'if no threshold is provided' do
- 938       it 'should output details for all methods' do
- 939         @calls.each do |class_method, call_list|
- 940           @flog.expects(:output_method_details).with(@handle, class_method, call_list).returns(5)
- 941         end
- 942         @flog.output_details(@handle)
- 943       end
- 944     end
- 945   end
- 946   
- 947   describe 'when reporting the details for a specific method' do
- 948     before :each do
- 949       @handle = stub('i/o handle', :puts => nil)
- 950       @totals = { 'foo#foo' => 42.0, 'foo#none' => 12.0 }
- 951       @data = { :assign => 10, :branch => 5, :case => 3 }
- 952       @flog.stubs(:totals).returns(@totals)
- 953     end
- 954     
- 955     it 'should require an i/o handle, a method name, and method details' do
- 956       lambda { @flog.output_method_details('foo', 'bar') }.should raise_error(ArgumentError)
- 957     end
- 958         
- 959     describe 'and ignoring non-method code' do
- 960       before :each do
- 961         @flog = Flog.new(:methods => true)
- 962         @flog.stubs(:totals).returns(@totals)
- 963       end
- 964       
- 965       describe 'and given non-method data to summarize' do
- 966         it 'should not generate any output on the i/o handle' do
- 967           @handle.expects(:puts).never
- 968           @flog.output_method_details(@handle, 'foo#none', @data)
- 969         end
- 970       
- 971         it 'should return 0' do
- 972           @flog.output_method_details(@handle, 'foo#none', @data).should == 0.0
- 973         end
- 974       end
- 975       
- 976       describe 'and given method data to summarize' do
- 977         it 'should return the total complexity for the method' do
- 978           @flog.output_method_details(@handle, 'foo#foo', @data).should == 42.0
- 979         end
- 980         
- 981         it 'should output the overall total for the method' do
- 982           @handle.expects(:puts).with do |string| 
- 983             string =~ Regexp.new(Regexp.escape("%.1f" % 42.0))
- 984           end
- 985           @flog.output_method_details(@handle, 'foo#foo', @data)          
- 986         end
- 987         
- 988         it 'should output call details for each call for the method' do
- 989           @data.each do |call, count|
- 990             @handle.expects(:puts).with do |string| 
- 991               string =~ Regexp.new(Regexp.escape("%6.1f: %s" % [ count, call ]))
- 992             end
- 993           end
- 994           @flog.output_method_details(@handle, 'foo#foo', @data)          
- 995         end
- 996       end
- 997     end
- 998     
- 999     describe 'and not excluding non-method code' do
-1000       it 'should return the total complexity for the method' do
-1001         @flog.output_method_details(@handle, 'foo#foo', @data).should == 42.0
-1002       end
-1003       
-1004       it 'should output the overall total for the method' do
-1005         @handle.expects(:puts).with do |string| 
-1006           string =~ Regexp.new(Regexp.escape("%.1f" % 42.0))
-1007         end
-1008         @flog.output_method_details(@handle, 'foo#foo', @data)          
-1009       end
-1010       
-1011       it 'should output call details for each call for the method' do
-1012         @data.each do |call, count|
-1013           @handle.expects(:puts).with do |string| 
-1014             string =~ Regexp.new(Regexp.escape("%6.1f: %s" % [ count, call ]))
-1015           end
-1016         end
-1017         @flog.output_method_details(@handle, 'foo#foo', @data)          
-1018       end
-1019     end
-1020   end
-1021   
-1022   describe 'when generating a report' do
-1023     it 'allows specifying an i/o handle' do
-1024       lambda { @flog.report 'handle' }.should_not raise_error(ArgumentError)
-1025     end
-1026     
-1027     it 'allows running the report without a specified i/o handle' do
-1028       lambda { @flog.report }.should_not raise_error(ArgumentError)
-1029     end
-1030     
-1031     describe 'and no i/o handle is specified' do      
-1032       it 'defaults the io handle to stdout' do
-1033         @flog.expects(:output_summary).with($stdout)
-1034         @flog.report
-1035       end
-1036     end
-1037 
-1038     describe 'and producing a summary report' do
-1039       before :each do
-1040         @flog = Flog.new(:score => true)
-1041         @flog.stubs(:output_summary)
-1042       end
-1043       
-1044       it 'produces an output summary on the i/o handle' do
-1045         @flog.expects(:output_summary).with('handle')
-1046         @flog.report('handle')
-1047       end
-1048       
-1049       it 'does not output a detailed report' do
-1050         @flog.expects(:output_details).never
-1051         @flog.report('handle')
-1052       end
-1053       
-1054       it 'should reset statistics when finished' do
-1055         @flog.expects(:reset)
-1056         @flog.report('handle')
-1057       end
-1058     end
-1059     
-1060     describe 'and producing a full report' do
-1061       before :each do
-1062         @flog.stubs(:output_summary)
-1063         @flog.stubs(:output_details)
-1064       end
-1065       
-1066       it 'produces an output summary on the i/o handle' do
-1067         @flog.expects(:output_summary).with('handle')
-1068         @flog.report('handle')
-1069       end
-1070       
-1071       it 'should generate a detailed report of method complexity on the i/o handle' do
-1072         @flog.expects(:output_details).with {|handle, max| handle == 'handle' }
-1073         @flog.report('handle')
-1074       end
-1075 
-1076       describe 'when flogging all methods in the system' do
-1077         before :each do
-1078           @flog = Flog.new(:all => true)
-1079           @flog.stubs(:output_summary)
-1080           @flog.stubs(:output_details)
-1081         end
-1082         
-1083         it 'should not limit the detailed report' do
-1084           @flog.expects(:output_details).with('handle')
-1085           @flog.report('handle')
-1086         end
-1087       end
-1088       
-1089       describe 'when flogging only the most expensive methods in the system' do
-1090         it 'should limit the detailed report to the Flog threshold' do
-1091           @flog.stubs(:total).returns(3.45)
-1092           @flog.expects(:output_details).with('handle', 3.45 * 0.60)
-1093           @flog.report('handle')
-1094         end
-1095       end
-1096       
-1097       it 'should reset statistics when finished' do
-1098         @flog.expects(:reset)
-1099         @flog.report(@handle)
-1100       end
-1101     end
-1102   end
-1103 end
+
   1 require File.dirname(__FILE__) + '/spec_helper.rb'
+   2 require 'flog'
+   3 require 'sexp_processor'
+   4 
+   5 describe Flog do
+   6   before :each do
+   7     @options = { }
+   8     @flog = Flog.new(@options)
+   9   end
+  10 
+  11   describe 'when initializing' do
+  12     it 'should require options arguments' do
+  13       lambda { Flog.new }.should raise_error(ArgumentError)
+  14     end
+  15     
+  16     it 'should not reference the parse tree' do
+  17       ParseTree.expects(:new).never
+  18       Flog.new(@options)
+  19     end
+  20   end
+  21   
+  22   describe 'after initializing' do
+  23     it 'should have options set' do
+  24       @flog.options.should == @options
+  25     end
+  26 
+  27     it 'should return an SexpProcessor' do
+  28       @flog.should be_a_kind_of(SexpProcessor)
+  29     end
+  30     
+  31     it 'should be initialized like all SexpProcessors' do
+  32       # less than ideal means of insuring the Flog instance was initialized properly, imo -RB
+  33       @flog.context.should == []  
+  34     end
+  35     
+  36     it 'should have no current class' do
+  37       @flog.class_name.should == :main
+  38     end
+  39     
+  40     it 'should have no current method' do
+  41       @flog.method_name.should == :none
+  42     end
+  43     
+  44     it 'should not have any calls yet' do
+  45       @flog.calls.should == {}
+  46     end
+  47     
+  48     it 'should have a means of accessing its parse tree' do
+  49       @flog.should respond_to(:parse_tree)
+  50     end
+  51     
+  52     it 'should not have any totals yet' do
+  53       @flog.totals.should == {}
+  54     end
+  55     
+  56     it 'should have a 0 total score' do
+  57       @flog.total.should == 0.0
+  58     end
+  59     
+  60     it 'should have a multiplier of 1' do
+  61       @flog.multiplier.should == 1.0
+  62     end
+  63     
+  64     currently "should have 'auto shift type' set to true" do
+  65       @flog.auto_shift_type.should be_true
+  66     end
+  67 
+  68     currently "should have 'require empty' set to false" do
+  69       @flog.require_empty.should be_false
+  70     end
+  71   end
+  72   
+  73   describe 'options' do
+  74     it 'should return the current options settings' do
+  75       @flog.should respond_to(:options)
+  76     end
+  77   end
+  78   
+  79   describe 'when accessing the parse tree' do
+  80     before :each do
+  81       @parse_tree = stub('parse tree')
+  82     end
+  83     
+  84     describe 'for the first time' do
+  85       it 'should create a new ParseTree' do
+  86         ParseTree.expects(:new)
+  87         @flog.parse_tree
+  88       end
+  89       
+  90       currently 'should leave newlines off when creating the ParseTree instance' do
+  91         ParseTree.expects(:new).with(false)
+  92         @flog.parse_tree
+  93       end
+  94       
+  95       it 'should return a ParseTree instance' do
+  96         ParseTree.stubs(:new).returns(@parse_tree)
+  97         @flog.parse_tree.should == @parse_tree
+  98       end
+  99     end
+ 100     
+ 101     describe 'after the parse tree has been initialized' do
+ 102       it 'should not attempt to create a new ParseTree instance' do
+ 103         @flog.parse_tree
+ 104         ParseTree.expects(:new).never
+ 105         @flog.parse_tree
+ 106       end
+ 107       
+ 108       it 'should return a ParseTree instance' do
+ 109         ParseTree.stubs(:new).returns(@parse_tree)
+ 110         @flog.parse_tree
+ 111         @flog.parse_tree.should == @parse_tree
+ 112       end
+ 113     end
+ 114   end
+ 115   
+ 116   describe "when flogging a list of files" do
+ 117     describe 'when no files are specified' do
+ 118       currently 'should not raise an exception' do
+ 119         lambda { @flog.flog_files }.should_not raise_error
+ 120       end
+ 121       
+ 122       it 'should never call flog_file' do
+ 123         @flog.expects(:flog_file).never
+ 124         @flog.flog_files
+ 125       end
+ 126     end
+ 127     
+ 128     describe 'when files are specified' do
+ 129       before :each do
+ 130         @files = [1, 2, 3, 4]
+ 131         @flog.stubs(:flog_file)
+ 132       end
+ 133       
+ 134       it 'should do a flog for each individual file' do
+ 135         @flog.expects(:flog_file).times(@files.size)
+ 136         @flog.flog_files(@files)
+ 137       end
+ 138       
+ 139       it 'should provide the filename when flogging a file' do
+ 140         @files.each do |file|
+ 141           @flog.expects(:flog_file).with(file)
+ 142         end
+ 143         @flog.flog_files(@files)          
+ 144       end
+ 145     end
+ 146     
+ 147     describe 'when flogging a single file' do
+ 148       before :each do
+ 149         @flog.stubs(:flog)
+ 150       end
+ 151       
+ 152       describe 'when the filename is "-"' do
+ 153         before :each do
+ 154           @stdin = $stdin  # HERE: working through the fact that zenspider is using $stdin in the middle of the system
+ 155           $stdin = stub('stdin', :read => 'data')
+ 156         end
+ 157 
+ 158         after :each do
+ 159           $stdin = @stdin
+ 160         end
+ 161         
+ 162         describe 'when reporting blame information' do
+ 163           before :each do
+ 164             @flog = Flog.new(:blame => true)
+ 165             @flog.stubs(:flog)
+ 166           end
+ 167           
+ 168           it 'should fail' do
+ 169             lambda { @flog.flog_file('-') }.should raise_error(RuntimeError)
+ 170           end
+ 171         end
+ 172 
+ 173         it 'should not raise an exception' do
+ 174           lambda { @flog.flog_file('-') }.should_not raise_error
+ 175         end
+ 176 
+ 177         it 'should read the data from stdin' do
+ 178           $stdin.expects(:read).returns('data')
+ 179           @flog.flog_file('-')
+ 180         end
+ 181         
+ 182         it 'should flog the read data' do
+ 183           @flog.expects(:flog).with('data', '-')
+ 184           @flog.flog_file('-')
+ 185         end
+ 186         
+ 187         describe 'when the verbose flag is on' do
+ 188           before :each do
+ 189             @flog = Flog.new(:verbose => true)
+ 190           end
+ 191           
+ 192           it 'should note which file is being flogged' do
+ 193             @flog.expects(:warn)
+ 194             @flog.flog_file('-')
+ 195           end
+ 196         end
+ 197         
+ 198         describe 'when the verbose flag is off' do
+ 199           before :each do
+ 200             @flog = Flog.new({})
+ 201           end
+ 202           
+ 203           it 'should not note which file is being flogged' do
+ 204             @flog.expects(:warn).never
+ 205             @flog.flog_file('-')
+ 206           end          
+ 207         end
+ 208       end
+ 209       
+ 210       describe 'when the filename points to a directory' do
+ 211         before :each do
+ 212           @flog.stubs(:flog_directory)
+ 213           @file = File.dirname(__FILE__)
+ 214         end
+ 215 
+ 216         it 'should expand the files under the directory' do
+ 217           @flog.expects(:flog_directory)
+ 218           @flog.flog_file(@file)
+ 219         end
+ 220         
+ 221         it 'should not read data from stdin' do
+ 222           $stdin.expects(:read).never
+ 223           @flog.flog_file(@file)          
+ 224         end
+ 225         
+ 226         it 'should not flog any data' do
+ 227           @flog.expects(:flog).never
+ 228           @flog.flog_file(@file)
+ 229         end
+ 230       end
+ 231       
+ 232       describe 'when the filename points to a non-existant file' do
+ 233         before :each do
+ 234           @file = '/adfasdfasfas/fasdfaf-#{rand(1000000).to_s}'
+ 235         end
+ 236         
+ 237         it 'should raise an exception' do
+ 238           lambda { @flog.flog_file(@file) }.should raise_error(Errno::ENOENT)
+ 239         end
+ 240       end
+ 241       
+ 242       describe 'when the filename points to an existing file' do
+ 243         before :each do
+ 244           @file = __FILE__
+ 245           File.stubs(:read).returns('data')
+ 246         end
+ 247         
+ 248         it 'should read the contents of the file' do
+ 249           File.expects(:read).with(@file).returns('data')
+ 250           @flog.flog_file(@file)
+ 251         end
+ 252         
+ 253         it 'should flog the contents of the file' do
+ 254           @flog.expects(:flog).with('data', @file)
+ 255           @flog.flog_file(@file)
+ 256         end
+ 257         
+ 258         describe 'when the verbose flag is on' do
+ 259           before :each do
+ 260             @flog = Flog.new(:verbose => true)
+ 261           end
+ 262           
+ 263           it 'should note which file is being flogged' do
+ 264             @flog.expects(:warn)
+ 265             @flog.flog_file(@file)
+ 266           end
+ 267         end
+ 268         
+ 269         describe 'when the verbose flag is off' do
+ 270           before :each do
+ 271             @flog = Flog.new({})
+ 272           end
+ 273           
+ 274           it 'should not note which file is being flogged' do
+ 275             @flog.expects(:warn).never
+ 276             @flog.flog_file(@file)
+ 277           end          
+ 278         end
+ 279       end
+ 280     end
+ 281   end
+ 282 
+ 283   describe 'when flogging a directory' do
+ 284     before :each do
+ 285       @files = ['a.rb', '/foo/b.rb', '/foo/bar/c.rb', '/foo/bar/baz/d.rb']
+ 286       @dir = File.dirname(__FILE__)
+ 287       Dir.stubs(:[]).returns(@files)
+ 288     end
+ 289     
+ 290     it 'should get the list of ruby files under the directory' do
+ 291       @flog.stubs(:flog_file)
+ 292       Dir.expects(:[]).returns(@files)
+ 293       @flog.flog_directory(@dir)
+ 294     end
+ 295     
+ 296     it "should call flog_file once for each file in the directory" do
+ 297       @files.each {|f| @flog.expects(:flog_file).with(f) }
+ 298       @flog.flog_directory(@dir)
+ 299     end
+ 300   end
+ 301 
+ 302   describe 'when flogging a Ruby string' do
+ 303     it 'should require both a Ruby string and a filename' do
+ 304       lambda { @flog.flog('string') }.should raise_error(ArgumentError)
+ 305     end
+ 306     
+ 307     describe 'when reporting blame information' do
+ 308       before :each do
+ 309         @flog = Flog.new(:blame => true)
+ 310       end
+ 311       
+ 312       it 'should gather blame information for the file' do
+ 313         @flog.expects(:collect_blame).with('filename')
+ 314         @flog.flog('string', 'filename')
+ 315       end
+ 316     end
+ 317     
+ 318     describe 'when not reporting blame information' do
+ 319       it 'should not gather blame information for the file' do
+ 320         @flog.expects(:collect_blame).never 
+ 321         @flog.flog('string', 'filename')
+ 322       end
+ 323     end
+ 324     
+ 325     describe 'when the string has a syntax error' do
+ 326       before :each do
+ 327         @flog.stubs(:warn)
+ 328         @flog.stubs(:process_parse_tree).raises(SyntaxError.new("<% foo %>"))
+ 329       end
+ 330       
+ 331       describe 'when the string has erb snippets' do
+ 332         currently 'should warn about skipping' do
+ 333           @flog.expects(:warn)
+ 334           @flog.flog('string', 'filename')
+ 335         end
+ 336         
+ 337         it 'should not raise an exception' do
+ 338           lambda { @flog.flog('string', 'filename') }.should_not raise_error
+ 339         end
+ 340         
+ 341         it 'should not process the failing code' do
+ 342           @flog.expects(:process).never
+ 343           @flog.flog('string', 'filename')
+ 344         end
+ 345       end
+ 346       
+ 347       describe 'when the string has no erb snippets' do
+ 348         before :each do
+ 349           @flog.stubs(:process_parse_tree).raises(SyntaxError)
+ 350         end
+ 351         
+ 352         it 'should raise a SyntaxError exception' do
+ 353           lambda { @flog.flog('string', 'filename') }.should raise_error(SyntaxError)
+ 354         end
+ 355         
+ 356         it 'should not process the failing code' do
+ 357           @flog.expects(:process).never
+ 358           lambda { @flog.flog('string', 'filename') }
+ 359         end
+ 360       end
+ 361     end
+ 362     
+ 363     describe 'when the string contains valid Ruby' do
+ 364       before :each do
+ 365         @flog.stubs(:process_parse_tree)
+ 366       end
+ 367       
+ 368       it 'should process the parse tree for the string' do
+ 369         @flog.expects(:process_parse_tree)
+ 370         @flog.flog('string', 'filename')
+ 371       end
+ 372       
+ 373       it 'should provide the string and the filename to the parse tree processor' do
+ 374         @flog.expects(:process_parse_tree).with('string', 'filename')
+ 375         @flog.flog('string', 'filename')
+ 376       end
+ 377     end
+ 378   end
+ 379   
+ 380   describe 'when processing a ruby parse tree' do
+ 381     before :each do
+ 382       @flog.stubs(:process)
+ 383       @sexp = stub('s-expressions')
+ 384       @parse_tree = stub('parse tree', :parse_tree_for_string => @sexp)
+ 385       ParseTree.stubs(:new).returns(@parse_tree)
+ 386     end
+ 387     
+ 388     it 'should require both a ruby string and a filename' do
+ 389       lambda { @flog.process_parse_tree('string') }.should raise_error(ArgumentError)
+ 390     end
+ 391     
+ 392     it 'should compute the parse tree for the ruby string' do
+ 393       Sexp.stubs(:from_array).returns(['1', '2'])
+ 394       @parse_tree.expects(:parse_tree_for_string).returns(@sexp)
+ 395       @flog.process_parse_tree('string', 'file')
+ 396     end
+ 397     
+ 398     it 'should use both the ruby string and the filename when computing the parse tree' do
+ 399       Sexp.stubs(:from_array).returns(['1', '2'])
+ 400       @parse_tree.expects(:parse_tree_for_string).with('string', 'file').returns(@sexp)
+ 401       @flog.process_parse_tree('string', 'file')      
+ 402     end
+ 403     
+ 404     describe 'if the ruby string is valid' do
+ 405       before :each do
+ 406         @parse_tree = stub('parse tree', :parse_tree_for_string => @sexp)
+ 407         @flog.stubs(:process)
+ 408         @flog.stubs(:parse_tree).returns(@parse_tree)        
+ 409       end
+ 410       
+ 411       it 'should convert the parse tree into a list of S-expressions' do
+ 412         Sexp.expects(:from_array).with(@sexp).returns(['1', '2'])
+ 413         @flog.process_parse_tree('string', 'file')
+ 414       end
+ 415       
+ 416       it 'should process the list of S-expressions' do
+ 417         @flog.expects(:process)
+ 418         @flog.process_parse_tree('string', 'file')
+ 419       end
+ 420       
+ 421       it 'should start processing at the first S-expression' do
+ 422         Sexp.stubs(:from_array).returns(['1', '2'])
+ 423         @flog.expects(:process).with('1')
+ 424         @flog.process_parse_tree('string', 'file')        
+ 425       end
+ 426     end
+ 427     
+ 428     describe 'if the ruby string is invalid' do
+ 429       before :each do
+ 430         @parse_tree = stub('parse tree')
+ 431         @flog.stubs(:parse_tree).returns(@parse_tree)        
+ 432         @parse_tree.stubs(:parse_tree_for_string).raises(SyntaxError)
+ 433       end
+ 434       
+ 435       it 'should fail' do
+ 436         lambda { @flog.process_parse_tree('string', 'file') }.should raise_error(SyntaxError)
+ 437       end
+ 438       
+ 439       it 'should not attempt to process the parse tree' do
+ 440         @flog.expects(:process).never
+ 441         lambda { @flog.process_parse_tree('string', 'file') }
+ 442       end
+ 443     end
+ 444   end
+ 445   
+ 446   describe 'when collecting blame information from a file' do
+ 447     it 'should require a filename' do
+ 448       lambda { @flog.collect_blame }.should raise_error(ArgumentError)
+ 449     end
+ 450     
+ 451     it 'should not fail when given a filename' do
+ 452       @flog.collect_blame('filename')
+ 453     end
+ 454     
+ 455     it 'should have more specs'
+ 456   end
+ 457 
+ 458   describe 'multiplier' do
+ 459     it 'should be possible to determine the current value of the multiplier' do
+ 460       @flog.should respond_to(:multiplier)
+ 461     end
+ 462   
+ 463     it 'should be possible to set the current value of the multiplier' do
+ 464       @flog.multiplier = 10
+ 465       @flog.multiplier.should == 10
+ 466     end
+ 467   end
+ 468   
+ 469   describe 'class_stack' do
+ 470     it 'should be possible to determine the current value of the class stack' do
+ 471       @flog.should respond_to(:class_stack)
+ 472     end
+ 473   
+ 474     it 'should be possible to set the current value of the class stack' do
+ 475       @flog.class_stack = [ 'name' ]
+ 476       @flog.class_stack.should == [ 'name' ]
+ 477     end
+ 478   end
+ 479   
+ 480   describe 'method_stack' do
+ 481     it 'should be possible to determine the current value of the method stack' do
+ 482       @flog.should respond_to(:method_stack)
+ 483     end
+ 484   
+ 485     it 'should be possible to set the current value of the method stack' do
+ 486       @flog.method_stack = [ 'name' ]
+ 487       @flog.method_stack.should == [ 'name' ]
+ 488     end
+ 489   end
+ 490   
+ 491   describe 'when adding to the current flog score' do
+ 492     before :each do
+ 493       @flog.multiplier = 1
+ 494       @flog.stubs(:class_name).returns('foo')
+ 495       @flog.stubs(:method_name).returns('bar')
+ 496       @flog.calls['foo#bar'] = { :alias => 0 }
+ 497     end
+ 498     
+ 499     it 'should require an operation name' do
+ 500       lambda { @flog.add_to_score() }.should raise_error(ArgumentError)
+ 501     end
+ 502     
+ 503     it 'should update the score for the current class, method, and operation' do
+ 504       @flog.add_to_score(:alias)
+ 505       @flog.calls['foo#bar'][:alias].should_not == 0
+ 506     end
+ 507     
+ 508     it 'should use the multiplier when updating the current call score' do
+ 509       @flog.multiplier = 10
+ 510       @flog.add_to_score(:alias)
+ 511       @flog.calls['foo#bar'][:alias].should == 10*Flog::SCORES[:alias]
+ 512     end
+ 513   end
+ 514   
+ 515   describe 'when computing the average per-call flog score' do
+ 516     it 'should not allow arguments' do
+ 517       lambda { @flog.average('foo') }.should raise_error(ArgumentError)
+ 518     end
+ 519     
+ 520     it 'should return the total flog score divided by the number of calls' do
+ 521       @flog.stubs(:total).returns(100.0)
+ 522       @flog.stubs(:calls).returns({ :bar => {}, :foo => {} })
+ 523       @flog.average.should be_close(100.0/2, 0.00000000001)
+ 524     end
+ 525   end
+ 526 
+ 527   describe 'when recursively analyzing the complexity of code' do
+ 528     it 'should require a complexity modifier value' do
+ 529       lambda { @flog.penalize_by }.should raise_error(ArgumentError)
+ 530     end
+ 531     
+ 532     it 'should require a block, for code to recursively analyze' do
+ 533       lambda { @flog.penalize_by(42) }.should raise_error(LocalJumpError)
+ 534     end
+ 535     
+ 536     it 'should recursively analyze the provided code block' do
+ 537       @flog.penalize_by(42) do
+ 538         @foo = true
+ 539       end
+ 540       
+ 541       @foo.should be_true
+ 542     end
+ 543     
+ 544     it 'should update the complexity multiplier when recursing' do
+ 545       @flog.multiplier = 1
+ 546       @flog.penalize_by(42) do
+ 547         @flog.multiplier.should == 43
+ 548       end
+ 549     end
+ 550     
+ 551     it 'when it is done it should restore the complexity multiplier to its original value' do
+ 552       @flog.multiplier = 1
+ 553       @flog.penalize_by(42) do
+ 554       end
+ 555       @flog.multiplier.should == 1
+ 556     end
+ 557   end
+ 558   
+ 559   describe 'when computing complexity of all remaining opcodes' do
+ 560     it 'should require a list of opcodes' do
+ 561       lambda { @flog.analyze_list }.should raise_error(ArgumentError)
+ 562     end
+ 563     
+ 564     it 'should process each opcode' do
+ 565       @opcodes = [ :foo, :bar, :baz ]
+ 566       @opcodes.each do |opcode|
+ 567          @flog.expects(:process).with(opcode)
+ 568       end
+ 569       
+ 570       @flog.analyze_list @opcodes
+ 571     end
+ 572   end
+ 573   
+ 574   describe 'when recording the current class being analyzed' do
+ 575     it 'should require a class name' do
+ 576       lambda { @flog.set_class }.should raise_error(ArgumentError)
+ 577     end
+ 578     
+ 579     it 'should require a block during which the class name is in effect' do
+ 580       lambda { @flog.set_class('name') }.should raise_error(LocalJumpError)
+ 581     end
+ 582     
+ 583     it 'should recursively analyze the provided code block' do
+ 584       @flog.set_class 'name' do
+ 585         @foo = true
+ 586       end
+ 587       
+ 588       @foo.should be_true
+ 589     end
+ 590     
+ 591     it 'should update the class stack when recursing' do
+ 592       @flog.class_stack = []
+ 593       @flog.set_class 'name' do
+ 594         @flog.class_stack.should == ['name']
+ 595       end
+ 596     end
+ 597     
+ 598     it 'when it is done it should restore the class stack to its original value' do
+ 599       @flog.class_stack = []
+ 600       @flog.set_class 'name' do
+ 601       end
+ 602       @flog.class_stack.should == []
+ 603     end
+ 604   end
+ 605   
+ 606   describe 'when looking up the name of the class currently under analysis' do
+ 607     it 'should not take any arguments' do
+ 608       lambda { @flog.class_name('foo') }.should raise_error(ArgumentError)
+ 609     end
+ 610     
+ 611     it 'should return the most recent class entered' do
+ 612       @flog.class_stack = [:foo, :bar, :baz]
+ 613       @flog.class_name.should == :foo
+ 614     end
+ 615     
+ 616     it 'should return the default class if no classes entered' do
+ 617       @flog.class_stack = []
+ 618       @flog.class_name.should == :main
+ 619     end
+ 620   end
+ 621 
+ 622   describe 'when recording the current method being analyzed' do
+ 623     it 'should require a method name' do
+ 624       lambda { @flog.set_method }.should raise_error(ArgumentError)
+ 625     end
+ 626     
+ 627     it 'should require a block during which the class name is in effect' do
+ 628       lambda { @flog.set_method('name') }.should raise_error(LocalJumpError)
+ 629     end
+ 630     
+ 631     it 'should recursively analyze the provided code block' do
+ 632       @flog.set_method 'name' do
+ 633         @foo = true
+ 634       end
+ 635       
+ 636       @foo.should be_true
+ 637     end
+ 638     
+ 639     it 'should update the class stack when recursing' do
+ 640       @flog.method_stack = []
+ 641       @flog.set_method 'name' do
+ 642         @flog.method_stack.should == ['name']
+ 643       end
+ 644     end
+ 645     
+ 646     it 'when it is done it should restore the class stack to its original value' do
+ 647       @flog.method_stack = []
+ 648       @flog.set_method 'name' do
+ 649       end
+ 650       @flog.method_stack.should == []
+ 651     end
+ 652   end
+ 653 
+ 654   describe 'when looking up the name of the method currently under analysis' do
+ 655     it 'should not take any arguments' do
+ 656       lambda { @flog.method_name('foo') }.should raise_error(ArgumentError)
+ 657     end
+ 658     
+ 659     it 'should return the most recent class entered' do
+ 660       @flog.method_stack = [:foo, :bar, :baz]
+ 661       @flog.method_name.should == :foo
+ 662     end
+ 663     
+ 664     it 'should return the default class if no classes entered' do
+ 665       @flog.method_stack = []
+ 666       @flog.method_name.should == :none
+ 667     end
+ 668   end
+ 669   
+ 670   describe 'when resetting state' do
+ 671     it 'should not take any arguments' do
+ 672       lambda { @flog.reset('foo') }.should raise_error(ArgumentError)
+ 673     end
+ 674     
+ 675     it 'should clear any recorded totals data' do
+ 676       @flog.totals['foo'] = 'bar'
+ 677       @flog.reset
+ 678       @flog.totals.should == {}
+ 679     end
+ 680         
+ 681     it 'should clear the total score' do
+ 682       # the only way I know to do this is to force the total score to be computed for actual code, then reset it
+ 683       @flog.flog_files(fixture_files('/simple/simple.rb'))
+ 684       @flog.reset
+ 685       @flog.total.should == 0
+ 686     end
+ 687     
+ 688     it 'should set the multiplier to 1.0' do
+ 689       @flog.multiplier = 20.0
+ 690       @flog.reset
+ 691       @flog.multiplier.should == 1.0
+ 692     end
+ 693     
+ 694     it 'should set clear any calls data' do
+ 695       @flog.calls['foobar'] = 'yoda'
+ 696       @flog.reset
+ 697       @flog.calls.should == {}
+ 698     end
+ 699     
+ 700     it 'should ensure that new recorded calls will get 0 counts without explicit initialization' do
+ 701       @flog.reset
+ 702       @flog.calls['foobar']['baz'] += 20
+ 703       @flog.calls['foobar']['baz'].should == 20
+ 704     end
+ 705   end
+ 706   
+ 707   describe 'when retrieving the total score' do
+ 708     it 'should take no arguments' do
+ 709       lambda { @flog.total('foo') }.should raise_error(ArgumentError)
+ 710     end
+ 711     
+ 712     it 'should return 0 if nothing has been analyzed' do
+ 713       @flog.total.should == 0
+ 714     end
+ 715     
+ 716     it 'should compute totals data when called the first time' do
+ 717       @flog.expects(:totals)
+ 718       @flog.total
+ 719     end
+ 720     
+ 721     it 'should not recompute totals data when called after the first time' do
+ 722       @flog.total
+ 723       @flog.expects(:totals).never
+ 724       @flog.total
+ 725     end
+ 726     
+ 727     it 'should return the score from the analysis once files have been analyzed' do
+ 728       @flog.flog_files(fixture_files('/simple/simple.rb'))
+ 729       @flog.total.should_not == 0
+ 730     end
+ 731   end
+ 732   
+ 733   describe 'when computing a score for a method' do
+ 734     it 'should require a hash of call tallies' do
+ 735       lambda { @flog.score_method }.should raise_error(ArgumentError)
+ 736     end
+ 737     
+ 738     it 'should return a score of 0 if no tallies are provided' do
+ 739       @flog.score_method({}).should == 0.0
+ 740     end
+ 741     
+ 742     it 'should compute the sqrt of summed squares for assignments, branches, and other tallies' do
+ 743       @flog.score_method({
+ 744         :assignment => 7,
+ 745         :branch => 23,
+ 746         :crap => 37
+ 747       }).should be_close(Math.sqrt(7*7 + 23*23 + 37*37), 0.0000000001)
+ 748     end
+ 749   end
+ 750   
+ 751   describe 'when recording a total for a method' do
+ 752     # guess what, @totals and @calls could be refactored to be first-class objects
+ 753     it 'should require a method and a score' do
+ 754       lambda { @flog.record_method_score('foo') }.should raise_error(ArgumentError)
+ 755     end
+ 756     
+ 757     it 'should set the total score for the provided method' do
+ 758       @flog.record_method_score('foo', 20)
+ 759       @flog.totals['foo'].should == 20
+ 760     end
+ 761   end
+ 762   
+ 763   describe 'when updating the total flog score' do
+ 764     it 'should require an amount to update by' do
+ 765       lambda { @flog.increment_total_score_by }.should raise_error(ArgumentError)
+ 766     end
+ 767     
+ 768     it 'should update the total flog score' do
+ 769       @flog.increment_total_score_by 42
+ 770       @flog.total.should == 42
+ 771     end
+ 772   end
+ 773   
+ 774   describe 'when compiling summaries for a method' do
+ 775     before :each do
+ 776       @tally = { :foo => 0.0 }
+ 777       @method = 'foo'
+ 778       @score = 42.0
+ 779       
+ 780       @flog.stubs(:score_method).returns(@score)
+ 781       @flog.stubs(:record_method_score)
+ 782       @flog.stubs(:increment_total_score_by)
+ 783     end
+ 784     
+ 785     it 'should require a method name and a tally' do
+ 786       lambda { @flog.summarize_method('foo') }.should raise_error(ArgumentError)
+ 787     end
+ 788     
+ 789     it 'should compute a score for the method, based on the tally' do
+ 790       @flog.expects(:score_method).with(@tally)
+ 791       @flog.summarize_method(@method, @tally)
+ 792     end
+ 793     
+ 794     it 'should record the score for the method' do
+ 795       @flog.expects(:record_method_score).with(@method, @score)
+ 796       @flog.summarize_method(@method, @tally)      
+ 797     end
+ 798     
+ 799     it 'should update the overall flog score' do
+ 800       @flog.expects(:increment_total_score_by).with(@score)
+ 801       @flog.summarize_method(@method, @tally)            
+ 802     end
+ 803 
+ 804     describe 'ignoring non-method code and given a non-method tally' do
+ 805       it 'should not compute a score for the tally' do
+ 806         @flog.expects(:score_method).never
+ 807         @flog.summarize_method(@method, @tally)
+ 808       end
+ 809       
+ 810       it 'should not record a score based on the tally' do
+ 811         @flog.expects(:record_method_score).never
+ 812         @flog.summarize_method(@method, @tally)      
+ 813       end
+ 814       
+ 815       it 'should not update the overall flog score' do
+ 816         @flog.expects(:increment_total_score_by).never
+ 817         @flog.summarize_method(@method, @tally)            
+ 818       end
+ 819     end    
+ 820   end
+ 821   
+ 822   describe 'when requesting totals' do
+ 823     it 'should not accept any arguments' do
+ 824       lambda { @flog.totals('foo') }.should raise_error(ArgumentError)
+ 825     end
+ 826     
+ 827     describe 'when called the first time' do
+ 828       it 'should access calls data' do
+ 829         @flog.expects(:calls).returns({})
+ 830         @flog.totals
+ 831       end
+ 832       
+ 833       it "will compile a summary for each method from the method's tally" do
+ 834         @calls = { :foo => 1.0, :bar => 2.0, :baz => 3.0 }
+ 835         @flog.stubs(:calls).returns(@calls)
+ 836         @calls.each do |meth, tally|
+ 837           @flog.expects(:summarize_method).with(meth, tally)
+ 838         end
+ 839         @flog.totals
+ 840       end
+ 841       
+ 842       it 'should return the totals data' do
+ 843         @flog.totals.should == {}
+ 844       end      
+ 845     end
+ 846     
+ 847     describe 'when called after the first time' do
+ 848       before :each do
+ 849         @flog.totals
+ 850       end
+ 851       
+ 852       it 'should not access calls data' do
+ 853         @flog.expects(:calls).never
+ 854         @flog.totals        
+ 855       end
+ 856       
+ 857       it 'should not compile method summaries' do
+ 858         @flog.expects(:summarize_method).never
+ 859         @flog.totals
+ 860       end
+ 861       
+ 862       it 'should return the totals data' do
+ 863         @flog.totals.should == {}
+ 864       end
+ 865     end
+ 866   end
+ 867   
+ 868   describe 'when producing a report summary' do
+ 869     before :each do
+ 870       @handle = stub('io handle)', :puts => nil)
+ 871       @flog.stubs(:total).returns(@total_score = 42.0)
+ 872       @flog.stubs(:average).returns(@average_score = 1.0)
+ 873     end
+ 874     
+ 875     it 'should require an io handle' do
+ 876       lambda { @flog.output_summary }.should raise_error(ArgumentError)
+ 877     end
+ 878 
+ 879     it 'computes the total flog score' do
+ 880       @flog.expects(:total).returns 42.0
+ 881       @flog.output_summary(@handle)
+ 882     end 
+ 883     
+ 884     it 'computes the average flog score' do
+ 885       @flog.expects(:average).returns 1.0
+ 886       @flog.output_summary(@handle)
+ 887     end
+ 888     
+ 889     it 'outputs the total flog score to the handle' do
+ 890       @handle.expects(:puts).with do |string|
+ 891         string =~ Regexp.new(Regexp.escape("%.1f" % @total_score))
+ 892       end
+ 893       @flog.output_summary(@handle)
+ 894     end
+ 895     
+ 896     it 'outputs the average flog score to the handle' do
+ 897       @handle.expects(:puts).with do |string|
+ 898         string =~ Regexp.new(Regexp.escape("%.1f" % @average_score))
+ 899       end
+ 900       @flog.output_summary(@handle)
+ 901     end
+ 902   end
+ 903   
+ 904   describe 'when producing a detailed call summary report' do
+ 905     before :each do
+ 906       @handle = stub('io handle)', :puts => nil)
+ 907       @calls = { :foo => {}, :bar => {}, :baz => {} }
+ 908       @totals = { :foo => 1, :bar => 2, :baz => 3 }
+ 909       
+ 910       @flog.stubs(:calls).returns(@calls)
+ 911       @flog.stubs(:totals).returns(@totals)
+ 912       @flog.stubs(:output_method_details).returns(5)
+ 913     end
+ 914     
+ 915     it 'should require an i/o handle' do
+ 916       lambda { @flog.output_details }.should raise_error(ArgumentError)
+ 917     end
+ 918     
+ 919     it 'should allow a threshold on the amount of detail to report' do
+ 920       lambda { @flog.output_details(@handle, 300) }.should_not raise_error(ArgumentError)
+ 921     end
+ 922       
+ 923     it 'retrieves the set of total statistics' do
+ 924       @flog.expects(:totals).returns(@totals)
+ 925       @flog.output_details(@handle)
+ 926     end
+ 927     
+ 928     it 'retrieves the set of call statistics' do
+ 929       @flog.expects(:calls).returns({})
+ 930       @flog.output_details(@handle)      
+ 931     end
+ 932 
+ 933     it 'should output a method summary for each located method' do
+ 934       @calls.each do |meth, list|
+ 935         @flog.expects(:output_method_details).with(@handle, meth, list).returns(5)
+ 936       end
+ 937       @flog.output_details(@handle)
+ 938     end
+ 939     
+ 940     describe 'if a threshold is provided' do
+ 941       it 'should only output details for methods until the threshold is reached' do
+ 942         @flog.expects(:output_method_details).with(@handle, :baz, {}).returns(5)
+ 943         @flog.expects(:output_method_details).with(@handle, :bar, {}).returns(5)
+ 944         @flog.expects(:output_method_details).with(@handle, :foo, {}).never
+ 945         @flog.output_details(@handle, 10)
+ 946       end
+ 947     end
+ 948     
+ 949     describe 'if no threshold is provided' do
+ 950       it 'should output details for all methods' do
+ 951         @calls.each do |class_method, call_list|
+ 952           @flog.expects(:output_method_details).with(@handle, class_method, call_list).returns(5)
+ 953         end
+ 954         @flog.output_details(@handle)
+ 955       end
+ 956     end
+ 957   end
+ 958   
+ 959   describe 'when reporting the details for a specific method' do
+ 960     before :each do
+ 961       @handle = stub('i/o handle', :puts => nil)
+ 962       @totals = { 'foo#foo' => 42.0, 'foo#none' => 12.0 }
+ 963       @data = { :assign => 10, :branch => 5, :case => 3 }
+ 964       @flog.stubs(:totals).returns(@totals)
+ 965     end
+ 966     
+ 967     it 'should require an i/o handle, a method name, and method details' do
+ 968       lambda { @flog.output_method_details('foo', 'bar') }.should raise_error(ArgumentError)
+ 969     end
+ 970         
+ 971     describe 'and ignoring non-method code' do
+ 972       before :each do
+ 973         @flog = Flog.new(:methods => true)
+ 974         @flog.stubs(:totals).returns(@totals)
+ 975       end
+ 976       
+ 977       describe 'and given non-method data to summarize' do
+ 978         it 'should not generate any output on the i/o handle' do
+ 979           @handle.expects(:puts).never
+ 980           @flog.output_method_details(@handle, 'foo#none', @data)
+ 981         end
+ 982       
+ 983         it 'should return 0' do
+ 984           @flog.output_method_details(@handle, 'foo#none', @data).should == 0.0
+ 985         end
+ 986       end
+ 987       
+ 988       describe 'and given method data to summarize' do
+ 989         it 'should return the total complexity for the method' do
+ 990           @flog.output_method_details(@handle, 'foo#foo', @data).should == 42.0
+ 991         end
+ 992         
+ 993         it 'should output the overall total for the method' do
+ 994           @handle.expects(:puts).with do |string| 
+ 995             string =~ Regexp.new(Regexp.escape("%.1f" % 42.0))
+ 996           end
+ 997           @flog.output_method_details(@handle, 'foo#foo', @data)          
+ 998         end
+ 999         
+1000         it 'should output call details for each call for the method' do
+1001           @data.each do |call, count|
+1002             @handle.expects(:puts).with do |string| 
+1003               string =~ Regexp.new(Regexp.escape("%6.1f: %s" % [ count, call ]))
+1004             end
+1005           end
+1006           @flog.output_method_details(@handle, 'foo#foo', @data)          
+1007         end
+1008       end
+1009     end
+1010     
+1011     describe 'and not excluding non-method code' do
+1012       it 'should return the total complexity for the method' do
+1013         @flog.output_method_details(@handle, 'foo#foo', @data).should == 42.0
+1014       end
+1015       
+1016       it 'should output the overall total for the method' do
+1017         @handle.expects(:puts).with do |string| 
+1018           string =~ Regexp.new(Regexp.escape("%.1f" % 42.0))
+1019         end
+1020         @flog.output_method_details(@handle, 'foo#foo', @data)          
+1021       end
+1022       
+1023       it 'should output call details for each call for the method' do
+1024         @data.each do |call, count|
+1025           @handle.expects(:puts).with do |string| 
+1026             string =~ Regexp.new(Regexp.escape("%6.1f: %s" % [ count, call ]))
+1027           end
+1028         end
+1029         @flog.output_method_details(@handle, 'foo#foo', @data)          
+1030       end
+1031     end
+1032   end
+1033   
+1034   describe 'when generating a report' do
+1035     it 'allows specifying an i/o handle' do
+1036       lambda { @flog.report 'handle' }.should_not raise_error(ArgumentError)
+1037     end
+1038     
+1039     it 'allows running the report without a specified i/o handle' do
+1040       lambda { @flog.report }.should_not raise_error(ArgumentError)
+1041     end
+1042     
+1043     describe 'and no i/o handle is specified' do      
+1044       it 'defaults the io handle to stdout' do
+1045         @flog.expects(:output_summary).with($stdout)
+1046         @flog.report
+1047       end
+1048     end
+1049 
+1050     describe 'and producing a summary report' do
+1051       before :each do
+1052         @flog = Flog.new(:score => true)
+1053         @flog.stubs(:output_summary)
+1054       end
+1055       
+1056       it 'produces an output summary on the i/o handle' do
+1057         @flog.expects(:output_summary).with('handle')
+1058         @flog.report('handle')
+1059       end
+1060       
+1061       it 'does not output a detailed report' do
+1062         @flog.expects(:output_details).never
+1063         @flog.report('handle')
+1064       end
+1065       
+1066       it 'should reset statistics when finished' do
+1067         @flog.expects(:reset)
+1068         @flog.report('handle')
+1069       end
+1070     end
+1071     
+1072     describe 'and producing a full report' do
+1073       before :each do
+1074         @flog.stubs(:output_summary)
+1075         @flog.stubs(:output_details)
+1076       end
+1077       
+1078       it 'produces an output summary on the i/o handle' do
+1079         @flog.expects(:output_summary).with('handle')
+1080         @flog.report('handle')
+1081       end
+1082       
+1083       it 'should generate a detailed report of method complexity on the i/o handle' do
+1084         @flog.expects(:output_details).with {|handle, max| handle == 'handle' }
+1085         @flog.report('handle')
+1086       end
+1087 
+1088       describe 'when flogging all methods in the system' do
+1089         before :each do
+1090           @flog = Flog.new(:all => true)
+1091           @flog.stubs(:output_summary)
+1092           @flog.stubs(:output_details)
+1093         end
+1094         
+1095         it 'should not limit the detailed report' do
+1096           @flog.expects(:output_details).with('handle')
+1097           @flog.report('handle')
+1098         end
+1099       end
+1100       
+1101       describe 'when flogging only the most expensive methods in the system' do
+1102         it 'should limit the detailed report to the Flog threshold' do
+1103           @flog.stubs(:total).returns(3.45)
+1104           @flog.expects(:output_details).with('handle', 3.45 * 0.60)
+1105           @flog.report('handle')
+1106         end
+1107       end
+1108       
+1109       it 'should reset statistics when finished' do
+1110         @flog.expects(:reset)
+1111         @flog.report(@handle)
+1112       end
+1113     end
+1114   end
+1115 end
 

Generated using the rcov code coverage analysis tool for Ruby version 0.8.1.2.

diff --git a/coverage/spec-spec_helper_rb.html b/coverage/spec-spec_helper_rb.html index 0d5a0b1..4ca54e2 100644 --- a/coverage/spec-spec_helper_rb.html +++ b/coverage/spec-spec_helper_rb.html @@ -553,7 +553,7 @@

C0 code coverage information

-

Generated on Mon Aug 04 22:47:36 -0500 2008 with rcov 0.8.1.2 +

Generated on Mon Aug 04 22:47:51 -0500 2008 with rcov 0.8.1.2


Code reported as executed by Ruby looks like this...
@@ -598,42 +598,42 @@
       
-
 1 # this is my favorite way to require ever
- 2 begin
- 3   require 'spec'
- 4 rescue LoadError
- 5   require 'rubygems'
- 6   gem 'rspec'
- 7   require 'spec'
- 8 end
- 9 
-10 begin
-11   require 'mocha'
-12 rescue LoadError
-13   require 'rubygems'
-14   gem 'mocha'
-15   require 'mocha'
-16 end
-17 
-18 
-19 module Spec::Example::ExampleGroupMethods
-20   def currently(name, &block)
-21     it("*** CURRENTLY *** #{name}", &block)
-22   end
-23 end
-24 
-25 Spec::Runner.configure do |config|
-26   config.mock_with :mocha
-27 end
-28 
-29 def fixture_files(paths)
-30   paths.collect do |path|
-31     File.expand_path(File.dirname(__FILE__) + '/../spec_fixtures/' + path)
-32   end
-33 end
-34 
-35 
-36 $:.unshift File.join(File.dirname(__FILE__), *%w[.. lib])
+
 1 # this is my favorite way to require ever
+ 2 begin
+ 3   require 'spec'
+ 4 rescue LoadError
+ 5   require 'rubygems'
+ 6   gem 'rspec'
+ 7   require 'spec'
+ 8 end
+ 9 
+10 begin
+11   require 'mocha'
+12 rescue LoadError
+13   require 'rubygems'
+14   gem 'mocha'
+15   require 'mocha'
+16 end
+17 
+18 
+19 module Spec::Example::ExampleGroupMethods
+20   def currently(name, &block)
+21     it("*** CURRENTLY *** #{name}", &block)
+22   end
+23 end
+24 
+25 Spec::Runner.configure do |config|
+26   config.mock_with :mocha
+27 end
+28 
+29 def fixture_files(paths)
+30   paths.collect do |path|
+31     File.expand_path(File.dirname(__FILE__) + '/../spec_fixtures/' + path)
+32   end
+33 end
+34 
+35 
+36 $:.unshift File.join(File.dirname(__FILE__), *%w[.. lib])
 

Generated using the rcov code coverage analysis tool for Ruby version 0.8.1.2.

diff --git a/lib/flog.rb b/lib/flog.rb index e6ab1b9..fdb97a7 100644 --- a/lib/flog.rb +++ b/lib/flog.rb @@ -111,6 +111,9 @@ def process_parse_tree(ruby, file) process Sexp.from_array(sexp).first end + def collect_blame(filename) + end + def add_to_score(name) @calls["#{class_name}##{method_name}"][name] += SCORES[name] * @multiplier end diff --git a/spec/flog_spec.rb b/spec/flog_spec.rb index 053261b..b52bcad 100644 --- a/spec/flog_spec.rb +++ b/spec/flog_spec.rb @@ -443,6 +443,18 @@ end end + describe 'when collecting blame information from a file' do + it 'should require a filename' do + lambda { @flog.collect_blame }.should raise_error(ArgumentError) + end + + it 'should not fail when given a filename' do + @flog.collect_blame('filename') + end + + it 'should have more specs' + end + describe 'multiplier' do it 'should be possible to determine the current value of the multiplier' do @flog.should respond_to(:multiplier)