Skip to content

Commit b88a8df

Browse files
authored
Merge pull request #1796 from Morred/fix-unavailable-locale-crash
Fix crash when available locales are enforced but fallback locale unavailable
2 parents ed0e221 + f0d1fa1 commit b88a8df

File tree

5 files changed

+76
-2
lines changed

5 files changed

+76
-2
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#### Fixes
1010

1111
* Your contribution here.
12+
* [#1796](https://github.com/ruby-grape/grape/pull/1796): Fix crash when available locales are enforced but fallback locale unavailable - [@Morred](https://github.com/Morred).
1213
* [#1776](https://github.com/ruby-grape/grape/pull/1776): Validate response returned by the exception handler - [@darren987469](https://github.com/darren987469).
1314
* [#1787](https://github.com/ruby-grape/grape/pull/1787): Add documented but not implemented ability to `.insert` a middleware in the stack - [@michaellennox](https://github.com/michaellennox).
1415
* [#1788](https://github.com/ruby-grape/grape/pull/1788): Fix route requirements bug - [@darren987469](https://github.com/darren987469), [@darrellnash](https://github.com/darrellnash).

README.md

+2
Original file line numberDiff line numberDiff line change
@@ -1559,6 +1559,8 @@ end
15591559
Grape supports I18n for parameter-related error messages, but will fallback to English if
15601560
translations for the default locale have not been provided. See [en.yml](lib/grape/locale/en.yml) for message keys.
15611561

1562+
In case your app enforces available locales only and :en is not included in your available locales, Grape cannot fall back to English and will return the translation key for the error message. To avoid this behaviour, either provide a translation for your default locale or add :en to your available locales.
1563+
15621564
### Custom Validation messages
15631565

15641566
Grape supports custom validation messages for parameter-related and coerce-related error messages.

lib/grape/exceptions/base.rb

+9-1
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,15 @@ def translate(key, **options)
7474
options = options.dup
7575
options[:default] &&= options[:default].to_s
7676
message = ::I18n.translate(key, **options)
77-
message.present? ? message : ::I18n.translate(key, locale: FALLBACK_LOCALE, **options)
77+
message.present? ? message : fallback_message(key, **options)
78+
end
79+
80+
def fallback_message(key, **options)
81+
if ::I18n.enforce_available_locales && !::I18n.available_locales.include?(FALLBACK_LOCALE)
82+
key
83+
else
84+
::I18n.translate(key, locale: FALLBACK_LOCALE, **options)
85+
end
7886
end
7987
end
8088
end

spec/grape/exceptions/base_spec.rb

+61
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
require 'spec_helper'
2+
3+
describe Grape::Exceptions::Base do
4+
describe '#compose_message' do
5+
subject { described_class.new.send(:compose_message, key, attributes) }
6+
7+
let(:key) { :invalid_formatter }
8+
let(:attributes) { { klass: String, to_format: 'xml' } }
9+
10+
after do
11+
I18n.available_locales = %i[en]
12+
I18n.default_locale = :en
13+
end
14+
15+
context 'when I18n enforces available locales' do
16+
before { I18n.enforce_available_locales = true }
17+
18+
context 'when the fallback locale is available' do
19+
before do
20+
I18n.available_locales = %i[de en]
21+
I18n.default_locale = :de
22+
end
23+
24+
it 'returns the translated message' do
25+
expect(subject).to eq('cannot convert String to xml')
26+
end
27+
end
28+
29+
context 'when the fallback locale is not available' do
30+
before do
31+
I18n.available_locales = %i[de jp]
32+
I18n.default_locale = :de
33+
end
34+
35+
it 'returns the translation string' do
36+
expect(subject).to eq("grape.errors.messages.#{key}")
37+
end
38+
end
39+
end
40+
41+
context 'when I18n does not enforce available locales' do
42+
before { I18n.enforce_available_locales = false }
43+
44+
context 'when the fallback locale is available' do
45+
before { I18n.available_locales = %i[de en] }
46+
47+
it 'returns the translated message' do
48+
expect(subject).to eq('cannot convert String to xml')
49+
end
50+
end
51+
52+
context 'when the fallback locale is not available' do
53+
before { I18n.available_locales = %i[de jp] }
54+
55+
it 'returns the translated message' do
56+
expect(subject).to eq('cannot convert String to xml')
57+
end
58+
end
59+
end
60+
end
61+
end

spec/spec_helper.rb

+3-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,9 @@
1212
require file
1313
end
1414

15-
I18n.enforce_available_locales = false
15+
# The default value for this setting is true in a standard Rails app,
16+
# so it should be set to true here as well to reflect that.
17+
I18n.enforce_available_locales = true
1618

1719
RSpec.configure do |config|
1820
config.include Rack::Test::Methods

0 commit comments

Comments
 (0)