apipie-rails 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.
Files changed (38) hide show
  1. data/.travis.yml +1 -2
  2. data/CHANGELOG.md +26 -0
  3. data/README.rst +94 -3
  4. data/app/controllers/apipie/apipies_controller.rb +28 -10
  5. data/app/views/apipie/apipies/_disqus.html.erb +4 -2
  6. data/app/views/apipie/apipies/_languages.erb +6 -0
  7. data/app/views/apipie/apipies/_method_detail.erb +7 -7
  8. data/app/views/apipie/apipies/_params.html.erb +2 -2
  9. data/app/views/apipie/apipies/_params_plain.html.erb +2 -2
  10. data/app/views/apipie/apipies/apipie_404.html.erb +7 -4
  11. data/app/views/apipie/apipies/getting_started.html.erb +5 -3
  12. data/app/views/apipie/apipies/index.html.erb +7 -6
  13. data/app/views/apipie/apipies/method.html.erb +4 -2
  14. data/app/views/apipie/apipies/plain.html.erb +3 -3
  15. data/app/views/apipie/apipies/resource.html.erb +3 -2
  16. data/app/views/apipie/apipies/static.html.erb +7 -7
  17. data/app/views/layouts/apipie/apipie.html.erb +1 -1
  18. data/config/locales/en.yml +27 -0
  19. data/lib/apipie-rails.rb +7 -0
  20. data/lib/apipie/apipie_module.rb +5 -2
  21. data/lib/apipie/application.rb +27 -16
  22. data/lib/apipie/configuration.rb +6 -1
  23. data/lib/apipie/extractor.rb +35 -26
  24. data/lib/apipie/extractor/recorder.rb +9 -5
  25. data/lib/apipie/extractor/writer.rb +36 -7
  26. data/lib/apipie/method_description.rb +6 -6
  27. data/lib/apipie/param_description.rb +9 -4
  28. data/lib/apipie/resource_description.rb +5 -5
  29. data/lib/apipie/routing.rb +1 -1
  30. data/lib/apipie/version.rb +1 -1
  31. data/lib/generators/apipie/install/templates/initializer.rb.erb +1 -1
  32. data/lib/tasks/apipie.rake +89 -47
  33. data/spec/dummy/doc/apipie_examples.json +1 -0
  34. data/spec/lib/extractor/middleware_spec.rb +21 -0
  35. data/spec/lib/extractor/writer_spec.rb +76 -0
  36. metadata +10 -5
  37. data/Gemfile.rails30 +0 -5
  38. data/spec/dummy/doc/apipie_examples.yml +0 -28
@@ -7,6 +7,7 @@
7
7
  <%= @resource[:name] %>
8
8
  <% if @resource[:version] %><% end %>
9
9
  </li>
10
+ <%= render(:partial => "languages", :locals => {:doc_url => @resource[:doc_url]}) %>
10
11
  </ul>
11
12
 
12
13
  <div class='page-header'>
@@ -62,6 +63,6 @@
62
63
  <% end %>
63
64
  </div>
64
65
 
65
- <% content_for :apipie_footer do %>
66
- <%= raw @doc[:copyright] %>
66
+ <% unless content_for(:apipie_footer) == @doc[:copyright] %>
67
+ <%= content_for :apipie_footer, raw(@doc[:copyright]) %>
67
68
  <% end %>
@@ -62,14 +62,14 @@
62
62
  <div>
63
63
  <%= raw method[:full_description] %>
64
64
  <% unless method[:examples].blank? %>
65
- <h2>Examples</h2>
65
+ <h2><%= t('apipie.examples') %></h2>
66
66
  <% method[:examples].each do |example| %>
67
67
  <pre><%= example %></pre>
68
68
  <% end %>
69
69
  <% end %>
70
70
 
71
71
  <% unless method[:errors].blank? %>
72
- <h2>Errors</h2>
72
+ <h2><%= t('apipie.errors') %></h2>
73
73
  <% method[:errors].each do |err| %>
74
74
  <%= err[:code] %>
75
75
  <%= err[:description] %>
@@ -79,12 +79,12 @@
79
79
  <% end %>
80
80
 
81
81
  <% unless method[:params].blank? %>
