"缺少翻译"当运行与ember-i18n包相关的Ember验收测试时

时间:2017-09-11 23:13:07

标签: ember.js qunit ember-qunit

我正在为Ember组件编写验收测试,允许用户通过ember-select-list包提供的下拉列表切换其i18n设置。我还使用ember-i18n包进行i18n设置。下拉组件如下所示:

import Ember from 'ember';

export default Ember.Component.extend({
  i18n: Ember.inject.service(),
  languagePreference: Ember.inject.service(),

  classNames: ['language-dropdown'],

  languageOptions: Ember.computed('i18n.locale', function() {
    let i18n = this.get('i18n');
    return i18n.get('locales').map((item) => {
      return {
        id: item,
        name: i18n.t(`languages.${item}`)
      };
    });
  }),

  onFinish: null,

  actions: {
    selectLanguage(i18n) {
      this.get('languagePreference').setUserI18nPreference(i18n);
      this.get('onFinish')();
    }
  }

});

language-preference服务如下所示:

import Ember from 'ember';

export default Ember.Service.extend({

  i18n: Ember.inject.service(),
  config: Ember.inject.service(),

  setSessionI18nPreference() {
    let setSessionI18n = (results) => {
      let { preferences, userName } = results;
      if (userName && preferences[userName]) {
        this.set('i18n.locale', preferences[userName].i18n);
      }
    };
    this._fetchUserPreferencesDB().then(setSessionI18n);
  },

  setUserI18nPreference(i18n) {
    let setUserI18n = (results) => {
      let { preferences, userName } = results;
      if (preferences[userName] === undefined) {
        preferences[userName] = {};
      }
      preferences[userName].i18n = i18n;
      this.get('config.configDB').put(preferences);
      this.set('i18n.locale', i18n);
    };
    this._fetchUserPreferencesDB().then(setUserI18n);
  },

  _fetchUserPreferencesDB() {
    let configDB = this.get('config.configDB');
    let userName;
    return configDB.get('current_user').then((user) => {
      userName = this._fetchUsername(user);
      let preferences = configDB.get('preferences');
      return Ember.RSVP.hash({ userName, preferences });
    }).catch((err) => {
      console.log(err);
      if (err.status === 404) {
        this._initPreferencesDB(userName, 'en');
      }
    });
  },

  _fetchUsername(user) {
    switch (typeof user.value) {
      case 'string':
        return user.value;
      case 'object':
        return user.value.name;
      default:
        return undefined;
    }
  },

  _initPreferencesDB(username, i18n) {
    let doc = {
      _id: 'preferences'
    };
    if (username != undefined) {
      doc[username] = {
        i18n: i18n || 'en'
      };
    }
    this.get('config.configDB').put(doc);
  }
});

对于验收测试,到目前为止我所拥有的是:

import Ember from 'ember';
import { module, test } from 'qunit';
import startApp from 'hospitalrun/tests/helpers/start-app';

module('Acceptance | language dropdown', {
  beforeEach() {
    this.application = startApp();
  },

  afterEach() {
    Ember.run(this.application, 'destroy');
  }
});

test('setting a language preference persists after logout', (assert) => {
  runWithPouchDump('default', () => {
  authenticateUser({ name: 'foobar', prefix: 'p2' });
  visit('/');

  andThen(() => {
    assert.equal(currentURL(), '/');
    assert.equal(find('.view-current-title').text(), 'Welcome to HospitalRun!');
    });
    andThen(() => {
      click('a.settings-trigger');
      waitToAppear('.settings-nav');
      // andThen(() => {
      //   select('.language-dropdown', 'French');
      //   andThen(() => {
      //     debugger;
      //   });
      // });
    });
  });
});

这很好,我的所有测试都通过了。但是,当我取消评论当前注释掉的块并重新运行测试时,我看到多个测试失败,从全局错误开始:

not ok 66 PhantomJS 2.1 - Global error: Error: Missing translation: navigation.subnav.textReplacements at http://localhost:7357/assets/tests.js, line 12058
---
    Log: |
        { type: 'error',
          text: 'Error: Missing translation: navigation.subnav.textReplacements at http://localhost:7357/assets/tests.js, line 12058\n' }
...
not ok 67 PhantomJS 2.1 - Acceptance | language dropdown: setting a language preference persists after logout
---
    actual: >
        null
    expected: >
        null
    stack: >
        http://localhost:7357/assets/tests.js:12058
    message: >
        Error: Missing translation: navigation.subnav.textReplacements
    Log: |
...

该应用程序在我的浏览器中正常工作(翻译文件全部到位,我可以在切换i18n时在浏览器中看到正确的i18n输出)。 ember-i18n文档说它可以在调用startApp()的测试中正常工作,而这个测试就是这样。对我来说奇怪的是,注释掉的行在取消注释时不仅打破了这个测试,还打破了其他文件中的测试。我猜它会影响某些全局(在测试过程中)i18n设置,并且在此测试结束后此设置不会被拆除,但我无法确定。

代码生活在这里 - https://github.com/richiethomas/hospitalrun-frontend/tree/debug

最新的提交代表了失败的测试。

编辑:当我在_fetchUserPreferencesDB内的language-preference函数中放置调试器时,我能够调用this.get('i18n.locales')并查看我期望的语言环境,因此我知道原因不同环境中的区域设置不同(即development vs test)。我甚至打电话给this.get('i18n').t('navigation.subnav.textReplacements'),这与失败的测试所说的翻译价值相同,我得到了正确的翻译。所以我真的不确定测试失败的原因。

1 个答案:

答案 0 :(得分:0)

显然我的测试是尝试使用德语翻译文件(没有navigation.subnav.textReplacements键),即使我的验收测试指定了法语。我通过在Chrome控制台中运行测试,在失败的行之前放置调试器,并检查this.get('i18n._locale')对象的translations属性来验证这一点。我发现他们出于某种原因都是德语。

所以缺少翻译元素的奥秘真的掩盖了另一个谜团,这就是为什么我的验收测试默认为德语,即使PhantomJS选择了法语i18n选项。但这是另一篇文章的主题。