ripper-tags 0.1.3 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- Yzc2MzlhZjllZTM4NTk1OWMzNmU3ZjkyNDIxNjVmYTk1NmJiOGJhZA==
5
- data.tar.gz: !binary |-
6
- ZDlmM2U4YmUyNzZkMGY3OTkxNTRmNWRjMGQxZTk1YjQzN2NiZGZlZA==
2
+ SHA1:
3
+ metadata.gz: 5a6a3d465781a89ac1728aae902fad12c456bbeb
4
+ data.tar.gz: cd72ea7c347ac44cf838eb4f68a2e6a4de44f269
7
5
  SHA512:
8
- metadata.gz: !binary |-
9
- Zjg2MDJmOTg4Y2UwYTA4MzI0ZDUwNWEzYWY3ZGZkYmE5ZTQ5YTRkN2FkMWZm
10
- MmQ1ODdmNmZhNWYwYzA1MzM4ZWY1OWNlMTU2M2VmNjI3MWNiYWVlZGJhY2M3
11
- MTEzNGQ3NDQ1ZmUyOGVlNjRlM2I0Njc4YzdjN2M3ZjNiOWQ3YjU=
12
- data.tar.gz: !binary |-
13
- NGY3N2YxMzU0NDM2MmIyNjRiZGU4MmUwNThmYzE2YjVjMWFlMjdmMzMwMTkx
14
- NzkxZWViZWZjMzRhNmRjZDYxYjQ2ZWNhNGI2MWI1ZjNhZTlmODBjN2VmYjcy
15
- ZjNkYjU0MjE4MTlhZmI5Nzc1ZDBkZTcwNDYxYTA4NmFhZDI5NTc=
6
+ metadata.gz: 5f0dc42cefd0807694183b743b1525926c6865b8474f7f17d20c95c1031a2c8d6b27930f4cd0c301d2845a5a773ccdea9a6e369997eb326f4ffa7698081e0683
7
+ data.tar.gz: e058985d5b4f662329e190a08e74f18df15138b68d07581028a3f0f42c2728064233725d1e0a9796e691a0c25d10efabfcaa449701b6aef2088952796c3903ab
@@ -1,5 +1,6 @@
1
1
  require 'optparse'
2
2
  require 'ostruct'
3
+ require 'set'
3
4
  require 'ripper-tags/parser'
4
5
  require 'ripper-tags/data_reader'
5
6
  require 'ripper-tags/default_formatter'
@@ -8,11 +9,14 @@ require 'ripper-tags/vim_formatter'
8
9
  require 'ripper-tags/json_formatter'
9
10
 
10
11
  module RipperTags
11
- def self.version() "0.1.2" end
12
+ def self.version() "0.2.0" end
13
+
14
+ FatalError = Class.new(RuntimeError)
12
15
 
13
16
  def self.default_options
14
17
  OpenStruct.new \
15
18
  :format => nil,
19
+ :extra_flags => Set.new,
16
20
  :tag_file_name => "./tags",
17
21
  :tag_relative => nil,
18
22
  :debug => false,
@@ -36,8 +40,8 @@ module RipperTags
36
40
  '"-" outputs to standard output') do |fname|
37
41
  options.tag_file_name = fname
38
42
  end
39
- opts.on("--tag-relative", "Make file paths relative to the directory of the tag file") do
40
- options.tag_relative = true
43
+ opts.on("--tag-relative[=OPTIONAL]", "Make file paths relative to the directory of the tag file") do |value|
44
+ options.tag_relative = value != "no"
41
45
  end
42
46
  opts.on("-R", "--recursive", "Descend recursively into subdirectories") do
43
47
  options.recursive = true
@@ -61,6 +65,16 @@ module RipperTags
61
65
  opts.on("-e", "--emacs", "Output Emacs format (default if `--tag-file' is `TAGS')") do
62
66
  options.format = "emacs"
63
67
  end
68
+ opts.on("--extra=FLAGS", "Specify extra flags for the formatter") do |flags|
69
+ flags = flags.split("")
70
+ operation = :add
71
+ if flags[0] == "+" || flags[0] == "-"
72
+ operation = :delete if flags.shift == "-"
73
+ else
74
+ options.extra_flags.clear
75
+ end
76
+ flags.each { |f| options.extra_flags.send(operation, f) }
77
+ end
64
78
 
65
79
  opts.separator ""
66
80
 
@@ -76,6 +90,22 @@ module RipperTags
76
90
  opts.on_tail("--force", "Skip files with parsing errors") do
77
91
  options.force = true
78
92
  end
93
+ opts.on_tail("--list-kinds=LANG", "Print tag kinds that this parser supports and exit") do |lang|
94
+ if lang.downcase == "ruby"
95
+ puts((<<-OUT).gsub(/^ +/, ''))
96
+ c classes
97
+ f methods
98
+ m modules
99
+ F singleton methods
100
+ C constants
101
+ a aliases
102
+ OUT
103
+ exit
104
+ else
105
+ $stderr.puts "Error: language %p is not supported" % lang
106
+ exit 1
107
+ end
108
+ end
79
109
  opts.on_tail("-v", "--version", "Print version information") do
80
110
  puts opts.ver
81
111
  exit
@@ -104,7 +134,7 @@ module RipperTags
104
134
  when "emacs" then RipperTags::EmacsFormatter
105
135
  when "json" then RipperTags::JSONFormatter
106
136
  when "custom" then RipperTags::DefaultFormatter
