fishman-i18n_routing 0.4.9

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.
@@ -0,0 +1,99 @@
1
+ 0.4.7 (February 14, 2011)
2
+
3
+ * Fix bug in empty translation handling
4
+ * Hack Rack::Mount to handle :locale constraints in top of i18n_locale
5
+ * Fix requirements bug introduced by Rails 3.0.4
6
+ * Add Gemfile with bundler for easy spec on different rails versions
7
+
8
+ 0.4.6 (February 14, 2011)
9
+
10
+ * Handle empty translation
11
+
12
+ 0.4.5 (November 04, 2010)
13
+
14
+ * Fixing Rails 3 scope bug with missing / and no translations
15
+
16
+ 0.4.4 (November 03, 2010)
17
+
18
+ * Fix bug with locale with a dash like pt-br
19
+
20
+ 0.4.3 (October 10, 2010)
21
+
22
+ * Named route can be translated by name or by path
23
+
24
+ 0.4.2 (September 20, 2010)
25
+
26
+ * Fix a Rails3 bug, enabling again to do things like that: get :one, :two, :three
27
+
28
+ 0.4.1 (September 11, 2010)
29
+
30
+ * Fix a Rails3 bug for named routes and prefixed path
31
+
32
+ 0.4.0 (September 08, 2010)
33
+
34
+ * Full support for Rails 3.0.0
35
+
36
+ 0.3.8 (August 30, 2010)
37
+
38
+ * Support the first Rails3 official release (but nested resources is still broken)
39
+
40
+ 0.3.7 (August 26, 2010)
41
+
42
+ * Support Rails3 RC2 thanks to fwalch / Rails3 final will probably require a new version of i18n_routing
43
+ * Not everything works on RC2 (nested resources), will be fixed when Rails3 will be officially released.
44
+
45
+ 0.3.6 (June 13, 2010)
46
+
47
+ * Works even if translations are the same as the translated name
48
+
49
+ 0.3.5 (June 9, 2010)
50
+
51
+ * Clean up some .to_sym in order to avoid unnecessary symbols during runtime
52
+ * Works with both I18n.locale as string or as symbol
53
+ * Try to fix a Pathname instead of string issue
54
+
55
+ 0.3.4 (June 3, 2010)
56
+
57
+ * Fix Rails3 issue with nested single resource again and pluralize controller name as it should be
58
+
59
+ 0.3.3 (June 2, 2010)
60
+
61
+ * Fix Rails3 issue with nested single resource
62
+
63
+ 0.3.2 (June 2, 2010)
64
+
65
+ * Add automatically config/locales/*.yml in the i18n load path in order to fix Rails3 issue
66
+
67
+ 0.3.1 (May 27, 2010)
68
+
69
+ * Add a small Rails3 verification
70
+
71
+ 0.3.0 (May 27, 2010)
72
+
73
+ * Add support for translating path_names, member and collection
74
+ * Fix Rails3 nested resources
75
+ * All specs are now passing under both Rails 2.3.5 and Rails 3
76
+
77
+ 0.2.4 (Apr 21, 2010)
78
+
79
+ * Fix latest Rails3 edge compatibility (previous rails3 beta version not supported any more)
80
+
81
+ 0.2.3 (Apr 21, 2010)
82
+
83
+ * Works on ruby 1.9.2-head
84
+
85
+ 0.2.2 (Apr 21, 2010)
86
+
87
+ * Add I18n gem dependency
88
+
89
+ 0.2.1 (Apr 09, 2010)
90
+
91
+ * Minor Rails3 modification, added gemspec and pushed gem on gemcutter
92
+
93
+ 0.2.0 (Apr 07, 2010)
94
+
95
+ * All specs pass for Rails2, including nested deep resources
96
+
97
+ 0.1.0 (Mar 22, 2010)
98
+
99
+ * Initial release
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source "http://rubygems.org"
2
+ gem "rails", '3.0.6'
3
+ gem 'rspec', '>=2.5.0'
@@ -0,0 +1,81 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ abstract (1.0.0)
5
+ actionmailer (3.0.6)
6
+ actionpack (= 3.0.6)
7
+ mail (~> 2.2.15)
8
+ actionpack (3.0.6)
9
+ activemodel (= 3.0.6)
10
+ activesupport (= 3.0.6)
11
+ builder (~> 2.1.2)
12
+ erubis (~> 2.6.6)
13
+ i18n (~> 0.5.0)
14
+ rack (~> 1.2.1)
15
+ rack-mount (~> 0.6.14)
16
+ rack-test (~> 0.5.7)
17
+ tzinfo (~> 0.3.23)
18
+ activemodel (3.0.6)
19
+ activesupport (= 3.0.6)
20
+ builder (~> 2.1.2)
21
+ i18n (~> 0.5.0)
22
+ activerecord (3.0.6)
23
+ activemodel (= 3.0.6)
24
+ activesupport (= 3.0.6)
25
+ arel (~> 2.0.2)
26
+ tzinfo (~> 0.3.23)
27
+ activeresource (3.0.6)
28
+ activemodel (= 3.0.6)
29
+ activesupport (= 3.0.6)
30
+ activesupport (3.0.6)
31
+ arel (2.0.9)
32
+ builder (2.1.2)
33
+ diff-lcs (1.1.2)
34
+ erubis (2.6.6)
35
+ abstract (>= 1.0.0)
36
+ i18n (0.5.0)
37
+ mail (2.2.16)
38
+ activesupport (>= 2.3.6)
39
+ i18n (>= 0.4.0)
40
+ mime-types (~> 1.16)
41
+ treetop (~> 1.4.8)
42
+ mime-types (1.16)
43
+ polyglot (0.3.1)
44
+ rack (1.2.2)
45
+ rack-mount (0.6.14)
46
+ rack (>= 1.0.0)
47
+ rack-test (0.5.7)
48
+ rack (>= 1.0)
49
+ rails (3.0.6)
50
+ actionmailer (= 3.0.6)
51
+ actionpack (= 3.0.6)
52
+ activerecord (= 3.0.6)
53
+ activeresource (= 3.0.6)
54
+ activesupport (= 3.0.6)
55
+ bundler (~> 1.0)
56
+ railties (= 3.0.6)
57
+ railties (3.0.6)
58
+ actionpack (= 3.0.6)
59
+ activesupport (= 3.0.6)
60
+ rake (>= 0.8.7)
61
+ thor (~> 0.14.4)
62
+ rake (0.8.7)
63
+ rspec (2.5.0)
64
+ rspec-core (~> 2.5.0)
65
+ rspec-expectations (~> 2.5.0)
66
+ rspec-mocks (~> 2.5.0)
67
+ rspec-core (2.5.1)
68
+ rspec-expectations (2.5.0)
69
+ diff-lcs (~> 1.1.2)
70
+ rspec-mocks (2.5.0)
71
+ thor (0.14.6)
72
+ treetop (1.4.9)
73
+ polyglot (>= 0.3.1)
74
+ tzinfo (0.3.26)
75
+
76
+ PLATFORMS
77
+ ruby
78
+
79
+ DEPENDENCIES
80
+ rails (= 3.0.6)
81
+ rspec (>= 2.5.0)
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2010 Guillaume Luccisano - g-mai|: guillaume.luccisano
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,32 @@
1
+ = I18nRouting
2
+
3
+ I18n_routing is a plugin for Ruby on Rails that lets you easily translate your routes trough the I18n api included in Rails since version 2.2
4
+
5
+ All necessary informations are available on the wiki: http://wiki.github.com/kwi/i18n_routing
6
+
7
+ For any question, use the i18_routing google group: http://groups.google.com/group/i18n-routing
8
+
9
+ Works with Rails 2.3 and Rails 3.0
10
+ => Rails3 beta and RC versions are no longer supported !
11
+
12
+ == TODO for next releases (written the 9th of June)
13
+
14
+ * Handle multiple translations for same resources name (Example: nested and not nested resources)
15
+ * Handle namespace translation (and path_prefix on Rails3)
16
+
17
+ == I18n gem version warning
18
+
19
+ Be careful when running Rails 2.3 with the shipped i18n gem: this is an old i18n version and i18_routing will install the latest i18n version as a gem.
20
+ This latest version may be incompatible with some old usages.
21
+ Furthermore, if the i18n gem is present on your system, Rails will load it and skip the shipped version; Keep that in mind.
22
+
23
+ == Contributors
24
+
25
+ * kwi (Guillaume Luccisano)
26
+ * bigtiger (Jim Remsik)
27
+ * mixr (Reiner Dieterich)
28
+ * fwalch
29
+ * doubledrones: h13ronim (Marcin Michałowski)
30
+ * rudionrails (Rudolf Schmidt)
31
+
32
+ Copyright (c) 2010 Guillaume Luccisano - g-mai|: guillaume.luccisano, released under the MIT license
@@ -0,0 +1,28 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+ require 'rspec/core/rake_task'
4
+
5
+ # Now using RSpec 2
6
+
7
+ desc "Run specs for current Rails version"
8
+ RSpec::Core::RakeTask.new do |t|
9
+ t.pattern = "spec/**/*_spec.rb"
10
+ t.verbose = true
11
+ # t.ruby_opts = lambda {
12
+ # @rails_spec_version ? ["-c --format specdoc -- rails_spec_version=#{@rails_spec_version}"] : ["-c --format specdoc"]
13
+ # }
14
+ end
15
+
16
+ task :default => :spec
17
+
18
+ desc "Run Rails 2.x specs"
19
+ task :rails2_spec do
20
+ @rails_spec_version = 2
21
+ Rake::Task['spec'].invoke
22
+ end
23
+
24
+ desc "Run Rails 3.x specs"
25
+ task :rails3_spec do
26
+ @rails_spec_version = 3
27
+ Rake::Task['spec'].invoke
28
+ end
data/init.rb ADDED
@@ -0,0 +1,2 @@
1
+ # encoding: utf-8
2
+ require 'i18n_routing'
@@ -0,0 +1,8 @@
1
+ # encoding: utf-8
2
+ require 'i18n_routing_common'
3
+
4
+ if Rails.version < '3'
5
+ require 'i18n_routing_rails2'
6
+ else
7
+ require 'i18n_routing_rails3'
8
+ end
@@ -0,0 +1,52 @@
1
+ # encoding: utf-8
2
+
3
+ # I18nRouting module for common usage methods
4
+ module I18nRouting
5
+ def self.locale_escaped(locale)
6
+ locale.to_s.downcase.gsub('-', '_')
7
+ end
8
+
9
+ # Return the correct translation for given values
10
+ def self.translation_for(name, type = :resources, option = nil)
11
+ # First, if an option is given, try to get the translation in the routes scope
12
+ if option
13
+ default = "{option}Noi18nRoutingTranslation"
14
+ t = I18n.t(option, :scope => "routes.#{name}.#{type}", :default => default)
15
+ return (t == default ? nil : t)
16
+ else
17
+ default = "{name}Noi18nRoutingTranslation"
18
+
19
+ # Try to get the translation in routes namescope first
20
+ t = I18n.t(:as, :scope => "routes.#{name}", :default => default)
21
+
22
+ return t if t and t != default
23
+
24
+ t = I18n.t(name.to_s, :scope => type, :default => default)
25
+ return (t == default ? nil : t)
26
+ end
27
+ end
28
+
29
+ DefaultPathNames = [:new, :edit]
30
+ PathNamesKeys = [:path_names, :member, :collection]
31
+
32
+ # Return path names hash for given resource
33
+ def self.path_names(name, options)
34
+ h = (options[:path_names] || {}).dup
35
+
36
+ path_names = DefaultPathNames
37
+ PathNamesKeys.each do |v|
38
+ path_names += options[v].keys if options[v] and Hash === options[v]
39
+ end
40
+
41
+ path_names.each do |pn|
42
+ n = translation_for(name, :path_names, pn)
43
+ n = nil if n == pn.to_s
44
+ # Get default path_names in path_names scope if no path_names found
45
+ n ||= I18n.t(pn, :scope => :path_names, :default => name.to_s)
46
+
47
+ h[pn] = n if n and n != name.to_s
48
+ end
49
+
50
+ return h
51
+ end
52
+ end
@@ -0,0 +1,237 @@
1
+ # encoding: utf-8
2
+
3
+ #
4
+ # WARNING : Old and dirty Rails 2.x code
5
+ # Need clean up and intensive refactoring
6
+ #
7
+
8
+ module ActionController
9
+ module Routing
10
+ class Route #:nodoc:
11
+ alias_method :mkd_initialize, :initialize
12
+ def initialize(segments = [], requirements = {}, conditions = {})
13
+ @glang = requirements.delete(:glang)
14
+ mkd_initialize(segments, requirements, conditions)
15
+ end
16
+
17
+ private
18
+ alias_method :mkd_generation_requirements, :generation_requirements
19
+ # Add locale requirements to ensure good route is used when using url_for
20
+ def generation_requirements
21
+ r = mkd_generation_requirements
22
+ if @glang and !r.blank?
23
+ r << " and I18n.locale.to_sym == :'#{@glang}'"
24
+ end
25
+
26
+ return r
27
+ end
28
+ end
29
+ end
30
+ end
31
+
32
+ module ActionController
33
+ module Routing
34
+ class RouteSet #:nodoc:
35
+ attr :locales, true
36
+ attr :i18n_verbose, true
37
+
38
+ class Mapper
39
+ def localized(locales = I18n.available_locales, opts = {})
40
+ old_value = @set.locales
41
+ @set.locales = locales
42
+ @set.i18n_verbose ||= opts.delete(:verbose)
43
+ yield
44
+ ensure
45
+ @set.locales = old_value
46
+ end
47
+ end
48
+
49
+ class NamedRouteCollection #:nodoc:
50
+ alias_method :mkd_define_url_helper, :define_url_helper
51
+ def define_url_helper(route, name, kind, options)
52
+ gl = Thread.current[:globalized]
53
+
54
+ mkd_define_url_helper(route, name, kind, options)
55
+
56
+ if gl
57
+ selector = url_helper_name(name, kind)
58
+
59
+ rlang = if i = name.to_s.rindex("_#{gl}")
60
+ "#{selector.to_s[0, i]}_glang_#{gl}#{selector.to_s[i + "_#{gl}".size, selector.to_s.size]}"
61
+ elsif (gls = Thread.current[:globalized_s]) and i = name.to_s.rindex("_#{gls}")
62
+ "#{selector.to_s[0, i]}_glang_#{gls}#{selector.to_s[i + "_#{gls}".size, selector.to_s.size]}"
63
+ else
64
+ "glang_#{selector}"
65
+ end
66
+
67
+ # surcharge de l'helper
68
+ @module.module_eval <<-end_eval # We use module_eval to avoid leaks
69
+ alias_method :gl#{selector}, :#{selector}
70
+
71
+ def #{selector}(*args)
72
+ selector_g = '#{rlang}'.gsub('glang', I18nRouting.locale_escaped(I18n.locale)).to_sym
73
+
74
+ #logger.debug "Call routes : #{selector} => \#{selector_g} (#{rlang}) "
75
+ #puts "Call routes : #{selector} => \#{selector_g} (#{rlang}) Found:\#{respond_to? selector_g and selector_g != :#{selector}}"
76
+ if respond_to? selector_g and selector_g != :#{selector}
77
+ send(selector_g, *args)
78
+ else
79
+ gl#{selector}(*args)
80
+ end
81
+ end
82
+ protected :gl#{selector}
83
+ end_eval
84
+ end
85
+ end
86
+ end
87
+
88
+ alias_method :gl_add_named_route, :add_named_route
89
+ def add_named_route(name, path, options = {}) #:nodoc:
90
+ if @locales and !path.blank? and !Thread.current[:i18n_no_named_localization]
91
+ # Here, try to translate standard named routes
92
+ name = name.to_s
93
+
94
+ stored_locale = I18n.locale
95
+ @locales.each do |l|
96
+ I18n.locale = l
97
+ nt = "#{I18nRouting.locale_escaped(l)}_#{name}"
98
+ t = I18nRouting.translation_for(name, :named_routes) || I18nRouting.translation_for(path, :named_routes_path)
99
+ if nt != name and !t.blank?
100
+ gl_add_named_route(nt, t, options.merge(:glang => l))
101
+ puts("[I18n] > localize %-10s: %40s (%s) => %s" % ['route', name, l, t]) if @i18n_verbose
102
+ end
103
+ end
104
+ I18n.locale = stored_locale
105
+
106
+ old_v = Thread.current[:globalized]
107
+ Thread.current[:globalized] = true
108
+ gl_add_named_route(name, path, options)
109
+ Thread.current[:globalized] = old_v
110
+ return
111
+ end
112
+
113
+ gl_add_named_route(name, path, options)
114
+ end
115
+ end
116
+ end
117
+ end
118
+
119
+ module ActionController
120
+ module Resources
121
+ class Resource
122
+ alias_method :mkd_initialize, :initialize
123
+ def initialize(entities, options)
124
+ @real_path = options.delete(:real_path)
125
+ @real_path = @real_path.to_s.singularize if @real_path
126
+
127
+ mkd_initialize(entities, options)
128
+ end
129
+
130
+ def nesting_name_prefix
131
+ @real_path ? "#{shallow_name_prefix}#{@real_path}_" : "#{shallow_name_prefix}#{singular}_"
132
+ end
133
+
134
+ def nesting_path_prefix
135
+ @nesting_path_prefix ||= (@real_path ? "#{shallow_path_prefix}/#{path_segment}/:#{@real_path}_id" : "#{shallow_path_prefix}/#{path_segment}/:#{singular}_id")
136
+ end
137
+ end
138
+
139
+ def switch_globalized_state(state)
140
+ old_g = Thread.current[:globalized]
141
+ Thread.current[:globalized] = state
142
+ yield
143
+ Thread.current[:globalized] = old_g
144
+ end
145
+
146
+ def switch_no_named_localization(state)
147
+ old_g = Thread.current[:i18n_no_named_localization]
148
+ Thread.current[:i18n_no_named_localization] = state
149
+ yield
150
+ Thread.current[:i18n_no_named_localization] = old_g
151
+ end
152
+
153
+ def create_globalized_resources(type, namespace, *entities, &block)
154
+ Thread.current[:i18n_nested_deep] ||= 0
155
+ Thread.current[:i18n_nested_deep] += 1
156
+
157
+ if @set.locales
158
+ name = entities.dup.shift.to_s
159
+
160
+ options = entities.extract_options!
161
+ opts = options.dup
162
+
163
+ locales = @set.locales
164
+ localized(nil) do
165
+ stored_locale = I18n.locale
166
+ locales.each do |l|
167
+ I18n.locale = l
168
+ nt = "#{I18nRouting.locale_escaped(l)}_#{name}"
169
+ if nt != name and !(t = I18nRouting.translation_for(name, namespace)).blank?
170
+ opts[:as] = t
171
+ opts[:glang] = l
172
+ opts[:controller] ||= name.to_s.pluralize
173
+ opts[:real_path] = opts[:singular] || name
174
+ opts[:path_names] = I18nRouting.path_names(name, options)
175
+ path_prefix_t = I18n.t(:path_prefix, :scope => :"routes.#{name}", :default => "NoPathPrefixTranslation")
176
+ opts[:path_prefix] = path_prefix_t unless path_prefix_t == "NoPathPrefixTranslation"
177
+
178
+ localized([l]) do
179
+ switch_no_named_localization(true) do
180
+ send(type, nt.to_sym, opts, &block)
181
+ end
182
+ end
183
+ puts("[I18n] > localize %-10s: %40s (%s) => %s" % [namespace, nt, l, t]) if @set.i18n_verbose
184
+ end
185
+ end
186
+ I18n.locale = stored_locale
187
+
188
+
189
+ if Thread.current[:i18n_nested_deep] < 2
190
+ switch_no_named_localization(nil) do
191
+ switch_globalized_state(true) do
192
+ send(type, *(entities << options), &block)
193
+ end
194
+ end
195
+ end
196
+ end
197
+
198
+ else
199
+ send(type, *entities, &block)
200
+ end
201
+
202
+ Thread.current[:i18n_nested_deep] -= 1
203
+ end
204
+
205
+ alias_method :gl_resources, :resources
206
+ def resources(*entities, &block)
207
+ create_globalized_resources(:gl_resources, :resources, *entities, &block)
208
+ end
209
+
210
+ alias_method :gl_resource, :resource
211
+ def resource(*entities, &block)
212
+ create_globalized_resources(:gl_resource, :resource, *entities, &block)
213
+ end
214
+
215
+ private
216
+ alias_method :gl_action_options_for, :action_options_for
217
+ def action_options_for(action, resource, method = nil, resource_options = {})
218
+ opts = gl_action_options_for(action, resource, method, resource_options)
219
+
220
+ if Thread.current[:globalized]
221
+ Thread.current[:globalized] = resource.plural
222
+ if resource.uncountable?
223
+ Thread.current[:globalized] = resource.plural.to_s + '_index'
224
+ end
225
+ Thread.current[:globalized_s] = resource.singular
226
+ else
227
+ Thread.current[:globalized] = nil
228
+ Thread.current[:globalized_s] = nil
229
+ end
230
+ if resource.options[:glang]
231
+ opts[:glang] = resource.options[:glang]
232
+ end
233
+
234
+ opts
235
+ end
236
+ end
237
+ end