require "spec_helper" describe I18n::JS do describe '.config_file_path' do let(:default_path) { I18n::JS::DEFAULT_CONFIG_PATH } let(:new_path) { File.join("tmp", default_path) } subject { described_class.config_file_path } context "when it is not set" do it { should eq default_path } end context "when it is set already" do before { described_class.config_file_path = new_path } it { should eq new_path } end end context "exporting" do before do stub_const('I18n::JS::DEFAULT_EXPORT_DIR_PATH', temp_path) end it "exports messages to default path when configuration file doesn't exist" do I18n::JS.export file_should_exist "translations.js" end it "exports messages using custom output path" do set_config "custom_path.yml" allow(I18n::JS::Segment).to receive(:new).with("tmp/i18n-js/all.js", translations, {js_extend: true, sort_translation_keys: true, json_only: false}).and_call_original allow_any_instance_of(I18n::JS::Segment).to receive(:save!).with(no_args) I18n::JS.export end it "sets default scope to * when not specified" do set_config "no_scope.yml" allow(I18n::JS::Segment).to receive(:new).with("tmp/i18n-js/no_scope.js", translations, {js_extend: true, sort_translation_keys: true, json_only: false}).and_call_original allow_any_instance_of(I18n::JS::Segment).to receive(:save!).with(no_args) I18n::JS.export end it "exports to multiple files" do set_config "multiple_files.yml" I18n::JS.export file_should_exist "all.js" file_should_exist "tudo.js" end it "ignores an empty config file" do set_config "no_config.yml" I18n::JS.export file_should_exist "translations.js" end it "exports to a JS file per available locale" do set_config "js_file_per_locale.yml" I18n::JS.export file_should_exist "en.js" file_should_exist "fr.js" en_output = File.read(File.join(I18n::JS.export_i18n_js_dir_path, "en.js")) expect(en_output).to eq(<(locale) { results[locale][:admin][:show][:title] } } context 'when I18n.available_locales is not set' do it { expect(subject).to eq ::I18n.available_locales } it 'should allow all locales' do expect(result.call(:en)).to eql('Show') expect(result.call(:fr)).to eql('Visualiser') expect(result.call(:ja)).to eql('Ignore me') end end context 'when I18n.available_locales is set' do let(:available_locales) { %i[en fr] } before { allow(::I18n).to receive(:available_locales).and_return(available_locales) } it { expect(subject).to eq available_locales } it 'should ignore non-valid locales' do expect(result.call(:en)).to eql('Show') expect(result.call(:fr)).to eql('Visualiser') expect(results).not_to include(:ja) end context 'when :js_available_locales set in config' do before { set_config 'js_available_locales_custom.yml' } it { expect(subject).to eq %i[en foo] } it 'should ignore non-valid locales' do expect(result.call(:en)).to eql('Show') expect(results).not_to include(:fr, :ja) end end end end context 'I18n.available_locales' do let(:results) { described_class.scoped_translations('*.admin.*.title') } let(:result) { ->(locale) { results[locale][:admin][:show][:title] } } context 'when I18n.available_locales is not set' do it 'should allow all locales' do expect(result.call(:en)).to eql('Show') expect(result.call(:fr)).to eql('Visualiser') expect(result.call(:ja)).to eql('Ignore me') end end context 'when I18n.available_locales is set' do before { allow(::I18n).to receive(:available_locales){ [:en, :fr] } } it 'should ignore non-valid locales' do expect(result.call(:en)).to eql('Show') expect(result.call(:fr)).to eql('Visualiser') expect(results).not_to include(:ja) end end end context "general" do it "sets export directory" do expect(I18n::JS::DEFAULT_EXPORT_DIR_PATH).to eql("public/javascripts") end it "sets empty hash as configuration when no file is found" do expect(I18n::JS.config_file_exists?).to eql(false) expect(I18n::JS.config).to eql({}) end it "executes erb in config file" do set_config "erb.yml" config_entry = I18n::JS.config[:translations].first expect(config_entry["only"]).to eq("*.date.formats") end end describe "i18n.js exporting" do after { begin described_class.send(:remove_instance_variable, :@export_i18n_js_dir_path); rescue; end } describe ".export_i18n_js with global variable" do before do allow(FileUtils).to receive(:mkdir_p).and_call_original allow(FileUtils).to receive(:cp).and_call_original allow(described_class).to receive(:export_i18n_js_dir_path).and_return(export_i18n_js_dir_path) I18n::JS.export_i18n_js end context 'when .export_i18n_js_dir_path returns something' do let(:export_i18n_js_dir_path) { temp_path } it "does create the folder before copying" do expect(FileUtils).to have_received(:mkdir_p).with(export_i18n_js_dir_path).once end it "does copy the file with FileUtils.cp" do expect(FileUtils).to have_received(:cp).once end it "exports the file" do expect(File).to be_file(File.join(I18n::JS.export_i18n_js_dir_path, "i18n.js")) end end context 'when .export_i18n_js_dir_path is set to nil' do let(:export_i18n_js_dir_path) { nil } it "does NOT create the folder before copying" do expect(FileUtils).to_not have_received(:mkdir_p) end it "does NOT copy the file with FileUtils.cp" do expect(FileUtils).to_not have_received(:cp) end end end describe ".export_i18n_js with config" do let(:export_action) do allow(FileUtils).to receive(:mkdir_p).and_call_original allow(FileUtils).to receive(:cp).and_call_original I18n::JS.export_i18n_js end context 'when :export_i18n_js set in config' do before { set_config "js_export_dir_custom.yml"; export_action } let(:export_i18n_js_dir_path) { temp_path } let(:config_export_path) { "tmp/i18n-js/foo" } it "does create the folder before copying" do expect(FileUtils).to have_received(:mkdir_p).with(config_export_path).once end it "does copy the file with FileUtils.cp" do expect(FileUtils).to have_received(:cp).once end it "exports the file" do expect(File).to be_file(File.join(config_export_path, "i18n.js")) end end context 'when .export_i18n_js_dir_path is set to false' do before { set_config "js_export_dir_none.yml"; export_action } it "does NOT create the folder before copying" do expect(FileUtils).to_not have_received(:mkdir_p) end it "does NOT copy the file with FileUtils.cp" do expect(FileUtils).to_not have_received(:cp) end end end describe '.export_i18n_js_dir_path' do let(:default_path) { I18n::JS::DEFAULT_EXPORT_DIR_PATH } let(:new_path) { File.join("tmp", default_path) } after { described_class.send(:remove_instance_variable, :@export_i18n_js_dir_path) } subject { described_class.export_i18n_js_dir_path } context "when it is not set" do it { should eq default_path } end context "when it is set to another path already" do before { described_class.export_i18n_js_dir_path = new_path } it { should eq new_path } end context "when it is set to nil already" do before { described_class.export_i18n_js_dir_path = nil } it { should eq :none } end end end describe "translation key sorting" do describe ".sort_translation_keys?" do after { described_class.send(:remove_instance_variable, :@sort_translation_keys) } subject { described_class.sort_translation_keys? } context "set with config" do context 'when :sort_translation_keys is not set in config' do before :each do set_config "default.yml" end it { should eq true } end context 'when :sort_translation_keys set to true in config' do before :each do set_config "js_sort_translation_keys_true.yml" end it { should eq true } end context 'when :sort_translation_keys set to false in config' do before :each do set_config "js_sort_translation_keys_false.yml" end it { should eq false } end end context 'set by .sort_translation_keys' do context "when it is not set" do it { should eq true } end context "when it is set to true" do before { described_class.sort_translation_keys = true } it { should eq true } end context "when it is set to false" do before { described_class.sort_translation_keys = false } it { should eq false } end end end context "exporting" do subject do I18n::JS.export file_should_exist "en.js" File.read(File.join(I18n::JS.export_i18n_js_dir_path, "en.js")) end before do stub_const('I18n::JS::DEFAULT_EXPORT_DIR_PATH', temp_path) end context 'sort_translation_keys is true' do before :each do set_config "js_sort_translation_keys_true.yml" end it "exports with the keys sorted" do expect(subject).to eq <