107
- else raise ArgumentError, "unknown format: #{options.format.inspect}"
137
+ else raise FatalError, "unknown format: #{options.format.inspect}"
108
138
  end.new(options)
109
139
  end
110
140
 
@@ -116,5 +146,11 @@ module RipperTags
116
146
  formatter.write(tag, out)
117
147
  end
118
148
  end
149
+ rescue FatalError => err
150
+ $stderr.puts "%s: %s" % [
151
+ File.basename($0),
152
+ err.message
153
+ ]
154
+ exit 1
119
155
  end
120
156
  end
@@ -61,9 +61,11 @@ module RipperTags
61
61
 
62
62
  class DataReader
63
63
  attr_reader :options
64
+ attr_accessor :read_mode
64
65
 
65
66
  def initialize(options)
66
67
  @options = options
68
+ @read_mode = defined?(::Encoding) ? 'r:utf-8' : 'r'
67
69
  end
68
70
 
69
71
  def file_finder
@@ -71,7 +73,7 @@ module RipperTags
71
73
  end
72
74
 
73
75
  def read_file(filename)
74
- str = File.open(filename, 'r:utf-8') {|f| f.read }
76
+ str = File.open(filename, read_mode) {|f| f.read }
75
77
  normalize_encoding(str)
76
78
  end
77
79
 
@@ -1,4 +1,5 @@
1
1
  require 'pathname'
2
+ require 'set'
2
3
 
3
4
  module RipperTags
4
5
  class DefaultFormatter
@@ -6,6 +7,22 @@ module RipperTags
6
7
 
7
8
  def initialize(options)
8
9
  @options = options
10
+
11
+ if @options.extra_flags
12
+ unsupported = @options.extra_flags - supported_flags.to_set
13
+ if unsupported.any?
14
+ raise FatalError, "these flags are not supported in the '%s' format: %s" % [
15
+ options.format,
16
+ unsupported.to_a.join(", ")
17
+ ]
18
+ end
19
+ end
20
+ end
21
+
22
+ def supported_flags() [] end
23
+
24
+ def extra_flag?(flag)
25
+ options.extra_flags && options.extra_flags.include?(flag)
9
26
  end
10
27
 
11
28
  def stdout?
@@ -35,6 +52,10 @@ module RipperTags
35
52
  end
36
53
  end
37
54
 
55
+ def constant?(tag)
56
+ tag[:kind] == 'class' || tag[:kind] == 'module' || tag[:kind] == 'constant'
57
+ end
58
+
38
59
  def display_kind(tag)
39
60
  case tag.fetch(:kind)
40
61
  when /method$/ then 'def'
@@ -17,6 +17,13 @@ module RipperTags
17
17
  @section_io = nil
18
18
  end
19
19
 
20
+ def supported_flags() ['q'] end
21
+
22
+ def include_qualified_names?
23
+ return @include_qualified_names if defined? @include_qualified_names
24
+ @include_qualified_names = extra_flag?('q')
25
+ end
26
+
20
27
  def with_output
21
28
  super do |io|
22
29
  begin
@@ -30,7 +37,10 @@ module RipperTags
30
37
  def write(tag, io)
31
38
  filename = relative_path(tag)
32
39
  section_io = start_file_section(filename, io)
33
- super(tag, section_io)
40
+ section_io.puts format(tag)
41
+ if include_qualified_names? && tag[:full_name] != tag[:name] && constant?(tag)
42
+ section_io.puts format(tag, :full_name)
43
+ end
34
44
  end
35
45
 
36
46
  def start_file_section(filename, io)
@@ -56,11 +66,10 @@ module RipperTags
56
66
  "\x0C\n%s,%d\n" % [ filename, data_size ]
57
67
  end
58
68
 
59
- def format(tag)
60
- pattern = tag.fetch(:pattern)
69
+ def format(tag, name_field = :name)
61
70
  "%s\x7F%s\x01%d,%d" % [
62
71
  tag.fetch(:pattern),
63
- tag.fetch(:name),
72
+ tag.fetch(name_field),
64
73
  tag.fetch(:line),
65
74
  0,
66
75
  ]
@@ -1,10 +1,34 @@
1
- require 'yajl'
1
+ begin
2
+ require 'yajl/json_gem' unless defined?(::JSON)
3
+ rescue LoadError
4
+ require 'json'
5
+ end
2
6
  require 'ripper-tags/default_formatter'
3
7
 
4
8
  module RipperTags
5
9
  class JSONFormatter < DefaultFormatter
6
- def format(tag)
7
- Yajl.dump(tag)
10
+ def supported_flags() ['s'] end
11
+
12
+ def stream_format?
13
+ return @stream_format if defined? @stream_format
14
+ @stream_format = extra_flag?('s')
15
+ end
16
+
17
+ def with_output
18
+ super do |true_out|
19
+ buffer = []
20
+ yield buffer
21
+
22
+ if stream_format?
23
+ buffer.each { |tag| true_out.puts ::JSON.dump(tag) }
24
+ else
25
+ true_out.write ::JSON.dump(buffer)
26
+ end
27
+ end
28
+ end
29
+
30
+ def write(tag, buffer)
31
+ buffer << tag
8
32
  end
9
33
  end
10
34
  end
@@ -81,6 +81,7 @@ class Parser < Ripper
81
81
  ret = [success, failure].flatten(1).compact
82
82
  ret.any?? ret : nil
83
83
  end
84
+ alias on_unless on_if
84
85
 
85
86
  def on_unless_mod(condition, success)
86
87
  nil
