yard-padrino 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source 'https://rubygems.org'
2
+
3
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2013 ITO Nobuaki
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,25 @@
1
+ # YARD::Padrino
2
+
3
+ A YARD plugin for parsing Padrino's controllers and helpers.
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ gem 'yard-padrino'
10
+
11
+ And then execute:
12
+
13
+ $ bundle
14
+
15
+ Or install it yourself as:
16
+
17
+ $ gem install yard-padrino
18
+
19
+ ## Contributing
20
+
21
+ 1. Fork it
22
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
23
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
24
+ 4. Push to the branch (`git push origin my-new-feature`)
25
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1 @@
1
+ require 'yard/padrino'
@@ -0,0 +1,381 @@
1
+ # -*- coding: utf-8 -*-
2
+ require 'yard/padrino/version'
3
+ require 'yard'
4
+
5
+ module YARD
6
+ class CLI::Stats
7
+ # Statistics for Padrino Handlers
8
+ def stats_for_padrino_handlers
9
+ output "P) Handlers", *type_statistics(:padrino_handler)
10
+ end
11
+
12
+ # Statistics for Padrino Routes
13
+ def stats_for_padrino_routes
14
+ output "P) Routes", *type_statistics(:padrino_route)
15
+ end
16
+ end
17
+
18
+ module Padrino
19
+ CONDITION_TAG = :'padrino.condition'
20
+
21
+ YARD::Tags::Library.define_tag("Conditions", CONDITION_TAG, :with_name)
22
+ YARD::Tags::Library.visible_tags << CONDITION_TAG
23
+
24
+ YARD::Templates::Engine.register_template_path File.dirname(__FILE__) + '/../../templates'
25
+
26
+ class RegexpObject
27
+ def initialize(pattern)
28
+ @pattern = pattern
29
+ end
30
+
31
+ def to_s
32
+ @pattern
33
+ end
34
+
35
+ def inspect
36
+ "(Regexp) #{@pattern}"
37
+ end
38
+ end
39
+
40
+ class AsisObject
41
+ def initialize(data)
42
+ @data = data
43
+ end
44
+
45
+ def to_s
46
+ @data
47
+ end
48
+
49
+ def inspect
50
+ @data
51
+ end
52
+ end
53
+
54
+ class HandlerObject < YARD::CodeObjects::Base
55
+ attr_accessor :verb
56
+ attr_accessor :args
57
+ attr_accessor :controller
58
+
59
+ def initialize(namespace, name, *args, &block)
60
+ super
61
+
62
+ signature = display_name
63
+ end
64
+
65
+ def <=>(target)
66
+ self.name <=> target.name
67
+ end
68
+
69
+ def display_name
70
+ verb.to_s + " " + args.map { |p| p.inspect }.join(", ")
71
+ end
72
+
73
+ def self.method_name_for_handler(controller, verb, args)
74
+ ([ controller, verb ] + args.map { |p| p.to_s.gsub(/[^\w_]/, '_') }).select { |i| ! i.nil? }.join('_')
75
+ end
76
+ end
77
+
78
+ class GeneralHandlerObject < HandlerObject
79
+ VERB_ORDER = {
80
+ 'before' => 3,
81
+ 'after' => 2,
82
+ 'error' => 1,
83
+ }
84
+
85
+ def type
86
+ :padrino_handler
87
+ end
88
+
89
+ def <=>(target)
90
+ r = self.namespace.to_s <=> target.namespace.to_s
91
+ return r if r != 0
92
+
93
+ r = self.controller.to_s <=> target.controller.to_s
94
+ return r if r != 0
95
+
96
+ r = (VERB_ORDER[self.verb] || 0) <=> (VERB_ORDER[target.verb] || 0)
97
+ return -r if r != 0
98
+
99
+ r = self.args <=> target.args
100
+ return r if r != 0
101
+
102
+ return 0
103
+ end
104
+ end
105
+
106
+ class RouteObject < HandlerObject
107
+ VERB_ORDER = {
108
+ 'GET' => 5,
109
+ 'POST' => 4,
110
+ 'HEAD' => 3,
111
+ 'PUT' => 2,
112
+ 'DELETE' => 1,
113
+ }
114
+
115
+ def type
116
+ :padrino_route
117
+ end
118
+
119
+ def <=>(target)
120
+ r = self.namespace.to_s <=> target.namespace.to_s
121
+ return r if r != 0
122
+
123
+ r = self.controller.to_s <=> target.controller.to_s
124
+ return r if r != 0
125
+
126
+ r = self.args <=> target.args
127
+ return r if r != 0
128
+
129
+ r = (VERB_ORDER[self.verb] || 0) <=> (VERB_ORDER[target.verb] || 0)
130
+ return -r if r != 0
131
+
132
+ return 0
133
+ end
134
+ end
135
+
136
+ class Handler < YARD::Handlers::Ruby::Base
137
+ handles method_call(:helpers)
138
+ handles method_call(:controllers)
139
+ handles method_call(:controller)
140
+
141
+ handles method_call(:before)
142
+ handles method_call(:after)
143
+
144
+ handles method_call(:error)
145
+
146
+ [ :get, :post, :put, :delete, :head ].each do |verb|
147
+ handles method_call(verb)
148
+ end
149
+
150
+ namespace_only
151
+
152
+ def process
153
+ case statement.method_name(true)
154
+ when :helpers
155
+ process_helpers
156
+ when :controllers, :controller
157
+ process_controllers
158
+ when :error
159
+ process_general_handler
160
+ when :before, :after
161
+ process_general_handler
162
+ else
163
+ process_http_verb
164
+ end
165
+ end
166
+
167
+ def process_helpers
168
+ name = statement.first.source.gsub(/\s/, '')
169
+ if statement[1] == :'.'
170
+ # Foo::Bar.helpers do ... end style
171
+ klass = YARD::CodeObjects::ClassObject.new(namespace, name)
172
+ register(klass)
173
+ else
174
+ # helpers do ... end style
175
+ klass = namespace
176
+ end
177
+
178
+ parse_block(statement.last[1], :namespace => klass)
179
+ end
180
+
181
+ def process_controllers
182
+ name = statement.first.source.gsub(/\s/, '')
183
+ if statement[1] == :'.'
184
+ # Foo::Bar.controllers :baz do ... end style
185
+ klass = YARD::CodeObjects::ClassObject.new(namespace, name)
186
+ register(klass)
187
+ else
188
+ # controllers :baz do ... end style
189
+ klass = namespace
190
+ end
191
+
192
+ controller = nil
193
+ param = statement.parameters.first
194
+ if is_literal?(param)
195
+ controller = convert_literal(param)
196
+ end
197
+
198
+ extra_state.padrino ||= {}
199
+ last_controller = extra_state.padrino[:controller]
200
+ begin
201
+ extra_state.padrino[:controller] = controller
202
+ parse_block(statement.last[1], :namespace => klass)
203
+ ensure
204
+ extra_state.padrino[:controller] = last_controller
205
+ end
206
+ end
207
+
208
+ def process_general_handler
209
+ verb = statement.method_name(true).to_s
210
+ paths = []
211
+
212
+ statement.parameters(false).each do |param|
213
+ if param.is_a? YARD::Parser::Ruby::LiteralNode
214
+ paths << convert_literal(param)
215
+ end
216
+ end
217
+
218
+ last_param = statement.parameters(false).last
219
+ options = convert_hash(last_param) if is_hash?(last_param)
220
+
221
+ controller = extra_state.padrino[:controller] if extra_state.padrino
222
+
223
+ register_padrino_general_handler(controller, verb, paths, options)
224
+ end
225
+
226
+ def process_http_verb
227
+ verb = statement.method_name(true).to_s.upcase
228
+ paths = [ convert_literal(statement.parameters.first) ]
229
+
230
+ last_param = statement.parameters(false).last
231
+ options = convert_hash(last_param) if is_hash?(last_param)
232
+
233
+ controller = extra_state.padrino[:controller] if extra_state.padrino
234
+
235
+ register_padrino_route(controller, verb, paths, options)
236
+ end
237
+
238
+ def register_padrino_route(controller, verb, args, options = nil, &block)
239
+ method_name = RouteObject.method_name_for_handler(controller, verb, args)
240
+
241
+ register_padrino_handler(
242
+ {
243
+ :class => RouteObject,
244
+ :group => "Padrino Routings",
245
+ :method_name => method_name,
246
+ :controller => controller,
247
+ :verb => verb,
248
+ :args => args,
249
+ :options => options,
250
+ },
251
+ &block
252
+ )
253
+ end
254
+
255
+ def register_padrino_general_handler(controller, verb, args, options = nil, &block)
256
+ method_name = GeneralHandlerObject.method_name_for_handler(controller, verb, args)
257
+ method_name = method_name + '#' + method_name.object_id.to_s
258
+
259
+ register_padrino_handler(
260
+ {
261
+ :class => GeneralHandlerObject,
262
+ :group => "Padrino Handlers",
263
+ :method_name => method_name,
264
+ :controller => controller,
265
+ :verb => verb,
266
+ :args => args,
267
+ :options => options,
268
+ },
269
+ &block
270
+ )
271
+ end
272
+
273
+ def register_padrino_handler(args = {}, &block)
274
+ handler = args[:class].new(namespace, args[:method_name]) do |o|
275
+ o.group = args[:group]
276
+ o.source = statement.source
277
+ o.docstring = statement.comments
278
+ o.add_file(parser.file, statement.line)
279
+
280
+ o.controller = args[:controller]
281
+ o.verb = args[:verb]
282
+ o.args = args[:args]
283
+
284
+ if args[:options]
285
+ args[:options].each do |key, value|
286
+ o.docstring.add_tag YARD::Tags::Tag.new(CONDITION_TAG, '+' + value.inspect + '+', nil, key.inspect)
287
+ end
288
+ end
289
+ end
290
+
291
+ block.call(handler) if block
292
+
293
+ register handler
294
+ end
295
+
296
+ private
297
+
298
+ def is_hash?(obj)
299
+ return false unless obj.is_a?(YARD::Parser::Ruby::AstNode)
300
+ obj.type == :list && obj.first.type == :assoc
301
+ end
302
+
303
+ def convert_hash(hash)
304
+ result = {}
305
+ return result unless hash.type == :list
306
+
307
+ hash.children.each do |obj|
308
+ next unless obj.type == :assoc
309
+
310
+ begin
311
+ key = convert_literal(obj.children[0])
312
+ begin
313
+ value = convert_literal(obj.children[1])
314
+ rescue YARD::Parser::UndocumentableError
315
+ value = AsisObject.new(obj.children[1].source)
316
+ end
317
+
318
+ result[key] = value
319
+ rescue YARD::Parser::UndocumentableError
320
+ # skip
321
+ end
322
+ end
323
+
324
+ return result
325
+ end
326
+
327
+ def is_literal?(obj)
328
+ return true if obj.is_a?(YARD::Parser::Ruby::LiteralNode)
329
+
330
+ return false unless obj.is_a?(YARD::Parser::Ruby::AstNode)
331
+ obj.type == :dyna_symbol
332
+ end
333
+
334
+ def convert_literal(obj)
335
+ case obj.type
336
+ when :label
337
+ obj.source.to_s.sub(/:$/, "").to_sym
338
+ when :symbol_literal
339
+ obj.jump(:ident, :op, :kw, :const).source.to_s.to_sym
340
+ when :dyna_symbol
341
+ obj.jump(:tstring_content).source.to_s.to_sym
342
+ when :string_literal
343
+ obj.jump(:string_content).source.to_s
344
+ when :regexp_literal
345
+ RegexpObject.new(obj.source)
346
+ when :int
347
+ obj.source.to_i
348
+ else
349
+ raise YARD::Parser::UndocumentableError, obj.source
350
+ end
351
+ end
352
+ end
353
+
354
+ module HtmlHelper
355
+ include YARD::Templates::Helpers::MarkupHelper
356
+ include YARD::Templates::Helpers::HtmlSyntaxHighlightHelper
357
+
358
+ # Formats the signature of Padrino +route+.
359
+ #
360
+ # @param [RouteObject] route the routing object to list the signature of
361
+ # @param [Boolean] link whether to link the method signature to the details view
362
+ # @return [String] the formatted route signature
363
+ def signature_for_padrino_handler(route, link = true)
364
+ name = route.display_name
365
+ blk = format_block(route)
366
+
367
+ title = "<strong>%s</strong>%s" % [h(name), blk]
368
+ if link
369
+ link_title = h(name)
370
+ obj = route.respond_to?(:object) ? route.object : route
371
+ url = url_for(object, obj)
372
+ link_url(url, title, :title => link_title)
373
+ else
374
+ title
375
+ end
376
+ end
377
+ end
378
+
379
+ YARD::Templates::Template.extra_includes << HtmlHelper
380
+ end
381
+ end
@@ -0,0 +1,5 @@
1
+ module YARD
2
+ module Padrino
3
+ VERSION = '0.0.1'
4
+ end
5
+ end
@@ -0,0 +1,35 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'yard/padrino/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "yard-padrino"
8
+ spec.version = YARD::Padrino::VERSION
9
+ spec.authors = ["ITO Nobuaki"]
10
+ spec.email = ["daydream.trippers@gmail.com"]
11
+ spec.description = %q{YARD plugin for Padrino controllers.}
12
+ spec.summary = %q{YARD plugin for Padrino controllers.}
13
+ spec.homepage = ""
14
+ spec.license = "MIT"
15
+
16
+ spec.files = [
17
+ "yard-padrino.gemspec",
18
+ "Gemfile",
19
+ "LICENSE.txt",
20
+ "README.md",
21
+ "Rakefile",
22
+ "lib/yard-padrino.rb",
23
+ "lib/yard/padrino/version.rb",
24
+ "lib/yard/padrino.rb",
25
+ ]
26
+
27
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
28
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
29
+ spec.require_paths = ["lib"]
30
+
31
+ spec.add_runtime_dependency "yard"
32
+
33
+ spec.add_development_dependency "bundler", "~> 1.3"
34
+ spec.add_development_dependency "rake"
35
+ end
metadata ADDED
@@ -0,0 +1,109 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: yard-padrino
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - ITO Nobuaki
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2013-04-16 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: yard
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: bundler
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ~>
36
+ - !ruby/object:Gem::Version
37
+ version: '1.3'
38
+ type: :development
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: '1.3'
46
+ - !ruby/object:Gem::Dependency
47
+ name: rake
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
54
+ type: :development
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ description: YARD plugin for Padrino controllers.
63
+ email:
64
+ - daydream.trippers@gmail.com
65
+ executables: []
66
+ extensions: []
67
+ extra_rdoc_files: []
68
+ files:
69
+ - yard-padrino.gemspec
70
+ - Gemfile
71
+ - LICENSE.txt
72
+ - README.md
73
+ - Rakefile
74
+ - lib/yard-padrino.rb
75
+ - lib/yard/padrino/version.rb
76
+ - lib/yard/padrino.rb
77
+ homepage: ''
78
+ licenses:
79
+ - MIT
80
+ post_install_message:
81
+ rdoc_options: []
82
+ require_paths:
83
+ - lib
84
+ required_ruby_version: !ruby/object:Gem::Requirement
85
+ none: false
86
+ requirements:
87
+ - - ! '>='
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ segments:
91
+ - 0
92
+ hash: -1963093461128883186
93
+ required_rubygems_version: !ruby/object:Gem::Requirement
94
+ none: false
95
+ requirements:
96
+ - - ! '>='
97
+ - !ruby/object:Gem::Version
98
+ version: '0'
99
+ segments:
100
+ - 0
101
+ hash: -1963093461128883186
102
+ requirements: []
103
+ rubyforge_project:
104
+ rubygems_version: 1.8.23
105
+ signing_key:
106
+ specification_version: 3
107
+ summary: YARD plugin for Padrino controllers.
108
+ test_files: []
109
+ has_rdoc: