racknga 0.9.3 → 0.9.4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (38) hide show
  1. checksums.yaml +7 -0
  2. data/Gemfile +3 -12
  3. data/README.textile +9 -8
  4. data/Rakefile +19 -272
  5. data/doc/text/news.textile +8 -0
  6. data/lib/racknga/access_log_parser.rb +1 -1
  7. data/lib/racknga/api-keys.rb +40 -0
  8. data/lib/racknga/cache_database.rb +2 -2
  9. data/lib/racknga/exception_mail_notifier.rb +5 -5
  10. data/lib/racknga/log_database.rb +1 -1
  11. data/lib/racknga/log_entry.rb +1 -1
  12. data/lib/racknga/middleware/auth/api-key.rb +95 -0
  13. data/lib/racknga/middleware/cache.rb +20 -6
  14. data/lib/racknga/middleware/deflater.rb +1 -1
  15. data/lib/racknga/middleware/exception_notifier.rb +1 -1
  16. data/lib/racknga/middleware/instance_name.rb +65 -12
  17. data/lib/racknga/middleware/jsonp.rb +24 -5
  18. data/lib/racknga/middleware/log.rb +1 -1
  19. data/lib/racknga/middleware/nginx_raw_uri.rb +1 -1
  20. data/lib/racknga/middleware/range.rb +1 -1
  21. data/lib/racknga/reverse_line_reader.rb +1 -1
  22. data/lib/racknga/utils.rb +1 -1
  23. data/lib/racknga/version.rb +2 -2
  24. data/lib/racknga.rb +2 -1
  25. data/munin/plugins/passenger_application_ +61 -47
  26. data/munin/plugins/passenger_status +64 -33
  27. data/test/racknga-test-utils.rb +2 -1
  28. data/test/run-test.rb +1 -3
  29. data/test/test-access-log-parser.rb +1 -1
  30. data/test/test-api-keys.rb +80 -0
  31. data/test/test-middleware-auth-api-key.rb +144 -0
  32. data/test/test-middleware-cache.rb +1 -1
  33. data/test/test-middleware-instance-name.rb +32 -10
  34. data/test/test-middleware-jsonp.rb +14 -2
  35. data/test/test-middleware-nginx-raw-uri.rb +1 -1
  36. data/test/test-middleware-range.rb +1 -1
  37. metadata +156 -156
  38. data/lib/racknga/will_paginate.rb +0 -48
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: cd550e89e845e0e90ccac2ef34bf3823e03639b0d61e71fe75ee02bb9ad63e2a
4
+ data.tar.gz: 4365f32450b7b0a9fc95b77cfbe3403119b8f2623824f3b4be199ec594255011
5
+ SHA512:
6
+ metadata.gz: a1d84e5281d56bd2f520d0483f1a9ba6cdd1dafbc363268e466b4fea860dd832892d7b5d84ec9ba6d38ebc74d5d356603e7857543ea21029a512fa0b1cd438ae
7
+ data.tar.gz: f983eab4c092d7d2215d2d52310ff51dc3568be0fb197444f4a5f0a8a7c36ef806cb45a2451b38636994d9fac6d53cda6ca07008d91f0d18557cf5f2d8ff0fc9
data/Gemfile CHANGED
@@ -1,6 +1,7 @@
1
1
  # -*- mode: ruby; coding: utf-8 -*-
2
2
  #
3
3
  # Copyright (C) 2011 Kouhei Sutou <kou@clear-code.com>
4
+ # Copyright (C) 2013 Haruka Yoshihara <yoshihara@clear-code.com>
4
5
  #
5
6
  # This library is free software; you can redistribute it and/or
6
7
  # modify it under the terms of the GNU Lesser General Public
@@ -13,18 +14,8 @@
13
14
  #
14
15
  # You should have received a copy of the GNU Lesser General Public
15
16
  # License along with this library; if not, write to the Free Software
16
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17
18
 
18
19
  source "http://rubygems.org/"
19
20
 
20
- gem "rroonga"
21
- gem "rack"
22
-
23
- group :development, :test do
24
- gem "test-unit"
25
- gem "test-unit-notify"
26
- gem "test-unit-capybara"
27
- gem "rake"
28
- gem "jeweler"
29
- gem "yard"
30
- end
21
+ gemspec
data/README.textile CHANGED
@@ -2,15 +2,15 @@ h1. README
2
2
 
3
3
  h2. Name
4
4
 
5
- racknga
5
+ Racknga
6
6
 
7
7
  h2. Description
8
8
 
9
- Rack middlewares that use rroonga features and
10
- middlewares/utilities that don't use rroonga features.
9
+ Rack middlewares that use Rroonga features and
10
+ middlewares/utilities that don't use Rroonga features.
11
11
 
12
- * "rroonga":http://groonga.rubyforge.org/
13
- * "Rack":http://rack.rubyforge.org/
12
+ * "Rroonga":http://ranguba.org/
13
+ * "Rack":http://rack.github.io/
14
14
 
15
15
  h2. Authors
16
16
 
@@ -26,7 +26,7 @@ including contributed patches.)
26
26
  h2. Dependencies
27
27
 
28
28
  * Ruby >= 1.9.1
29
- * rroonga
29
+ * Rroonga
30
30
  * Rack
31
31
 
32
32
  h2. Suggested libraries
@@ -41,11 +41,12 @@ h2. Install
41
41
 
42
42
  h2. Documents
43
43
 
44
- http://groonga.rubyforge.org/racknga/en/
44
+ http://ranguba.org/racknga/en/
45
45
 
46
46
  h2. Mailing list
47
47
 
48
- http://rubyforge.org/mailman/listinfo/groonga-users-en
48
+ * English: "groonga-talk":http://lists.sourceforge.net/mailman/listinfo/groonga-talk
49
+ * Japanese: "groonga-dev":http://lists.sourceforge.jp/mailman/listinfo/groonga-dev
49
50
 
50
51
  h2. Thanks
51
52
 
data/Rakefile CHANGED
@@ -13,7 +13,7 @@
13
13
  #
14
14
  # You should have received a copy of the GNU Lesser General Public
15
15
  # License along with this library; if not, write to the Free Software
16
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17
17
 
18
18
  require 'English'
19
19
 
@@ -21,289 +21,36 @@ require 'fileutils'
21
21
  require 'pathname'
22
22
  require 'erb'
23
23
  require 'rubygems'
24
- require 'jeweler'
25
- require "rake/clean"
26
- require "yard"
24
+ require 'rubygems/package_task'
25
+ require 'bundler/gem_helper'
26
+ require "packnga"
27
27
 
28
28
  base_dir = Pathname.new(__FILE__).dirname
29
29
  racknga_lib_dir = base_dir + 'lib'
30
30
  $LOAD_PATH.unshift(racknga_lib_dir.to_s)
31
31
 
32
- def guess_version
33
- require 'racknga/version'
34
- Racknga::VERSION
32
+ helper = Bundler::GemHelper.new(base_dir)
33
+ def helper.version_tag
34
+ version
35
35
  end
36
+ helper.install
37
+ spec = helper.gemspec
36
38
 
37
- ENV["VERSION"] ||= guess_version
38
- version = ENV["VERSION"].dup
39
- project = nil
40
- spec = nil
41
- Jeweler::Tasks.new do |_spec|
42
- spec = _spec
43
- spec.name = 'racknga'
44
- spec.version = version
45
- spec.rubyforge_project = 'groonga'
46
- spec.homepage = "http://groonga.rubyforge.org/"
47
- authors_file = File.join(base_dir, "AUTHORS")
48
- authors = []
49
- emails = []
50
- File.readlines(authors_file).each do |line|
51
- if /\s*<([^<>]*)>$/ =~ line
52
- authors << $PREMATCH
53
- emails << $1
54
- end
55
- end
56
- spec.authors = authors
57
- spec.email = emails
58
- spec.summary = "A Rack middleware collection for rroonga features."
59
- spec.description = <<-EOD.gsub(/\n/, ' ').strip
60
- Racknga is a Rack middlewares that uses rroonga features.
61
- EOD
62
- spec.license = "LGPLv2.1 or later"
63
- spec.files = FileList["lib/**/*.rb",
64
- "{license,munin,doc/text/}/**/*",
65
- "example/*.rb",
66
- "AUTHORS",
67
- "Rakefile",
68
- "Gemfile",
69
- "README*"]
70
- spec.test_files = FileList["test/**/*.rb"]
39
+ Gem::PackageTask.new(spec) do |pkg|
40
+ pkg.need_tar_gz = true
71
41
  end
72
42
 
73
- Rake::Task["release"].prerequisites.clear
74
- Jeweler::RubygemsDotOrgTasks.new do
43
+ Packnga::DocumentTask.new(spec) do |task|
44
+ task.original_language = "en"
45
+ task.translate_languages = ["ja"]
75
46
  end
76
47
 
77
- reference_base_dir = Pathname.new("doc/reference")
78
- doc_en_dir = reference_base_dir + "en"
79
- html_base_dir = Pathname.new("doc/html")
80
- html_reference_dir = html_base_dir + spec.name
81
- YARD::Rake::YardocTask.new do |task|
82
- task.options += ["--title", spec.name]
83
- task.options += ["--readme", "README.textile"]
84
- task.options += ["--files", "doc/text/**/*"]
85
- task.options += ["--output-dir", doc_en_dir.to_s]
86
- task.options += ["--charset", "utf-8"]
48
+ Packnga::ReleaseTask.new(spec) do
87
49
  end
88
50
 
89
- task :yard do
90
- doc_en_dir.find do |path|
91
- next if path.extname != ".html"
92
- html = path.read
93
- html = html.gsub(/<div id="footer">.+<\/div>/m,
94
- "<div id=\"footer\"></div>")
95
- path.open("w") do |html_file|
96
- html_file.print(html)
97
- end
98
- end
51
+ desc "Run test"
52
+ task :test do
53
+ ruby("-rubygems", "test/run-test.rb")
99
54
  end
100
55
 
101
- include ERB::Util
102
-
103
- def apply_template(content, paths, templates, language)
104
- content = content.sub(/lang="en"/, "lang=\"#{language}\"")
105
-
106
- title = nil
107
- content = content.sub(/<title>(.+?)<\/title>/m) do
108
- title = $1
109
- templates[:head].result(binding)
110
- end
111
-
112
- content = content.sub(/<body(?:.*?)>/) do |body_start|
113
- "#{body_start}\n#{templates[:header].result(binding)}\n"
114
- end
115
-
116
- content = content.sub(/<\/body/) do |body_end|
117
- "\n#{templates[:footer].result(binding)}\n#{body_end}"
118
- end
119
-
120
- content
121
- end
122
-
123
- def erb_template(name)
124
- file = File.join("doc/templates", "#{name}.html.erb")
125
- template = File.read(file)
126
- erb = ERB.new(template, nil, "-")
127
- erb.filename = file
128
- erb
129
- end
130
-
131
- def rsync_to_rubyforge(spec, source, destination, options={})
132
- config = YAML.load(File.read(File.expand_path("~/.rubyforge/user-config.yml")))
133
- host = "#{config["username"]}@rubyforge.org"
134
-
135
- rsync_args = "-av --exclude '*.erb' --chmod=ug+w"
136
- rsync_args << " --delete" if options[:delete]
137
- remote_dir = "/var/www/gforge-projects/#{spec.rubyforge_project}/"
138
- sh("rsync #{rsync_args} #{source} #{host}:#{remote_dir}#{destination}")
139
- end
140
-
141
- def rake(*arguments)
142
- ruby($0, *arguments)
143
- end
144
-
145
- namespace :reference do
146
- translate_languages = [:ja]
147
- supported_languages = [:en, *translate_languages]
148
- html_files = FileList[doc_en_dir + "**/*.html"].to_a
149
-
150
- directory reference_base_dir.to_s
151
- CLOBBER.include(reference_base_dir.to_s)
152
-
153
- po_dir = "doc/po"
154
- pot_file = "#{po_dir}/#{spec.name}.pot"
155
- namespace :pot do
156
- directory po_dir
157
- file pot_file => [po_dir, *html_files] do |t|
158
- sh("xml2po", "--keep-entities", "--output", t.name, *html_files)
159
- end
160
-
161
- desc "Generates pot file."
162
- task :generate => pot_file
163
- end
164
-
165
- namespace :po do
166
- translate_languages.each do |language|
167
- namespace language do
168
- po_file = "#{po_dir}/#{language}.po"
169
-
170
- if File.exist?(po_file)
171
- file po_file => html_files do |t|
172
- sh("xml2po", "--keep-entities", "--update", t.name, *html_files)
173
- end
174
- else
175
- file po_file => pot_file do |t|
176
- sh("msginit",
177
- "--input=#{pot_file}",
178
- "--output=#{t.name}",
179
- "--locale=#{language}")
180
- end
181
- end
182
-
183
- desc "Updates po file for #{language}."
184
- task :update => po_file
185
- end
186
- end
187
-
188
- desc "Updates po files."
189
- task :update do
190
- rake("clobber")
191
- rake("yard")
192
- translate_languages.each do |language|
193
- rake("reference:po:#{language}:update")
194
- end
195
- end
196
- end
197
-
198
- namespace :translate do
199
- translate_languages.each do |language|
200
- po_file = "#{po_dir}/#{language}.po"
201
- translate_doc_dir = "#{reference_base_dir}/#{language}"
202
-
203
- desc "Translates documents to #{language}."
204
- task language => [po_file, reference_base_dir, *html_files] do
205
- doc_en_dir.find do |path|
206
- base_path = path.relative_path_from(doc_en_dir)
207
- translated_path = "#{translate_doc_dir}/#{base_path}"
208
- if path.directory?
209
- mkdir_p(translated_path)
210
- next
211
- end
212
- case path.extname
213
- when ".html"
214
- sh("xml2po --keep-entities " +
215
- "--po-file #{po_file} --language #{language} " +
216
- "#{path} > #{translated_path}")
217
- else
218
- cp(path.to_s, translated_path, :preserve => true)
219
- end
220
- end
221
- end
222
- end
223
- end
224
-
225
- translate_task_names = translate_languages.collect do |language|
226
- "reference:translate:#{language}"
227
- end
228
- desc "Translates references."
229
- task :translate => translate_task_names
230
-
231
- desc "Generates references."
232
- task :generate => [:yard, :translate]
233
-
234
- namespace :publication do
235
- task :prepare do
236
- supported_languages.each do |language|
237
- raw_reference_dir = reference_base_dir + language.to_s
238
- prepared_reference_dir = html_reference_dir + language.to_s
239
- rm_rf(prepared_reference_dir.to_s)
240
- head = erb_template("head.#{language}")
241
- header = erb_template("header.#{language}")
242
- footer = erb_template("footer.#{language}")
243
- raw_reference_dir.find do |path|
244
- relative_path = path.relative_path_from(raw_reference_dir)
245
- prepared_path = prepared_reference_dir + relative_path
246
- if path.directory?
247
- mkdir_p(prepared_path.to_s)
248
- else
249
- case path.basename.to_s
250
- when /(?:file|method|class)_list\.html\z/
251
- cp(path.to_s, prepared_path.to_s)
252
- when /\.html\z/
253
- relative_dir_path = relative_path.dirname
254
- current_path = relative_dir_path + path.basename
255
- if current_path.basename.to_s == "index.html"
256
- current_path = current_path.dirname
257
- end
258
- top_path = html_base_dir.relative_path_from(prepared_path.dirname)
259
- package_path = top_path + spec.name
260
- paths = {
261
- :top => top_path,
262
- :current => current_path,
263
- :package => package_path,
264
- }
265
- templates = {
266
- :head => head,
267
- :header => header,
268
- :footer => footer
269
- }
270
- content = apply_template(File.read(path.to_s),
271
- paths,
272
- templates,
273
- language)
274
- File.open(prepared_path.to_s, "w") do |file|
275
- file.print(content)
276
- end
277
- else
278
- cp(path.to_s, prepared_path.to_s)
279
- end
280
- end
281
- end
282
- end
283
- File.open("#{html_reference_dir}/.htaccess", "w") do |file|
284
- file.puts("RedirectMatch permanent ^/#{spec.name}/$ " +
285
- "#{spec.homepage}#{spec.name}/en/")
286
- end
287
- end
288
- end
289
-
290
- desc "Upload document to rubyforge."
291
- task :publish => [:generate, "reference:publication:prepare"] do
292
- rsync_to_rubyforge(spec, "#{html_reference_dir}/", spec.name)
293
- end
294
- end
295
-
296
- namespace :html do
297
- desc "Publish HTML to Web site."
298
- task :publish do
299
- rsync_to_rubyforge(spec, "#{html_base_dir}/", "")
300
- end
301
- end
302
-
303
- desc "Upload document to rubyforge."
304
- task :publish => ["reference:publish"]
305
-
306
- desc "Tag the current revision."
307
- task :tag do
308
- sh("git tag -a #{version} -m 'release #{version}!!!'")
309
- end
56
+ task :default => :test
@@ -1,5 +1,13 @@
1
1
  h1. NEWS
2
2
 
3
+ h2. 0.9.4: 2023-09-03
4
+
5
+ h3. Improvments
6
+
7
+ * [cache] Made Rroonga dependency optional. Users must add Rroonga
8
+ dependency explicitly.
9
+ * And more improvements...
10
+
3
11
  h2. 0.9.3: 2011-11-12
4
12
 
5
13
  h3. Improvments
@@ -15,7 +15,7 @@
15
15
  #
16
16
  # You should have received a copy of the GNU Lesser General Public
17
17
  # License along with this library; if not, write to the Free Software
18
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19
19
 
20
20
  require "racknga/log_entry"
21
21
  require "racknga/reverse_line_reader"
@@ -0,0 +1,40 @@
1
+ # -*- coding: utf-8 -*-
2
+ #
3
+ # Copyright (C) 2012 Haruka Yoshihara <yoshihara@clear-code.com>
4
+ #
5
+ # This library is free software; you can redistribute it and/or
6
+ # modify it under the terms of the GNU Lesser General Public
7
+ # License as published by the Free Software Foundation; either
8
+ # version 2.1 of the License, or (at your option) any later version.
9
+ #
10
+ # This library is distributed in the hope that it will be useful,
11
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
+ # Lesser General Public License for more details.
14
+ #
15
+ # You should have received a copy of the GNU Lesser General Public
16
+ # License along with this library; if not, write to the Free Software
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
+
19
+ module Racknga
20
+ # This is a store for API keys. It is used with
21
+ # Racknga::Middleware::Auth::APIKeys.
22
+ class APIKeys
23
+ # @param [String] query_parameter query parameter to specify an API key.
24
+ # @param [Array] api_keys stored API keys.
25
+ def initialize(query_parameter, api_keys)
26
+ @query_parameter = query_parameter
27
+ @api_keys = api_keys
28
+ end
29
+
30
+ # Checks whether stored API keys includes an API key in a request.
31
+ # @param [Hash] environment an environment for Rack.
32
+ # @return [Boolean] true if an API key is included, or false if not.
33
+ def include?(environment)
34
+ request = Rack::Request.new(environment)
35
+ key = request[@query_parameter]
36
+
37
+ @api_keys.include?(key)
38
+ end
39
+ end
40
+ end
@@ -14,7 +14,7 @@
14
14
  #
15
15
  # You should have received a copy of the GNU Lesser General Public
16
16
  # License along with this library; if not, write to the Free Software
17
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
18
 
19
19
  require 'fileutils'
20
20
 
@@ -98,7 +98,7 @@ module Racknga
98
98
  :key_type => "ShortText") do |table|
99
99
  table.uint32("status")
100
100
  table.short_text("headers")
101
- table.text("body", :compress => :zlib)
101
+ table.text("body")
102
102
  table.short_text("checksum")
103
103
  table.uint32("age")
104
104
  table.time("created_at")
@@ -14,7 +14,7 @@
14
14
  #
15
15
  # You should have received a copy of the GNU Lesser General Public
16
16
  # License along with this library; if not, write to the Free Software
17
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
18
 
19
19
  require 'time'
20
20
  require 'net/smtp'
@@ -132,10 +132,10 @@ EOE
132
132
  end
133
133
 
134
134
  def send_summaries
