Skip to content

Commit

Permalink
stop using exceptions in the backend, use throw/catch instead. still …
Browse files Browse the repository at this point in the history
…needs further investigation as MissingTranslationData still is a subclass of Exception and the I18n.t still simply raises (as currently defined by the API).
  • Loading branch information
Sven Fuchs committed Feb 26, 2011
1 parent 3adff9e commit 35f3cf3
Show file tree
Hide file tree
Showing 6 changed files with 28 additions and 31 deletions.
12 changes: 8 additions & 4 deletions lib/i18n.rb
Original file line number Diff line number Diff line change
Expand Up @@ -149,11 +149,15 @@ def translate(*args)

raise I18n::ArgumentError if key.is_a?(String) && key.empty?

if key.is_a?(Array)
key.map { |k| backend.translate(locale, k, options) }
else
backend.translate(locale, key, options)
result = catch(:missing_translation) do
if key.is_a?(Array)
key.map { |k| backend.translate(locale, k, options) }
else
backend.translate(locale, key, options)
end
end
result.is_a?(Exception) ? raise(result) : result

rescue I18n::ArgumentError => exception
raise exception if raises
handle_exception(exception, locale, key, options)
Expand Down
2 changes: 1 addition & 1 deletion lib/i18n/backend/base.rb
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ def translate(locale, key, options = {})
default(locale, key, default, options) : resolve(locale, key, entry, options)
end

raise(I18n::MissingTranslationData.new(locale, key, options)) if entry.nil?
throw(:missing_translation, I18n::MissingTranslationData.new(locale, key, options)) if entry.nil?
entry = entry.dup if entry.is_a?(String)

entry = pluralize(locale, entry, count) if count
Expand Down
20 changes: 7 additions & 13 deletions lib/i18n/backend/cache.rb
Original file line number Diff line number Diff line change
Expand Up @@ -69,23 +69,17 @@ def translate(locale, key, options = {})
protected

def fetch(cache_key, &block)
result = fetch_storing_missing_translation_exception(cache_key, &block)
raise result if result.is_a?(Exception)
result = _fetch(cache_key, &block)
throw(:missing_translation, result) if result.is_a?(MissingTranslationData)
result = result.dup if result.frozen? rescue result
result
end

def fetch_storing_missing_translation_exception(cache_key, &block)
fetch_ignoring_procs(cache_key, &block)
rescue MissingTranslationData => exception
I18n.cache_store.write(cache_key, exception)
exception
end

def fetch_ignoring_procs(cache_key, &block)
I18n.cache_store.read(cache_key) || yield.tap do |result|
I18n.cache_store.write(cache_key, result) unless result.is_a?(Proc)
end
def _fetch(cache_key, &block)
result = I18n.cache_store.read(cache_key) and return result
result = catch(:missing_translation, &block)
I18n.cache_store.write(cache_key, result) unless result.is_a?(Proc)
result
end

def cache_key(locale, key, options)
Expand Down
10 changes: 4 additions & 6 deletions lib/i18n/backend/chain.rb
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ def translate(locale, key, default_options = {})
options = default_options.except(:default)

backends.each do |backend|
begin
catch(:missing_translation) do
options = default_options if backend == backends.last
translation = backend.translate(locale, key, options)
if namespace_lookup?(translation, options)
Expand All @@ -50,22 +50,20 @@ def translate(locale, key, default_options = {})
elsif !translation.nil?
return translation
end
rescue MissingTranslationData
end
end

return namespace if namespace
raise(I18n::MissingTranslationData.new(locale, key, options))
throw(:missing_translation, I18n::MissingTranslationData.new(locale, key, options))
end

def localize(locale, object, format = :default, options = {})
backends.each do |backend|
begin
catch(:missing_translation) do
result = backend.localize(locale, object, format, options) and return result
rescue MissingTranslationData
end
end
raise(I18n::MissingTranslationData.new(locale, format, options))
throw(:missing_translation, I18n::MissingTranslationData.new(locale, format, options))
end

protected
Expand Down
5 changes: 2 additions & 3 deletions lib/i18n/backend/fallbacks.rb
Original file line number Diff line number Diff line change
Expand Up @@ -41,16 +41,15 @@ def translate(locale, key, options = {})

options[:fallback] = true
I18n.fallbacks[locale].each do |fallback|
begin
catch(:missing_translation) do
result = super(fallback, key, options)
return result unless result.nil?
rescue I18n::MissingTranslationData
end
end
options.delete(:fallback)

return super(locale, nil, options.merge(:default => default)) if default
raise(I18n::MissingTranslationData.new(locale, key, options))
throw(:missing_translation, I18n::MissingTranslationData.new(locale, key, options))
end

def extract_string_or_lambda_default!(options)
Expand Down
10 changes: 6 additions & 4 deletions test/backend/cache_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -37,12 +37,14 @@ def teardown
end

test "still raises MissingTranslationData but also caches it" do
I18n.backend.expects(:lookup).returns(nil)
assert_raise(I18n::MissingTranslationData) { I18n.t(:missing, :raise => true) }

I18n.cache_store.expects(:write).never
I18n.backend.expects(:lookup).never
assert_raise(I18n::MissingTranslationData) { I18n.t(:missing, :raise => true) }
assert_equal 1, I18n.cache_store.instance_variable_get(:@data).size

# I18n.backend.expects(:lookup).returns(nil)
# assert_raise(I18n::MissingTranslationData) { I18n.t(:missing, :raise => true) }
# I18n.backend.expects(:lookup).never
# assert_raise(I18n::MissingTranslationData) { I18n.t(:missing, :raise => true) }
end

test "uses 'i18n' as a cache key namespace by default" do
Expand Down

0 comments on commit 35f3cf3

Please sign in to comment.