82
- <h2>Params</h2>
82
+ <h2><%= t('apipie.params') %></h2>
83
83
  <table class='table'>
84
84
  <thead>
85
85
  <tr>
86
- <th>Param name</th>
87
- <th>Description</th>
86
+ <th><%= t('apipie.param_name') %></th>
87
+ <th><%= t('apipie.description') %></th>
88
88
  </tr>
89
89
  </thead>
90
90
  <tbody>
@@ -97,6 +97,6 @@
97
97
  </div>
98
98
  <% end %>
99
99
 
100
- <% content_for :apipie_footer do %>
101
- <%= raw @doc[:copyright] %>
100
+ <% unless content_for(:apipie_footer) == @doc[:copyright] %>
101
+ <%= content_for :apipie_footer, raw(@doc[:copyright]) %>
102
102
  <% end %>
@@ -1,7 +1,7 @@
1
1
  <!DOCTYPE html>
2
2
  <html>
3
3
  <head>
4
- <title>API documentation</title>
4
+ <title><%= t('apipie.api_documentation') %></title>
5
5
  <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
6
6
  <%= Apipie.include_stylesheets %>
7
7
  <link type='text/css' rel='stylesheet' href='<%= Apipie.full_url("stylesheets/application.css")%>'/>
@@ -0,0 +1,27 @@
1
+ en:
2
+ apipie:
3
+ resources: Resources
4
+ resource: Resource
5
+ description: Description
6
+ no_docs_found: No documentation found
7
+ no_docs_found_descr: We have not found any documentation for your API.
8
+ follow_instructions_html: Follow %{href} on how to describe your controllers.
9
+ follow_instructions_href: further instructions
10
+ oops: Oops!!
11
+ resource_not_found_html: Resource %{res} not found.
12
+ method_not_found_html: Method %{method} not found for resource %{resource}.
13
+ goto_homepage_html: Try going to %{href}
14
+ goto_homepage_href: "%{app_name} API documentation homepage"
15
+ required: required
16
+ optional: optional
17
+ nil_allowed: nil allowed
18
+ param_name: Param name
19
+ params: Params
20
+ examples: Examples
21
+ metadata: Metadata
22
+ errors: Errors
23
+ supported_formats: Supported Formats
24
+ enable_javascript_html: Please enable JavaScript to view the %{comments_href}.
25
+ comments_powered_by_disqus: comments powered by %{disqus}
26
+ api_documentation: API documentation
27
+
data/lib/apipie-rails.rb CHANGED
@@ -1,3 +1,6 @@
1
+ require 'i18n'
2
+ require 'active_support/hash_with_indifferent_access'
3
+
1
4
  require "apipie/routing"
2
5
  require "apipie/markup"
3
6
  require "apipie/apipie_module"
@@ -13,3 +16,7 @@ require "apipie/validator"
13
16
  require "apipie/railtie"
14
17
  require 'apipie/extractor'
15
18
  require "apipie/version"
19
+
20
+ if Rails.version.start_with?("3.0")
21
+ warn 'Warning: apipie-rails is not going to support Rails 3.0 anymore in future versions'
22
+ end
@@ -8,9 +8,9 @@ module Apipie
8
8
  @application ||= Apipie::Application.new
9
9
  end
10
10
 
11
- def self.to_json(version = nil, resource_name = nil, method_name = nil)
11
+ def self.to_json(version = nil, resource_name = nil, method_name = nil, lang = nil)
12
12
  version ||= Apipie.configuration.default_version
13
- app.to_json(version, resource_name, method_name)
13
+ app.to_json(version, resource_name, method_name, lang)
14
14
  end
15
15
 
16
16
  # all calls delegated to Apipie::Application instance
@@ -59,4 +59,7 @@ module Apipie
59
59
  version && self.configuration.api_base_url.has_key?(version)
60
60
  end
61
61
 
62
+ def self.record(record)
63
+ Apipie::Extractor.start record
64
+ end
62
65
  end
@@ -207,25 +207,14 @@ module Apipie
207
207
 
208
208
  def recorded_examples
209
209
  return @recorded_examples if @recorded_examples