135
- subject = "summaries of #{@summaries.size} notifications"
136
- mail = create_mail(:subject => subject,
137
- :body => report_body)
138
- send(mail)
135
+ subject = "summaries of #{@summaries.size} notifications"
136
+ mail = create_mail(:subject => subject,
137
+ :body => report_body)
138
+ send(mail)
139
139
  end
140
140
 
141
141
  def report_body
@@ -14,7 +14,7 @@
14
14
  #
15
15
  # You should have received a copy of the GNU Lesser General Public
16
16
  # License along with this library; if not, write to the Free Software
17
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
18
 
19
19
  require 'fileutils'
20
20
 
@@ -15,7 +15,7 @@
15
15
  #
16
16
  # You should have received a copy of the GNU Lesser General Public
17
17
  # License along with this library; if not, write to the Free Software
18
- # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19
19
 
20
20
  module Racknga
21
21
  class LogEntry
@@ -0,0 +1,95 @@
1
+ # -*- coding: utf-8 -*-
2
+ #
3
+ # Copyright (C) 2012 Haruka Yoshihara <yoshihara@clear-code.com>
4
+ #
5
+ # This library is free software; you can redistribute it and/or
6
+ # modify it under the terms of the GNU Lesser General Public
7
+ # License as published by the Free Software Foundation; either
8
+ # version 2.1 of the License, or (at your option) any later version.
9
+ #
10
+ # This library is distributed in the hope that it will be useful,
11
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
+ # Lesser General Public License for more details.
14
+ #
15
+ # You should have received a copy of the GNU Lesser General Public
16
+ # License along with this library; if not, write to the Free Software
17
+ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
+
19
+ module Racknga
20
+ module Middleware
21
+ module Auth
22
+ # This is a middleware that provides an authentication of API key.
23
+ # This middleware checks whether a URL requests API and
24
+ # whether API key in its request is authorized.
25
+ # When a URL requests API with unauthorized API key,
26
+ # this middleware returns json response with :error_message.
27
+ # Racknga::APIKeys is used as authorized API keys.
28
+ # Usage:
29
+ # require 'racknga'
30
+ #
31
+ # authorized_api_keys =
32
+ # Racknga::APIKeys.new("api-query-parameter", ["key1", "key2"])
33
+ # error_response =
34
+ # api_key_options = {
35
+ # :api_url_prefixes => ["/api"],
36
+ # :authorized_api_keys => authorized_api_keys,
37
+ # :error_response => {"error" => "this api key is not authorized"}
38
+ # }
39
+ # use Racknga::Middleware::Auth::APIKey, api_key_options
40
+ # run YourApplication
41
+ class APIKey
42
+ def initialize(application, options={})
43
+ @application = application
44
+ @authorized_api_keys = options[:authorized_api_keys]
45
+ url_prefixes_option = options[:api_url_prefixes]
46
+ @api_url_prefixes = url_prefixes_option.collect do |url|
47
+ /\A#{Regexp.escape(url)}/
48
+ end
49
+ @error_response = options[:error_response].to_json
50
+ @disable_authorization = options[:disable_authorization]
51
+ end
52
+
53
+ # For Rack.
54
+ def call(environment)
55
+ if api_url?(environment) and not authorized?(environment)
56
+ unauthorized_access_response
57
+ else
58
+ @application.call(environment)
59
+ end
60
+ end
61
+
62
+ private
63
+ def api_url?(environment)
64
+ @api_url_prefixes.any? do |prefix|
65
+ environment["PATH_INFO"] =~ prefix
66
+ end
67
+ end
68
+
69
+ def authorized?(environment)
70
+ if disable_authorization?
71
+ true
72
+ else
73
+ if @authorized_api_keys
74
+ @authorized_api_keys.include?(environment)
75
+ else
76
+ false
77
+ end
78
+ end
79
+ end
80
+
81
+ def disable_authorization?
82
+ @disable_authorization
83
+ end
84
+
85
+ def unauthorized_access_response
86
+ [
87
+ 401,
88
+ {"Content-Type" => "application/json; charset=utf-8"},
89
+ [@error_response],
90
+ ]
91
+ end
92
+ end
93
+ end
94
+ end
95
+ end