@@ -93,6 +94,7 @@ class Parser < Ripper
93
94
  end
94
95
  end
95
96
 
97
+ undef on_tstring_content
96
98
  def on_tstring_content(str)
97
99
  str
98
100
  end
@@ -144,13 +146,14 @@ class Parser < Ripper
144
146
  gen
145
147
  end
146
148
  when "has_many", "has_and_belongs_to_many"
147
- a = args[1][0].to_s
149
+ a = args[1][0]
148
150
  kind = name.to_sym
149
151
  gen = []
150
- unless a.is_a?(Enumerable)
152
+ unless a.is_a?(Enumerable) && !a.is_a?(String)
153
+ a = a.to_s
151
154
  gen << [:rails_def, kind, a, line]
152
155
  gen << [:rails_def, kind, "#{a}=", line]
153
- if a.respond_to?(:chomp) && (sing = a.chomp('s')) != a
156
+ if (sing = a.chomp('s')) != a
154
157
  # poor man's singularize
155
158
  gen << [:rails_def, kind, "#{sing}_ids", line]
156
159
  gen << [:rails_def, kind, "#{sing}_ids=", line]
@@ -159,10 +162,10 @@ class Parser < Ripper
159
162
  gen
160
163
  when "belongs_to", "has_one"
161
164
  a = args[1][0]
162
- unless a.is_a?(Enumerable)
165
+ unless a.is_a?(Enumerable) && !a.is_a?(String)
163
166
  kind = name.to_sym