210
- tape_file = File.join(Rails.root,"doc","apipie_examples.yml")
211
- if File.exists?(tape_file)
212
- #if SafeYAML gem is enabled, it will load examples as an array of Hash, instead of hash
213
- if YAML.respond_to?(:safe_load_file) && defined?(SafeYAML)
214
- @recorded_examples = YAML.load_file(tape_file, :safe=>false)
215
- else
216
- @recorded_examples = YAML.load_file(tape_file)
217
- end
218
- else
219
- @recorded_examples = {}
220
- end
221
- @recorded_examples
210
+ @recorded_examples = Apipie::Extractor::Writer.load_recorded_examples
222
211
  end
223
212
 
224
213
  def reload_examples
225
214
  @recorded_examples = nil
226
215
  end
227
216
 
228
- def to_json(version, resource_name, method_name)
217
+ def to_json(version, resource_name, method_name, lang)
229
218
 
230
219
  return unless resource_descriptions.has_key?(version)
231
220
 
@@ -233,11 +222,11 @@ module Apipie
233
222
  # take just resources which have some methods because
234
223
  # we dont want to show eg ApplicationController as resource
235
224
  resource_descriptions[version].inject({}) do |result, (k,v)|
236
- result[k] = v.to_json unless v._methods.blank?
225
+ result[k] = v.to_json(nil, lang) unless v._methods.blank?
237
226
  result
238
227
  end
239
228
  else
240
- [@resource_descriptions[version][resource_name].to_json(method_name)]
229
+ [@resource_descriptions[version][resource_name].to_json(method_name, lang)]
241
230
  end
242
231
 
243
232
  url_args = Apipie.configuration.version_in_url ? version : ''
