]> git.openstreetmap.org Git - rails.git/blob - vendor/gems/rspec-1.1.2/lib/spec/runner/spec_parser.rb
added RSpec and RSpec on Rails
[rails.git] / vendor / gems / rspec-1.1.2 / lib / spec / runner / spec_parser.rb
1 module Spec
2   module Runner
3     # Parses a spec file and finds the nearest example for a given line number.
4     class SpecParser
5       def spec_name_for(io, line_number)
6         source  = io.read
7         example_group, example_group_line = example_group_at_line(source, line_number)
8         example, example_line = example_at_line(source, line_number)
9         if example_group && example && (example_group_line < example_line)
10           "#{example_group} #{example}"
11         elsif example_group
12           example_group
13         else
14           nil
15         end
16       end
17
18     protected
19
20       def example_group_at_line(source, line_number)
21         find_above(source, line_number, /^\s*(context|describe)\s+(.*)\s+do/)
22       end
23
24       def example_at_line(source, line_number)
25         find_above(source, line_number, /^\s*(specify|it)\s+(.*)\s+do/)
26       end
27
28       # Returns the context/describe or specify/it name and the line number
29       def find_above(source, line_number, pattern)
30         lines_above_reversed(source, line_number).each_with_index do |line, n|
31           return [parse_description($2), line_number-n] if line =~ pattern
32         end
33         nil
34       end
35
36       def lines_above_reversed(source, line_number)
37         lines = source.split("\n")
38         lines[0...line_number].reverse
39       end
40       
41       def parse_description(str)
42         return str[1..-2] if str =~ /^['"].*['"]$/
43         if matches = /^['"](.*)['"](,.*)?$/.match(str)
44           return ::Spec::Example::ExampleGroupMethods.description_text(matches[1])
45         end
46         if matches = /^(.*)\s*,\s*['"](.*)['"](,.*)?$/.match(str)
47           return ::Spec::Example::ExampleGroupMethods.description_text(matches[1], matches[2])
48         end
49         return str
50       end
51     end
52   end
53 end