164
- %W[ #{a} #{a}= build_#{a} create_#{a} create_#{a}! ].inject([]) do |gen, ident|
165
- gen << [:rails_def, kind, ident, line]
167
+ %W[ #{a} #{a}= build_#{a} create_#{a} create_#{a}! ].inject([]) do |all, ident|
168
+ all << [:rails_def, kind, ident, line]
166
169
  end
167
170
  end
168
171
  end
@@ -224,6 +227,8 @@ end
224
227
  @lines = data.split("\n")
225
228
  @namespace = []
226
229
  @tags = []
230
+ @is_singleton = false
231
+ @current_access = nil
227
232
 
228
233
  process(sexp)
229
234
  end
@@ -248,14 +253,13 @@ end
248
253
  sexp.each{ |child| process(child) }
249
254
  when Symbol
250
255
  name, *args = sexp
251
- handler = "on_#{name}"
252
- __send__(handler, *args) if respond_to?(handler)
256
+ __send__("on_#{name}", *args) unless name.to_s.index("@") == 0
253
257
  when String, nil
254
258
  # nothing
255
259
  end
256
260
  end
257
261
 
258
- def on_module_or_class(kind, name, superclass, body)
262
+ def on_module_or_class(kind, name, superclass, *body)
259
263
  name, line = *name
260
264
  @namespace << name
261
265
 
@@ -284,12 +288,12 @@ end
284
288
  @namespace.pop
285
289
  end
286
290
 
287
- def on_module(name, body = nil)
288
- on_module_or_class(:module, name, nil, body)
291
+ def on_module(name, *body)
292
+ on_module_or_class(:module, name, nil, *body)
289
293
  end
290
294
 
291
- def on_class(name, superclass, body = nil)
292
- on_module_or_class(:class, name, superclass, body)
295
+ def on_class(name, superclass, *body)
296
+ on_module_or_class(:class, name, superclass, *body)
293
297
  end
294
298
 
295
299
  def on_private() @current_access = 'private' end
@@ -306,10 +310,17 @@ end
306
310
  return on_module_or_class(kind, [name, line], superclass, rhs[4])
307
311
  end
308
312
 
313
+ namespace = @namespace
314
+ if name.include?('::')
315
+ parts = name.split('::')
316
+ name = parts.pop
317
+ namespace = namespace + parts
318
+ end
319
+
309
320
  emit_tag :constant, line,
310
321
  :name => name,
311
- :full_name => (@namespace + [name]).join('::'),
312
- :class => @namespace.join('::')
322
+ :full_name => (namespace + [name]).join('::'),
323
+ :class => namespace.join('::')
313
324
  end
314
325
 
315
326
  def on_alias(name, other, line)
@@ -351,7 +362,7 @@ end
351
362
  end
352
363
 
353
364
  def on_sclass(name, body)
354
- name, line = *name
365
+ name, _ = *name
355
366
  @namespace << name unless name == 'self'
356
367
  prev_is_singleton, @is_singleton = @is_singleton, true
357
368
  process(body)
@@ -361,7 +372,7 @@ end
361
372
  end
362
373
 
363
374
  def on_class_eval(name, body)
364
- name, line = *name
375
+ name, _ = *name
365
376
  @namespace << name
366
377
  process(body)
367
378
  ensure
@@ -2,6 +2,13 @@ require 'ripper-tags/default_formatter'
2
2
 
3
3
  module RipperTags
4
4
  class VimFormatter < DefaultFormatter
5
+ def supported_flags() ['q'] end
6
+
7
+ def include_qualified_names?
8
+ return @include_qualified_names if defined? @include_qualified_names
9
+ @include_qualified_names = extra_flag?('q')
10
+ end
11
+
5
12
  def header
6
13
  <<-EOC
7
14
  !_TAG_FILE_FORMAT\t2\t/extended format; --format=1 will not append ;" to lines/
@@ -23,6 +30,9 @@ module RipperTags
23
30
 
24
31
  def write(tag, out)
25
32
  @queued_write << format(tag)
33
+ if include_qualified_names? && tag[:full_name] != tag[:name] && constant?(tag)
34
+ @queued_write << format(tag, :full_name)
35
+ end
26
36
  end
27
37
 
28
38
  def display_constant(const)
@@ -60,13 +70,13 @@ module RipperTags
60
70
  end
61
71
  end
62
72
 
63
- def format(tag)
73
+ def format(tag, name_field = :name)
64
74
  "%s\t%s\t/^%s$/;\"\t%s%s%s" % [
65
- tag.fetch(:name),
75
+ tag.fetch(name_field),
66
76
  relative_path(tag),
67
77
  display_pattern(tag),
68
78
  display_kind(tag),
69
- display_class(tag),
79
+ name_field == :full_name ? nil : display_class(tag),
70
80
  display_inheritance(tag),
71
81
  ]
72
82
  end
metadata CHANGED
@@ -1,29 +1,15 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ripper-tags
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.3
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Aman Gupta
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2013-12-11 00:00:00.000000000 Z
12
- dependencies:
13
- - !ruby/object:Gem::Dependency
14
- name: yajl-ruby
15
- requirement: !ruby/object:Gem::Requirement
16
- requirements:
17
- - - ! '>='
18
- - !ruby/object:Gem::Version
19
- version: '0'
20
- type: :runtime
21
- prerelease: false
22
- version_requirements: !ruby/object:Gem::Requirement
23
- requirements:
24
- - - ! '>='
25
- - !ruby/object:Gem::Version
26
- version: '0'
11
+ date: 2015-07-29 00:00:00.000000000 Z
12
+ dependencies: []
27
13
  description: fast, accurate ctags generator for ruby source code using Ripper
28
14
  email:
29
15
  - aman@tmm1.net
@@ -32,11 +18,8 @@ executables:
32
18
  extensions: []
33
19
  extra_rdoc_files: []
34
20
  files:
35
- - .gitignore
36
- - Gemfile
37
21
  - LICENSE
38
22
  - README.md
39
- - Rakefile
40
23
  - bin/ripper-tags
41
24
  - lib/ripper-tags.rb
42
25
  - lib/ripper-tags/data_reader.rb
@@ -45,16 +28,6 @@ files:
45
28
  - lib/ripper-tags/json_formatter.rb
46
29
  - lib/ripper-tags/parser.rb
47
30
  - lib/ripper-tags/vim_formatter.rb
48
- - ripper-tags.gemspec
49
- - test/fixtures/_git/hooks/hook.rb
50
- - test/fixtures/encoding.rb
51
- - test/fixtures/non-script.txt
52
- - test/fixtures/very/deep/script.rb
53
- - test/fixtures/very/inter.rb
54
- - test/test_cli.rb
55
- - test/test_data_reader.rb
56
- - test/test_formatters.rb
57
- - test/test_ripper_tags.rb
58
31
  homepage: http://github.com/tmm1/ripper-tags
59
32
  licenses:
60
33
  - MIT
@@ -65,19 +38,18 @@ require_paths:
65
38
  - lib
66
39
  required_ruby_version: !ruby/object:Gem::Requirement
67
40
  requirements:
68
- - - ! '>='
41
+ - - ">="
69
42
  - !ruby/object:Gem::Version
70
43
  version: '0'
71
44
  required_rubygems_version: !ruby/object:Gem::Requirement
72
45
  requirements:
73
- - - ! '>='
46
+ - - ">="
74
47
  - !ruby/object:Gem::Version
75
48
  version: '0'
76
49
  requirements: []
77
50
  rubyforge_project:
78
- rubygems_version: 2.1.11
51
+ rubygems_version: 2.2.3
79
52
  signing_key:
80
53
  specification_version: 4
81
54
  summary: ctags generator for ruby code
82
55
  test_files: []
83
- has_rdoc: false
data/.gitignore DELETED
@@ -1,5 +0,0 @@
1
- tags
2
- TAGS
3
- ripper-tags-*gem
4
- *.swp
5
- Gemfile.lock
data/Gemfile DELETED
@@ -1,5 +0,0 @@
1
- source 'https://rubygems.org'
2
- gemspec
3
-
4
- gem 'rake'
5
- gem 'ripper', :platforms => :mri_18
data/Rakefile DELETED
@@ -1,6 +0,0 @@
1
- task :default => :test
2
-
3
- require 'rake/testtask'
4
- Rake::TestTask.new 'test' do |t|
5
- t.test_files = FileList['test/test_*.rb']
6
- end
@@ -1,23 +0,0 @@
1
- Gem::Specification.new do |s|
2
- s.name = 'ripper-tags'
3
- s.version = '0.1.3'
4
-
5
- s.summary = 'ctags generator for ruby code'
6
- s.description = 'fast, accurate ctags generator for ruby source code using Ripper'
7
-
8
- s.homepage = 'http://github.com/tmm1/ripper-tags'
9
- s.has_rdoc = false
10
-
11
- s.authors = ['Aman Gupta']
12
- s.email = ['aman@tmm1.net']
13
-
14
- s.add_dependency 'yajl-ruby'
15
-
16
- s.require_paths = ['lib']
17
- s.bindir = 'bin'
18
- s.executables << 'ripper-tags'
19
-
20
- s.license = 'MIT'
21
-
22
- s.files = `git ls-files`.split("\n")
23
- end
File without changes
@@ -1,4 +0,0 @@
1
- # vi:fenc=latin1
2
- def encoding
3
- "This is a test. I�t�rn�ti�n�liz�ti�n\n"
4
- end
File without changes
File without changes
File without changes
@@ -1,84 +0,0 @@
1
- require 'test/unit'
2
- require 'stringio'
3
- require 'ripper-tags'
4
-
5
- class CliTest < Test::Unit::TestCase
6
- def process_args(argv)
7
- RipperTags.process_args(argv, lambda {|o| o})
8
- end
9
-
10
- def test_empty_args
11
- err = assert_raise(SystemExit) do
12
- with_program_name('ripper-tags') do
13
- capture_stderr do
14
- RipperTags.process_args([])
15
- end
16
- end
17
- end
18
- assert_equal "Usage: ripper-tags [options] FILES...", err.message
19
- end
20
-
21
- def test_invalid_option
22
- err = assert_raise(OptionParser::InvalidOption) do
23
- RipperTags.process_args(%[--moo])
24
- end
25
- assert_equal "invalid option: --moo", err.message
26
- end
27
-
28
- def test_recurse_defaults_to_current_dir
29
- options = process_args(%w[-R])
30
- assert_equal true, options.recursive
31
- assert_equal %w[.], options.files
32
- end
33
-
34
- def test_exclude_add_patterns
35
- options = process_args(%w[-R --exclude vendor --exclude=bundle/*])
36
- assert_equal %w[.git vendor bundle/*], options.exclude
37
- end
38
-
39
- def test_exclude_clear
40
- options = process_args(%w[-R --exclude=])
41
- assert_equal [], options.exclude
42
- end
43
-
44
- def test_TAGS_triggers_to_emacs_format
45
- options = process_args(%w[-f ./TAGS script.rb])
46
- assert_equal './TAGS', options.tag_file_name
47
- assert_equal 'emacs', options.format
48
- end
49
-
50
- def test_tag_relative_off_by_default
51
- options = process_args(%w[ -R ])
52
- assert_equal false, options.tag_relative
53
- end
54
-
55
- def test_tag_relative_on
56
- options = process_args(%w[ -R --tag-relative ])
57
- assert_equal true, options.tag_relative
58
- end
59
-
60
- def test_tag_relative_on_for_emacs
61
- options = process_args(%w[ -R -e ])
62
- assert_equal true, options.tag_relative
63
- end
64
-
65
- def with_program_name(name)
66
- old_name = $0
67
- $0 = name
68
- begin
69
- yield
70
- ensure
71
- $0 = old_name
72
- end
73
- end
74
-
75
- def capture_stderr
76
- old_stderr = $stderr
77
- $stderr = StringIO.new
78
- begin
79
- yield
80
- ensure
81
- $stderr = old_stderr
82
- end
83
- end
84
- end
@@ -1,80 +0,0 @@
1
- require 'test/unit'
2
- require 'ostruct'
3
- require 'ripper-tags/data_reader'
4
-
5
- class DataReaderTest < Test::Unit::TestCase
6
- FIXTURES = File.expand_path('../fixtures', __FILE__)
7
-
8
- def fixture(path)
9
- File.join(FIXTURES, path)
10
- end
11
-
12
- def find_files(*files)
13
- opts = files.last.is_a?(Hash) ? files.pop : {}
14
- options = OpenStruct.new({:files => files, :recursive => true}.merge(opts))
15
- finder = RipperTags::FileFinder.new(options)
16
- finder.each_file.map {|f| f.sub("#{FIXTURES}/", '') }
17
- end
18
-
19
- def test_encoding
20
- with_default_encoding('utf-8') do
21
- options = OpenStruct.new(:files => [fixture('encoding.rb')])
22
- reader = RipperTags::DataReader.new(options)
23
- tags = reader.each_tag.to_a
24
- assert_equal 'Object#encoding', tags[0][:full_name]
25
- end
26
- end
27
-
28
- def test_encoding_non_utf8_default
29
- with_default_encoding('us-ascii') do
30
- options = OpenStruct.new(:files => [fixture('encoding.rb')])
31
- reader = RipperTags::DataReader.new(options)
32
- tags = reader.each_tag.to_a
33
- assert_equal 'Object#encoding', tags[0][:full_name]
34
- end
35
- end
36
-
37
- def test_file_finder
38
- files = find_files(fixture(''), :exclude => %w[_git])
39
- expected = %w[
40
- encoding.rb
41
- very/deep/script.rb
42
- very/inter.rb
43
- ]
44
- assert_equal Set.new(expected), Set.new(files)
45
- end
46
-
47
- def test_file_finder_no_exclude
48
- files = find_files(fixture(''), :exclude => [])
49
- assert files.include?('_git/hooks/hook.rb'), files.inspect
50
- end
51
-
52
- def test_file_finder_exclude
53
- files = find_files(fixture(''), :exclude => %w[_git very])
54
- expected = %w[ encoding.rb ]
55
- assert_equal expected, files
56
- end
57
-
58
- def test_file_finder_exclude_glob
59
- files = find_files(fixture(''), :exclude => %w[_git very/deep/*])
60
- expected = %w[
61
- encoding.rb
62
- very/inter.rb
63
- ]
64
- assert_equal Set.new(expected), Set.new(files)
65
- end
66
-
67
- def with_default_encoding(name)
68
- if defined?(Encoding)
69
- old_default = Encoding.default_external
70
- Encoding.default_external = name
71
- begin
72
- yield
73
- ensure
74
- Encoding.default_external = old_default
75
- end
76
- else
77
- yield
78
- end
79
- end
80
- end
@@ -1,120 +0,0 @@
1
- require 'test/unit'
2
- require 'stringio'
3
- require 'ostruct'
4
- require 'ripper-tags'
5
-
6
- class FormattersTest < Test::Unit::TestCase
7
- def build_tag(attrs = {})
8
- { :kind => 'class',
9
- :line => 1,
10
- :path => './script.rb',
11
- :access => 'public',
12
- }.merge(attrs)
13
- end
14
-
15
- def formatter_for(opts)
16
- options = OpenStruct.new(opts)
17
- RipperTags.formatter_for(options)
18
- end
19
-
20
- def test_custom
21
- default = formatter_for(:format => 'custom', :tag_file_name => '-')
22
-
23
- tags = []
24
- tags << build_tag(:line => 1, :kind => 'class', :full_name => 'A::B', :inherits => 'C')
25
- tags << build_tag(:line => 2, :kind => 'method', :full_name => 'A::B#imethod')
26
- tags << build_tag(:line => 3, :kind => 'singleton method', :full_name => 'A::B.smethod')
27
-
28
- output = capture_stdout do
29
- default.with_output do |out|
30
- tags.each { |tag| default.write(tag, out) }
31
- end
32
- end
33
-
34
- assert_equal <<-OUT, output
35
- 1 class A::B < C
36
- 2 def A::B#imethod
37
- 3 def A::B.smethod
38
- OUT
39
- end
40
-
41
- def test_vim
42
- vim = formatter_for(:format => 'vim')
43
- assert_equal %{C\t./script.rb\t/^class C < D$/;"\tc\tclass:A.B\tinherits:D}, vim.format(build_tag(
44
- :kind => 'class', :name => 'C',
45
- :pattern => "class C < D",
46
- :class => 'A::B', :inherits => 'D'
47
- ))
48
- assert_equal %{M\t./script.rb\t/^module M$/;"\tm\tclass:A.B}, vim.format(build_tag(
49
- :kind => 'module', :name => 'M',
50
- :pattern => "module M",
51
- :class => 'A::B'
52
- ))
53
- assert_equal %{imethod\t./script.rb\t/^ def imethod(*args)$/;"\tf\tclass:A.B}, vim.format(build_tag(
54
- :kind => 'method', :name => 'imethod',
55
- :pattern => " def imethod(*args)",
56
- :class => 'A::B'
57
- ))
58
- assert_equal %{smethod\t./script.rb\t/^ def self.smethod(*args)$/;"\tF\tclass:A.B}, vim.format(build_tag(
59
- :kind => 'singleton method', :name => 'smethod',
60
- :pattern => " def self.smethod(*args)",
61
- :class => 'A::B'
62
- ))
63
- end
64
-
65
- def test_emacs
66
- emacs = formatter_for(:format => 'emacs')
67
- assert_equal %{ class C < D\x7FC\x015,0}, emacs.format(build_tag(
68
- :kind => 'class', :name => 'C',
69
- :pattern => " class C < D", :line => 5,
70
- :class => 'A::B', :inherits => 'D'
71
- ))
72
- end
73
-
74
- def test_emacs_file_section_headers
75
- emacs = formatter_for(:format => 'emacs', :tag_file_name => '-')
76
-
77
- tags = []
78
- tags << build_tag(:line => 1, :path => 'path/to/source.rb', :name => 'imethod', :pattern => 'def imethod')
79
- tags << build_tag(:line => 2, :path => 'path/to/source.rb', :name => 'smethod', :pattern => 'def self.smethod')
80
- tags << build_tag(:line => 3, :path => 'path/to/another.rb', :name => 'imethod', :pattern => 'def imethod')
81
-
82
- output = capture_stdout do
83
- emacs.with_output do |out|
84
- tags.each { |tag| emacs.write(tag, out) }
85
- end
86
- end
87
-
88
- assert_equal <<-OUT, output
89
- \x0C
90
- path/to/source.rb,53
91
- def imethod\x7Fimethod\x011,0
92
- def self.smethod\x7Fsmethod\x012,0
93
- \x0C
94
- path/to/another.rb,24
95
- def imethod\x7Fimethod\x013,0
96
- OUT
97
- end
98
-
99
- def test_relative
100
- formatter = formatter_for(:format => 'custom', :tag_file_name => '.git/tags', :tag_relative => true)
101
- tag = build_tag(:path => 'path/to/script.rb')
102
- assert_equal '../path/to/script.rb', formatter.relative_path(tag)
103
- end
104
-
105
- def test_no_relative
106
- formatter = formatter_for(:format => 'custom', :tag_file_name => '.git/tags')
107
- tag = build_tag(:path => 'path/to/script.rb')
108
- assert_equal 'path/to/script.rb', formatter.relative_path(tag)
109
- end
110
-
111
- def capture_stdout
112
- old_stdout, $stdout = $stdout, StringIO.new
113
- begin
114
- yield
115
- $stdout.string
116
- ensure
117
- $stdout = old_stdout
118
- end
119
- end
120
- end
@@ -1,342 +0,0 @@
1
- require 'test/unit'
2
- require 'ripper-tags/parser'
3
-
4
- class TagRipperTest < Test::Unit::TestCase
5
- def extract(code)
6
- RipperTags::Parser.extract(code)
7
- end
8
-
9
- def inspect(tag)
10
- raise ArgumentError, "expected tag, got %p" % tag unless tag
11
- "%d: %s %s%s" % [
12
- tag[:line],
13
- tag[:kind],
14
- tag[:full_name],
15
- tag[:inherits] ? " < #{tag[:inherits]}" : "",
16
- ]
17
- end
18
-
19
- def test_extract_basics
20
- tags = extract(<<-EOC)
21
- Const1 = 123
22
- def gmethod
23
- end
24
- module M
25
- class C
26
- Const2 = 456
27
- def imethod
28
- end
29
- alias imethod_alias imethod
30
- def self.cmethod
31
- end
32
- end
33
- end
34
- class M::C
35
- def imethod2
36
- end
37
- def self.cmethod2
38
- end
39
- class << self
40
- def cmethod3
41
- end
42
- alias cmethod_alias cmethod3
43
- end
44
- end
45
- M::C.class_eval do
46
- def imethod3
47
- end
48
- def self.cmethod4
49
- end
50
- end
51
- M::C::Const3 = true
52
- M.class_eval do
53
- def imethod5
54
- end
55
- end
56
- EOC
57
-
58
- assert_equal %w[
59
- Const1
60
- Object#gmethod
61
- M
62
- M::C
63
- M::C::Const2
64
- M::C#imethod
65
- M::C#imethod_alias
66
- M::C.cmethod
67
- M::C
68
- M::C#imethod2
69
- M::C.cmethod2
70
- M::C.cmethod3
71
- M::C.cmethod_alias
72
- M::C#imethod3
73
- M::C.cmethod4
74
- M::C::Const3
75
- M#imethod5
76
- ], tags.map{ |t| t[:full_name] }
77
- end
78
-
79
- def test_extract_access
80
- tags = extract(<<-EOC)
81
- class Test
82
- def abc() end
83
- private
84
- def def() end
85
- protected
86
- def ghi() end
87
- public
88
- def jkl() end
89
- end
90
- EOC
91
-
92
- assert_equal nil, tags.find{ |t| t[:name] == 'abc' }[:access]
93
- assert_equal 'private', tags.find{ |t| t[:name] == 'def' }[:access]
94
- assert_equal 'protected', tags.find{ |t| t[:name] == 'ghi' }[:access]
95
- assert_equal 'public', tags.find{ |t| t[:name] == 'jkl' }[:access]
96
- end
97
-
98
- def test_extract_module_eval
99
- tags = extract(<<-EOC)
100
- M.module_eval do
101
- class C; end
102
- def imethod; end
103
- end
104
- EOC
105
- assert_equal '2: class M::C', inspect(tags[0])
106
- assert_equal '3: method M#imethod', inspect(tags[1])
107
- end
108
-
109
- def test_extract_manual_subclass
110
- tags = extract(<<-EOC)
111
- module M
112
- C = Class.new(Sup::Klass)
113
- C = Class.new Sup::Klass
114
- C = Class.new
115
- C = Class.new(klass)
116
- end
117
- EOC
118
- assert_equal '2: class M::C < Sup::Klass', inspect(tags[1])
119
- assert_equal '3: class M::C < Sup::Klass', inspect(tags[2])
120
- assert_equal '4: class M::C', inspect(tags[3])
121
- assert_equal '5: class M::C', inspect(tags[4])
122
- end
123
-
124
- def test_extract_assign_from_struct
125
- tags = extract(<<-EOC)
126
- module M
127
- C = Struct.new(:name)
128
- C = Struct.new :name
129
- end
130
- EOC
131
- assert_equal '2: class M::C', inspect(tags[1])
132
- assert_equal '3: class M::C', inspect(tags[2])
133
- end
134
-
135
- def test_extract_class_struct_scope
136
- tags = extract(<<-EOC)
137
- module M
138
- S = Struct.new(:name) do
139
- def imethod; end
140
- end
141
- C = Class.new(SuperClass) do
142
- def imethod; end
143
- end
144
- end
145
- EOC
146
- assert_equal '3: method M::S#imethod', inspect(tags[2])
147
- assert_equal '5: class M::C < SuperClass', inspect(tags[3])
148
- assert_equal '6: method M::C#imethod', inspect(tags[4])
149
- end
150
-
151
- def test_extract_manual_module
152
- tags = extract(<<-EOC)
153
- class C
154
- M = Module.new
155
- M = Module.new do
156
- def imethod; end
157
- end
158
- end
159
- EOC
160
- assert_equal '2: module C::M', inspect(tags[1])
161
- assert_equal '3: module C::M', inspect(tags[2])
162
- assert_equal '4: method C::M#imethod', inspect(tags[3])
163
- end
164
-
165
- def test_extract_define_method
166
- tags = extract(<<-EOC)
167
- module M
168
- define_method(:imethod) do |arg|
169
- end
170
- define_method :imethod do |arg|
171
- end
172
- define_method(:imethod) { |arg| }
173
- end
174
- EOC
175
- assert_equal '2: method M#imethod', inspect(tags[1])
176
- assert_equal '4: method M#imethod', inspect(tags[2])
177
- assert_equal '6: method M#imethod', inspect(tags[3])
178
- end
179
-
180
- def test_ignore_dynamic_define_method
181
- tags = extract(<<-EOC)
182
- module M
183
- define_method(:"imethod_\#{i}") { |arg| }
184
- define_method("imethod_\#{i}") { |arg| }
185
- end
186
- EOC
187
- assert_equal 1, tags.length
188
- end
189
-
190
- def test_extract_alias
191
- tags = extract(<<-EOC)
192
- module M
193
- alias :"[]" :get
194
- alias :"[]=" :set
195
- alias :set :"[]="
196
- end
197
- EOC
198
- assert_equal '2: alias M#[] < get', inspect(tags[1])
199
- assert_equal '3: alias M#[]= < set', inspect(tags[2])
200
- assert_equal '4: alias M#set < []=', inspect(tags[3])
201
- end
202
-
203
- def test_ignore_dynamic_alias
204
- tags = extract(<<-EOC)
205
- module M
206
- alias :"imethod_\#{i}" :foo
207
- alias "imethod_\#{i}" :foo
208
- end
209
- EOC
210
- assert_equal 1, tags.length
211
- end
212
-
213
- def test_extract_alias_method
214
- tags = extract(<<-EOC)
215
- module M
216
- alias_method(:imethod, :foo)
217
- alias_method :imethod, :foo
218
- end
219
- EOC
220
- assert_equal '2: alias M#imethod < foo', inspect(tags[1])
221
- assert_equal '3: alias M#imethod < foo', inspect(tags[2])
222
- end
223
-
224
- def test_ignore_dynamic_alias_method
225
- tags = extract(<<-EOC)
226
- module M
227
- alias_method :"imethod_\#{i}", :foo
228
- alias_method "imethod_\#{i}", :foo
229
- end
230
- EOC
231
- assert_equal 1, tags.length
232
- end
233
-
234
- def test_extract_attr_accessor
235
- tags = extract(<<-EOC)
236
- module M
237
- attr_accessor :a, :b
238
- attr_reader(:a, :b)
239
- attr_writer(:a, :b)
240
- end
241
- EOC
242
- assert_equal '2: method M#a', inspect(tags[1])
243
- assert_equal '2: method M#a=', inspect(tags[2])
244
- assert_equal '2: method M#b', inspect(tags[3])
245
- assert_equal '2: method M#b=', inspect(tags[4])
246
- assert_equal '3: method M#a', inspect(tags[5])
247
- assert_equal '3: method M#b', inspect(tags[6])
248
- assert_equal '4: method M#a=', inspect(tags[7])
249
- assert_equal '4: method M#b=', inspect(tags[8])
250
- end
251
-
252
- def test_extract_rails_associations
253
- tags = extract(<<-EOC)
254
- class C
255
- belongs_to :org, :touch => true
256
- has_one :author, :dependent => :destroy
257
- has_many :posts
258
- has_and_belongs_to_many :tags, :join_table => 'c_tags'
259
- end
260
- EOC
261
- assert_equal 'Rails', tags[1][:language]
262
-
263
- assert_equal '2: belongs_to C.org', inspect(tags[1])
264
- assert_equal '2: belongs_to C.org=', inspect(tags[2])
265
- assert_equal '2: belongs_to C.build_org', inspect(tags[3])
266
- assert_equal '2: belongs_to C.create_org', inspect(tags[4])
267
- assert_equal '2: belongs_to C.create_org!', inspect(tags[5])
268
-
269
- assert_equal '3: has_one C.author', inspect(tags[6])
270
- assert_equal '3: has_one C.author=', inspect(tags[7])
271
- assert_equal '3: has_one C.build_author', inspect(tags[8])
272
- assert_equal '3: has_one C.create_author', inspect(tags[9])
273
- assert_equal '3: has_one C.create_author!', inspect(tags[10])
274
-
275
- assert_equal '4: has_many C.posts', inspect(tags[11])
276
- assert_equal '4: has_many C.posts=', inspect(tags[12])
277
- assert_equal '4: has_many C.post_ids', inspect(tags[13])
278
- assert_equal '4: has_many C.post_ids=', inspect(tags[14])
279
-
280
- assert_equal '5: has_and_belongs_to_many C.tags', inspect(tags[15])
281
- assert_equal '5: has_and_belongs_to_many C.tags=', inspect(tags[16])
282
- assert_equal '5: has_and_belongs_to_many C.tag_ids', inspect(tags[17])
283
- assert_equal '5: has_and_belongs_to_many C.tag_ids=', inspect(tags[18])
284
- end
285
-
286
- def test_extract_rails_scopes
287
- tags = extract(<<-EOC)
288
- class C
289
- named_scope(:red) { {:conditions=>{:color => 'red'}} }
290
- scope :red, where(:color => 'red')
291
- end
292
- EOC
293
- assert_equal 'Rails', tags[1][:language]
294
-
295
- assert_equal '2: scope C.red', inspect(tags[1])
296
- assert_equal '3: scope C.red', inspect(tags[2])
297
- end
298
-
299
- def test_extract_from_erb
300
- tags = extract(<<-EOC)
301
- class NavigationTest < ActionDispatch::IntegrationTest
302
- <% unless options[:skip_active_record] -%>
303
- fixtures :all
304
- <% end -%>
305
-
306
- # test "the truth" do
307
- # assert true
308
- # end
309
- end
310
- EOC
311
-
312
- assert_equal 1, tags.size
313
- assert_equal 'NavigationTest', tags[0][:name]
314
- end
315
-
316
- def test_extract_with_keyword_variables
317
- tags = extract(<<-EOC)
318
- class Foo
319
- @public
320
- @protected
321
- @private
322
- end
323
- EOC
324
-
325
- assert_equal 1, tags.size
326
- assert_equal 'Foo', tags[0][:name]
327
- end
328
-
329
- def test_extract_associations_with_class_name
330
- tags = extract(<<-EOC)
331
- class Foo
332
- belongs_to Bar
333
- has_one Bar
334
- has_and_belongs_to_many Bar
335
- has_many Bar
336
- end
337
- EOC
338
-
339
- assert_equal 1, tags.size
340
- assert_equal 'Foo', tags[0][:name]
341
- end
342
- end