@@ -245,7 +234,7 @@ module Apipie
245
234
  {
246
235
  :docs => {
247
236
  :name => Apipie.configuration.app_name,
248
- :info => Apipie.app_info(version),
237
+ :info => translate(Apipie.app_info(version), lang),
249
238
  :copyright => Apipie.configuration.copyright,
250
239
  :doc_url => Apipie.full_url(url_args),
251
240
  :api_url => Apipie.api_base_url(version),
@@ -259,12 +248,18 @@ module Apipie
259
248
  end
260
249
 
261
250
  def reload_documentation
251
+ # don't load translated strings, we'll translate them later
252
+ old_locale = locale
253
+ locale = Apipie.configuration.default_locale
254
+
262
255
  rails_mark_classes_for_reload
263
256
 
264
257
  api_controllers_paths.each do |f|
265
258
  load_controller_from_file f
266
259
  end
267
260
  @checksum = nil if Apipie.configuration.update_checksum
261
+
262
+ locale = old_locale
268
263
  end
269
264
 
270
265
  def compute_checksum
@@ -311,6 +306,22 @@ module Apipie
311
306
  end
312
307
  end
313
308
 
309
+ def locale
310
+ Apipie.configuration.locale.call(nil) if Apipie.configuration.locale
311
+ end
312
+
313
+ def locale=(locale)
314
+ Apipie.configuration.locale.call(locale) if Apipie.configuration.locale
315
+ end
316
+
317
+ def translate(str, locale)
318
+ if Apipie.configuration.translate
319
+ Apipie.configuration.translate.call(str, locale)
320
+ else
321
+ str
322
+ end
323
+ end
324
+
314
325
  private
315
326
 
316
327
  def version_prefix(klass)
@@ -6,7 +6,7 @@ module Apipie
6
6
  :default_version, :debug, :version_in_url, :namespaced_resources,
7
7
  :validate, :validate_value, :validate_presence, :authenticate, :doc_path,
8
8
  :show_all_examples, :process_params, :update_checksum, :checksum_path,
9
- :link_extension
9
+ :link_extension, :record, :languages, :translate, :locale, :default_locale
10
10
 
11
11
  alias_method :validate?, :validate
12
12
  alias_method :required_by_default?, :required_by_default
@@ -141,6 +141,11 @@ module Apipie
141
141
  @checksum_path = [@doc_base_url, '/api/']
142
142
  @update_checksum = false
143
143
  @link_extension = ".html"
144
+ @record = false
145
+ @languages = []
146
+ @default_locale = 'en'
147
+ @locale = lambda { |locale| @default_locale }
148
+ @translate = lambda { |str, locale| str }
144
149
  end
145
150
  end
146
151
  end
@@ -7,17 +7,17 @@ require 'apipie/extractor/writer'
7
7
  require 'apipie/extractor/collector'
8
8
 
9
9
  class Apipie::Railtie
10
- if ENV["APIPIE_RECORD"]
11
- initializer 'apipie.extractor' do |app|
12
- ActiveSupport.on_load :action_controller do
13
- before_filter do |controller|
10
+ initializer 'apipie.extractor' do |app|
11
+ ActiveSupport.on_load :action_controller do
12
+ before_filter do |controller|
13
+ if Apipie.configuration.record
14
14
  Apipie::Extractor.call_recorder.analyse_controller(controller)
15
15
  end
16
16
  end
17
- app.middleware.use ::Apipie::Extractor::Recorder::Middleware
18
- ActionController::TestCase::Behavior.instance_eval do
19
- include Apipie::Extractor::Recorder::FunctionalTestRecording
20
- end
17
+ end
18
+ app.middleware.use ::Apipie::Extractor::Recorder::Middleware
19
+ ActionController::TestCase::Behavior.instance_eval do
20
+ include Apipie::Extractor::Recorder::FunctionalTestRecording
21
21
  end
22
22
  end
23
23
  end
@@ -28,6 +28,29 @@ module Apipie
28
28
 
29
29
  class << self
30
30
 
31
+ def start(record)
32
+ Apipie.configuration.record = record
33
+ Apipie.configuration.force_dsl = true
34
+ end
35
+
36
+ def finish
37
+ record_params, record_examples = false, false
38
+ case Apipie.configuration.record
39
+ when "params" then record_params = true
40
+ when "examples" then record_examples = true
41
+ when "all" then record_params = true, record_examples = true
42
+ end
43
+
44
+ if record_examples
45
+ puts "Writing examples to a file"
46
+ write_examples
47
+ end
48
+ if record_params
49
+ puts "Updating auto-generated documentation"
50
+ write_docs
51
+ end
52
+ end
53
+
31
54
  def logger
32
55
  Rails.logger
33
56
  end
@@ -144,28 +167,14 @@ module Apipie
144
167
  end
145
168
  end
146
169
  end
147
-
148
170
  end
149
171
  end
150
172
  end
151
173
 
152
174
  if ENV["APIPIE_RECORD"]
153
- Apipie.configuration.force_dsl = true
154
- at_exit do
155
- record_params, record_examples = false, false
156
- case ENV["APIPIE_RECORD"]
157
- when "params" then record_params = true
158
- when "examples" then record_examples = true
159
- when "all" then record_params = true, record_examples = true
160
- end
175
+ Apipie::Extractor.start ENV["APIPIE_RECORD"]
176
+ end
161
177
 
162
- if record_examples
163
- puts "Writing examples to a file"
164
- Apipie::Extractor.write_examples
165
- end
166
- if record_params
167
- puts "Updating auto-generated documentation"
168
- Apipie::Extractor.write_docs
169
- end
170
- end
178
+ at_exit do
179
+ Apipie::Extractor.finish
171
180
  end
@@ -89,7 +89,11 @@ module Apipie
89
89
  end
90
90
 
91
91
  def call(env)
92
- analyze(env) do
92
+ if Apipie.configuration.record
93
+ analyze(env) do
94
+ @app.call(env)
95
+ end
96
+ else
93
97
  @app.call(env)
94
98
  end
95
99
  end
@@ -112,15 +116,15 @@ module Apipie
112
116
 
113
117
  def process_with_api_recording(*args) # action, parameters = nil, session = nil, flash = nil, http_method = 'GET')
114
118
  ret = process_without_api_recording(*args)
115
- Apipie::Extractor.call_recorder.analyze_functional_test(self)
116
- Apipie::Extractor.call_finished
119
+ if Apipie.configuration.record
120
+ Apipie::Extractor.call_recorder.analyze_functional_test(self)
121
+ Apipie::Extractor.call_finished
122
+ end
117
123
  ret
118
124
  ensure
119
125
  Apipie::Extractor.clean_call_recorder
120
126
  end
121
127
  end
122
-
123
128
  end
124
-
125
129
  end
126
130
  end
@@ -6,15 +6,11 @@ module Apipie
6
6
 
7
7
  def initialize(collector)
8
8
  @collector = collector
9
- @examples_file = File.join(Rails.root, "doc", "apipie_examples.yml")
10
9
  end
11
10
 
12
11
  def write_examples
13
12
  merged_examples = merge_old_new_examples
14
- FileUtils.mkdir_p(File.dirname(@examples_file))
15
- File.open(@examples_file, "w") do |f|
16
- f << YAML.dump(OrderedHash[*merged_examples.sort_by(&:first).flatten(1)])
17
- end
13
+ self.class.write_recorded_examples(merged_examples)
18
14
  end
19
15
 
20
16
  def write_docs
@@ -40,8 +36,38 @@ module Apipie
40
36
  logger.warn("REST_API: Couldn't find action #{action} in #{controller}")
41
37
  end
42
38
 
39
+ def self.write_recorded_examples(examples)
40
+ examples_file = self.examples_file
41
+ FileUtils.mkdir_p(File.dirname(examples_file))
42
+ File.open(examples_file, "w") do |f|
43
+ f << JSON.pretty_generate(OrderedHash[*examples.sort_by(&:first).flatten(1)])
44
+ end
45
+ end
46
+
47
+ def self.load_recorded_examples
48
+ examples_file = self.examples_file
49
+ if File.exists?(examples_file)
50
+ return load_json_examples
51
+ end
52
+ return {}
53
+ end
54
+
55
+ def self.examples_file
56
+ File.join(Rails.root,"doc","apipie_examples.json")
57
+ end
58
+
43
59
  protected
44
60
 
61
+ def self.load_json_examples
62
+ examples = JSON.load(IO.read(examples_file))
63
+ return {} if examples.nil?
64
+ examples.each do |method, records|
65
+ records.each do |record|
66
+ record["verb"] = record["verb"].to_sym if record["verb"]
67
+ end
68
+ end
69
+ end
70
+
45
71
  def desc_to_s(description)
46
72
  "#{description[:controller].name}##{description[:action]}"
47
73
  end
@@ -61,9 +87,13 @@ module Apipie
61
87
  return ordered_call
62
88
  end
63
89
 
90
+ def load_recorded_examples
91
+ self.class.load_recorded_examples
92
+ end
93
+
64
94
  def merge_old_new_examples
65
95
  new_examples = self.load_new_examples
66
- old_examples = self.load_old_examples
96
+ old_examples = self.load_recorded_examples
67
97
  merged_examples = []
68
98
  (new_examples.keys + old_examples.keys).uniq.each do |key|
69
99
  if new_examples.has_key?(key)
@@ -364,6 +394,5 @@ module Apipie
364
394
  end
365
395
  end
366
396
  end
367
-
368
397
  end
369
398
  end
@@ -108,12 +108,12 @@ module Apipie
108
108
  return path
109
109
  end
110
110
 
111
- def method_apis_to_json
111
+ def method_apis_to_json(lang = nil)
112
112
  @apis.each.collect do |api|
113
113
  {
114
114
  :api_url => create_api_url(api),
115
115
  :http_method => api.http_method.to_s,
116
- :short_description => api.short_description
116
+ :short_description => Apipie.app.translate(api.short_description, lang)
117
117
  }
118
118
  end
119
119
  end
@@ -126,15 +126,15 @@ module Apipie
126
126
  @formats || @resource._formats
127
127
  end
128
128
 
129
- def to_json
129
+ def to_json(lang=nil)
130
130
  {
131
131
  :doc_url => doc_url,
132
132
  :name => @method,
133
- :apis => method_apis_to_json,
133
+ :apis => method_apis_to_json(lang),
134
134
  :formats => formats,
135
- :full_description => @full_description,
135
+ :full_description => Apipie.app.translate(@full_description, lang),
136
136
  :errors => errors.map(&:to_json),
137
- :params => params_ordered.map(&:to_json).flatten,
137
+ :params => params_ordered.map{ |param| param.to_json(lang) }.flatten,
138
138
  :examples => @examples,
139
139
  :metadata => @metadata,
140
140
  :see => see.map(&:to_json)