diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 0000000..6437276 --- /dev/null +++ b/.eslintignore @@ -0,0 +1,18 @@ +# unconventional js +/blueprints/*/files/ +/vendor/ + +# compiled output +/dist/ +/tmp/ + +# dependencies +/bower_components/ + +# misc +/coverage/ + +# ember-try +/.node_modules.ember-try/ +/bower.json.ember-try +/package.json.ember-try diff --git a/.eslintrc.js b/.eslintrc.js index 0887f21..1718b38 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -1,7 +1,4 @@ module.exports = { - globals: { - server: true, - }, root: true, parserOptions: { ecmaVersion: 2017, @@ -24,8 +21,10 @@ module.exports = { // node files { files: [ - 'testem.js', + '.template-lintrc.js', 'ember-cli-build.js', + 'testem.js', + 'blueprints/*/index.js', 'config/**/*.js', 'lib/*/index.js' ], @@ -37,24 +36,6 @@ module.exports = { browser: false, node: true } - }, - - // test files - { - files: ['tests/**/*.js'], - excludedFiles: ['tests/dummy/**/*.js'], - env: { - embertest: true - }, - globals: { - backButton: true, - pollHasUser: true, - pollHasUsersCount: true, - pollParticipate: true, - setupBrowserNavigationButtons: true, - switchTab: true, - t: true, - } } ] }; diff --git a/.gitignore b/.gitignore index 91e15ef..f89a284 100644 --- a/.gitignore +++ b/.gitignore @@ -1,27 +1,27 @@ # See https://help.github.com/ignore-files/ for more about ignoring files. # compiled output -/dist -/tmp -/api/tests/_output -/api/tests/_tmp -/api/tests/_support/_generated +/dist/ +/tmp/ +/api/tests/_output/ +/api/tests/_tmp/ +/api/tests/_support/_generated/ # dependencies -/node_modules -/bower_components -/api/vendor +/bower_components/ +/node_modules/ +/api/vendor/ # misc /.sass-cache /connect.lock -/coverage/* +/coverage/ /libpeerconnection.log -npm-debug.log* -yarn-error.log -testem.log +/npm-debug.log* +/testem.log +/yarn-error.log # ember-try -.node_modules.ember-try/ -bower.json.ember-try -package.json.ember-try +/.node_modules.ember-try/ +/bower.json.ember-try +/package.json.ember-try diff --git a/.template-lintrc.js b/.template-lintrc.js new file mode 100644 index 0000000..b45e96f --- /dev/null +++ b/.template-lintrc.js @@ -0,0 +1,5 @@ +'use strict'; + +module.exports = { + extends: 'recommended' +}; diff --git a/.travis.yml b/.travis.yml index 0a2f3a1..d790eb2 100644 --- a/.travis.yml +++ b/.travis.yml @@ -45,6 +45,7 @@ before_script: script: # run frontend and integration tests + - if $TEST_EMBER; then yarn run lint:hbs; fi - if $TEST_EMBER; then yarn run lint:js; fi - if $TEST_EMBER; then yarn test; fi # test against different browsers using sauce lab diff --git a/MODULE_REPORT.md b/MODULE_REPORT.md deleted file mode 100644 index 7b02e07..0000000 --- a/MODULE_REPORT.md +++ /dev/null @@ -1,252 +0,0 @@ -## Module Report -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/create.js` at line 3 - -```js -import Ember from 'ember'; - -const { computed, Controller, getOwner, inject } = Ember; - -const formStepObject = Ember.Object.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/adapters/application.js` at line 5 - -```js - -const { RESTAdapter } = DS; -const { inject } = Ember; - -export default RESTAdapter.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/poll.js` at line 7 - -```js - computed, - Controller, - inject, - isEmpty, - isPresent, -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/create-options-dates.js` at line 4 - -```js -import moment from 'moment'; - -const { computed, Component, inject, isArray, isEmpty } = Ember; - -export default Component.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/create-options-datetime.js` at line 9 - -```js -import Form from 'ember-bootstrap/components/bs-form'; - -const { computed, Component, inject, isArray, isEmpty, isPresent, observer } = Ember; -const { filter, mapBy, readOnly } = computed; - -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/create-options-text.js` at line 5 - -```js -import { anyBy } from 'ember-array-computed-macros'; - -const { Component, computed, inject, observer, run } = Ember; - -export default Component.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/create-options.js` at line 7 - -```js -from 'ember-cp-validations'; - -const { Component, inject } = Ember; - -let Validations = buildValidations({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/form-navigation-buttons.js` at line 4 - -```js -import { translationMacro as t } from 'ember-i18n'; - -const { Component, computed, get, inject } = Ember; - -export default Component.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/language-select.js` at line 4 - -```js -import localesMeta from 'croodle/locales/meta'; - -const { Component, computed, inject } = Ember; - -export default Component.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/components/poll-evaluation-chart.js` at line 4 - -```js -import moment from 'moment'; - -const { Component, computed, get, inject, isArray, isPresent } = Ember; - -const addArrays = function() { -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/models/option.js` at line 12 - -```js - -const { attr } = DS; -const { assert, computed, inject, isEmpty } = Ember; - -const Validations = buildValidations({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/create/index.js` at line 7 - -```js -from 'ember-cp-validations'; - -const { computed, Controller, getOwner, Object: EmberObject, inject } = Ember; - -const Validations = buildValidations({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/create/meta.js` at line 7 - -```js -from 'ember-cp-validations'; - -const { computed, Controller, inject } = Ember; - -const Validations = buildValidations({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/create/settings.js` at line 13 - -```js - copy, - getOwner, - inject, - isEmpty, - Object: EmberObject, -``` - -### Unknown Global - -**Global**: `Ember.ObjectController` - -**Location**: `app/controllers/modal/save-retry.js` at line 3 - -```js -import Ember from 'ember'; - -const { $, ObjectController } = Ember; - -export default ObjectController.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/poll/evaluation.js` at line 3 - -```js -import Ember from 'ember'; - -const { $, computed, Controller, inject } = Ember; - -export default Controller.extend({ -``` - -### Unknown Global - -**Global**: `Ember.inject` - -**Location**: `app/controllers/poll/participation.js` at line 12 - -```js - Controller, - getOwner, - inject, - isEmpty, - isPresent, -``` - -### Unknown Global - -**Global**: `Ember.K` - -**Location**: `tests/helpers/flash-message.js` at line 4 - -```js -import FlashObject from 'ember-cli-flash/flash/object'; - -const { K } = Ember; - -FlashObject.reopen({ init: K }); -``` diff --git a/app/components/create-options-dates.js b/app/components/create-options-dates.js index 8fef049..6dab14b 100644 --- a/app/components/create-options-dates.js +++ b/app/components/create-options-dates.js @@ -13,7 +13,7 @@ export default Component.extend({ */ optionsBootstrapDatepicker: computed('options', { get() { - const options = this.get('options'); + const options = this.options; const validDates = options.filter(function(option) { return moment(option.get('title')).isValid(); }); @@ -38,7 +38,7 @@ export default Component.extend({ * value is an of Date objects set by ember-cli-bootstrap-datepicker */ set(key, days) { - const options = this.get('options'); + const options = this.options; // remove all days if value isn't an array of if it's empty if (!isArray(days) || isEmpty(days)) { @@ -81,7 +81,7 @@ export default Component.extend({ } options.insertAt( position, - this.get('store').createFragment('option', { + this.store.createFragment('option', { title: moment(newDay).format('YYYY-MM-DD') }) ); diff --git a/app/components/create-options-datetime.js b/app/components/create-options-datetime.js index 0f6c471..59c9564 100644 --- a/app/components/create-options-datetime.js +++ b/app/components/create-options-datetime.js @@ -28,9 +28,9 @@ let modelValidations = buildValidations({ export default Component.extend(modelValidations, { actions: { addOption(afterOption) { - let options = this.get('dates'); + let options = this.dates; let dayString = afterOption.get('day'); - let fragment = this.get('store').createFragment('option', { + let fragment = this.store.createFragment('option', { title: dayString }); let position = options.indexOf(afterOption) + 1; @@ -40,10 +40,10 @@ export default Component.extend(modelValidations, { ); }, adoptTimesOfFirstDay() { - const dates = this.get('dates'); - const datesForFirstDay = this.get('datesForFirstDay'); - const timesForFirstDay = this.get('timesForFirstDay'); - const datesWithoutFirstDay = this.get('groupedDates').slice(1); + const dates = this.dates; + const datesForFirstDay = this.datesForFirstDay; + const timesForFirstDay = this.timesForFirstDay; + const datesWithoutFirstDay = this.groupedDates.slice(1); /* validate if times on firstDay are valid */ const datesForFirstDayAreValid = datesForFirstDay.every((date) => { @@ -82,7 +82,7 @@ export default Component.extend(modelValidations, { const basisDate = get(items[0], 'date').clone(); let [hour, minute] = timeOfFirstDate.split(':'); let dateString = basisDate.hour(hour).minute(minute).toISOString(); - let fragment = this.get('store').createFragment('option', { + let fragment = this.store.createFragment('option', { title: dateString }); dates.insertAt( @@ -104,12 +104,12 @@ export default Component.extend(modelValidations, { * otherwise it deletes time for this date */ deleteOption(target) { - let position = this.get('dates').indexOf(target); - let datesForThisDay = this.get('groupedDates').find((group) => { + let position = this.dates.indexOf(target); + let datesForThisDay = this.groupedDates.find((group) => { return group.value === target.get('day'); }).items; if (datesForThisDay.length > 1) { - this.get('dates').removeAt(position); + this.dates.removeAt(position); } else { target.set('time', null); } @@ -154,7 +154,7 @@ export default Component.extend(modelValidations, { return isArray(formElements) ? formElements : []; }), daysValidationState: computed('formElements.@each.validation', function() { - return this.get('formElements').reduce(function(daysValidationState, item) { + return this.formElements.reduce(function(daysValidationState, item) { const day = item.get('model.day'); const validation = item.get('validation'); let currentValidationState; diff --git a/app/components/create-options-text.js b/app/components/create-options-text.js index 98e94f0..43b6cf4 100644 --- a/app/components/create-options-text.js +++ b/app/components/create-options-text.js @@ -2,24 +2,32 @@ import { inject as service } from '@ember/service'; import { filter } from '@ember/object/computed'; import Component from '@ember/component'; import { observer, computed, get } from '@ember/object'; -import { run } from '@ember/runloop'; +import { run, next } from '@ember/runloop'; import BsFormElement from 'ember-bootstrap/components/bs-form/element'; import { any } from 'ember-awesome-macros/array'; export default Component.extend({ actions: { addOption(element) { - let fragment = this.get('store').createFragment('option'); - let options = this.get('options'); - let position = this.get('options').indexOf(element) + 1; + let fragment = this.store.createFragment('option'); + let options = this.options; + let position = this.options.indexOf(element) + 1; options.insertAt( position, fragment ); + + next(() => { + this.notifyPropertyChange('childViews'); + }); }, deleteOption(element) { - let position = this.get('options').indexOf(element); - this.get('options').removeAt(position); + let position = this.options.indexOf(element); + this.options.removeAt(position); + + next(() => { + this.notifyPropertyChange('childViews'); + }); } }, @@ -32,13 +40,13 @@ export default Component.extend({ }), everyElementIsValid: computed('childFormElements.@each.validation', function() { - const anyElementIsInvalid = this.get('anyElementIsInvalid'); + const anyElementIsInvalid = this.anyElementIsInvalid; if (anyElementIsInvalid) { return false; } // childFormElements contains button wrapper element which should not be taken into account here - const childFormElements = this.get('childFormElements').filterBy('hasValidator'); + const childFormElements = this.childFormElements.filterBy('hasValidator'); if (childFormElements) { return childFormElements.every((childFormElement) => { return childFormElement.get('hasFeedback') && childFormElement.get('validation') === 'success'; @@ -57,11 +65,11 @@ export default Component.extend({ run.scheduleOnce('sync', () => { let validationClass; - if (!this.get('anyElementHasFeedback')) { + if (!this.anyElementHasFeedback) { validationClass = 'label-has-no-validation'; - } else if (this.get('anyElementIsInvalid')) { + } else if (this.anyElementIsInvalid) { validationClass = 'label-has-error'; - } else if (this.get('everyElementIsValid')) { + } else if (this.everyElementIsValid) { validationClass = 'label-has-success'; } else { validationClass = 'label-has-no-validation'; @@ -75,14 +83,18 @@ export default Component.extend({ enforceMinimalOptionsAmount: observer('options', 'isMakeAPoll', function() { if (this.get('options.length') < 2) { - let options = this.get('options'); + let options = this.options; for (let missingOptions = 2 - this.get('options.length'); missingOptions > 0; missingOptions--) { options.pushObject( - this.get('store').createFragment('option') + this.store.createFragment('option') ); } } }).on('init'), - store: service('store') + store: service('store'), + + didInsertElement() { + this.notifyPropertyChange('childViews'); + } }); diff --git a/app/components/form-navigation-buttons.js b/app/components/form-navigation-buttons.js index 73b7f1b..ada93f5 100644 --- a/app/components/form-navigation-buttons.js +++ b/app/components/form-navigation-buttons.js @@ -1,6 +1,6 @@ import { inject as service } from '@ember/service'; import Component from '@ember/component'; -import { get, computed } from '@ember/object'; +import { computed } from '@ember/object'; import { translationMacro as t } from 'ember-i18n'; export default Component.extend({ @@ -38,7 +38,7 @@ export default Component.extend({ * @private */ nextButtonClasses: computed('renderPrevButton', function() { - let renderPrevButton = get(this, 'renderPrevButton'); + let renderPrevButton = this.renderPrevButton; if (renderPrevButton) { return ['col-xs-6', 'col-md-8']; @@ -53,7 +53,7 @@ export default Component.extend({ * @private */ nextButtonClassesString: computed('nextButtonClasses.[]', function() { - let nextButtonClasses = get(this, 'nextButtonClasses'); + let nextButtonClasses = this.nextButtonClasses; return nextButtonClasses.join(' '); }), diff --git a/app/components/language-select.js b/app/components/language-select.js index 76f48c8..d0e538e 100644 --- a/app/components/language-select.js +++ b/app/components/language-select.js @@ -25,6 +25,12 @@ export default Component.extend({ change() { let locale = this.$().val(); - this.get('i18n').set('locale', locale); + + this.i18n.set('locale', locale); + this.moment.changeLocale(locale); + + if (window.localStorage) { + window.localStorage.setItem('locale', locale); + } } }); diff --git a/app/components/poll-evaluation-chart.js b/app/components/poll-evaluation-chart.js index 8fb7043..c68bc52 100644 --- a/app/components/poll-evaluation-chart.js +++ b/app/components/poll-evaluation-chart.js @@ -27,30 +27,30 @@ export default Component.extend({ i18n: service(), type: 'bar', data: computed('users.[]', 'options.{[],each.title}', 'currentLocale', function() { - let labels = this.get('options').map((option) => { + let labels = this.options.map((option) => { let value = get(option, 'title'); - if (!get(this, 'isFindADate')) { + if (!this.isFindADate) { return value; } let hasTime = value.length > 10; // 'YYYY-MM-DD'.length === 10 - let momentFormat = hasTime ? 'LLLL' : get(this, 'momentLongDayFormat'); - let timezone = get(this, 'timezone'); + let momentFormat = hasTime ? 'LLLL' : this.momentLongDayFormat; + let timezone = this.timezone; let date = hasTime && isPresent(timezone) ? moment.tz(value, timezone) : moment(value); - date.locale(get(this, 'currentLocale')); + date.locale(this.currentLocale); return date.format(momentFormat); }); let datasets = []; let participants = this.get('users.length'); - let yes = this.get('users').map((user) => { + let yes = this.users.map((user) => { return user.get('selections').map((selection) => { return selection.get('type') === 'yes' ? 1 : 0; }); }); datasets.push({ - label: this.get('i18n').t('answerTypes.yes.label').toString(), + label: this.i18n.t('answerTypes.yes.label').toString(), backgroundColor: 'rgba(151,187,205,0.5)', borderColor: 'rgba(151,187,205,0.8)', hoverBackgroundColor: 'rgba(151,187,205,0.75)', @@ -58,14 +58,14 @@ export default Component.extend({ data: addArrays.apply(this, yes).map((value) => Math.round(value / participants * 100)) }); - if (this.get('answerType') === 'YesNoMaybe') { - let maybe = this.get('users').map((user) => { + if (this.answerType === 'YesNoMaybe') { + let maybe = this.users.map((user) => { return user.get('selections').map((selection) => { return selection.get('type') === 'maybe' ? 1 : 0; }); }); datasets.push({ - label: this.get('i18n').t('answerTypes.maybe.label').toString(), + label: this.i18n.t('answerTypes.maybe.label').toString(), backgroundColor: 'rgba(220,220,220,0.5)', borderColor: 'rgba(220,220,220,0.8)', hoverBackgroundColor: 'rgba(220,220,220,0.75)', diff --git a/app/controllers/create.js b/app/controllers/create.js index 9288605..6234deb 100644 --- a/app/controllers/create.js +++ b/app/controllers/create.js @@ -7,7 +7,7 @@ import { getOwner } from '@ember/application'; const formStepObject = EmberObject.extend({ active: computed('routing.currentRouteName', function() { const currentRouteName = this.get('routing.currentRouteName'); - return currentRouteName === this.get('route'); + return currentRouteName === this.route; }), disabled: true, hidden: false, @@ -15,7 +15,7 @@ const formStepObject = EmberObject.extend({ route: null, routing: service('-routing'), updateDisabledState: observer('active', function() { - if (this.get('active')) { + if (this.active) { this.set('disabled', false); } }).on('init'), @@ -35,7 +35,7 @@ export default Controller.extend({ }), formStepObject.extend({ label: computed('pollType', function() { - const pollType = this.get('pollType'); + const pollType = this.pollType; if (pollType === 'FindADate') { return 'create.formStep.options.days'; } else { @@ -44,18 +44,18 @@ export default Controller.extend({ }), pollType: readOnly('model.pollType') }).create(owner.ownerInjection(), { - model: this.get('model'), + model: this.model, route: 'create.options' }), formStepObject.extend({ hidden: computed('pollType', function() { - const pollType = this.get('pollType'); + const pollType = this.pollType; return pollType !== 'FindADate'; }), pollType: readOnly('model.pollType') }).create(owner.ownerInjection(), { label: 'create.formStep.options-datetime', - model: this.get('model'), + model: this.model, route: 'create.options-datetime' }), formStepObject.create(owner.ownerInjection(), { diff --git a/app/controllers/create/index.js b/app/controllers/create/index.js index 143ac5a..6c51d04 100644 --- a/app/controllers/create/index.js +++ b/app/controllers/create/index.js @@ -24,7 +24,7 @@ const Validations = buildValidations({ const TranslateableObject = EmberObject.extend({ i18n: service(), label: computed('labelTranslation', 'i18n.locale', function() { - return this.get('i18n').t(this.get('labelTranslation')); + return this.i18n.t(this.labelTranslation); }), labelTranslation: undefined }); diff --git a/app/controllers/create/options-datetime.js b/app/controllers/create/options-datetime.js index 1f61f6e..0810047 100644 --- a/app/controllers/create/options-datetime.js +++ b/app/controllers/create/options-datetime.js @@ -12,7 +12,7 @@ export default Controller.extend({ }, normalizeOptions() { - const options = this.get('options'); + const options = this.options; // remove all days from options which haven't a time but there is atleast // one option with time for that day diff --git a/app/controllers/create/options.js b/app/controllers/create/options.js index d860a70..51f6b66 100644 --- a/app/controllers/create/options.js +++ b/app/controllers/create/options.js @@ -4,7 +4,7 @@ import Controller from '@ember/controller'; export default Controller.extend({ actions: { nextPage() { - if (this.get('isFindADate')) { + if (this.isFindADate) { this.transitionToRoute('create.options-datetime'); } else { this.transitionToRoute('create.settings'); diff --git a/app/controllers/create/settings.js b/app/controllers/create/settings.js index 8f39a3f..b1eb482 100644 --- a/app/controllers/create/settings.js +++ b/app/controllers/create/settings.js @@ -1,7 +1,6 @@ import { inject as service } from '@ember/service'; import { alias } from '@ember/object/computed'; import Controller from '@ember/controller'; -import { copy } from '@ember/object/internals'; import { getOwner } from '@ember/application'; import { isEmpty } from '@ember/utils'; import EmberObject, { observer, computed } from '@ember/object'; @@ -32,7 +31,7 @@ const Validations = buildValidations({ const TranslateableObject = EmberObject.extend({ i18n: service(), label: computed('labelTranslation', 'i18n.locale', function() { - return this.get('i18n').t(this.get('labelTranslation')); + return this.i18n.t(this.labelTranslation); }), labelTranslation: undefined }); @@ -41,7 +40,7 @@ export default Controller.extend(Validations, { actions: { submit() { if (this.get('validations.isValid')) { - const model = this.get('model'); + const model = this.model; // set timezone if there is atleast one option with time if ( this.get('model.isFindADate') && @@ -58,7 +57,7 @@ export default Controller.extend(Validations, { // reload as workaround for bug: duplicated records after save model.reload().then((model) => { // redirect to new poll - this.get('target').send('transitionToPoll', model); + this.target.send('transitionToPoll', model); }); }) .catch(() => { @@ -169,13 +168,13 @@ export default Controller.extend(Validations, { */ updateAnswers: observer('model.answerType', function() { const selectedAnswer = this.get('model.answerType'); - const answerTypes = this.get('answerTypes'); + const answerTypes = this.answerTypes; let answers = []; if (selectedAnswer !== null) { for (let i = 0; i < answerTypes.length; i++) { if (answerTypes[i].id === selectedAnswer) { - answers = answerTypes[i].answers.map(copy); + answers = answerTypes[i].answers.slice(); } } @@ -184,7 +183,7 @@ export default Controller.extend(Validations, { }), updateExpirationDate: observer('expirationDuration', function() { - const expirationDuration = this.get('expirationDuration'); + const expirationDuration = this.expirationDuration; if (isEmpty(expirationDuration)) { this.set('model.expirationDate', ''); diff --git a/app/controllers/poll.js b/app/controllers/poll.js index 76a59a5..781ae38 100644 --- a/app/controllers/poll.js +++ b/app/controllers/poll.js @@ -8,7 +8,7 @@ import moment from 'moment'; export default Controller.extend({ actions: { linkAction(type) { - let flashMessages = this.get('flashMessages'); + let flashMessages = this.flashMessages; switch (type) { case 'copied': flashMessages.success(`poll.link.copied`); @@ -47,7 +47,7 @@ export default Controller.extend({ i18n: service(), momentLongDayFormat: computed('currentLocale', function() { - let currentLocale = this.get('currentLocale'); + let currentLocale = this.currentLocale; return moment.localeData(currentLocale) .longDateFormat('LLLL') .replace( @@ -62,10 +62,10 @@ export default Controller.extend({ preventEncryptionKeyChanges: observer('encryptionKey', function() { if ( !isEmpty(this.get('encryption.key')) && - this.get('encryptionKey') !== this.get('encryption.key') + this.encryptionKey !== this.get('encryption.key') ) { // work-a-round for url not being updated - window.location.hash = window.location.hash.replace(this.get('encryptionKey'), this.get('encryption.key')); + window.location.hash = window.location.hash.replace(this.encryptionKey, this.get('encryption.key')); this.set('encryptionKey', this.get('encryption.key')); } @@ -92,10 +92,10 @@ export default Controller.extend({ useLocalTimezone: false, mustChooseTimezone: computed('timezoneDiffers', 'timezoneChoosen', function() { - return this.get('timezoneDiffers') && !this.get('timezoneChoosen'); + return this.timezoneDiffers && !this.timezoneChoosen; }), timezone: computed('useLocalTimezone', function() { - return this.get('useLocalTimezone') ? undefined : this.get('model.timezone'); + return this.useLocalTimezone ? undefined : this.get('model.timezone'); }) }); diff --git a/app/controllers/poll/participation.js b/app/controllers/poll/participation.js index f90a2b3..9674358 100644 --- a/app/controllers/poll/participation.js +++ b/app/controllers/poll/participation.js @@ -65,14 +65,14 @@ export default Controller.extend(Validations, { version: config.APP.version, }); - user.set('name', this.get('name')); + user.set('name', this.name); const selections = user.get('selections'); const possibleAnswers = this.get('pollController.model.answers'); - this.get('selections').forEach((selection) => { + this.selections.forEach((selection) => { if (selection.get('value') !== null) { - if (this.get('isFreeText')) { + if (this.isFreeText) { selections.createFragment({ label: selection.get('value') }); @@ -95,18 +95,18 @@ export default Controller.extend(Validations, { } }, save() { - const user = this.get('newUserRecord'); + const user = this.newUserRecord; user.save() .then(() => { this.set('savingFailed', false); // reset form this.set('name', ''); - this.get('selections').forEach((selection) => { + this.selections.forEach((selection) => { selection.set('value', null); }); - this.transitionToRoute('poll.evaluation', this.get('model'), { + this.transitionToRoute('poll.evaluation', this.model, { queryParams: { encryptionKey: this.get('encryption.key') } }); }, () => { @@ -151,7 +151,7 @@ export default Controller.extend(Validations, { return AnswerObject.extend(owner.ownerInjection(), { i18n: service(), label: computed('i18n.locale', function() { - return this.get('i18n').t(this.get('labelTranslation')); + return this.i18n.t(this.labelTranslation); }), labelTranslation: answer.get('labelTranslation') }).create(); @@ -166,8 +166,8 @@ export default Controller.extend(Validations, { savingFailed: false, selections: computed('options', 'pollController.dates', function() { - let options = this.get('options'); - let isFindADate = this.get('isFindADate'); + let options = this.options; + let isFindADate = this.isFindADate; let lastDate; // https://github.com/offirgolan/ember-cp-validations#basic-usage---objects @@ -177,8 +177,8 @@ export default Controller.extend(Validations, { let SelectionObject = EmberObject.extend(owner.ownerInjection(), SelectionValidations, { // forceAnswer and isFreeText must be included in model // cause otherwise validations can't depend on it - forceAnswer: this.get('forceAnswer'), - isFreeText: this.get('isFreeText'), + forceAnswer: this.forceAnswer, + isFreeText: this.isFreeText, value: null }); @@ -190,7 +190,7 @@ export default Controller.extend(Validations, { // format label if (isFindADate) { let hasTime = value.length > 10; // 'YYYY-MM-DD'.length === 10 - let timezone = this.get('timezone'); + let timezone = this.timezone; let date = isPresent(timezone) ? moment.tz(value, timezone) : moment(value); if (hasTime && lastDate && date.format('YYYY-MM-DD') === lastDate.format('YYYY-MM-DD')) { labelValue = value; diff --git a/app/instance-initializers/i18n.js b/app/instance-initializers/i18n.js index 5d70a8b..db8f25f 100644 --- a/app/instance-initializers/i18n.js +++ b/app/instance-initializers/i18n.js @@ -1,14 +1,16 @@ -import { getOwner } from '@ember/application'; import { isPresent, isEmpty } from '@ember/utils'; export default { name: 'i18n', initialize(appInstance) { let i18n = appInstance.lookup('service:i18n'); - let availableLocales = i18n.get('locales'); + let moment = appInstance.lookup('service:moment'); - i18n.addObserver('locale', i18n, localeChanged); - i18n.set('locale', getLocale(availableLocales)); + let availableLocales = i18n.get('locales'); + let locale = getLocale(availableLocales); + + i18n.set('locale', locale); + moment.changeLocale(locale); } }; @@ -102,20 +104,3 @@ function getSavedLocale() { return [locale]; } - -function saveLocale(locale) { - let { localStorage } = window; - - // test browser support - if (!localStorage) { - return; - } - - localStorage.setItem('locale', locale); -} - -function localeChanged() { - let locale = this.get('locale'); - getOwner(this).lookup('service:moment').changeLocale(locale); - saveLocale(locale); -} diff --git a/app/mixins/autofocus-support.js b/app/mixins/autofocus-support.js index 9faa21a..e8442a8 100644 --- a/app/mixins/autofocus-support.js +++ b/app/mixins/autofocus-support.js @@ -9,7 +9,7 @@ export default Mixin.create({ didInsertElement() { this._super(...arguments); - if (this.get('autofocus')) { + if (this.autofocus) { this.$().focus(); } } diff --git a/app/models/option.js b/app/models/option.js index 8edd1df..cc4fe91 100644 --- a/app/models/option.js +++ b/app/models/option.js @@ -61,7 +61,7 @@ export default Fragment.extend(Validations, { 'YYYY-MM-DD', 'YYYY-MM-DDTHH:mm:ss.SSSZ' ]; - const value = this.get('title'); + const value = this.title; if (isEmpty(value)) { return; } @@ -79,7 +79,7 @@ export default Fragment.extend(Validations, { }), day: computed('date', function() { - const date = this.get('date'); + const date = this.date; if (!moment.isMoment(date)) { return; } @@ -87,7 +87,7 @@ export default Fragment.extend(Validations, { }), dayFormatted: computed('date', 'i18n.locale', function() { - let date = this.get('date'); + let date = this.date; if (!moment.isMoment(date)) { return; } @@ -110,19 +110,19 @@ export default Fragment.extend(Validations, { }), hasTime: computed('title', function() { - return moment.isMoment(this.get('date')) && - this.get('title').length === 'YYYY-MM-DDTHH:mm:ss.SSSZ'.length; + return moment.isMoment(this.date) && + this.title.length === 'YYYY-MM-DDTHH:mm:ss.SSSZ'.length; }), time: computed('date', { get() { - const date = this.get('date'); + const date = this.date; if (!moment.isMoment(date)) { return; } // verify that value is an ISO 8601 date string containg time // testing length is faster than parsing with moment - const value = this.get('title'); + const value = this.title; if (value.length !== 'YYYY-MM-DDTHH:mm:ss.SSSZ'.length) { return; } @@ -130,7 +130,7 @@ export default Fragment.extend(Validations, { return date.format('HH:mm'); }, set(key, value) { - const date = this.get('date'); + const date = this.date; assert( 'can not set a time if current value is not a valid date', moment.isMoment(date) diff --git a/app/models/poll.js b/app/models/poll.js index 870afee..a233037 100644 --- a/app/models/poll.js +++ b/app/models/poll.js @@ -65,14 +65,14 @@ export default Model.extend({ * computed properties */ isFindADate: computed('pollType', function() { - return this.get('pollType') === 'FindADate'; + return this.pollType === 'FindADate'; }), isFreeText: computed('answerType', function() { - return this.get('answerType') === 'FreeText'; + return this.answerType === 'FreeText'; }), isMakeAPoll: computed('pollType', function() { - return this.get('pollType') === 'MakeAPoll'; + return this.pollType === 'MakeAPoll'; }) }); diff --git a/app/routes/create.js b/app/routes/create.js index 6269084..7bb160c 100644 --- a/app/routes/create.js +++ b/app/routes/create.js @@ -9,7 +9,7 @@ export default Route.extend({ transitionToPoll(poll) { this.transitionTo('poll', poll, { queryParams: { - encryptionKey: this.get('encryptionKey') + encryptionKey: this.encryptionKey } }); } @@ -22,7 +22,7 @@ export default Route.extend({ } // set encryption key - this.get('encryption').generateKey(); + this.encryption.generateKey(); }, encryption: service(), diff --git a/app/serializers/application.js b/app/serializers/application.js index 2d3ea02..4e09082 100644 --- a/app/serializers/application.js +++ b/app/serializers/application.js @@ -31,7 +31,7 @@ export default DS.RESTSerializer.extend({ attributes.options.encrypted !== false ) { if (typeof resourceHash[key] !== 'undefined' && resourceHash[key] !== null) { - resourceHash[key] = this.get('encryption').decrypt(resourceHash[key]); + resourceHash[key] = this.encryption.decrypt(resourceHash[key]); } } }, this); @@ -63,7 +63,7 @@ export default DS.RESTSerializer.extend({ if ( attribute.options.encrypted !== false ) { - json[key] = this.get('encryption').encrypt(json[key]); + json[key] = this.encryption.encrypt(json[key]); } } }); diff --git a/app/services/encryption.js b/app/services/encryption.js index 8a5d205..27cfae6 100644 --- a/app/services/encryption.js +++ b/app/services/encryption.js @@ -8,7 +8,7 @@ export default Service.extend({ decrypt(value) { return JSON.parse( sjcl.decrypt( - this.get('key'), + this.key, value ) ); @@ -16,7 +16,7 @@ export default Service.extend({ encrypt(value) { return sjcl.encrypt( - this.get('key'), + this.key, JSON.stringify(value) ); }, diff --git a/app/templates/application.hbs b/app/templates/application.hbs index d8b3bf2..bff7296 100644 --- a/app/templates/application.hbs +++ b/app/templates/application.hbs @@ -1,8 +1,8 @@ -{{title 'Croodle'}} +{{title "Croodle"}}
@@ -25,4 +20,4 @@
-{{outlet 'modal'}} +{{outlet "modal"}} diff --git a/app/templates/components/create-options-dates.hbs b/app/templates/components/create-options-dates.hbs index ff80264..ab49944 100644 --- a/app/templates/components/create-options-dates.hbs +++ b/app/templates/components/create-options-dates.hbs @@ -1,8 +1,8 @@ {{#form.element - classNames='days' - label=(t 'create.options.dates.label') - property='options' - as |el| + classNames="days" + label=(t "create.options.dates.label") + property="options" +as |el| }} {{bootstrap-datepicker-inline id=el.id diff --git a/app/templates/components/create-options-datetime.hbs b/app/templates/components/create-options-datetime.hbs index 58105e5..c55fa84 100644 --- a/app/templates/components/create-options-datetime.hbs +++ b/app/templates/components/create-options-datetime.hbs @@ -6,18 +6,24 @@ {{/if}} {{#bs-form - onSubmit=(action 'submit') - formLayout='horizontal' + onSubmit=(action "submit") + formLayout="horizontal" model=this novalidate=true - as |form| + as |form| }}
{{#each dates as |date index|}} {{! show summarized validation state for all times in a day }} -
+
{{! show label only if it differ from label before Nested-helpers are called first and object-at requires a positive integer @@ -26,34 +32,56 @@ by zero there can't be any element with an index === array.length. }} {{#form.element - classNames='option' + classNames="option" label=date.dayFormatted - invisibleLabel=(eq date.dayFormatted (get (object-at (if index (sub index 1) dates.length) dates) 'dayFormatted')) + invisibleLabel=(eq date.dayFormatted (get (object-at (if index (sub index 1) dates.length) dates) "dayFormatted")) model=date - property='time' - as |el| + property="time" + as |el| }}
{{bs-form/element/control/input autofocus=(unless index true false) id=el.id - placeholder='00:00' - type='time' + placeholder="00:00" + type="time" value=el.value onChange=(action (mut el.value)) }}
{{! disable delete button if there is only one option }} - - + {{#bs-button + onClick=(action "deleteOption" date) + type=(if + (eq el.validation "success") + "btn-success" + (if + (eq el.validation "error") + "btn-danger" + "btn-default" + ) + ) + class="delete" + }} + + {{t "create.options.button.delete.label"}} + {{/bs-button}} + {{#bs-button + onClick=(action "addOption" date) + type=(if + (eq el.validation "success") + "btn-success" + (if + (eq el.validation "error") + "btn-danger" + "btn-default" + ) + ) + class="add" + }} + + {{t "create.options.button.add.label"}} + {{/bs-button}}
{{/form.element}} @@ -63,12 +91,17 @@ {{#if (gt groupedDates.length 1)}} {{#form.element}} - + {{#bs-button + onClick=(action "adoptTimesOfFirstDay") + class="adopt-times-of-first-day" + }} + {{t "create.options-datetime.copy-first-line"}} + {{/bs-button}} {{/form.element}} {{/if}} {{form-navigation-buttons - onPrev=(action 'previousPage') + onPrev=(action "previousPage") }} {{/bs-form}}
diff --git a/app/templates/components/create-options-text.hbs b/app/templates/components/create-options-text.hbs index 29322ed..876a5ba 100644 --- a/app/templates/components/create-options-text.hbs +++ b/app/templates/components/create-options-text.hbs @@ -1,11 +1,11 @@ {{#each options as |option index|}} {{! show label only on first item }} {{#form.element - classNames='option' - label=(unless index (t 'create.options.options.label')) + classNames="option" + label=(unless index (t "create.options.options.label")) model=option - property='title' - as |el| + property="title" + as |el| }}
{{bs-form/element/control/input @@ -16,17 +16,39 @@ }}
{{! disable delete button if there is only one option }} - - + {{#bs-button + onClick=(action "deleteOption" option) + type=(if + (eq el.validation "success") + "btn-success" + (if + (eq el.validation "error") + "btn-danger" + "btn-default" + ) + ) + disabled=(lte options.length 1) + class="delete" + }} + + {{t "create.options.button.delete.label"}} + {{/bs-button}} + {{#bs-button + onClick=(action "addOption" option) + type=(if + (eq el.validation "success") + "btn-success" + (if + (eq el.validation "error") + "btn-danger" + "btn-default" + ) + ) + class="add" + }} + + {{t "create.options.button.add.label"}} + {{/bs-button}}
{{/form.element}} diff --git a/app/templates/components/create-options.hbs b/app/templates/components/create-options.hbs index b66fa7d..61ce91b 100644 --- a/app/templates/components/create-options.hbs +++ b/app/templates/components/create-options.hbs @@ -1,17 +1,17 @@
{{#bs-form - action='submit' - formLayout='horizontal' + action="submit" + formLayout="horizontal" model=this novalidate=true - onSubmit=(action 'submit') - as |form| + onSubmit=(action "submit") + as |form| }} {{#if isMakeAPoll}} {{create-options-text options=options - addOption='addOption' - deleteOption='deleteOption' + addOption="addOption" + deleteOption="deleteOption" form=form }} {{else}} @@ -22,7 +22,7 @@ {{/if}} {{form-navigation-buttons - onPrev=(action 'previousPage') + onPrev=(action "previousPage") }} {{/bs-form}}
diff --git a/app/templates/components/form-navigation-buttons.hbs b/app/templates/components/form-navigation-buttons.hbs index d9956ea..09e96c0 100644 --- a/app/templates/components/form-navigation-buttons.hbs +++ b/app/templates/components/form-navigation-buttons.hbs @@ -2,21 +2,21 @@ {{#if renderPrevButton}}
{{bs-button - onClick=(action 'prev') - classNames='prev' + onClick=(action "prev") + classNames="prev" disabled=disablePrevButton defaultText=prevButtonText }}
{{/if}} {{#if renderNextButton}} -
+
{{bs-button - buttonType='submit' - classNames='next' + buttonType="submit" + classNames="next" defaultText=nextButtonText disabled=disableNextButton - type='primary' + type="primary" }}
{{/if}} diff --git a/app/templates/components/language-select.hbs b/app/templates/components/language-select.hbs index de1d044..07433bb 100644 --- a/app/templates/components/language-select.hbs +++ b/app/templates/components/language-select.hbs @@ -1,3 +1,5 @@ {{#each locales as |locale|}} - + {{/each}} diff --git a/app/templates/components/poll-evaluation-participants-table.hbs b/app/templates/components/poll-evaluation-participants-table.hbs index 8f5fddb..4734f27 100644 --- a/app/templates/components/poll-evaluation-participants-table.hbs +++ b/app/templates/components/poll-evaluation-participants-table.hbs @@ -5,7 +5,7 @@   {{#each optionsGroupedByDates as |optionGroup|}} - + {{moment-format optionGroup.value momentLongDayFormat @@ -26,7 +26,7 @@ {{#if option.hasTime}} {{moment-format option.title - 'LT' + "LT" locale=currentLocale timeZone=timezone }} @@ -60,8 +60,8 @@ {{/if}} {{#if selection.labelTranslation}} {{#unless isFreeText}} - - + + {{t selection.labelTranslation}} {{/unless}} diff --git a/app/templates/components/poll-evaluation-summary-option.hbs b/app/templates/components/poll-evaluation-summary-option.hbs index c95b50f..a03dd1c 100644 --- a/app/templates/components/poll-evaluation-summary-option.hbs +++ b/app/templates/components/poll-evaluation-summary-option.hbs @@ -3,37 +3,58 @@ we will see a space between option string and following dot. --}} {{#if isFindADate}} - {{moment-format - evaluationBestOption.option.title - (if evaluationBestOption.option.hasTime 'LLLL' momentLongDayFormat) - locale=currentLocale - timeZone=timezone - }}. + {{! Need to disable block indentation rule cause there shouldn't be a space between date and dot }} + {{! template-lint-disable block-indentation }} + + {{moment-format + evaluationBestOption.option.title + (if evaluationBestOption.option.hasTime "LLLL" momentLongDayFormat) + locale=currentLocale + timeZone=timezone + }}. + {{! template-lint-enable block-indentation }} {{else}} - {{evaluationBestOption.option.title}}. + {{evaluationBestOption.option.title}}. {{/if}} - -
+
{{#if isFindADate}} {{#if evaluationBestOption.answers.yes}} - {{t "poll.evaluation.bestOptionParticipants.findADate.yes" count=evaluationBestOption.answers.yes}} + {{t + "poll.evaluation.bestOptionParticipants.findADate.yes" + count=evaluationBestOption.answers.yes + }} {{/if}} {{#if evaluationBestOption.answers.maybe}} - {{t "poll.evaluation.bestOptionParticipants.findADate.maybe" count=evaluationBestOption.answers.maybe}} + {{t + "poll.evaluation.bestOptionParticipants.findADate.maybe" + count=evaluationBestOption.answers.maybe + }} {{/if}} {{#if evaluationBestOption.answers.no}} - {{t "poll.evaluation.bestOptionParticipants.findADate.no" count=evaluationBestOption.answers.no}} + {{t + "poll.evaluation.bestOptionParticipants.findADate.no" + count=evaluationBestOption.answers.no + }} {{/if}} {{else}} {{#if evaluationBestOption.answers.yes}} - {{t "poll.evaluation.bestOptionParticipants.makeAPoll.yes" count=evaluationBestOption.answers.yes}} + {{t + "poll.evaluation.bestOptionParticipants.makeAPoll.yes" + count=evaluationBestOption.answers.yes + }} {{/if}} {{#if evaluationBestOption.answers.maybe}} - {{t "poll.evaluation.bestOptionParticipants.makeAPoll.maybe" count=evaluationBestOption.answers.maybe}} + {{t + "poll.evaluation.bestOptionParticipants.makeAPoll.maybe" + count=evaluationBestOption.answers.maybe + }} {{/if}} {{#if evaluationBestOption.answers.no}} - {{t "poll.evaluation.bestOptionParticipants.makeAPoll.no" count=evaluationBestOption.answers.no}} + {{t + "poll.evaluation.bestOptionParticipants.makeAPoll.no" + count=evaluationBestOption.answers.no + }} {{/if}} {{/if}} diff --git a/app/templates/components/poll-evaluation-summary.hbs b/app/templates/components/poll-evaluation-summary.hbs index c931536..59b0b91 100644 --- a/app/templates/components/poll-evaluation-summary.hbs +++ b/app/templates/components/poll-evaluation-summary.hbs @@ -8,38 +8,47 @@

{{#if poll.isFindADate}} - {{t "poll.evaluation.bestOption.label.findADate" count=evaluationBestOptions.length}} + {{t + "poll.evaluation.bestOption.label.findADate" + count=evaluationBestOptions.length + }} {{else}} - {{t "poll.evaluation.bestOption.label.makeAPoll" count=evaluationBestOptions.length}} + {{t + "poll.evaluation.bestOption.label.makeAPoll" + count=evaluationBestOptions.length + }} {{/if}} {{#if evaluationBestOptionsMultiple}}

    {{#each evaluationBestOptions as |evaluationBestOption|}} - {{component 'poll-evaluation-summary-option' + {{component + "poll-evaluation-summary-option" currentLocale=currentLocale evaluationBestOption=evaluationBestOption isFindADate=poll.isFindADate momentLongDayFormat=momentLongDayFormat - tagName='li' + tagName="li" timezone=timezone }} {{/each}}
{{else}} - {{component 'poll-evaluation-summary-option' + {{component + "poll-evaluation-summary-option" currentLocale=currentLocale evaluationBestOption=evaluationBestOptions.firstObject isFindADate=poll.isFindADate momentLongDayFormat=momentLongDayFormat - tagName='span' + tagName="span" timezone=timezone }} {{/if}}

- {{t "poll.evaluation.lastParticipation" + {{t + "poll.evaluation.lastParticipation" ago=(moment-from-now evaluationLastParticipation locale=currentLocale timezone=timezone) }}

diff --git a/app/templates/create.hbs b/app/templates/create.hbs index 908f52f..f13bbe6 100644 --- a/app/templates/create.hbs +++ b/app/templates/create.hbs @@ -1,10 +1,14 @@ -{{title (t 'create.title')}} +{{title (t "create.title")}} {{#bs-button-group justified=true classNames="form-steps"}} {{#each formSteps as |formStep|}} {{#unless formStep.hidden}}
- {{#bs-button action=(transition-to formStep.route) type=(if formStep.active 'primary' 'default') disabled=formStep.disabled}} + {{#bs-button + onClick=(transition-to formStep.route) + type=(if formStep.active "primary" "default") + disabled=formStep.disabled + }} {{t formStep.label}} {{/bs-button}}
diff --git a/app/templates/create/index.hbs b/app/templates/create/index.hbs index f78e310..6669814 100644 --- a/app/templates/create/index.hbs +++ b/app/templates/create/index.hbs @@ -3,16 +3,16 @@ formLayout="horizontal" model=this novalidate=true - onSubmit=(action 'submit') - as |form| + onSubmit=(action "submit") + as |form| }} {{#form.element - classNames='poll-type' - label=(t 'create.index.input.pollType.label') + classNames="poll-type" + label=(t "create.index.input.pollType.label") property="pollType" - showValidationOn=(array 'change' 'focusOut') + showValidationOn=(array "change" "focusOut") useIcons=false - as |el| + as |el| }} {{simple-select autofocus=true @@ -21,7 +21,7 @@ optionLabelPath="label" optionValuePath="id" value=el.value - action=(action (mut el.value) value='id') + action=(action (mut el.value) value="id") }} {{/form.element}} {{form-navigation-buttons diff --git a/app/templates/create/meta.hbs b/app/templates/create/meta.hbs index 09a1cba..005549f 100644 --- a/app/templates/create/meta.hbs +++ b/app/templates/create/meta.hbs @@ -3,26 +3,26 @@ formLayout="horizontal" model=this novalidate=true - onSubmit=(action 'submit') - as |form| + onSubmit=(action "submit") + as |form| }} {{form.element autofocus=true - classNames='title' + classNames="title" controlType="text" - label=(t 'create.meta.input.title.label') - placeholder=(t 'create.meta.input.title.placeholder') + label=(t "create.meta.input.title.label") + placeholder=(t "create.meta.input.title.placeholder") property="title" }} {{form.element - classNames='description' + classNames="description" controlType="textarea" - label=(t 'create.meta.input.description.label') - placeholder=(t 'create.meta.input.description.placeholder') + label=(t "create.meta.input.description.label") + placeholder=(t "create.meta.input.description.placeholder") property="description" }} {{form-navigation-buttons - onPrev=(route-action 'previousPage') + onPrev=(route-action "previousPage") }} {{/bs-form}}
diff --git a/app/templates/create/options-datetime.hbs b/app/templates/create/options-datetime.hbs index a162485..94188cd 100644 --- a/app/templates/create/options-datetime.hbs +++ b/app/templates/create/options-datetime.hbs @@ -1,5 +1,5 @@ {{create-options-datetime dates=options - onNextPage=(action 'nextPage') - onPrevPage=(route-action 'previousPage') + onNextPage=(action "nextPage") + onPrevPage=(route-action "previousPage") }} diff --git a/app/templates/create/options.hbs b/app/templates/create/options.hbs index 399c39c..37b92b6 100644 --- a/app/templates/create/options.hbs +++ b/app/templates/create/options.hbs @@ -2,6 +2,6 @@ isFindADate=model.isFindADate isMakeAPoll=model.isMakeAPoll options=model.options - onPrevPage=(route-action 'previousPage') - onNextPage=(action 'nextPage') + onPrevPage=(route-action "previousPage") + onNextPage=(action "nextPage") }} diff --git a/app/templates/create/settings.hbs b/app/templates/create/settings.hbs index e68cf35..6fe5295 100644 --- a/app/templates/create/settings.hbs +++ b/app/templates/create/settings.hbs @@ -3,16 +3,16 @@ formLayout="horizontal" model=this novalidate=true - onSubmit=(action 'submit') - as |form| + onSubmit=(action "submit") + as |form| }} {{#form.element - classNames='answer-type' - label=(t 'create.settings.answerType.label') + classNames="answer-type" + label=(t "create.settings.answerType.label") property="answerType" - showValidationOn=(array 'change' 'focusOut') + showValidationOn=(array "change" "focusOut") useIcons=false - as |el| + as |el| }} {{simple-select autofocus=true @@ -21,43 +21,43 @@ optionLabelPath="label" optionValuePath="id" value=el.value - action=(action (mut el.value) value='id') + action=(action (mut el.value) value="id") }} {{/form.element}} {{#form.element - classNames='expiration-duration' - label=(t 'create.settings.expirationDate.label') - property='expirationDuration' - showValidationOn=(array 'change' 'focusOut') + classNames="expiration-duration" + label=(t "create.settings.expirationDate.label") + property="expirationDuration" + showValidationOn=(array "change" "focusOut") useIcons=false - as |el| + as |el| }} {{simple-select id=el.id content=expirationDurations - optionLabelPath='label' - optionValuePath='id' + optionLabelPath="label" + optionValuePath="id" value=el.value - action=(action (mut el.value) value='id') + action=(action (mut el.value) value="id") }} {{/form.element}} {{form.element - classNames='anonymous-user' - controlType='checkbox' - label=(t 'create.settings.anonymousUser.label') - showValidationOn='change' + classNames="anonymous-user" + controlType="checkbox" + label=(t "create.settings.anonymousUser.label") + showValidationOn="change" value=anonymousUser }} {{form.element - classNames='force-answer' - controlType='checkbox' - label=(t 'create.settings.forceAnswer.label') - showValidationOn='change' + classNames="force-answer" + controlType="checkbox" + label=(t "create.settings.forceAnswer.label") + showValidationOn="change" value=forceAnswer }} {{form-navigation-buttons - nextButtonText=(t 'action.save') - onPrev=(route-action 'previousPage') + nextButtonText=(t "action.save") + onPrev=(route-action "previousPage") }} {{/bs-form}}
diff --git a/app/templates/index.hbs b/app/templates/index.hbs index 6a7edb0..8dc18f2 100644 --- a/app/templates/index.hbs +++ b/app/templates/index.hbs @@ -31,7 +31,7 @@

- {{#link-to 'create'}}{{t "index.link.have-a-try"}}{{/link-to}} + {{#link-to "create"}}{{t "index.link.have-a-try"}}{{/link-to}}

diff --git a/app/templates/poll.hbs b/app/templates/poll.hbs index 4acc1f8..5de6749 100644 --- a/app/templates/poll.hbs +++ b/app/templates/poll.hbs @@ -7,10 +7,20 @@

{{model.title}}

{{model.description}}

- {{t "poll.created-date" date=(moment-format model.creationDate 'LLLL' locale=currentLocale)}} + + {{t + "poll.created-date" + date=(moment-format model.creationDate "LLLL" locale=currentLocale) + }} + {{#if model.expirationDate}}
- {{t "poll.expiration-date" date=(moment-format model.expirationDate 'LLLL' locale=currentLocale)}} + + {{t + "poll.expiration-date" + date=(moment-format model.expirationDate "LLLL" locale=currentLocale) + }} + {{/if}}

@@ -19,18 +29,20 @@ @@ -39,8 +51,11 @@ {{#if showExpirationWarning}}
- {{#bs-alert type="warning" classNames='expiration-warning'}} - {{t "poll.expiration-date-warning" timeToNow=(moment-from-now model.expirationDate locale=currentLocale)}} + {{#bs-alert type="warning" classNames="expiration-warning"}} + {{t + "poll.expiration-date-warning" + timeToNow=(moment-from-now model.expirationDate locale=currentLocale) + }} {{/bs-alert}}
@@ -48,14 +63,26 @@
@@ -75,19 +102,25 @@ closeButton=false keyboard=false autoClose=false - id='modal-choose-timezone' - as |modal| + id="modal-choose-timezone" +as |modal| }} {{#modal.body}}

{{t "poll.modal.timezoneDiffers.body"}}

{{/modal.body}} - {{#modal.footer as |footer|}} - {{#bs-button onClick=(action "useLocalTimezone") class="use-local-timezone"}} + {{#modal.footer}} + {{#bs-button + onClick=(action "useLocalTimezone") + class="use-local-timezone" + }} {{t "poll.modal.timezoneDiffers.button.useLocalTimezone"}} {{/bs-button}} - {{#bs-button onClick=(action (mut timezoneChoosen) true) classNames="use-poll-timezone"}} + {{#bs-button + onClick=(action (mut timezoneChoosen) true) + classNames="use-poll-timezone" + }} {{t "poll.modal.timezoneDiffers.button.usePollTimezone"}} {{/bs-button}} {{/modal.footer}} diff --git a/app/templates/poll/evaluation.hbs b/app/templates/poll/evaluation.hbs index 60850b7..effbbd2 100644 --- a/app/templates/poll/evaluation.hbs +++ b/app/templates/poll/evaluation.hbs @@ -7,7 +7,7 @@ timezone=timezone }} -

{{t 'poll.evaluation.overview'}}

+

{{t "poll.evaluation.overview"}}

{{poll-evaluation-chart answerType=model.answerType currentLocale=currentLocale @@ -19,7 +19,7 @@ }} {{/if}} -

{{t 'poll.evaluation.participantTable'}}

+

{{t "poll.evaluation.participantTable"}}

{{poll-evaluation-participants-table currentLocale=currentLocale hasTimes=hasTimes diff --git a/app/templates/poll/participation.hbs b/app/templates/poll/participation.hbs index 5ce1dc5..e569088 100644 --- a/app/templates/poll/participation.hbs +++ b/app/templates/poll/participation.hbs @@ -1,52 +1,52 @@
{{#bs-form - onSubmit=(action 'submit') - formLayout='horizontal' + onSubmit=(action "submit") + formLayout="horizontal" model=this novalidate=true - as |form| + as |form| }} {{form.element autofocus=true - controlType='text' - label=(t 'poll.input.newUserName.label') - placeholder=(t 'poll.input.newUserName.placeholder') - property='name' - classNames='name' + controlType="text" + label=(t "poll.input.newUserName.label") + placeholder=(t "poll.input.newUserName.placeholder") + property="name" + classNames="name" }}
- {{#each selections as |selection index|}} + {{#each selections as |selection|}} {{#if isFreeText}} {{form.element - controlType='text' + controlType="text" label=(if isFindADate (moment-format selection.labelValue - (if (eq selection.momentFormat 'day') momentLongDayFormat selection.momentFormat) + (if (eq selection.momentFormat "day") momentLongDayFormat selection.momentFormat) locale=currentLocale timeZone=timezone ) selection.labelValue ) model=selection - property='value' + property="value" }} {{else}} {{#form.element label=(if isFindADate (moment-format selection.labelValue - (if (eq selection.momentFormat 'day') momentLongDayFormat selection.momentFormat) + (if (eq selection.momentFormat "day") momentLongDayFormat selection.momentFormat) locale=currentLocale timeZone=timezone ) selection.labelValue ) model=selection - property='value' - showValidationOn='change' + property="value" + showValidationOn="change" useIcons=false - as |el| + as |el| }} {{#each possibleAnswers as |possibleAnswer|}}
@@ -73,22 +73,22 @@ {{#bs-modal open=savingFailed - title=(t 'modal.save-retry.title') + title=(t "modal.save-retry.title") body=false footer=false closeButton=false autoClose=false - id='modal-saving-failed' - as |modal| + id="modal-saving-failed" +as |modal| }} {{#modal.body}}

{{t "modal.save-retry.text"}}

{{/modal.body}} {{#modal.footer}} {{bs-button - defaultText=(t 'modal.save-retry.button-retry') - type='primary' - onClick=(action 'save') + defaultText=(t "modal.save-retry.button-retry") + type="primary" + onClick=(action "save") }} {{/modal.footer}} {{/bs-modal}} diff --git a/config/optional-features.json b/config/optional-features.json new file mode 100644 index 0000000..21f1dc7 --- /dev/null +++ b/config/optional-features.json @@ -0,0 +1,3 @@ +{ + "jquery-integration": true +} diff --git a/config/targets.js b/config/targets.js index 082e68b..8ffae36 100644 --- a/config/targets.js +++ b/config/targets.js @@ -1,8 +1,18 @@ +'use strict'; + +const browsers = [ + 'last 1 Chrome versions', + 'last 1 Firefox versions', + 'last 1 Safari versions' +]; + +const isCI = !!process.env.CI; +const isProduction = process.env.EMBER_ENV === 'production'; + +if (isCI || isProduction) { + browsers.push('ie 11'); +} + module.exports = { - browsers: [ - 'ie 9', - 'last 1 Chrome versions', - 'last 1 Firefox versions', - 'last 1 Safari versions' - ] + browsers }; diff --git a/package.json b/package.json index af5a985..27f1181 100644 --- a/package.json +++ b/package.json @@ -2,76 +2,81 @@ "name": "croodle", "version": "0.5.6", "private": true, + "repository": "https://github.com/jelhan/croodle", "license": "MIT", "author": "", "directories": { "doc": "doc", "test": "tests" }, - "repository": "https://github.com/jelhan/croodle", "scripts": { "build": "ember build", - "lint:js": "eslint ./*.js app config lib server tests", + "lint:hbs": "ember-template-lint .", + "lint:js": "eslint .", "start": "ember serve", "test": "ember test" }, "devDependencies": { + "@ember/jquery": "^0.5.2", + "@ember/optional-features": "^0.6.3", "bootstrap": "^3.3.7", - "ember-ajax": "^3.0.0", + "ember-ajax": "^4.0.0", + "ember-array-helper": "^5.0.0", "ember-awesome-macros": "^3.1.0", "ember-bootstrap": "^2.1.2", "ember-bootstrap-cp-validations": "^1.0.0", "ember-browserify": "^1.1.11", - "ember-cli": "~2.18.2", + "ember-cli": "~3.4.4", "ember-cli-acceptance-test-helpers": "^1.0.0", - "ember-cli-app-version": "^3.0.0", - "ember-cli-babel": "^6.6.0", + "ember-cli-app-version": "^3.2.0", + "ember-cli-babel": "^6.16.0", "ember-cli-bootstrap-datepicker": "^0.6.1", - "ember-cli-browser-navigation-button-test-helper": "^0.0.4", + "ember-cli-browser-navigation-button-test-helper": "^0.1.1", "ember-cli-chart": "^3.3.1", "ember-cli-clipboard": "^0.8.0", "ember-cli-content-security-policy": "^0.6.2", - "ember-cli-dependency-checker": "^2.0.0", + "ember-cli-dependency-checker": "^3.0.0", "ember-cli-deprecation-workflow": "^0.2.3", - "ember-cli-eslint": "^4.2.1", + "ember-cli-eslint": "^4.2.3", "ember-cli-flash": "^1.4.0", - "ember-cli-htmlbars": "^2.0.1", - "ember-cli-htmlbars-inline-precompile": "^1.0.0", - "ember-cli-inject-live-reload": "^1.4.1", + "ember-cli-htmlbars": "^3.0.0", + "ember-cli-htmlbars-inline-precompile": "^1.0.3", + "ember-cli-inject-live-reload": "^1.8.2", "ember-cli-less": "^1.5.3", "ember-cli-mirage": "^0.4.10", "ember-cli-moment-shim": "^3.7.1", "ember-cli-page-object": "^1.11.0", - "ember-cli-qunit": "^4.1.1", + "ember-cli-qunit": "^4.3.2", "ember-cli-release": "^0.2.9", "ember-cli-sauce": "^1.6.0", - "ember-cli-shims": "^1.2.0", - "ember-cli-sri": "^2.1.0", - "ember-cli-uglify": "^2.0.0", + "ember-cli-sri": "^2.1.1", + "ember-cli-template-lint": "^1.0.0-beta.1", + "ember-cli-uglify": "^2.1.0", "ember-composable-helpers": "^2.1.0", "ember-cp-validations": "^3.5.0", - "ember-data": "~2.18.0", - "ember-data-model-fragments": "^2.14.0", + "ember-data": "~3.4.0", + "ember-data-model-fragments": "^3.3.0", "ember-export-application-global": "^2.0.0", "ember-i18n": "^5.0.2", "ember-i18n-cp-validations": "^3.0.2", - "ember-load-initializers": "^1.0.0", + "ember-load-initializers": "^1.1.0", "ember-math-helpers": "^2.8.1", + "ember-maybe-import-regenerator": "^0.1.6", "ember-moment": "^7.8.0", - "ember-native-dom-helpers": "^0.6.2", "ember-page-title": "^3.0.6", "ember-radio-buttons": "^4.0.1", - "ember-resolver": "^4.0.0", + "ember-resolver": "^5.0.1", "ember-route-action-helper": "^2.0.6", - "ember-simple-select": "^0.6.1", - "ember-source": "~2.18.0", + "ember-simple-select": "jelhan/ember-simple-select#ember-3.4", + "ember-source": "~3.4.0", "ember-transition-helper": "^1.0.0", "ember-truth-helpers": "^2.1.0", - "eslint-plugin-ember": "^5.0.0", - "loader.js": "^4.2.3" + "eslint-plugin-ember": "^5.2.0", + "loader.js": "^4.7.0", + "qunit-dom": "^0.7.1" }, "engines": { - "node": "^4.5 || 6.* || >= 7.*" + "node": "6.* || 8.* || >= 10.*" }, "ember-addon": { "paths": [ diff --git a/testem.js b/testem.js index cfbe4c6..1beec48 100644 --- a/testem.js +++ b/testem.js @@ -9,13 +9,14 @@ module.exports = { ], browser_args: { Chrome: { - mode: 'ci', - args: [ + ci: [ // --no-sandbox is needed when running Chrome inside a container - process.env.TRAVIS ? '--no-sandbox' : null, - - '--disable-gpu', + process.env.CI ? '--no-sandbox' : null, '--headless', + '--disable-gpu', + '--disable-dev-shm-usage', + '--disable-software-rasterizer', + '--mute-audio', '--remote-debugging-port=0', '--window-size=1440,900' ].filter(Boolean) diff --git a/tests/acceptance/build-info-test.js b/tests/acceptance/build-info-test.js index 2f4b6f4..aad0e22 100644 --- a/tests/acceptance/build-info-test.js +++ b/tests/acceptance/build-info-test.js @@ -1,13 +1,14 @@ -import { test } from 'qunit'; +import { visit } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; import jQuery from 'jquery'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; -moduleForAcceptance('Acceptance | build info'); +module('Acceptance | build info', function(hooks) { + setupApplicationTest(hooks); -test('version is included as html meta tag', function(assert) { - visit('/'); + test('version is included as html meta tag', async function(assert) { + await visit('/'); - andThen(function() { // ToDo: figure out why find() helper does not work but jQuery does assert.ok(jQuery('head meta[name="build-info"]').length === 1, 'tag exists'); assert.ok( diff --git a/tests/acceptance/create-a-poll-test.js b/tests/acceptance/create-a-poll-test.js index 9005364..e818583 100644 --- a/tests/acceptance/create-a-poll-test.js +++ b/tests/acceptance/create-a-poll-test.js @@ -1,5 +1,9 @@ -import { test } from 'qunit'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; +import { currentURL, currentRouteName } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; +import setupMirage from 'ember-cli-mirage/test-support/setup-mirage'; +import { t } from 'ember-i18n/test-support'; +import { setupBrowserNavigationButtons, backButton } from 'ember-cli-browser-navigation-button-test-helper/test-support'; import moment from 'moment'; import pageCreateIndex from 'croodle/tests/pages/create/index'; import pageCreateMeta from 'croodle/tests/pages/create/meta'; @@ -7,26 +11,23 @@ import pageCreateOptions from 'croodle/tests/pages/create/options'; import pageCreateOptionsDatetime from 'croodle/tests/pages/create/options-datetime'; import pageCreateSettings from 'croodle/tests/pages/create/settings'; import pagePollParticipation from 'croodle/tests/pages/poll/participation'; -/* jshint proto: true */ -moduleForAcceptance('Acceptance | create a poll', { - beforeEach() { +module('Acceptance | create a poll', function(hooks) { + hooks.beforeEach(function() { window.localStorage.setItem('locale', 'en'); - moment.locale('en'); - } -}); + }); -test('create a default poll', function(assert) { - const dates = [ - moment().add(1, 'day'), - moment().add(1, 'week') - ]; + setupApplicationTest(hooks); + setupMirage(hooks); - pageCreateIndex - .visit(); + test('create a default poll', async function(assert) { + const dates = [ + moment().add(1, 'day'), + moment().add(1, 'week') + ]; - andThen(function() { - assert.equal(currentPath(), 'create.index'); + await pageCreateIndex.visit(); + assert.equal(currentRouteName(), 'create.index'); assert.equal( pageCreateIndex.statusBar().active, t('create.formStep.type').toString(), @@ -53,151 +54,123 @@ test('create a default poll', function(assert) { 'poll type selection has autofocus' ); - pageCreateIndex + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); + assert.equal( + pageCreateMeta.statusBar().active, + t('create.formStep.meta').toString(), + 'status bar shows correct item as current path (meta)' + ); + assert.deepEqual( + pageCreateMeta.statusBar().toArray().map((el) => el.isDisabled), + [false, false, true, true, true], + 'status bar has correct items disabled (meta)' + ); + assert.ok( + pageCreateMeta.titleHasFocus, + 'title input has autofocus' + ); + + await pageCreateMeta + .title('default poll') .next(); + assert.equal(currentRouteName(), 'create.options'); + assert.equal( + pageCreateOptions.statusBar().active, + t('create.formStep.options.days').toString(), + 'status bar shows correct item as current path (options.days)' + ); + assert.deepEqual( + pageCreateOptions.statusBar().toArray().map((el) => el.isDisabled), + [false, false, false, true, true], + 'status bar has correct items disabled (options)' + ); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); - assert.equal( - pageCreateMeta.statusBar().active, - t('create.formStep.meta').toString(), - 'status bar shows correct item as current path (meta)' - ); - assert.deepEqual( - pageCreateMeta.statusBar().toArray().map((el) => el.isDisabled), - [false, false, true, true, true], - 'status bar has correct items disabled (meta)' - ); - assert.ok( - pageCreateMeta.titleHasFocus, - 'title input has autofocus' - ); + await pageCreateOptions.dateOptions(dates); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.equal( + pageCreateOptionsDatetime.statusBar().active, + t('create.formStep.options-datetime').toString(), + 'status bar shows correct item as current path (options-datetime)' + ); + assert.deepEqual( + pageCreateOptionsDatetime.statusBar().toArray().map((el) => el.isDisabled), + [false, false, false, false, true], + 'status bar has correct items disabled (options-datetime)' + ); + assert.ok( + pageCreateOptionsDatetime.firstTime.inputHasFocus, + 'first time input has autofocus' + ); - pageCreateMeta - .title('default poll') - .next(); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); + assert.equal( + pageCreateSettings.statusBar().active, + t('create.formStep.settings').toString(), + 'status bar shows correct item as current path (settings)' + ); + assert.deepEqual( + pageCreateSettings.statusBar().toArray().map((el) => el.isDisabled), + [false, false, false, false, false], + 'status bar has correct items disabled (settings)' + ); + assert.ok( + pageCreateSettings.availableAnswersHasFocus, + 'available answers selection has autofocus' + ); - andThen(function() { - assert.equal(currentPath(), 'create.options'); - assert.equal( - pageCreateOptions.statusBar().active, - t('create.formStep.options.days').toString(), - 'status bar shows correct item as current path (options.days)' - ); - assert.deepEqual( - pageCreateOptions.statusBar().toArray().map((el) => el.isDisabled), - [false, false, false, true, true], - 'status bar has correct items disabled (options)' - ); + // simulate temporate this.server error + this.server.post('/polls', undefined, 503); - pageCreateOptions - .dateOptions(dates); - pageCreateOptions - .next(); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); - assert.equal( - pageCreateOptionsDatetime.statusBar().active, - t('create.formStep.options-datetime').toString(), - 'status bar shows correct item as current path (options-datetime)' - ); - assert.deepEqual( - pageCreateOptionsDatetime.statusBar().toArray().map((el) => el.isDisabled), - [false, false, false, false, true], - 'status bar has correct items disabled (options-datetime)' - ); - assert.ok( - pageCreateOptionsDatetime.firstTime.inputHasFocus, - 'first time input has autofocus' - ); + // simulate this.server is available again + this.server.post('/polls'); - pageCreateOptionsDatetime - .next(); - - andThen(() => { - assert.equal(currentPath(), 'create.settings'); - assert.equal( - pageCreateSettings.statusBar().active, - t('create.formStep.settings').toString(), - 'status bar shows correct item as current path (settings)' - ); - assert.deepEqual( - pageCreateSettings.statusBar().toArray().map((el) => el.isDisabled), - [false, false, false, false, false], - 'status bar has correct items disabled (settings)' - ); - assert.ok( - pageCreateSettings.availableAnswersHasFocus, - 'available answers selection has autofocus' - ); - - // simulate temporate server error - server.post('/polls', undefined, 503); - - pageCreateSettings - .save(); - - andThen(() => { - assert.equal(currentPath(), 'create.settings'); - - // simulate server is available again - server.post('/polls'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - `poll url ${currentURL()} is valid` - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - '', - 'poll description is correct' - ); - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); - assert.deepEqual( - pagePollParticipation.options().labels, - dates.map((date) => date.format(dayFormat)), - 'options are correctly labeled' - ); - assert.deepEqual( - pagePollParticipation.options().answers, - [ - t('answerTypes.yes.label').toString(), - t('answerTypes.no.label').toString() - ], - 'answers are correctly labeled' - ); - assert.ok( - pagePollParticipation.nameHasFocus, - 'name input has autofocus' - ); - }); - }); - }); - }); - }); - }); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + `poll url ${currentURL()} is valid` + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + '', + 'poll description is correct' + ); + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); + assert.deepEqual( + pagePollParticipation.options().labels, + dates.map((date) => date.format(dayFormat)), + 'options are correctly labeled' + ); + assert.deepEqual( + pagePollParticipation.options().answers, + [ + t('answerTypes.yes.label').toString(), + t('answerTypes.no.label').toString() + ], + 'answers are correctly labeled' + ); + assert.ok( + pagePollParticipation.nameHasFocus, + 'name input has autofocus' + ); }); -}); -test('create a poll for answering a question', function(assert) { - pageCreateIndex - .visit(); - - andThen(function() { + test('create a poll for answering a question', async function(assert) { + await pageCreateIndex.visit(); assert.equal( pageCreateIndex.statusBar().active, t('create.formStep.type').toString(), @@ -209,781 +182,542 @@ test('create a poll for answering a question', function(assert) { 'status bar has correct items disabled' ); - pageCreateIndex + await pageCreateIndex .pollType('MakeAPoll') .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.meta'); - assert.equal( - pageCreateMeta.statusBar().active, + assert.equal(currentRouteName(), 'create.meta'); + assert.equal( + pageCreateMeta.statusBar().active, + t('create.formStep.meta').toString(), + 'status bar shows correct item as current path (meta)' + ); + assert.deepEqual( + pageCreateMeta.statusBar().toArray().map((el) => el.text), + [ + t('create.formStep.type').toString(), t('create.formStep.meta').toString(), - 'status bar shows correct item as current path (meta)' - ); - assert.deepEqual( - pageCreateMeta.statusBar().toArray().map((el) => el.text), - [ - t('create.formStep.type').toString(), - t('create.formStep.meta').toString(), - t('create.formStep.options.text').toString(), - t('create.formStep.settings').toString() - ], - 'status bar has correct items' - ); - assert.deepEqual( - pageCreateMeta.statusBar().toArray().map((el) => el.isDisabled), - [false, false, true, true], - 'status bar has correct items disabled (meta)' - ); + t('create.formStep.options.text').toString(), + t('create.formStep.settings').toString() + ], + 'status bar has correct items' + ); + assert.deepEqual( + pageCreateMeta.statusBar().toArray().map((el) => el.isDisabled), + [false, false, true, true], + 'status bar has correct items disabled (meta)' + ); - pageCreateMeta - .title('default poll') - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.options'); - assert.equal( - pageCreateOptions.statusBar().active, - t('create.formStep.options.text').toString(), - 'status bar shows correct item as current path (options.text)' - ); - assert.deepEqual( - pageCreateOptions.statusBar().toArray().map((el) => el.isDisabled), - [false, false, false, true], - 'status bar has correct items disabled (options)' - ); - assert.hasComponent('create-options-text'); - assert.ok( - pageCreateOptions.firstTextOption.inputHasFocus, - 'first option input has autofocus' - ); - - assert.equal( - pageCreateOptions.textOptions().count, - 2, - 'there are two input fields as default' - ); - - pageCreateOptions.next(); - - andThen(function() { - assert.equal( - currentPath(), - 'create.options', - 'validation errors prevents transition' - ); - assert.equal( - pageCreateOptions.statusBar().active, - t('create.formStep.options.text').toString(), - 'status bar shows correct item as current path (options.text)' - ); - assert.ok( - pageCreateOptions.textOptions(0).hasError && - pageCreateOptions.textOptions(1).hasError, - 'validation errors are shown after submit' - ); - - pageCreateOptions - .textOptions(0).title('option a'); - pageCreateOptions - .textOptions(1).title('option c'); - pageCreateOptions - .textOptions(0).add(); - - andThen(function() { - assert.equal( - pageCreateOptions.textOptions().count, - 3, - 'option was added' - ); - pageCreateOptions - .textOptions(1).title('option b'); - pageCreateOptions - .textOptions(2).add(); - - andThen(function() { - assert.equal( - pageCreateOptions.textOptions().count, - 4, - 'option was added' - ); - pageCreateOptions - .textOptions(3).title('to be deleted'); - pageCreateOptions - .textOptions(3).delete(); - - andThen(function() { - assert.equal( - pageCreateOptions.textOptions().count, - 3, - 'option got deleted' - ); - - pageCreateOptions - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - assert.equal( - pageCreateSettings.statusBar().active, - t('create.formStep.settings').toString(), - 'status bar shows correct item as current path (settings)' - ); - assert.deepEqual( - pageCreateSettings.statusBar().toArray().map((el) => el.isDisabled), - [false, false, false, false], - 'status bar has correct items disabled (settings)' - ); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - '', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - ['option a', 'option b', 'option c'], - 'options are labeled correctly' - ); - }); - }); - }); - }); - }); - }); - }); - }); - }); -}); - -test('create a poll with times and description', function(assert) { - let days = [ - moment().add(1, 'day'), - moment().add(1, 'week') - ]; - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); - - pageCreateIndex - .visit(); - - andThen(function() { - pageCreateIndex + await pageCreateMeta + .title('default poll') .next(); + assert.equal(currentRouteName(), 'create.options'); + assert.equal( + pageCreateOptions.statusBar().active, + t('create.formStep.options.text').toString(), + 'status bar shows correct item as current path (options.text)' + ); + assert.deepEqual( + pageCreateOptions.statusBar().toArray().map((el) => el.isDisabled), + [false, false, false, true], + 'status bar has correct items disabled (options)' + ); + assert.ok( + pageCreateOptions.firstTextOption.inputHasFocus, + 'first option input has autofocus' + ); + assert.equal( + pageCreateOptions.textOptions().count, + 2, + 'there are two input fields as default' + ); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); + await pageCreateOptions.next(); + assert.equal( + currentRouteName(), + 'create.options', + 'validation errors prevents transition' + ); + assert.equal( + pageCreateOptions.statusBar().active, + t('create.formStep.options.text').toString(), + 'status bar shows correct item as current path (options.text)' + ); + assert.ok( + pageCreateOptions.textOptions(0).hasError && + pageCreateOptions.textOptions(1).hasError, + 'validation errors are shown after submit' + ); - pageCreateMeta - .title('default poll') - .description('a sample description') - .next(); + await pageCreateOptions.textOptions(0).title('option a'); + await pageCreateOptions.textOptions(1).title('option c'); + await pageCreateOptions.textOptions(0).add(); + assert.equal( + pageCreateOptions.textOptions().count, + 3, + 'option was added' + ); - andThen(function() { - assert.equal(currentPath(), 'create.options'); + await pageCreateOptions.textOptions(1).title('option b'); + await pageCreateOptions.textOptions(2).add(); + assert.equal( + pageCreateOptions.textOptions().count, + 4, + 'option was added' + ); - pageCreateOptions - .dateOptions(days); - pageCreateOptions - .next(); + await pageCreateOptions.textOptions(3).title('to be deleted'); + await pageCreateOptions.textOptions(3).delete(); + assert.equal( + pageCreateOptions.textOptions().count, + 3, + 'option got deleted' + ); - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.settings'); + assert.equal( + pageCreateSettings.statusBar().active, + t('create.formStep.settings').toString(), + 'status bar shows correct item as current path (settings)' + ); + assert.deepEqual( + pageCreateSettings.statusBar().toArray().map((el) => el.isDisabled), + [false, false, false, false], + 'status bar has correct items disabled (settings)' + ); - assert.deepEqual( - pageCreateOptionsDatetime.days().labels, - days.map((day) => day.format(dayFormat)), - 'time inputs having days as label' - ); - - pageCreateOptionsDatetime - .times(0).time('10:00'); - pageCreateOptionsDatetime - .times(0).add(); - - andThen(() => { - pageCreateOptionsDatetime - .times(1).time('18:00'); - pageCreateOptionsDatetime - .times(2).time('12:00'); - - pageCreateOptionsDatetime - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - 'a sample description', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - [ - days[0].hour(10).minute(0).format('LLLL'), - days[0].hour(18).minute(0).format('LT'), - days[1].hour(12).minute(0).format('LLLL') - ], - 'options are correctly labeled' - ); - }); - }); - }); - }); - }); - }); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + '', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + ['option a', 'option b', 'option c'], + 'options are labeled correctly' + ); }); -}); -test('create a poll with only one day and multiple times', function(assert) { - let day = moment().add(1, 'day'); - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); + test('create a poll with times and description', async function(assert) { + let days = [ + moment().add(1, 'day'), + moment().add(1, 'week') + ]; + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); - pageCreateIndex - .visit(); + await pageCreateIndex.visit(); + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); - andThen(function() { - pageCreateIndex + await pageCreateMeta + .title('default poll') + .description('a sample description') .next(); + assert.equal(currentRouteName(), 'create.options'); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); + await pageCreateOptions.dateOptions(days); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.deepEqual( + pageCreateOptionsDatetime.days().labels, + days.map((day) => day.format(dayFormat)), + 'time inputs having days as label' + ); - pageCreateMeta - .title('default poll') - .description('a sample description') - .next(); + await pageCreateOptionsDatetime.times(0).time('10:00'); + await pageCreateOptionsDatetime.times(0).add(); + await pageCreateOptionsDatetime.times(1).time('18:00'); + await pageCreateOptionsDatetime.times(2).time('12:00'); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.options'); - - pageCreateOptions - .dateOptions([ day ]); - pageCreateOptions - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); - - assert.deepEqual( - pageCreateOptionsDatetime.days().labels, - [ day.format(dayFormat) ], - 'time inputs having days as label' - ); - - pageCreateOptionsDatetime - .times(0).time('10:00'); - pageCreateOptionsDatetime - .times(0).add(); - - andThen(() => { - pageCreateOptionsDatetime - .times(1).time('18:00'); - - pageCreateOptionsDatetime - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - 'a sample description', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - [ - day.hour(10).minute(0).format('LLLL'), - day.hour(18).minute(0).format('LT') - ], - 'options are correctly labeled' - ); - }); - }); - }); - }); - }); - }); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + 'a sample description', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + [ + days[0].hour(10).minute(0).format('LLLL'), + days[0].hour(18).minute(0).format('LT'), + days[1].hour(12).minute(0).format('LLLL') + ], + 'options are correctly labeled' + ); }); -}); -test('create a poll with only one day (without time)', function(assert) { - let day = moment().add(1, 'day'); - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); + test('create a poll with only one day and multiple times', async function(assert) { + let day = moment().add(1, 'day'); + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); - pageCreateIndex - .visit(); + await pageCreateIndex.visit(); + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); - andThen(function() { - pageCreateIndex + await pageCreateMeta + .title('default poll') + .description('a sample description') .next(); + assert.equal(currentRouteName(), 'create.options'); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); + await pageCreateOptions.dateOptions([ day ]); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.deepEqual( + pageCreateOptionsDatetime.days().labels, + [ day.format(dayFormat) ], + 'time inputs having days as label' + ); - pageCreateMeta - .title('default poll') - .description('a sample description') - .next(); + await pageCreateOptionsDatetime.times(0).time('10:00'); + await pageCreateOptionsDatetime.times(0).add(); + await pageCreateOptionsDatetime.times(1).time('18:00'); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.options'); - - pageCreateOptions - .dateOptions([ day ]); - pageCreateOptions - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); - - assert.deepEqual( - pageCreateOptionsDatetime.days().labels, - [ day.format(dayFormat) ], - 'time inputs having days as label' - ); - - pageCreateOptionsDatetime - .next(); - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - 'a sample description', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - [ - day.format(dayFormat) - ], - 'options are correctly labeled' - ); - }); - }); - }); - }); - }); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + 'a sample description', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + [ + day.hour(10).minute(0).format('LLLL'), + day.hour(18).minute(0).format('LT') + ], + 'options are correctly labeled' + ); }); -}); -test('create a poll with only one day (with time)', function(assert) { - let day = moment().add(1, 'day'); - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); + test('create a poll with only one day (without time)', async function(assert) { + let day = moment().add(1, 'day'); + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); - pageCreateIndex - .visit(); + await pageCreateIndex.visit(); + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); - andThen(function() { - pageCreateIndex + await pageCreateMeta + .title('default poll') + .description('a sample description') .next(); + assert.equal(currentRouteName(), 'create.options'); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); + await pageCreateOptions.dateOptions([ day ]); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.deepEqual( + pageCreateOptionsDatetime.days().labels, + [ day.format(dayFormat) ], + 'time inputs having days as label' + ); - pageCreateMeta - .title('default poll') - .description('a sample description') - .next(); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.options'); - - pageCreateOptions - .dateOptions([ day ]); - pageCreateOptions - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); - - assert.deepEqual( - pageCreateOptionsDatetime.days().labels, - [ day.format(dayFormat) ], - 'time inputs having days as label' - ); - - pageCreateOptionsDatetime - .times(0).time('22:30'); - pageCreateOptionsDatetime - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - 'a sample description', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - [ - day.hour(22).minute(30).format('LLLL') - ], - 'options are correctly labeled' - ); - }); - }); - }); - }); - }); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + 'a sample description', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + [ + day.format(dayFormat) + ], + 'options are correctly labeled' + ); }); -}); -test('create a poll for answering a question with only one option', function(assert) { - pageCreateIndex - .visit(); + test('create a poll with only one day (with time)', async function(assert) { + let day = moment().add(1, 'day'); + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); - andThen(function() { - pageCreateIndex + await pageCreateIndex.visit(); + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); + + await pageCreateMeta + .title('default poll') + .description('a sample description') + .next(); + assert.equal(currentRouteName(), 'create.options'); + + await pageCreateOptions.dateOptions([ day ]); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.deepEqual( + pageCreateOptionsDatetime.days().labels, + [ day.format(dayFormat) ], + 'time inputs having days as label' + ); + + await pageCreateOptionsDatetime.times(0).time('22:30'); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); + + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + 'a sample description', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + [ + day.hour(22).minute(30).format('LLLL') + ], + 'options are correctly labeled' + ); + }); + + test('create a poll for answering a question with only one option', async function(assert) { + await pageCreateIndex.visit(); + + await pageCreateIndex .pollType('MakeAPoll') .next(); + assert.equal(currentRouteName(), 'create.meta'); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); - - pageCreateMeta - .title('default poll') - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.options'); - assert.hasComponent('create-options-text'); - - assert.equal( - pageCreateOptions.textOptions().count, - 2, - 'there are two input fields as default' - ); - - pageCreateOptions - .textOptions(0).title('option a'); - pageCreateOptions - .textOptions(1).delete(); - - andThen(function() { - assert.equal( - pageCreateOptions.textOptions().count, - 1, - 'option was deleted' - ); - - pageCreateOptions - .next(); - - andThen(function() { - assert.equal(currentPath(), 'create.settings'); - - pageCreateSettings - .save(); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - '', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - ['option a'], - 'options are labeled correctly' - ); - }); - }); - }); - }); - }); - }); -}); - -test('create a poll and using back button (find a date)', function(assert) { - let days = [ - moment().add(1, 'day').hours(0).minutes(0).seconds(0).milliseconds(0), - moment().add(1, 'week').hours(0).minutes(0).seconds(0).milliseconds(0) - ]; - const dayFormat = moment.localeData().longDateFormat('LLLL') - .replace( - moment.localeData().longDateFormat('LT'), '') - .trim(); - - setupBrowserNavigationButtons(); - - pageCreateIndex - .visit(); - - andThen(function() { - pageCreateIndex + await pageCreateMeta + .title('default poll') .next(); + assert.equal(currentRouteName(), 'create.options'); + assert.equal( + pageCreateOptions.textOptions().count, + 2, + 'there are two input fields as default' + ); - andThen(function() { - assert.equal(currentPath(), 'create.meta'); + await pageCreateOptions.textOptions(0).title('option a'); + await pageCreateOptions.textOptions(1).delete(); + assert.equal( + pageCreateOptions.textOptions().count, + 1, + 'option was deleted' + ); - pageCreateMeta - .title('default poll') - .description('a sample description') - .next(); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.options'); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + '', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + ['option a'], + 'options are labeled correctly' + ); + }); - pageCreateOptions - .dateOptions(days); - pageCreateOptions - .next(); + test('create a poll and using back button (find a date)', async function(assert) { + let days = [ + moment().add(1, 'day').hours(0).minutes(0).seconds(0).milliseconds(0), + moment().add(1, 'week').hours(0).minutes(0).seconds(0).milliseconds(0) + ]; + const dayFormat = moment.localeData().longDateFormat('LLLL') + .replace( + moment.localeData().longDateFormat('LT'), '') + .trim(); - andThen(function() { - assert.equal(currentPath(), 'create.options-datetime'); + setupBrowserNavigationButtons(); - assert.deepEqual( - pageCreateOptionsDatetime.days().labels, - days.map((day) => day.format(dayFormat)), - 'time inputs having days as label' - ); - pageCreateOptionsDatetime.times(1).time('10:00'); + await pageCreateIndex.visit(); + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); - backButton(); + await pageCreateMeta + .title('default poll') + .description('a sample description') + .next(); + assert.equal(currentRouteName(), 'create.options'); - andThen(() => { - assert.equal(currentPath(), 'create.options'); - assert.deepEqual( - pageCreateOptions.dateOptions().map((date) => date.toISOString()), - days.map((day) => day.toISOString()), - 'days are still present after back button is used' - ); + await pageCreateOptions.dateOptions(days); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + assert.deepEqual( + pageCreateOptionsDatetime.days().labels, + days.map((day) => day.format(dayFormat)), + 'time inputs having days as label' + ); - pageCreateOptions - .next(); + await pageCreateOptionsDatetime.times(1).time('10:00'); + await backButton(); + assert.equal(currentRouteName(), 'create.options'); + assert.deepEqual( + pageCreateOptions.dateOptions().map((date) => date.toISOString()), + days.map((day) => day.toISOString()), + 'days are still present after back button is used' + ); - andThen(() => { - assert.equal(currentPath(), 'create.options-datetime'); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); - pageCreateOptionsDatetime - .next(); + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); - andThen(function() { - assert.equal(currentPath(), 'create.settings'); + await pageCreateSettings.save(); + assert.equal(currentRouteName(), 'poll.participation'); + assert.ok( + pagePollParticipation.urlIsValid() === true, + 'poll url is valid' + ); + assert.equal( + pagePollParticipation.title, + 'default poll', + 'poll title is correct' + ); + assert.equal( + pagePollParticipation.description, + 'a sample description', + 'poll description is correct' + ); + assert.deepEqual( + pagePollParticipation.options().labels, + [ + days[0].format(dayFormat), + days[1].hour(10).minute(0).format('LLLL') + ], + 'options are correctly labeled' + ); + }); - pageCreateSettings - .save(); - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - assert.ok( - pagePollParticipation.urlIsValid() === true, - 'poll url is valid' - ); - assert.equal( - pagePollParticipation.title, - 'default poll', - 'poll title is correct' - ); - assert.equal( - pagePollParticipation.description, - 'a sample description', - 'poll description is correct' - ); - assert.deepEqual( - pagePollParticipation.options().labels, - [ - days[0].format(dayFormat), - days[1].hour(10).minute(0).format('LLLL') - ], - 'options are correctly labeled' - ); - }); - }); - }); - }); - }); - }); - }); - }); -}); - -test('Start at first step is enforced', function(assert) { - pageCreateSettings.visit(); - andThen(() => { - assert.equal(currentPath(), 'create.index'); - }); -}); - -test('back button', function(assert) { - pageCreateIndex.visit(); - - andThen(() => { - assert.equal(currentPath(), 'create.index'); - pageCreateIndex.next(); - - andThen(() => { - assert.equal(currentPath(), 'create.meta'); - pageCreateMeta - .title('foo') - .next(); - - andThen(() => { - assert.equal(currentPath(), 'create.options'); - pageCreateOptions - .dateOptions([new Date()]); - pageCreateOptions - .next(); - - andThen(() => { - assert.equal(currentPath(), 'create.options-datetime'); - pageCreateOptionsDatetime.next(); - - andThen(() => { - assert.equal(currentPath(), 'create.settings'); - pageCreateSettings.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.options-datetime'); - pageCreateOptionsDatetime.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.options'); - pageCreateOptions.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.meta'); - pageCreateMeta.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.index'); - pageCreateIndex - .pollType('MakeAPoll') - .next(); - - andThen(() => { - assert.equal(currentPath(), 'create.meta'); - pageCreateMeta.next(); - - andThen(() => { - assert.equal(currentPath(), 'create.options'); - pageCreateOptions - .textOptions(1).title('bar'); - pageCreateOptions.next(); - - andThen(() => { - assert.equal(currentPath(), 'create.settings'); - pageCreateSettings.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.options'); - pageCreateOptions.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.meta'); - pageCreateMeta.back(); - - andThen(() => { - assert.equal(currentPath(), 'create.index'); - }); - }); - }); - }); - }); - }); - }); - }); - }); - }); - }); - }); - }); - }); + test('Start at first step is enforced', async function(assert) { + await pageCreateSettings.visit(); + assert.equal(currentRouteName(), 'create.index'); + }); + + test('back button', async function(assert) { + await pageCreateIndex.visit(); + assert.equal(currentRouteName(), 'create.index'); + + await pageCreateIndex.next(); + assert.equal(currentRouteName(), 'create.meta'); + + await pageCreateMeta + .title('foo') + .next(); + assert.equal(currentRouteName(), 'create.options'); + + await pageCreateOptions.dateOptions([new Date()]); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.options-datetime'); + + await pageCreateOptionsDatetime.next(); + assert.equal(currentRouteName(), 'create.settings'); + + await pageCreateSettings.back(); + assert.equal(currentRouteName(), 'create.options-datetime'); + + await pageCreateOptionsDatetime.back(); + assert.equal(currentRouteName(), 'create.options'); + + await pageCreateOptions.back(); + assert.equal(currentRouteName(), 'create.meta'); + + await pageCreateMeta.back(); + assert.equal(currentRouteName(), 'create.index'); + + await pageCreateIndex + .pollType('MakeAPoll') + .next(); + assert.equal(currentRouteName(), 'create.meta'); + + await pageCreateMeta.next(); + assert.equal(currentRouteName(), 'create.options'); + + await pageCreateOptions.textOptions(1).title('bar'); + await pageCreateOptions.next(); + assert.equal(currentRouteName(), 'create.settings'); + + await pageCreateSettings.back(); + assert.equal(currentRouteName(), 'create.options'); + + await pageCreateOptions.back(); + assert.equal(currentRouteName(), 'create.meta'); + + await pageCreateMeta.back(); + assert.equal(currentRouteName(), 'create.index'); }); }); diff --git a/tests/acceptance/i18n-test.js b/tests/acceptance/i18n-test.js index 247fa34..415a2d9 100644 --- a/tests/acceptance/i18n-test.js +++ b/tests/acceptance/i18n-test.js @@ -1,26 +1,24 @@ -import { test } from 'qunit'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; +import { find, visit } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; import pageIndex from 'croodle/tests/pages/index'; -moduleForAcceptance('Acceptance | i18n', { - beforeEach() { - window.localStorage.setItem('locale', 'en'); - } -}); +module('Acceptance | i18n', function(hooks) { + hooks.beforeEach(function() { + window.localStorage.setItem('locale', 'de'); + }); -test('locale is saved in localStorage', function(assert) { - visit('/'); + setupApplicationTest(hooks); - andThen(() => { - assert.equal(find('.language-select').val(), 'en'); - pageIndex.locale('de'); + test('locale is saved in localStorage', async function(assert) { + await visit('/'); + assert.equal(find('.language-select').value, 'de', 'picks up locale in locale storage'); - andThen(function() { - assert.equal(find('.language-select').val(), 'de'); - assert.equal( - window.localStorage.getItem('locale'), 'de', - 'persisted in localeStorage' - ); - }); + await pageIndex.locale('en'); + assert.equal(find('.language-select').value, 'en'); + assert.equal( + window.localStorage.getItem('locale'), 'en', + 'persisted in localeStorage' + ); }); }); diff --git a/tests/acceptance/legacy-support-test.js b/tests/acceptance/legacy-support-test.js index 7c3f509..be384a0 100644 --- a/tests/acceptance/legacy-support-test.js +++ b/tests/acceptance/legacy-support-test.js @@ -1,43 +1,47 @@ -import { test } from 'qunit'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; +import { currentRouteName, visit } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; +import setupMirage from 'ember-cli-mirage/test-support/setup-mirage'; +import { t } from 'ember-i18n/test-support'; +import switchTab from 'croodle/tests/helpers/switch-tab'; +import pollHasUser from 'croodle/tests/helpers/poll-has-user'; +import pollParticipate from 'croodle/tests/helpers/poll-participate'; import moment from 'moment'; import pagePollParticipation from 'croodle/tests/pages/poll/participation'; -/* jshint proto: true */ -moduleForAcceptance('Acceptance | legacy support', { - beforeEach() { +module('Acceptance | legacy support', function(hooks) { + hooks.beforeEach(function() { window.localStorage.setItem('locale', 'en'); - moment.locale('en'); - } -}); - -test('show a default poll created with v0.3.0', function(assert) { - const encryptionKey = '5MKFuNTKILUXw6RuqkAw6ooZw4k3mWWx98ZQw8vH'; - - let poll = server.create('poll', { - encryptionKey, - // property 'id' of answers has been renamed to 'type' in v0.4.0 - answers: [{ 'id': 'yes','labelTranslation': 'answerTypes.yes.label','icon': 'glyphicon glyphicon-thumbs-up','label': 'Ja' },{ 'id': 'maybe','labelTranslation': 'answerTypes.maybe.label','icon': 'glyphicon glyphicon-hand-right','label': 'Vielleicht' },{ 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' }], - options: [{ 'title': '2015-12-24T17:00:00.000Z' },{ 'title': '2015-12-24T19:00:00.000Z' },{ 'title': '2015-12-31T22:59:00.000Z' }], - users: [ - server.create('user', { - encryptionKey, - name: 'Fritz Bauer', - // selections.value was renamed to selections.label - // selections.id was renamed to selections.type - selections: [{ 'value': { 'id': 'yes','labelTranslation': 'answerTypes.yes.label','icon': 'glyphicon glyphicon-thumbs-up','label': 'Ja' } },{ 'value': { 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' } },{ 'value': { 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' } }], - // version tag had have wrong format - version: 'v0.3-0' - }) - ], - // version tag had have wrong format - version: 'v0.3-0' }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + setupApplicationTest(hooks); + setupMirage(hooks); - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); + test('show a default poll created with v0.3.0', async function(assert) { + const encryptionKey = '5MKFuNTKILUXw6RuqkAw6ooZw4k3mWWx98ZQw8vH'; + + let poll = this.server.create('poll', { + encryptionKey, + // property 'id' of answers has been renamed to 'type' in v0.4.0 + answers: [{ 'id': 'yes','labelTranslation': 'answerTypes.yes.label','icon': 'glyphicon glyphicon-thumbs-up','label': 'Ja' },{ 'id': 'maybe','labelTranslation': 'answerTypes.maybe.label','icon': 'glyphicon glyphicon-hand-right','label': 'Vielleicht' },{ 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' }], + options: [{ 'title': '2015-12-24T17:00:00.000Z' },{ 'title': '2015-12-24T19:00:00.000Z' },{ 'title': '2015-12-31T22:59:00.000Z' }], + users: [ + this.server.create('user', { + encryptionKey, + name: 'Fritz Bauer', + // selections.value was renamed to selections.label + // selections.id was renamed to selections.type + selections: [{ 'value': { 'id': 'yes','labelTranslation': 'answerTypes.yes.label','icon': 'glyphicon glyphicon-thumbs-up','label': 'Ja' } },{ 'value': { 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' } },{ 'value': { 'id': 'no','labelTranslation': 'answerTypes.no.label','icon': 'glyphicon glyphicon-thumbs-down','label': 'Nein' } }], + // version tag had have wrong format + version: 'v0.3-0' + }) + ], + // version tag had have wrong format + version: 'v0.3-0' + }); + + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); assert.deepEqual( pagePollParticipation.options().labels, [ @@ -55,70 +59,57 @@ test('show a default poll created with v0.3.0', function(assert) { ] ); - switchTab('evaluation'); + await switchTab('evaluation'); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUser(assert, + 'Fritz Bauer', + [ + t('answerTypes.yes.label'), + t('answerTypes.no.label'), + t('answerTypes.no.label') + ] + ); - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); + await switchTab('participation'); + assert.equal(currentRouteName(), 'poll.participation'); - pollHasUser(assert, - 'Fritz Bauer', - [ - t('answerTypes.yes.label'), - t('answerTypes.no.label'), - t('answerTypes.no.label') - ] - ); + await pollParticipate('Hermann Langbein', ['yes', 'maybe', 'yes']); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUser(assert, + 'Hermann Langbein', + [ + t('answerTypes.yes.label'), + t('answerTypes.maybe.label'), + t('answerTypes.yes.label') + ] + ); + }); - switchTab('participation'); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - - pollParticipate('Hermann Langbein', ['yes', 'maybe', 'yes']); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUser(assert, - 'Hermann Langbein', - [ - t('answerTypes.yes.label'), - t('answerTypes.maybe.label'), - t('answerTypes.yes.label') - ] - ); - }); - }); + test('show a poll using free text created with v0.3.0', async function(assert) { + let encryptionKey = 'Rre6dAGOYLW9gYKOP4LhX7Qwfhe5Th3je0uKDtyy'; + let poll = this.server.create('poll', { + encryptionKey, + answerType: 'FreeText', + answers: [], + options: [{ 'title': 'apple pie' }, { 'title': 'pecan pie' }, { 'title': 'plum pie' }], + pollType: 'MakeAPoll', + users: [ + this.server.create('user', { + encryptionKey, + name: 'Paul Levi', + // selections.value was renamed to selections.label + // selections.id was renamed to selections.type + selections: [{ 'value': 'would be great!' }, { 'value': 'no way' }, { 'value': 'if I had to' }], + // version tag had have wrong format + version: 'v0.3-0' + }) + ], + // version tag had have wrong format + version: 'v0.3-0' }); - }); -}); -test('show a poll using free text created with v0.3.0', function(assert) { - let encryptionKey = 'Rre6dAGOYLW9gYKOP4LhX7Qwfhe5Th3je0uKDtyy'; - let poll = server.create('poll', { - encryptionKey, - answerType: 'FreeText', - answers: [], - options: [{ 'title': 'apple pie' }, { 'title': 'pecan pie' }, { 'title': 'plum pie' }], - pollType: 'MakeAPoll', - users: [ - server.create('user', { - encryptionKey, - name: 'Paul Levi', - // selections.value was renamed to selections.label - // selections.id was renamed to selections.type - selections: [{ 'value': 'would be great!' }, { 'value': 'no way' }, { 'value': 'if I had to' }], - // version tag had have wrong format - version: 'v0.3-0' - }) - ], - // version tag had have wrong format - version: 'v0.3-0' - }); - - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); assert.deepEqual( pagePollParticipation.options().labels, [ @@ -128,37 +119,29 @@ test('show a poll using free text created with v0.3.0', function(assert) { ] ); - switchTab('evaluation'); + await switchTab('evaluation'); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUser(assert, + 'Paul Levi', + [ + 'would be great!', + 'no way', + 'if I had to' + ] + ); - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUser(assert, - 'Paul Levi', - [ - 'would be great!', - 'no way', - 'if I had to' - ] - ); + await switchTab('participation'); + assert.equal(currentRouteName(), 'poll.participation'); - switchTab('participation'); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - pollParticipate('Hermann Langbein', ["I don't care", 'would be awesome', "can't imagine anything better"]); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUser(assert, - 'Hermann Langbein', - [ - "I don't care", - 'would be awesome', - "can't imagine anything better" - ] - ); - }); - }); - }); + await pollParticipate('Hermann Langbein', ["I don't care", 'would be awesome', "can't imagine anything better"]); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUser(assert, + 'Hermann Langbein', + [ + "I don't care", + 'would be awesome', + "can't imagine anything better" + ] + ); }); }); diff --git a/tests/acceptance/participate-in-a-poll-test.js b/tests/acceptance/participate-in-a-poll-test.js index e120c3a..47cc798 100644 --- a/tests/acceptance/participate-in-a-poll-test.js +++ b/tests/acceptance/participate-in-a-poll-test.js @@ -1,145 +1,135 @@ -import { test } from 'qunit'; +import { + click, + find, + findAll, + currentURL, + currentRouteName, + visit +} from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; +import setupMirage from 'ember-cli-mirage/test-support/setup-mirage'; +import { t } from 'ember-i18n/test-support'; +import pollHasUser, { pollHasUsersCount } from 'croodle/tests/helpers/poll-has-user'; +import pollParticipate from 'croodle/tests/helpers/poll-participate'; import jQuery from 'jquery'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; -/* jshint proto: true */ -moduleForAcceptance('Acceptance | participate in a poll', { - beforeEach() { +module('Acceptance | participate in a poll', function(hooks) { + hooks.beforeEach(function() { window.localStorage.setItem('locale', 'en'); - } -}); - -test('participate in a default poll', function(assert) { - server.logging = true; - - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`).then(function() { - assert.equal(currentPath(), 'poll.participation', 'poll is redirected to poll.participation'); - pollParticipate('Max Meiner', ['yes', 'no']); + setupApplicationTest(hooks); + setupMirage(hooks); - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - assert.equal( - currentURL().split('?')[1], - `encryptionKey=${encryptionKey}`, - 'encryption key is part of query params' - ); - pollHasUsersCount(assert, 1, 'user is added to user selections table'); - pollHasUser(assert, 'Max Meiner', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); - - click('.nav .participation'); - - andThen(() => { - assert.equal(currentPath(), 'poll.participation'); - assert.equal(find('.name input').val(), '', 'input for name is cleared'); - assert.ok( - !find('input[type="radio"]').toArray().some((el) => jQuery(el).prop('checked')), - 'radios are cleared' - ); - pollParticipate('Peter Müller', ['yes', 'yes']); - - andThen(() => { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUsersCount(assert, 2, 'user is added to user selections table'); - pollHasUser(assert, 'Peter Müller', [t('answerTypes.yes.label'), t('answerTypes.yes.label')]); - }); - }); + test('participate in a default poll', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey }); - }); -}); -test('participate in a poll using freetext', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - answerType: 'FreeText', - answers: [], - encryptionKey + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation', 'poll is redirected to poll.participation'); + + await pollParticipate('Max Meiner', ['yes', 'no']); + assert.equal(currentRouteName(), 'poll.evaluation'); + assert.equal( + currentURL().split('?')[1], + `encryptionKey=${encryptionKey}`, + 'encryption key is part of query params' + ); + pollHasUsersCount(assert, 1, 'user is added to user selections table'); + pollHasUser(assert, 'Max Meiner', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); + + await click('.nav .participation'); + assert.equal(currentRouteName(), 'poll.participation'); + assert.equal(find('.name input').value, '', 'input for name is cleared'); + assert.ok( + !findAll('input[type="radio"]').toArray().some((el) => el.checked), + 'radios are cleared' + ); + + await pollParticipate('Peter Müller', ['yes', 'yes']); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUsersCount(assert, 2, 'user is added to user selections table'); + pollHasUser(assert, 'Peter Müller', [t('answerTypes.yes.label'), t('answerTypes.yes.label')]); }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`).then(function() { - assert.equal(currentPath(), 'poll.participation'); - pollParticipate('Max Manus', ['answer 1', 'answer 2']); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUsersCount(assert, 1, 'user is added to user selections table'); - pollHasUser(assert, 'Max Manus', ['answer 1', 'answer 2']); + test('participate in a poll using freetext', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + answerType: 'FreeText', + answers: [], + encryptionKey }); - }); -}); -test('participate in a poll which does not force an answer to all options', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey, - forceAnswer: false + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`) + assert.equal(currentRouteName(), 'poll.participation'); + + await pollParticipate('Max Manus', ['answer 1', 'answer 2']); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUsersCount(assert, 1, 'user is added to user selections table'); + pollHasUser(assert, 'Max Manus', ['answer 1', 'answer 2']); }); - visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`).then(function() { - assert.equal(currentPath(), 'poll.participation'); - pollParticipate('Karl Käfer', ['yes', null]); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUsersCount(assert, 1, 'user is added to user selections table'); - pollHasUser(assert, 'Karl Käfer', [t('answerTypes.yes.label'), '']); + test('participate in a poll which does not force an answer to all options', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey, + forceAnswer: false }); - }); -}); -test('participate in a poll which allows anonymous participation', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - anonymousUser: true, - encryptionKey + await visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); + + await pollParticipate('Karl Käfer', ['yes', null]); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUsersCount(assert, 1, 'user is added to user selections table'); + pollHasUser(assert, 'Karl Käfer', [t('answerTypes.yes.label'), '']); }); - visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`).then(function() { - assert.equal(currentPath(), 'poll.participation'); - pollParticipate(null, ['yes', 'no']); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUsersCount(assert, 1, 'user is added to user selections table'); - pollHasUser(assert, '', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); + test('participate in a poll which allows anonymous participation', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + anonymousUser: true, + encryptionKey }); - }); -}); -test('network connectivity errors', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey + await visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); + + await pollParticipate(null, ['yes', 'no']); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUsersCount(assert, 1, 'user is added to user selections table'); + pollHasUser(assert, '', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); }); - server.post('/users', undefined, 503); - - visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`).then(function() { - assert.equal(currentPath(), 'poll.participation'); - pollParticipate('foo bar', ['yes', 'no']); - - andThen(() => { - assert.ok( - find('#modal-saving-failed-modal').is(':visible'), - 'user gets notified that saving failed' - ); - - server.post('/users'); - click('#modal-saving-failed-modal button'); - - andThen(() => { - assert.notOk( - find('#modal-saving-failed-modal').is(':visible'), - 'modal is hidden after saving was successful' - ); - assert.equal(currentPath(), 'poll.evaluation'); - pollHasUsersCount(assert, 1, 'user is added to user selections table'); - pollHasUser(assert, 'foo bar', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); - }); + test('network connectivity errors', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey }); + + this.server.post('/users', undefined, 503); + + await visit(`/poll/${poll.id}/participation?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); + + await pollParticipate('foo bar', ['yes', 'no']); + assert.ok( + jQuery(find('#modal-saving-failed-modal')).is(':visible'), + 'user gets notified that saving failed' + ); + + this.server.post('/users'); + + await click('#modal-saving-failed-modal button'); + assert.notOk( + jQuery(find('#modal-saving-failed-modal')).is(':visible'), + 'modal is hidden after saving was successful' + ); + assert.equal(currentRouteName(), 'poll.evaluation'); + pollHasUsersCount(assert, 1, 'user is added to user selections table'); + pollHasUser(assert, 'foo bar', [t('answerTypes.yes.label'), t('answerTypes.no.label')]); }); }); diff --git a/tests/acceptance/view-evaluation-test.js b/tests/acceptance/view-evaluation-test.js index fed9d98..c7181d6 100644 --- a/tests/acceptance/view-evaluation-test.js +++ b/tests/acceptance/view-evaluation-test.js @@ -1,307 +1,295 @@ -import { test } from 'qunit'; -import jQuery from 'jquery'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; +import { findAll, currentRouteName, find, visit } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; +import setupMirage from 'ember-cli-mirage/test-support/setup-mirage'; +import { t } from 'ember-i18n/test-support'; +import switchTab from 'croodle/tests/helpers/switch-tab'; import moment from 'moment'; -/* jshint proto: true */ -moduleForAcceptance('Acceptance | view evaluation', { - beforeEach() { +module('Acceptance | view evaluation', function(hooks) { + hooks.beforeEach(function() { window.localStorage.setItem('locale', 'en'); - moment.locale('en'); - } -}); - -test('evaluation summary is not present for poll without participants', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + setupApplicationTest(hooks); + setupMirage(hooks); - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - switchTab('evaluation'); - - andThen(function() { - assert.equal(find('.tab-content .tab-pane .evaluation-summary').length, 0, 'evaluation summary is not present'); + test('evaluation summary is not present for poll without participants', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey }); - }); -}); -test('evaluation is correct for FindADate', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let user1 = server.create('user', { - creationDate: '2015-01-01T00:00:00.000Z', - encryptionKey, - name: 'Maximilian', - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }); - let user2 = server.create('user', { - creationDate: '2015-08-01T00:00:00.000Z', - encryptionKey, - name: 'Peter', - selections: [ - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - }, - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }); - let poll = server.create('poll', { - answers: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - } - ], - encryptionKey, - options: [ - { title: '2015-12-12' }, - { title: '2016-01-01' } - ], - users: [user1, user2] + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); + + await switchTab('evaluation'); + assert.equal(findAll('.tab-content .tab-pane .evaluation-summary').length, 0, 'evaluation summary is not present'); }); - visit(`/poll/${poll.id}/evaluation?encryptionKey=${encryptionKey}`); + test('evaluation is correct for FindADate', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let user1 = this.server.create('user', { + creationDate: '2015-01-01T00:00:00.000Z', + encryptionKey, + name: 'Maximilian', + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }); + let user2 = this.server.create('user', { + creationDate: '2015-08-01T00:00:00.000Z', + encryptionKey, + name: 'Peter', + selections: [ + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + }, + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }); + let poll = this.server.create('poll', { + answers: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + } + ], + encryptionKey, + options: [ + { title: '2015-12-12' }, + { title: '2016-01-01' } + ], + users: [user1, user2] + }); - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - assert.equal(find('.tab-content .tab-pane .evaluation-summary').length, 1, 'evaluation summary is present'); + await visit(`/poll/${poll.id}/evaluation?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.evaluation'); + assert.equal(findAll('.tab-content .tab-pane .evaluation-summary').length, 1, 'evaluation summary is present'); assert.equal( - find('.participants').text().trim(), + find('.participants').textContent.trim(), t('poll.evaluation.participants', { count: 2 }).toString(), 'participants are counted correctly' ); assert.equal( - find('.best-options strong').text().trim(), + find('.best-options strong').textContent.trim(), 'Friday, January 1, 2016', 'options are evaluated correctly' ); assert.equal( - find('.last-participation').text().trim(), + find('.last-participation').textContent.trim(), t('poll.evaluation.lastParticipation', { ago: moment('2015-08-01T00:00:00.000Z').from() }).toString(), 'last participation is evaluated correctly' ); }); -}); -test('evaluation is correct for MakeAPoll', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let user1 = server.create('user', { - creationDate: '2015-01-01T00:00:00.000Z', - encryptionKey, - name: 'Maximilian', - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }); - let user2 = server.create('user', { - creationDate: '2015-08-01T00:00:00.000Z', - encryptionKey, - name: 'Peter', - selections: [ - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - }, - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }); - let poll = server.create('poll', { - answers: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - } - ], - encryptionKey, - options: [ - { title: 'first option' }, - { title: 'second option' } - ], - pollType: 'MakeAPoll', - users: [user1, user2] - }); + test('evaluation is correct for MakeAPoll', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let user1 = this.server.create('user', { + creationDate: '2015-01-01T00:00:00.000Z', + encryptionKey, + name: 'Maximilian', + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }); + let user2 = this.server.create('user', { + creationDate: '2015-08-01T00:00:00.000Z', + encryptionKey, + name: 'Peter', + selections: [ + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + }, + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }); + let poll = this.server.create('poll', { + answers: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + } + ], + encryptionKey, + options: [ + { title: 'first option' }, + { title: 'second option' } + ], + pollType: 'MakeAPoll', + users: [user1, user2] + }); - visit(`/poll/${poll.id}/evaluation?encryptionKey=${encryptionKey}`); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - assert.equal(find('.tab-content .tab-pane .evaluation-summary').length, 1, 'evaluation summary is present'); + await visit(`/poll/${poll.id}/evaluation?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.evaluation'); + assert.equal(findAll('.tab-content .tab-pane .evaluation-summary').length, 1, 'evaluation summary is present'); assert.equal( - find('.participants').text().trim(), + find('.participants').textContent.trim(), t('poll.evaluation.participants', { count: 2 }).toString(), 'participants are counted correctly' ); assert.equal( - find('.best-options strong').text().trim(), + find('.best-options strong').textContent.trim(), 'second option', 'options are evaluated correctly' ); assert.ok( - find('.user-selections-table').length, + findAll('.user-selections-table').length, 'has a table showing user selections' ); assert.deepEqual( - find('.user-selections-table thead th').map((i, el) => jQuery(el).text().trim()).get(), + findAll('.user-selections-table thead th').toArray().map((el) => el.textContent.trim()), ['', 'first option', 'second option'], 'dates are used as table headers' ); assert.deepEqual( - find('.user-selections-table tbody tr:nth-child(1) td').map((i, el) => jQuery(el).text().trim()).get(), + findAll('.user-selections-table tbody tr:nth-child(1) td').toArray().map((el) => el.textContent.trim()), ['Maximilian', 'Yes', 'Yes'], 'answers shown in table are correct for first user' ); assert.deepEqual( - find('.user-selections-table tbody tr:nth-child(2) td').map((i, el) => jQuery(el).text().trim()).get(), + findAll('.user-selections-table tbody tr:nth-child(2) td').toArray().map((el) => el.textContent.trim()), ['Peter', 'No', 'Yes'], 'answers shown in table are correct for second user' ); assert.equal( - find('.last-participation').text().trim(), + find('.last-participation').textContent.trim(), t('poll.evaluation.lastParticipation', { ago: moment('2015-08-01T00:00:00.000Z').from() }).toString(), 'last participation is evaluated correctly' ); }); -}); -test('could open evaluation by tab from poll participation', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - answers: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - } - ], - encryptionKey, - options: [ - { title: '2015-12-12' }, - { title: '2016-01-01' } - ], - users: [ - server.create('user', { - creationDate: '2015-01-01T00:00:00.000Z', - encryptionKey, - name: 'Maximilian', - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }), - server.create('user', { - creationDate: '2015-08-01T00:00:00.000Z', - encryptionKey, - name: 'Peter', - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - id: 'no', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - } - ] - }) - ] - }); - - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); - - andThen(function() { - assert.equal(currentPath(), 'poll.participation'); - switchTab('evaluation'); - - andThen(function() { - assert.equal(currentPath(), 'poll.evaluation'); - assert.equal( - find('.tab-pane h2').text().trim(), - t('poll.evaluation.label').toString(), - 'headline is there' - ); + test('could open evaluation by tab from poll participation', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + answers: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + } + ], + encryptionKey, + options: [ + { title: '2015-12-12' }, + { title: '2016-01-01' } + ], + users: [ + this.server.create('user', { + creationDate: '2015-01-01T00:00:00.000Z', + encryptionKey, + name: 'Maximilian', + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }), + this.server.create('user', { + creationDate: '2015-08-01T00:00:00.000Z', + encryptionKey, + name: 'Peter', + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + id: 'no', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + } + ] + }) + ] }); + + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.equal(currentRouteName(), 'poll.participation'); + + await switchTab('evaluation'); + assert.equal(currentRouteName(), 'poll.evaluation'); + assert.equal( + find('.tab-pane h2').textContent.trim(), + t('poll.evaluation.label').toString(), + 'headline is there' + ); }); }); diff --git a/tests/acceptance/view-poll-test.js b/tests/acceptance/view-poll-test.js index 8a1e429..4a46bb4 100644 --- a/tests/acceptance/view-poll-test.js +++ b/tests/acceptance/view-poll-test.js @@ -1,24 +1,27 @@ -import { test } from 'qunit'; -import moduleForAcceptance from 'croodle/tests/helpers/module-for-acceptance'; +import { find, click, visit } from '@ember/test-helpers'; +import { module, test } from 'qunit'; +import { setupApplicationTest } from 'ember-qunit'; +import setupMirage from 'ember-cli-mirage/test-support/setup-mirage'; +import switchTab from 'croodle/tests/helpers/switch-tab'; import pageParticipation from 'croodle/tests/pages/poll/participation'; import pageEvaluation from 'croodle/tests/pages/poll/evaluation'; import moment from 'moment'; -/* jshint proto: true */ +import jQuery from 'jquery'; -moduleForAcceptance('Acceptance | view poll', { - beforeEach() { +module('Acceptance | view poll', function(hooks) { + hooks.beforeEach(function() { window.localStorage.setItem('locale', 'en'); - moment.locale('en'); - } -}); + }); -test('poll url', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz012345789'; - let poll = server.create('poll', { encryptionKey }); - let pollUrl = `/poll/${poll.id}?encryptionKey=${encryptionKey}`; + setupApplicationTest(hooks); + setupMirage(hooks); - visit(pollUrl); - andThen(function() { + test('poll url', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz012345789'; + let poll = this.server.create('poll', { encryptionKey }); + let pollUrl = `/poll/${poll.id}?encryptionKey=${encryptionKey}`; + + await visit(pollUrl); assert.equal( pageParticipation.url, window.location.href, @@ -34,32 +37,31 @@ test('poll url', function(assert) { * https://github.com/poteto/ember-cli-flash/issues/202 */ }); -}); -test('shows a warning if poll is about to be expired', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey, - expirationDate: moment().add(1, 'week') - }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`).then(function() { + test('shows a warning if poll is about to be expired', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey, + expirationDate: moment().add(1, 'week') + }); + + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); assert.ok( pageParticipation.showsExpirationWarning ); }); -}); -test('view a poll with dates', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let poll = server.create('poll', { - encryptionKey, - options: [ - { title: '2015-12-12' }, - { title: '2016-01-01' } - ] - }); + test('view a poll with dates', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let poll = this.server.create('poll', { + encryptionKey, + options: [ + { title: '2015-12-12' }, + { title: '2016-01-01' } + ] + }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`).then(function() { + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); assert.deepEqual( pageParticipation.options().labels, [ @@ -68,24 +70,23 @@ test('view a poll with dates', function(assert) { ] ); }); -}); -test('view a poll with dates and times', function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let timezone = moment.tz.guess(); - let poll = server.create('poll', { - encryptionKey, - expirationDate: moment().add(1, 'year'), - isDateTime: true, - options: [ - { title: '2015-12-12T11:11:00.000Z' }, - { title: '2015-12-12T13:13:00.000Z' }, - { title: '2016-01-01T11:11:00.000Z' } - ], - timezone - }); + test('view a poll with dates and times', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let timezone = moment.tz.guess(); + let poll = this.server.create('poll', { + encryptionKey, + expirationDate: moment().add(1, 'year'), + isDateTime: true, + options: [ + { title: '2015-12-12T11:11:00.000Z' }, + { title: '2015-12-12T13:13:00.000Z' }, + { title: '2016-01-01T11:11:00.000Z' } + ], + timezone + }); - visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`).then(function() { + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); assert.deepEqual( pageParticipation.options().labels, [ @@ -102,123 +103,122 @@ test('view a poll with dates and times', function(assert) { 'does not show an expiration warning if poll will not expire in next weeks' ); }); -}); -test('view a poll while timezone differs from the one poll got created in and choose local timezone', async function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let timezoneUser = moment.tz.guess(); - let timezonePoll = timezoneUser !== 'America/Caracas' ? 'America/Caracas' : 'Europe/Moscow'; - let poll = server.create('poll', { - encryptionKey, - isDateTime: true, - options: [ - { title: '2015-12-12T11:11:00.000Z' }, - { title: '2016-01-01T11:11:00.000Z' } - ], - timezone: timezonePoll, - users: [ - server.create('user', { - encryptionKey, - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - } - ] - }) - ] + test('view a poll while timezone differs from the one poll got created in and choose local timezone', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let timezoneUser = moment.tz.guess(); + let timezonePoll = timezoneUser !== 'America/Caracas' ? 'America/Caracas' : 'Europe/Moscow'; + let poll = this.server.create('poll', { + encryptionKey, + isDateTime: true, + options: [ + { title: '2015-12-12T11:11:00.000Z' }, + { title: '2016-01-01T11:11:00.000Z' } + ], + timezone: timezonePoll, + users: [ + this.server.create('user', { + encryptionKey, + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + } + ] + }) + ] + }); + + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.ok( + jQuery(find('#modal-choose-timezone-modal')).is(':visible'), + 'user gets asked which timezone should be used' + ); + + await click('#modal-choose-timezone-modal button.use-local-timezone'); + assert.deepEqual( + pageParticipation.options().labels, + [ + moment.tz('2015-12-12T11:11:00.000Z', timezoneUser).locale('en').format('LLLL'), + moment.tz('2016-01-01T11:11:00.000Z', timezoneUser).locale('en').format('LLLL') + ] + ); + assert.notOk( + jQuery(find('#modal-choose-timezone-modal')).is(':visible'), + 'modal is closed' + ); + + await switchTab('evaluation'); + assert.deepEqual( + pageEvaluation.preferedOptions, + [moment.tz('2015-12-12T11:11:00.000Z', timezoneUser).locale('en').format('LLLL')] + ); }); - await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); - assert.ok( - find('#modal-choose-timezone-modal').is(':visible'), - 'user gets asked which timezone should be used' - ); + test('view a poll while timezone differs from the one poll got created in and choose poll timezone', async function(assert) { + let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; + let timezoneUser = moment.tz.guess(); + let timezonePoll = timezoneUser !== 'America/Caracas' ? 'America/Caracas' : 'Europe/Moscow'; + let poll = this.server.create('poll', { + encryptionKey, + isDateTime: true, + options: [ + { title: '2015-12-12T11:11:00.000Z' }, + { title: '2016-01-01T11:11:00.000Z' } + ], + timezone: timezonePoll, + users: [ + this.server.create('user', { + encryptionKey, + selections: [ + { + type: 'yes', + labelTranslation: 'answerTypes.yes.label', + icon: 'glyphicon glyphicon-thumbs-up', + label: 'Yes' + }, + { + type: 'no', + labelTranslation: 'answerTypes.no.label', + icon: 'glyphicon glyphicon-thumbs-down', + label: 'No' + } + ] + }) + ] + }); - await click('#modal-choose-timezone-modal button.use-local-timezone'); - assert.deepEqual( - pageParticipation.options().labels, - [ - moment.tz('2015-12-12T11:11:00.000Z', timezoneUser).locale('en').format('LLLL'), - moment.tz('2016-01-01T11:11:00.000Z', timezoneUser).locale('en').format('LLLL') - ] - ); - assert.notOk( - find('#modal-choose-timezone-modal').is(':visible'), - 'modal is closed' - ); + await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); + assert.ok( + jQuery(find('#modal-choose-timezone-modal')).is(':visible'), + 'user gets asked which timezone should be used' + ); - await switchTab('evaluation'); - assert.deepEqual( - pageEvaluation.preferedOptions, - [moment.tz('2015-12-12T11:11:00.000Z', timezoneUser).locale('en').format('LLLL')] - ); -}); + await click('#modal-choose-timezone-modal button.use-poll-timezone'); + assert.deepEqual( + pageParticipation.options().labels, + [ + moment.tz('2015-12-12T11:11:00.000Z', timezonePoll).locale('en').format('LLLL'), + moment.tz('2016-01-01T11:11:00.000Z', timezonePoll).locale('en').format('LLLL') + ] + ); + assert.notOk( + jQuery(find('#modal-choose-timezone-modal')).is(':visible'), + 'modal is closed' + ); -test('view a poll while timezone differs from the one poll got created in and choose poll timezone', async function(assert) { - let encryptionKey = 'abcdefghijklmnopqrstuvwxyz0123456789'; - let timezoneUser = moment.tz.guess(); - let timezonePoll = timezoneUser !== 'America/Caracas' ? 'America/Caracas' : 'Europe/Moscow'; - let poll = server.create('poll', { - encryptionKey, - isDateTime: true, - options: [ - { title: '2015-12-12T11:11:00.000Z' }, - { title: '2016-01-01T11:11:00.000Z' } - ], - timezone: timezonePoll, - users: [ - server.create('user', { - encryptionKey, - selections: [ - { - type: 'yes', - labelTranslation: 'answerTypes.yes.label', - icon: 'glyphicon glyphicon-thumbs-up', - label: 'Yes' - }, - { - type: 'no', - labelTranslation: 'answerTypes.no.label', - icon: 'glyphicon glyphicon-thumbs-down', - label: 'No' - } - ] - }) - ] + await switchTab('evaluation'); + assert.deepEqual( + pageEvaluation.preferedOptions, + [moment.tz('2015-12-12T11:11:00.000Z', timezonePoll).locale('en').format('LLLL')] + ); }); - - await visit(`/poll/${poll.id}?encryptionKey=${encryptionKey}`); - assert.ok( - find('#modal-choose-timezone-modal').is(':visible'), - 'user gets asked which timezone should be used' - ); - - await click('#modal-choose-timezone-modal button.use-poll-timezone'); - assert.deepEqual( - pageParticipation.options().labels, - [ - moment.tz('2015-12-12T11:11:00.000Z', timezonePoll).locale('en').format('LLLL'), - moment.tz('2016-01-01T11:11:00.000Z', timezonePoll).locale('en').format('LLLL') - ] - ); - - assert.notOk( - find('#modal-choose-timezone-modal').is(':visible'), - 'modal is closed' - ); - - await switchTab('evaluation'); - assert.deepEqual( - pageEvaluation.preferedOptions, - [moment.tz('2015-12-12T11:11:00.000Z', timezonePoll).locale('en').format('LLLL')] - ); }); diff --git a/tests/helpers/.gitkeep b/tests/helpers/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/tests/helpers/destroy-app.js b/tests/helpers/destroy-app.js deleted file mode 100644 index ace61a5..0000000 --- a/tests/helpers/destroy-app.js +++ /dev/null @@ -1,10 +0,0 @@ -import { run } from '@ember/runloop'; - -export default function destroyApp(application) { - // this is required to fix "second Pretender instance" warnings - if (server) { - server.shutdown(); - } - - run(application, 'destroy'); -} diff --git a/tests/helpers/module-for-acceptance.js b/tests/helpers/module-for-acceptance.js deleted file mode 100644 index 3c5bf9b..0000000 --- a/tests/helpers/module-for-acceptance.js +++ /dev/null @@ -1,21 +0,0 @@ -import { module } from 'qunit'; -import { resolve } from 'rsvp'; -import startApp from '../helpers/start-app'; -import destroyApp from '../helpers/destroy-app'; - -export default function(name, options = {}) { - module(name, { - beforeEach(assert) { - this.application = startApp({ assert }); - - if (options.beforeEach) { - return options.beforeEach.apply(this, arguments); - } - }, - - afterEach() { - let afterEach = options.afterEach && options.afterEach.apply(this, arguments); - return resolve(afterEach).then(() => destroyApp(this.application)); - } - }); -} diff --git a/tests/helpers/poll-has-user.js b/tests/helpers/poll-has-user.js new file mode 100644 index 0000000..974d2e7 --- /dev/null +++ b/tests/helpers/poll-has-user.js @@ -0,0 +1,33 @@ +import { isEmpty } from '@ember/utils'; +import { findAll } from '@ember/test-helpers'; + +function pollHasUser(assert, name, selections) { + let elBase = findAll('.user').find((el) => { + return el.querySelector('td:nth-child(1)').textContent.trim() === name; + }); + assert.ok(elBase, `user ${name} exists`); + + if (elBase) { + selections.forEach((selection, index) => { + assert.equal( + elBase.querySelector(`td:nth-child(${index + 2})`).textContent.trim(), + selection.toString(), + `selection ${index} is as expected` + ); + }); + } +} + +function pollHasUsersCount(assert, count, message) { + if (isEmpty(message)) { + message = 'poll has expected count of users'; + } + assert.equal( + findAll('.user').length, + count, + message + ); +} + +export default pollHasUser; +export { pollHasUsersCount }; diff --git a/tests/helpers/poll-has-users.js b/tests/helpers/poll-has-users.js deleted file mode 100644 index d6f5685..0000000 --- a/tests/helpers/poll-has-users.js +++ /dev/null @@ -1,37 +0,0 @@ -import { isEmpty } from '@ember/utils'; -import { registerHelper } from '@ember/test'; - -const helpers = function() { - registerHelper('pollHasUser', function(app, assert, name, selections) { - let elBase; - find('.user').each((index, el) => { - if (find('td:nth-child(1)', el).text().trim() === name) { - elBase = el; - } - }); - assert.ok(elBase, `user ${name} exists`); - - if (elBase) { - selections.forEach((selection, index) => { - assert.equal( - find(`td:nth-child(${index + 2})`, elBase).text().trim(), - selection, - `selection ${index} is as expected` - ); - }); - } - }); - - registerHelper('pollHasUsersCount', function(app, assert, count, message) { - if (isEmpty(message)) { - message = 'poll has expected count of users'; - } - assert.equal( - find('.user').length, - count, - message - ); - }); -}; - -export default helpers(); diff --git a/tests/helpers/poll-participate.js b/tests/helpers/poll-participate.js index 7e0baf4..184df75 100644 --- a/tests/helpers/poll-participate.js +++ b/tests/helpers/poll-participate.js @@ -1,21 +1,21 @@ import { isEmpty } from '@ember/utils'; -import { registerAsyncHelper } from '@ember/test'; +import { findAll, fillIn, click } from '@ember/test-helpers'; -export default registerAsyncHelper('pollParticipate', function(app, name, selections) { +export default async function(name, selections) { if (!isEmpty(name)) { - fillIn('.participation .name input', name); + await fillIn('.participation .name input', name); } - const isFreeText = find('.participation .selections .radio').length ? false : true; - selections.forEach((selection, index) => { + const isFreeText = findAll('.participation .selections .radio').length > 0 ? false : true; + for (let [index, selection] of selections.entries()) { if (!isEmpty(selection)) { if (isFreeText) { - fillIn(`.participation .selections .form-group:nth-child(${index + 1}) input`, selection); + await fillIn(`.participation .selections .form-group:nth-child(${index + 1}) input`, selection); } else { - click(`.participation .selections .form-group:nth-child(${index + 1}) .${selection}.radio input`); + await click(`.participation .selections .form-group:nth-child(${index + 1}) .${selection}.radio input`); } } - }); + } - click('.participation button[type="submit"]'); -}); + await click('.participation button[type="submit"]'); +} diff --git a/tests/helpers/start-app.js b/tests/helpers/start-app.js deleted file mode 100644 index 5544fc9..0000000 --- a/tests/helpers/start-app.js +++ /dev/null @@ -1,27 +0,0 @@ -import Application from '../../app'; -import config from '../../config/environment'; -import { merge } from '@ember/polyfills'; -import { run } from '@ember/runloop'; -import './poll-has-users'; -import './poll-participate'; -import './switch-tab'; -import registerAcceptanceTestHelpers from './201-created/register-acceptance-test-helpers'; -import registerBrowserNavigationButtonTestHelpers from './browser-navigation-buttons'; -import './ember-i18n/test-helpers'; - -export default function startApp(attrs) { - let attributes = merge({}, config.APP); - attributes.autoboot = true; - attributes = merge(attributes, attrs); // use defaults, but you can override; - - return run(() => { - let application = Application.create(attributes); - application.setupForTesting(); - - registerAcceptanceTestHelpers(attrs.assert || window.QUnit.assert); - registerBrowserNavigationButtonTestHelpers(); - - application.injectTestHelpers(); - return application; - }); -} diff --git a/tests/helpers/switch-tab.js b/tests/helpers/switch-tab.js index d4dc17a..fc189da 100644 --- a/tests/helpers/switch-tab.js +++ b/tests/helpers/switch-tab.js @@ -1,5 +1,5 @@ -import { registerAsyncHelper } from '@ember/test'; +import { click } from '@ember/test-helpers'; -export default registerAsyncHelper('switchTab', function(app, tab) { - click(`.nav-tabs .${tab} a`); -}); +export default function(tab) { + return click(`.nav-tabs .${tab} a`); +} diff --git a/tests/integration/components/create-options-dates-test.js b/tests/integration/components/create-options-dates-test.js index 918caf8..5a6bbab 100644 --- a/tests/integration/components/create-options-dates-test.js +++ b/tests/integration/components/create-options-dates-test.js @@ -1,66 +1,68 @@ import EmberObject from '@ember/object'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; import moment from 'moment'; -moduleForComponent('create-options-dates', 'Integration | Component | create options dates', { - integration: true -}); - -test('it renders a ember-cli-bootstrap-datepicker component', function(assert) { - this.set('options', []); - this.render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); - - assert.equal( - this.$('.days .ember-view:has(.datepicker:first-child)').length, 1 - ); -}); - -test('bootstrap-datepicker shows dates in options', function(assert) { - this.set('options', [ - EmberObject.create({ title: '2015-01-01' }), - EmberObject.create({ title: '2015-01-02' }) - ]); - this.render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); - - assert.equal( - this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('getDates')[0].toISOString(), - moment('2015-01-01').toISOString(), - 'date is correct (a)' - ); - assert.equal( - this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('getDates')[1].toISOString(), - moment('2015-01-02').toISOString(), - 'date is correct (b)' - ); -}); - -test('dates set in bootstrap-datepicker are set to options', function(assert) { - this.set('options', []); - this.render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); - - this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('setDates', [ - moment('2015-01-01').toDate(), - moment('2015-01-02').toDate() - ]); - assert.equal( - this.get('options.0.title'), - '2015-01-01', - 'dates are correct (a)' - ); - assert.equal( - this.get('options.1.title'), - '2015-01-02', - 'dates are correct (b)' - ); - - this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('setDates', [ - moment('2016-12-31').toDate(), - moment('2016-01-01').toDate() - ]); - assert.equal( - this.get('options.firstObject.title'), - '2016-01-01', - 'dates are sorted' - ); +module('Integration | Component | create options dates', function(hooks) { + setupRenderingTest(hooks); + + test('it renders a ember-cli-bootstrap-datepicker component', async function(assert) { + this.set('options', []); + await render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); + + assert.equal( + this.$('.days .ember-view:has(.datepicker:first-child)').length, 1 + ); + }); + + test('bootstrap-datepicker shows dates in options', async function(assert) { + this.set('options', [ + EmberObject.create({ title: '2015-01-01' }), + EmberObject.create({ title: '2015-01-02' }) + ]); + await render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); + + assert.equal( + this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('getDates')[0].toISOString(), + moment('2015-01-01').toISOString(), + 'date is correct (a)' + ); + assert.equal( + this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('getDates')[1].toISOString(), + moment('2015-01-02').toISOString(), + 'date is correct (b)' + ); + }); + + test('dates set in bootstrap-datepicker are set to options', async function(assert) { + this.set('options', []); + await render(hbs`{{#bs-form as |form|}}{{create-options-dates options=options form=form}}{{/bs-form}}`); + + this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('setDates', [ + moment('2015-01-01').toDate(), + moment('2015-01-02').toDate() + ]); + assert.equal( + this.get('options.0.title'), + '2015-01-01', + 'dates are correct (a)' + ); + assert.equal( + this.get('options.1.title'), + '2015-01-02', + 'dates are correct (b)' + ); + + this.$('.days .ember-view:has(.datepicker:first-child)').datepicker('setDates', [ + moment('2016-12-31').toDate(), + moment('2016-01-01').toDate() + ]); + assert.equal( + this.get('options.firstObject.title'), + '2016-01-01', + 'dates are sorted' + ); + }); }); diff --git a/tests/integration/components/create-options-datetime-test.js b/tests/integration/components/create-options-datetime-test.js index bb9db09..b15245e 100644 --- a/tests/integration/components/create-options-datetime-test.js +++ b/tests/integration/components/create-options-datetime-test.js @@ -1,196 +1,204 @@ import { alias } from '@ember/object/computed'; import { run } from '@ember/runloop'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { + render, + click, + fillIn, + find, + findAll, + triggerEvent +} from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; import jQuery from 'jquery'; import moment from 'moment'; -moduleForComponent('create-options-datetime', 'Integration | Component | create options datetime', { - integration: true, - beforeEach() { - this.inject.service('store'); - } -}); +module('Integration | Component | create options datetime', function(hooks) { + setupRenderingTest(hooks); -/* - * watch out: - * polyfill adds another input[type="text"] for every input[type="time"] - * if browser doesn't support input[type="time"] - * that ones could be identifed by class 'ws-inputreplace' - */ - -test('it generates inpute field for options iso 8601 date string (without time)', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false, - options: [ - { title: '2015-01-01' } - ] - })); + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - assert.equal( - this.$('.days .form-group input').length, - 1, - 'there is one input field' - ); - assert.equal( - this.$('.days .form-group input').val(), - '', - 'value is an empty string' - ); -}); + /* + * watch out: + * polyfill adds another input[type="text"] for every input[type="time"] + * if browser doesn't support input[type="time"] + * that ones could be identifed by class 'ws-inputreplace' + */ -test('it generates inpute field for options iso 8601 datetime string (with time)', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false, - options: [ - { title: '2015-01-01T11:11:00.000Z' } - ] - })); - }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); + test('it generates inpute field for options iso 8601 date string (without time)', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false, + options: [ + { title: '2015-01-01' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); - assert.equal( - this.$('.days .form-group input').length, - 1, - 'there is one input field' - ); - assert.equal( - this.$('.days .form-group input').val(), - moment('2015-01-01T11:11:00.000Z').format('HH:mm'), - 'it has time in option as value' - ); -}); - -test('it hides repeated labels', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false, - options: [ - { title: moment('2015-01-01T10:11').toISOString() }, - { title: moment('2015-01-01T22:22').toISOString() }, - { title: '2015-02-02' } - ] - })); - }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - - assert.equal( - this.$('.days label').length, - 3, - 'every form-group has a label' - ); - assert.equal( - this.$('.days label:not(.sr-only)').length, - 2, - 'there are two not hidden labels for two different dates' - ); - assert.notOk( - this.$('.days .form-group').eq(0).find('label').hasClass('sr-only'), - 'the first label is shown' - ); - assert.ok( - this.$('.days .form-group').eq(1).find('label').hasClass('sr-only'), - 'the repeated label on second form-group is hidden by sr-only class' - ); - assert.notOk( - this.$('.days .form-group').eq(2).find('label').hasClass('sr-only'), - 'the new label on third form-group is shown' - ); -}); - -test('allows to add another option', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - options: [ - { title: '2015-01-01' }, - { title: '2015-02-02' } - ] - })); - }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - - assert.equal( - this.$('.days .form-group input').length, - 2, - 'there are two input fields before' - ); - this.$('.days .form-group').eq(0).find('.add').click(); - assert.equal( - this.$('.days .form-group input').length, - 3, - 'another input field is added' - ); - assert.equal( - this.$('.days .form-group').eq(1).find('label').text(), - this.$('.days .form-group').eq(0).find('label').text(), - 'new input has correct label' - ); - assert.ok( - this.$('.days .form-group').eq(1).find('label').hasClass('sr-only'), - 'label ofnew input is hidden cause it\'s repeated' - ); -}); - -test('allows to delete an option', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false, - options: [ - { title: moment('2015-01-01T11:11').toISOString() }, - { title: moment('2015-01-01T22:22').toISOString() } - ] - })); - }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - - assert.equal( - this.$('.days input').length, - 2, - 'there are two input fields before' - ); - assert.ok( - this.$('.delete').get().every((el) => { - return el.disabled === false; - }), - 'options are deleteable' - ); - this.$('.days .form-group').eq(0).find('.delete').click(); - run(() => { assert.equal( - this.$('.days .form-group input').length, + findAll('.days .form-group input').length, + 1, + 'there is one input field' + ); + assert.equal( + find('.days .form-group input').value, + '', + 'value is an empty string' + ); + }); + + test('it generates inpute field for options iso 8601 datetime string (with time)', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false, + options: [ + { title: '2015-01-01T11:11:00.000Z' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + + assert.equal( + findAll('.days .form-group input').length, + 1, + 'there is one input field' + ); + assert.equal( + find('.days .form-group input').value, + moment('2015-01-01T11:11:00.000Z').format('HH:mm'), + 'it has time in option as value' + ); + }); + + test('it hides repeated labels', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false, + options: [ + { title: moment('2015-01-01T10:11').toISOString() }, + { title: moment('2015-01-01T22:22').toISOString() }, + { title: '2015-02-02' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + + assert.equal( + findAll('.days label').length, + 3, + 'every form-group has a label' + ); + assert.equal( + findAll('.days label:not(.sr-only)').length, + 2, + 'there are two not hidden labels for two different dates' + ); + assert.notOk( + this.$('.days .form-group').eq(0).find('label').hasClass('sr-only'), + 'the first label is shown' + ); + assert.ok( + this.$('.days .form-group').eq(1).find('label').hasClass('sr-only'), + 'the repeated label on second form-group is hidden by sr-only class' + ); + assert.notOk( + this.$('.days .form-group').eq(2).find('label').hasClass('sr-only'), + 'the new label on third form-group is shown' + ); + }); + + test('allows to add another option', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + options: [ + { title: '2015-01-01' }, + { title: '2015-02-02' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + + assert.equal( + findAll('.days .form-group input').length, + 2, + 'there are two input fields before' + ); + + await click(findAll('.days .form-group')[0].querySelector('.add')); + assert.equal( + findAll('.days .form-group input').length, + 3, + 'another input field is added' + ); + assert.equal( + this.$('.days .form-group').eq(1).find('label').text(), + this.$('.days .form-group').eq(0).find('label').text(), + 'new input has correct label' + ); + assert.ok( + this.$('.days .form-group').eq(1).find('label').hasClass('sr-only'), + 'label ofnew input is hidden cause it\'s repeated' + ); + }); + + test('allows to delete an option', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false, + options: [ + { title: moment('2015-01-01T11:11').toISOString() }, + { title: moment('2015-01-01T22:22').toISOString() } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + + assert.equal( + findAll('.days input').length, + 2, + 'there are two input fields before' + ); + assert.ok( + findAll('.delete').every((el) => el.disabled === false), + 'options are deleteable' + ); + + await click(findAll('.days .form-group')[0].querySelector('.delete')); + assert.equal( + findAll('.days .form-group input').length, 1, 'one input field is removed after deletion' ); assert.equal( - this.$('.days .form-group input').val(), + find('.days .form-group input').value, '22:22', 'correct input field is deleted' ); @@ -205,150 +213,141 @@ test('allows to delete an option', function(assert) { 'correct option is deleted' ); }); -}); -test('adopt times of first day - simple', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - options: [ - { title: moment().hour(10).minute(0).toISOString() }, - { title: '2015-02-02' }, - { title: '2015-03-03' } - ] - })); + test('adopt times of first day - simple', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + options: [ + { title: moment().hour(10).minute(0).toISOString() }, + { title: '2015-02-02' }, + { title: '2015-03-03' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + await click('button.adopt-times-of-first-day'); + assert.equal( + findAll('.days .form-group')[0].querySelector('input').value, + '10:00', + 'time was not changed for first day' + ); + assert.equal( + findAll('.days .form-group')[1].querySelector('input').value, + '10:00', + 'time was adopted for second day' + ); + assert.equal( + findAll('.days .form-group')[2].querySelector('input').value, + '10:00', + 'time was adopted for third day' + ); }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - run(() => { - this.$('button.adopt-times-of-first-day').click(); - }); - assert.equal( - this.$('.days .form-group').eq(0).find('input').val(), - '10:00', - 'time was not changed for first day' - ); - assert.equal( - this.$('.days .form-group').eq(1).find('input').val(), - '10:00', - 'time was adopted for second day' - ); - assert.equal( - this.$('.days .form-group').eq(2).find('input').val(), - '10:00', - 'time was adopted for third day' - ); -}); -test('adopt times of first day - more times on first day than on others', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - options: [ - { title: moment().hour(10).minute(0).toISOString() }, - { title: moment().hour(22).minute(0).toISOString() }, - { title: '2015-02-02' }, - { title: '2015-03-03' } - ] - })); + test('adopt times of first day - more times on first day than on others', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + options: [ + { title: moment().hour(10).minute(0).toISOString() }, + { title: moment().hour(22).minute(0).toISOString() }, + { title: '2015-02-02' }, + { title: '2015-03-03' } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + await click('button.adopt-times-of-first-day'); + assert.deepEqual( + this.$('.days .form-group input').map((i, el) => jQuery(el).val()).toArray(), + ['10:00', '22:00', '10:00', '22:00', '10:00', '22:00'], + 'times were adopted correctly' + ); }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - run(() => { - this.$('button.adopt-times-of-first-day').click(); - }); - assert.deepEqual( - this.$('.days .form-group input').map((i, el) => jQuery(el).val()).toArray(), - ['10:00', '22:00', '10:00', '22:00', '10:00', '22:00'], - 'times were adopted correctly' - ); -}); -test('adopt times of first day - excess times on other days got deleted', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false, - options: [ - { title: moment().hour(10).minute(0).toISOString() }, - { title: moment().add(1, 'day').hour(10).minute(0).toISOString() }, - { title: moment().add(1, 'day').hour(22).minute(0).toISOString() } - ] - })); + test('adopt times of first day - excess times on other days got deleted', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false, + options: [ + { title: moment().hour(10).minute(0).toISOString() }, + { title: moment().add(1, 'day').hour(10).minute(0).toISOString() }, + { title: moment().add(1, 'day').hour(22).minute(0).toISOString() } + ] + })); + }); + await render(hbs`{{create-options-datetime dates=poll.options}}`); + await click('button.adopt-times-of-first-day'); + assert.equal( + findAll('.days .form-group').length, + 2, + 'one excess time input got deleted' + ); + assert.deepEqual( + this.$('.days .form-group input').map((i, el) => jQuery(el).val()).toArray(), + ['10:00', '10:00'], + 'additional time on secondary day got deleted' + ); }); - this.render(hbs`{{create-options-datetime dates=poll.options}}`); - run(() => { - this.$('button.adopt-times-of-first-day').click(); - }); - assert.equal( - this.$('.days .form-group').length, - 2, - 'one excess time input got deleted' - ); - assert.deepEqual( - this.$('.days .form-group input').map((i, el) => jQuery(el).val()).toArray(), - ['10:00', '10:00'], - 'additional time on secondary day got deleted' - ); -}); -test('validation', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - run(() => { - this.set('poll', this.store.createRecord('poll', { - isFindADate: true, - isMakeAPoll: false - })); - this.set('options', alias('poll.options')); - this.get('options').pushObjects([ - { title: '2015-01-01' }, - { title: '2015-02-02' } - ]); + test('validation', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + run(() => { + this.set('poll', this.store.createRecord('poll', { + isFindADate: true, + isMakeAPoll: false + })); + this.set('options', alias('poll.options')); + this.get('options').pushObjects([ + { title: '2015-01-01' }, + { title: '2015-02-02' } + ]); + }); + await render(hbs`{{create-options-datetime dates=options}}`); + assert.ok( + findAll('.has-error').length === 0, + 'does not show a validation error before user interaction' + ); + + await fillIn(findAll('.form-group')[1].querySelector('input'), '10:'); + assert.ok( + findAll('.form-group')[1].classList.contains('has-error') || + // browsers with input type time support prevent non time input + findAll('.form-group')[1].querySelector('input').value === '', + 'shows error after invalid input or prevents invalid input' + ); + + // simulate unique violation + await click(findAll('.form-group')[0].querySelector('.add')); + await fillIn(findAll('.form-group')[0].querySelector('input'), '10:00'); + await fillIn(findAll('.form-group')[1].querySelector('input'), '10:00'); + await fillIn(findAll('.form-group')[2].querySelector('input'), '10:00'); + await triggerEvent('form', 'submit'); + assert.ok( + findAll('.form-group')[0].classList.contains('has-success'), + 'first time shows validation success' + ); + assert.ok( + findAll('.form-group')[1].classList.contains('has-error'), + 'same time for same day shows validation error' + ); + assert.ok( + findAll('.form-group')[2].classList.contains('has-success'), + 'same time for different day shows validation success' + ); }); - this.render(hbs`{{create-options-datetime dates=options}}`); - assert.ok( - this.$('.has-error').length === 0, - 'does not show a validation error before user interaction' - ); - this.$('.form-group').eq(1).find('input').trigger('focusout'); - assert.ok( - this.$('.form-group').eq(1).hasClass('has-success'), - 'does show validation errors after user interaction' - ); - this.$('.form-group').eq(1).find('input').val('10:').trigger('change'); - assert.ok( - this.$('.form-group').eq(1).hasClass('has-error') || - // browsers with input type time support prevent non time input - this.$('.form-group').eq(1).find('input').val() === '', - 'shows error after invalid input or prevents invalid input' - ); - // simulate unique violation - this.$('.form-group').eq(0).find('.add').click(); - this.$('.form-group input').eq(0).val('10:00').trigger('change'); - this.$('.form-group input').eq(1).val('10:00').trigger('change'); - this.$('.form-group input').eq(2).val('10:00').trigger('change'); - this.$('form').submit(); - assert.ok( - this.$('.form-group').eq(0).hasClass('has-success'), - 'first time shows validation success' - ); - assert.ok( - this.$('.form-group').eq(1).hasClass('has-error'), - 'same time for same day shows validation error' - ); - assert.ok( - this.$('.form-group').eq(2).hasClass('has-success'), - 'same time for different day shows validation success' - ); }); diff --git a/tests/integration/components/create-options-test.js b/tests/integration/components/create-options-test.js index 58fdfa5..db7c20e 100644 --- a/tests/integration/components/create-options-test.js +++ b/tests/integration/components/create-options-test.js @@ -1,187 +1,197 @@ import { run } from '@ember/runloop'; -import { moduleForComponent, test } from 'ember-qunit'; -import { blur, fillIn, findAll, focus } from 'ember-native-dom-helpers'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render, findAll, blur, fillIn, focus } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; import hasComponent from 'croodle/tests/helpers/201-created/raw/has-component'; -moduleForComponent('create-options', 'Integration | Component | create options', { - integration: true, - beforeEach() { - this.inject.service('store'); - } -}); +module('Integration | Component | create options', function(hooks) { + setupRenderingTest(hooks); -test('renders component', function(assert) { - this.set('options', []); - this.set('isDateTime', false); - this.set('isFindADate', true); - this.set('isMakeAPoll', false); - this.render(hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}`); - - assert.ok( - hasComponent(this.container, assert, 'create-options-dates').ok - ); - assert.notOk( - hasComponent(this.container, assert, 'create-options-text').ok - ); - - this.set('isDateTime', false); - this.set('isFindADate', false); - this.set('isMakeAPoll', true); - - assert.notOk( - hasComponent(this.container, assert, 'create-options-dates').ok - ); - assert.ok( - hasComponent(this.container, assert, 'create-options-text').ok - ); -}); - -test('shows validation errors if options are not unique (makeAPoll)', async function(assert) { - assert.expect(5); - - this.set('isDateTime', false); - this.set('isFindADate', false); - this.set('isMakeAPoll', true); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: this.get('isFindADate'), - isDateTime: this.get('isDateTime'), - isMakeAPoll: this.get('isMakeAPoll') - }); + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); }); - this.set('options', poll.get('options')); - this.render(hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}`); + test('renders component', async function(assert) { + this.set('options', []); + this.set('isDateTime', false); + this.set('isFindADate', true); + this.set('isMakeAPoll', false); + await render( + hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}` + ); - assert.ok( - this.$('input').length === 2, - 'assumptions are correct' - ); + assert.ok( + hasComponent(this.owner, assert, 'create-options-dates').ok + ); + assert.notOk( + hasComponent(this.owner, assert, 'create-options-text').ok + ); - await fillIn(findAll('input')[0], 'foo'); - await blur(findAll('input')[0]); - await fillIn(findAll('input')[1], 'foo'); - await blur(findAll('input')[1]); - assert.ok( - this.$('.form-group').eq(1).hasClass('has-error'), - 'second input field has validation error' - ); + this.set('isDateTime', false); + this.set('isFindADate', false); + this.set('isMakeAPoll', true); - assert.ok( - this.$('.form-group').eq(1).find('.help-block').length === 1, - 'validation error is shown' - ); - - await fillIn(findAll('input')[0], 'bar'); - await blur(findAll('input')[0]); - assert.ok( - this.$('.form-group .help-block').length === 0, - 'there is no validation error anymore after a unique value is entered' - ); - - assert.ok( - this.$('.form-group.has-error').length === 0, - 'has-error classes are removed' - ); -}); - -test('shows validation errors if option is empty (makeAPoll)', async function(assert) { - this.set('isDateTime', false); - this.set('isFindADate', false); - this.set('isMakeAPoll', true); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: this.get('isFindADate'), - isDateTime: this.get('isDateTime'), - isMakeAPoll: this.get('isMakeAPoll') - }); + assert.notOk( + hasComponent(this.owner, assert, 'create-options-dates').ok + ); + assert.ok( + hasComponent(this.owner, assert, 'create-options-text').ok + ); }); - this.set('options', poll.get('options')); - this.render(hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}`); + test('shows validation errors if options are not unique (makeAPoll)', async function(assert) { + assert.expect(5); - assert.equal( - this.$('.form-group.has-error').length, 0 - ); + this.set('isDateTime', false); + this.set('isFindADate', false); + this.set('isMakeAPoll', true); - await focus(findAll('input')[0]); - await blur(findAll('input')[0]); - await focus(findAll('input')[1]); - await blur(findAll('input')[1]); - assert.equal( - this.$('.form-group.has-error').length, 2 - ); - - await fillIn(findAll('input')[0], 'foo'); - await blur(findAll('input')[0]); - assert.equal( - this.$('.form-group.has-error').length, 1 - ); - - await fillIn(findAll('input')[1], 'bar'); - await blur(findAll('input')[1]); - assert.equal( - this.$('.form-group.has-error').length, 0 - ); -}); - -test('label reflects validation state of all inputs (makeAPoll)', async function(assert) { - this.set('isDateTime', false); - this.set('isFindADate', false); - this.set('isMakeAPoll', true); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: this.get('isFindADate'), - isDateTime: this.get('isDateTime'), - isMakeAPoll: this.get('isMakeAPoll') + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: this.get('isFindADate'), + isDateTime: this.get('isDateTime'), + isMakeAPoll: this.get('isMakeAPoll') + }); }); + this.set('options', poll.get('options')); + + await render( + hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}` + ); + + assert.ok( + findAll('input').length === 2, + 'assumptions are correct' + ); + + await fillIn(findAll('input')[0], 'foo'); + await blur(findAll('input')[0]); + await fillIn(findAll('input')[1], 'foo'); + await blur(findAll('input')[1]); + assert.ok( + this.$('.form-group').eq(1).hasClass('has-error'), + 'second input field has validation error' + ); + + assert.ok( + this.$('.form-group').eq(1).find('.help-block').length === 1, + 'validation error is shown' + ); + + await fillIn(findAll('input')[0], 'bar'); + await blur(findAll('input')[0]); + assert.ok( + findAll('.form-group .help-block').length === 0, + 'there is no validation error anymore after a unique value is entered' + ); + + assert.ok( + findAll('.form-group.has-error').length === 0, + 'has-error classes are removed' + ); }); - this.set('options', poll.get('options')); - this.render(hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}`); + test('shows validation errors if option is empty (makeAPoll)', async function(assert) { + this.set('isDateTime', false); + this.set('isFindADate', false); + this.set('isMakeAPoll', true); - assert.ok( - this.$('form').children().hasClass('label-has-no-validation'), - 'does not show validation state if there wasn\'t any user interaction yet' - ); + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: this.get('isFindADate'), + isDateTime: this.get('isDateTime'), + isMakeAPoll: this.get('isMakeAPoll') + }); + }); + this.set('options', poll.get('options')); - await focus(findAll('input')[0]); - await blur(findAll('input')[0]); - assert.ok( - this.$('form').children().hasClass('label-has-error'), - 'shows as having error if atleast on field has an error' - ); + await render( + hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}` + ); - await fillIn(findAll('input')[0], 'foo'); - await blur(findAll('input')[0]); - assert.ok( - this.$('form').children().hasClass('label-has-no-validation'), - 'does not show validation state if no field has error but not all fields are showing error yet' - ); + assert.equal( + findAll('.form-group.has-error').length, 0 + ); - await fillIn(findAll('input')[1], 'bar'); - await blur(findAll('input')[1]); - assert.ok( - this.$('form').children().hasClass('label-has-success'), - 'shows as having success if all fields are showing success' - ); + await focus(findAll('input')[0]); + await blur(findAll('input')[0]); + await focus(findAll('input')[1]); + await blur(findAll('input')[1]); + assert.equal( + findAll('.form-group.has-error').length, 2 + ); + + await fillIn(findAll('input')[0], 'foo'); + await blur(findAll('input')[0]); + assert.equal( + findAll('.form-group.has-error').length, 1 + ); + + await fillIn(findAll('input')[1], 'bar'); + await blur(findAll('input')[1]); + assert.equal( + findAll('.form-group.has-error').length, 0 + ); + }); + + test('label reflects validation state of all inputs (makeAPoll)', async function(assert) { + this.set('isDateTime', false); + this.set('isFindADate', false); + this.set('isMakeAPoll', true); + + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: this.get('isFindADate'), + isDateTime: this.get('isDateTime'), + isMakeAPoll: this.get('isMakeAPoll') + }); + }); + this.set('options', poll.get('options')); + + await render( + hbs`{{create-options options=options isDateTime=isDateTime isFindADate=isFindADate isMakeAPoll=isMakeAPoll}}` + ); + + assert.ok( + this.$('form').children().hasClass('label-has-no-validation'), + 'does not show validation state if there wasn\'t any user interaction yet' + ); + + await focus(findAll('input')[0]); + await blur(findAll('input')[0]); + assert.ok( + this.$('form').children().hasClass('label-has-error'), + 'shows as having error if atleast on field has an error' + ); + + await fillIn(findAll('input')[0], 'foo'); + await blur(findAll('input')[0]); + assert.ok( + this.$('form').children().hasClass('label-has-no-validation'), + 'does not show validation state if no field has error but not all fields are showing error yet' + ); + + await fillIn(findAll('input')[1], 'bar'); + await blur(findAll('input')[1]); + assert.ok( + this.$('form').children().hasClass('label-has-success'), + 'shows as having success if all fields are showing success' + ); + }); }); diff --git a/tests/integration/components/create-options-text-test.js b/tests/integration/components/create-options-text-test.js index e0a63f8..8dff9f6 100644 --- a/tests/integration/components/create-options-text-test.js +++ b/tests/integration/components/create-options-text-test.js @@ -1,173 +1,171 @@ import { run } from '@ember/runloop'; import EmberObject from '@ember/object'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render, findAll, click } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; import jQuery from 'jquery'; -moduleForComponent('create-options-text', 'Integration | Component | create options text', { - integration: true, - beforeEach() { - this.inject.service('store'); - } -}); +module('Integration | Component | create options text', function(hooks) { + setupRenderingTest(hooks); -test('it generates at least two input fields', function(assert) { - this.set('options', []); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); + }); - assert.equal(this.$('input').length, 2); -}); + test('it generates at least two input fields', async function(assert) { + this.set('options', []); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); -test('generates input fields according options', function(assert) { - this.set('options', [ - EmberObject.create({ title: 'foo' }), - EmberObject.create({ title: 'bar' }), - EmberObject.create({ title: 'baz' }) - ]); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + assert.equal(findAll('input').length, 2); + }); - assert.equal( - this.$('input').length, - 3, - 'correct amount of input fields' - ); - assert.deepEqual( - this.$('input').map(function() { - return jQuery(this).val(); - }).get(), - ['foo', 'bar', 'baz'], - 'input fields have correct values and order' - ); -}); - -test('observes changes to options', function(assert) { - this.set('options', [ - EmberObject.create({ title: 'foo' }), - EmberObject.create({ title: 'bar' }) - ]); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); - - assert.equal( - this.$('input').length, - 2, - 'has correct amount of input fields before change' - ); - - run(() => { - this.get('options').pushObject( + test('generates input fields according options', async function(assert) { + this.set('options', [ + EmberObject.create({ title: 'foo' }), + EmberObject.create({ title: 'bar' }), EmberObject.create({ title: 'baz' }) - ); - }); + ]); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); - assert.equal( - this.$('input').length, - 3, - 'has correct amount of input fields after change' - ); - assert.equal( - this.$('input').eq(2).val(), - 'baz', - 'input field was added with correct value' - ); -}); - -test('changes to value updates option', function(assert) { - this.set('options', [ - EmberObject.create({ title: 'foo' }), - EmberObject.create({ title: 'bar' }) - ]); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); - - this.$('input').eq(0).val('baz').trigger('change'); - assert.equal( - this.get('options')[0].get('title'), - 'baz', - 'option was updated' - ); -}); - -test('allows to add another option', function(assert) { - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: this.get('isFindADate'), - isDateTime: this.get('isDateTime'), - isMakeAPoll: this.get('isMakeAPoll'), - options: [ - { title: 'foo' }, - { title: 'bar' } - ] - }); - }); - this.set('options', poll.get('options')); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); - - assert.equal( - this.$('.form-group input').length, - 2, - 'there are two input fields before' - ); - - run(() => { - this.$('.form-group .add').eq(0).click(); - }); - assert.equal( - this.$('.form-group input').length, - 3, - 'another input field is added' - ); - assert.deepEqual( - this.$('input').map(function() { - return jQuery(this).val(); - }).get(), - ['foo', '', 'bar'], - 'it is added at correct position' - ); - - run(() => { - this.$('.form-group input').eq(1).val('baz').trigger('change'); - }); - assert.equal( - this.get('options').objectAt(1).get('title'), - 'baz', - 'options are observed for new input field' - ); -}); - -test('allows to delete an option', function(assert) { - this.set('options', [ - EmberObject.create({ title: 'foo' }), - EmberObject.create({ title: 'bar' }), - EmberObject.create({ title: 'baz' }) - ]); - this.render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); - - assert.equal( - this.$('.form-group input').length, - 3, - 'there are three input fields before' - ); - assert.ok( - this.$('.delete').get().every((el) => { - return el.disabled === false; - }), - 'options are deleteable' - ); - this.$('.form-group .delete').eq(1).click(); - run(() => { assert.equal( - this.$('.form-group input').length, - 2, - 'one input field is deleted' + findAll('input').length, + 3, + 'correct amount of input fields' ); assert.deepEqual( this.$('input').map(function() { return jQuery(this).val(); }).get(), + ['foo', 'bar', 'baz'], + 'input fields have correct values and order' + ); + }); + + test('observes changes to options', async function(assert) { + this.set('options', [ + EmberObject.create({ title: 'foo' }), + EmberObject.create({ title: 'bar' }) + ]); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + + assert.equal( + findAll('input').length, + 2, + 'has correct amount of input fields before change' + ); + + run(() => { + this.get('options').pushObject( + EmberObject.create({ title: 'baz' }) + ); + }); + + assert.equal( + findAll('input').length, + 3, + 'has correct amount of input fields after change' + ); + assert.equal( + this.$('input').eq(2).val(), + 'baz', + 'input field was added with correct value' + ); + }); + + test('changes to value updates option', async function(assert) { + this.set('options', [ + EmberObject.create({ title: 'foo' }), + EmberObject.create({ title: 'bar' }) + ]); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + + this.$('input').eq(0).val('baz').trigger('change'); + assert.equal( + this.get('options')[0].get('title'), + 'baz', + 'option was updated' + ); + }); + + test('allows to add another option', async function(assert) { + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: this.get('isFindADate'), + isDateTime: this.get('isDateTime'), + isMakeAPoll: this.get('isMakeAPoll'), + options: [ + { title: 'foo' }, + { title: 'bar' } + ] + }); + }); + this.set('options', poll.get('options')); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + + assert.equal( + findAll('.form-group input').length, + 2, + 'there are two input fields before' + ); + + run(() => { + this.$('.form-group .add').eq(0).click(); + }); + assert.equal( + findAll('.form-group input').length, + 3, + 'another input field is added' + ); + assert.deepEqual( + this.$('input').map(function() { + return jQuery(this).val(); + }).get(), + ['foo', '', 'bar'], + 'it is added at correct position' + ); + + run(() => { + this.$('.form-group input').eq(1).val('baz').trigger('change'); + }); + assert.equal( + this.get('options').objectAt(1).get('title'), + 'baz', + 'options are observed for new input field' + ); + }); + + test('allows to delete an option', async function(assert) { + this.set('options', [ + EmberObject.create({ title: 'foo' }), + EmberObject.create({ title: 'bar' }), + EmberObject.create({ title: 'baz' }) + ]); + await render(hbs`{{#bs-form as |form|}}{{create-options-text options=options form=form}}{{/bs-form}}`); + + assert.equal( + findAll('.form-group input').length, + 3, + 'there are three input fields before' + ); + assert.ok( + findAll('.delete').every((el) => el.disabled === false), + 'options are deleteable' + ); + + await click(findAll('.form-group .delete')[1]); + assert.equal( + findAll('.form-group input').length, + 2, + 'one input field is deleted' + ); + assert.deepEqual( + findAll('input').toArray().map((el) => el.value), ['foo', 'baz'], 'correct input field is deleted' ); diff --git a/tests/integration/components/form-navigation-buttons-test.js b/tests/integration/components/form-navigation-buttons-test.js index ac29f08..3d97721 100644 --- a/tests/integration/components/form-navigation-buttons-test.js +++ b/tests/integration/components/form-navigation-buttons-test.js @@ -1,23 +1,25 @@ -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render, findAll, find } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; -moduleForComponent('form-navigation-buttons', 'Integration | Component | form navigation buttons', { - integration: true -}); +module('Integration | Component | form navigation buttons', function(hooks) { + setupRenderingTest(hooks); -test('it renders two buttons as default', function(assert) { - this.render(hbs`{{form-navigation-buttons}}`); - assert.equal(this.$('button').length, 2); -}); + test('it renders two buttons as default', async function(assert) { + await render(hbs`{{form-navigation-buttons}}`); + assert.equal(findAll('button').length, 2); + }); -test('buttons could be disabled', function(assert) { - this.render(hbs`{{form-navigation-buttons disableNextButton=true disablePrevButton=true}}`); - assert.equal(this.$('button.next').prop('disabled'), true, 'next button is disabled'); - assert.equal(this.$('button.prev').prop('disabled'), true, 'prev button is disabled'); -}); + test('buttons could be disabled', async function(assert) { + await render(hbs`{{form-navigation-buttons disableNextButton=true disablePrevButton=true}}`); + assert.equal(find('button.next').disabled, true, 'next button is disabled'); + assert.equal(find('button.prev').disabled, true, 'prev button is disabled'); + }); -test('could prevent rendering of prev button', function(assert) { - this.render(hbs`{{form-navigation-buttons renderPrevButton=false}}`); - assert.ok(this.$('button.prev').length === 0, 'prev button is not rendered'); - assert.ok(this.$('button.next').length === 1, 'next button is rendered'); + test('could prevent rendering of prev button', async function(assert) { + await render(hbs`{{form-navigation-buttons renderPrevButton=false}}`); + assert.ok(findAll('button.prev').length === 0, 'prev button is not rendered'); + assert.ok(findAll('button.next').length === 1, 'next button is rendered'); + }); }); diff --git a/tests/integration/components/poll-evaluation-chart-test.js b/tests/integration/components/poll-evaluation-chart-test.js index 2704c58..abf4de3 100644 --- a/tests/integration/components/poll-evaluation-chart-test.js +++ b/tests/integration/components/poll-evaluation-chart-test.js @@ -1,75 +1,78 @@ import EmberObject from '@ember/object'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; import moment from 'moment'; -moduleForComponent('poll-evaluation-chart', 'Integration | Component | poll evaluation chart', { - integration: true, - beforeEach() { - moment.locale('en'); - } -}); +module('Integration | Component | poll evaluation chart', function(hooks) { + setupRenderingTest(hooks); -test('it renders', function(assert) { - this.set('options', [ - EmberObject.create({ - formatted: 'Thursday, January 1, 2015', - title: moment('2015-01-01'), - hasTime: false - }), - EmberObject.create({ - formatted: 'Monday, February 2, 2015', - title: moment('2015-02-02'), - hasTime: false - }), - EmberObject.create({ - formatted: 'Tuesday, March 3, 2015 1:00 AM', - title: moment('2015-03-03T01:00'), - hasTime: true - }), - EmberObject.create({ - formatted: 'Tuesday, March 3, 2015 11:00 AM', - title: moment('2015-03-03T11:00'), - hasTime: true - }) - ]); - this.set('answerType', 'YesNoMaybe'); - this.set('users', [ - EmberObject.create({ - id: 1, - selections: [ - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' - }) - ] - }), - EmberObject.create({ - id: 2, - selections: [ - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' - }), - EmberObject.create({ - type: 'no' - }) - ] - }) - ]); - this.render(hbs`{{poll-evaluation-chart options=options answerType=answerType users=users}}`); - assert.ok(this.$('canvas'), 'it renders a canvas element'); + hooks.beforeEach(function() { + moment.locale('en'); + }); + + test('it renders', async function(assert) { + this.set('options', [ + EmberObject.create({ + formatted: 'Thursday, January 1, 2015', + title: moment('2015-01-01'), + hasTime: false + }), + EmberObject.create({ + formatted: 'Monday, February 2, 2015', + title: moment('2015-02-02'), + hasTime: false + }), + EmberObject.create({ + formatted: 'Tuesday, March 3, 2015 1:00 AM', + title: moment('2015-03-03T01:00'), + hasTime: true + }), + EmberObject.create({ + formatted: 'Tuesday, March 3, 2015 11:00 AM', + title: moment('2015-03-03T11:00'), + hasTime: true + }) + ]); + this.set('answerType', 'YesNoMaybe'); + this.set('users', [ + EmberObject.create({ + id: 1, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }) + ] + }), + EmberObject.create({ + id: 2, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }), + EmberObject.create({ + type: 'no' + }) + ] + }) + ]); + await render(hbs`{{poll-evaluation-chart options=options answerType=answerType users=users}}`); + assert.ok(this.$('canvas'), 'it renders a canvas element'); + }); }); diff --git a/tests/integration/mirage-test.js b/tests/integration/mirage-test.js index 47be606..1f1c98d 100644 --- a/tests/integration/mirage-test.js +++ b/tests/integration/mirage-test.js @@ -3,31 +3,32 @@ import { module, test } from 'qunit'; import { startMirage } from 'croodle/initializers/ember-cli-mirage'; import sjcl from 'sjcl'; -module('Integration | Mirage api mocking', { - beforeEach() { +module('Integration | Mirage api mocking', function(hooks) { + hooks.beforeEach(function() { this.server = startMirage(); - }, - afterEach() { + }); + + hooks.afterEach(function() { this.server.shutdown(); - } -}); - -test('poll factory | encrypts properties', function(assert) { - let encryptionKey = 'abc'; - let poll = this.server.create('poll', { - description: 'bar', - encryptionKey, - title: 'foo' }); - assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(poll, 'title'))), 'foo'); - assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(poll, 'description'))), 'bar'); -}); -test('user factory | encrypts properties', function(assert) { - let encryptionKey = 'abc'; - let user = this.server.create('user', { - encryptionKey, - name: 'foo' + test('poll factory | encrypts properties', function(assert) { + let encryptionKey = 'abc'; + let poll = this.server.create('poll', { + description: 'bar', + encryptionKey, + title: 'foo' + }); + assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(poll, 'title'))), 'foo'); + assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(poll, 'description'))), 'bar'); + }); + + test('user factory | encrypts properties', function(assert) { + let encryptionKey = 'abc'; + let user = this.server.create('user', { + encryptionKey, + name: 'foo' + }); + assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(user, 'name'))), 'foo'); }); - assert.equal(JSON.parse(sjcl.decrypt(encryptionKey, get(user, 'name'))), 'foo'); }); diff --git a/tests/integration/translations-test.js b/tests/integration/translations-test.js index 36f7469..3e79bfe 100644 --- a/tests/integration/translations-test.js +++ b/tests/integration/translations-test.js @@ -1,76 +1,77 @@ import { getOwner } from '@ember/application'; -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import config from 'croodle/config/environment'; import LocaleHelper from 'ember-i18n/utils/locale'; import localesMeta from 'croodle/locales/meta'; -moduleFor('service:i18n', 'Integration | translations', { - integration: true -}); +module('Integration | translations', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('configuration is correct', function(assert) { - const i18n = this.subject(); - const locales = i18n.get('locales'); - const { defaultLocale } = config.i18n; + // Replace this with your real tests. + test('configuration is correct', function(assert) { + const i18n = this.owner.lookup('service:i18n'); + const locales = i18n.get('locales'); + const { defaultLocale } = config.i18n; - assert.ok(defaultLocale, 'default locale is set'); - assert.ok(locales, 'there are locales'); - assert.ok(locales.indexOf(defaultLocale) !== -1, 'default locale is part of locales'); -}); - -test('all locales have same amount of translation strings as default locale', function(assert) { - const i18n = this.subject(); - const locales = i18n.get('locales'); - const { defaultLocale } = config.i18n; - const { translations: defaultTranslations } = new LocaleHelper(defaultLocale, getOwner(i18n)); - - assert.expect((locales.length - 1) * 2); - - locales.map((locale) => { - if (locale === defaultLocale) { - return; - } - const { translations } = new LocaleHelper(locale, getOwner(i18n)); - assert.ok(translations, `could retrive locale ${locale}`); - assert.equal( - Object.keys(translations).length, - Object.keys(defaultTranslations).length, - `correct amount of translations for locale ${locale}` - ); + assert.ok(defaultLocale, 'default locale is set'); + assert.ok(locales, 'there are locales'); + assert.ok(locales.indexOf(defaultLocale) !== -1, 'default locale is part of locales'); }); -}); -test('all locales have same translation strings as default locale', function(assert) { - const i18n = this.subject(); - const locales = i18n.get('locales'); - const { defaultLocale } = config.i18n; - const { translations: defaultTranslations } = new LocaleHelper(defaultLocale, getOwner(i18n)); + test('all locales have same amount of translation strings as default locale', function(assert) { + const i18n = this.owner.lookup('service:i18n'); + const locales = i18n.get('locales'); + const { defaultLocale } = config.i18n; + const { translations: defaultTranslations } = new LocaleHelper(defaultLocale, this.owner); - assert.expect( - // count of non default locales * translation strings of default locale - (locales.length - 1) * Object.keys(defaultTranslations).length - ); + assert.expect((locales.length - 1) * 2); - Object.keys(defaultTranslations).map((translationString) => { locales.map((locale) => { if (locale === defaultLocale) { return; } - - i18n.set('locale', locale); - assert.ok( - i18n.exists(translationString), - `translation for ${translationString} exists in locale ${locale}` + const { translations } = new LocaleHelper(locale, getOwner(i18n)); + assert.ok(translations, `could retrive locale ${locale}`); + assert.equal( + Object.keys(translations).length, + Object.keys(defaultTranslations).length, + `correct amount of translations for locale ${locale}` ); }); }); -}); -test('all locales have an entry in locales/meta', function(assert) { - const i18n = this.subject(); - assert.deepEqual( - i18n.get('locales'), - Object.keys(localesMeta) - ); + test('all locales have same translation strings as default locale', function(assert) { + const i18n = this.owner.lookup('service:i18n'); + const locales = i18n.get('locales'); + const { defaultLocale } = config.i18n; + const { translations: defaultTranslations } = new LocaleHelper(defaultLocale, this.owner); + + assert.expect( + // count of non default locales * translation strings of default locale + (locales.length - 1) * Object.keys(defaultTranslations).length + ); + + Object.keys(defaultTranslations).map((translationString) => { + locales.map((locale) => { + if (locale === defaultLocale) { + return; + } + + i18n.set('locale', locale); + assert.ok( + i18n.exists(translationString), + `translation for ${translationString} exists in locale ${locale}` + ); + }); + }); + }); + + test('all locales have an entry in locales/meta', function(assert) { + const i18n = this.owner.lookup('service:i18n'); + assert.deepEqual( + i18n.get('locales'), + Object.keys(localesMeta) + ); + }); }); diff --git a/tests/pages/create/options.js b/tests/pages/create/options.js index 2179f00..18ccb26 100644 --- a/tests/pages/create/options.js +++ b/tests/pages/create/options.js @@ -21,7 +21,7 @@ const setBootstrapDatepicker = function(selector, options = {}) { return { isDescriptor: true, value(dates) { - const el = findElementWithAssert(this, selector, options); + const el = findElementWithAssert(this, selector, options).parent(); if (isPresent(dates)) { const normalizedDates = dates.map((date) => { if (typeof date.toDate === 'function') { @@ -41,7 +41,7 @@ const setBootstrapDatepicker = function(selector, options = {}) { }; export default PageObject.create(assign({}, defaultsForCreate, { - dateOptions: setBootstrapDatepicker('.days .ember-view:has(.datepicker:first-child)'), + dateOptions: setBootstrapDatepicker('.days .datepicker'), dateHasError: isVisible('.days.has-error'), dateError: text('.days .help-block'), textOptions: collection({ diff --git a/tests/pages/poll.js b/tests/pages/poll.js index bddb770..c803c9d 100644 --- a/tests/pages/poll.js +++ b/tests/pages/poll.js @@ -4,6 +4,7 @@ import { isVisible, text } from 'ember-cli-page-object'; +import { currentURL } from '@ember/test-helpers'; const urlMatches = function(regExp) { return function() { diff --git a/tests/unit/components/create-options-dates-test.js b/tests/unit/components/create-options-dates-test.js index 3941a30..e4fb777 100644 --- a/tests/unit/components/create-options-dates-test.js +++ b/tests/unit/components/create-options-dates-test.js @@ -1,208 +1,209 @@ import { isArray } from '@ember/array'; import EmberObject from '@ember/object'; import { run } from '@ember/runloop'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; -moduleForComponent('create-options-dates', 'Unit | Component | create options dates', { - needs: ['config:environment', 'model:option', 'service:i18n'], - unit: true, - beforeEach() { - this.inject.service('store'); - } -}); +module('Unit | Component | create options dates', function(hooks) { + setupTest(hooks); -test('options get mapped to dates as optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { - let controller = this.subject(); - controller.set('options', [ - EmberObject.create({ title: '1945-05-09' }), - EmberObject.create({ title: '1987-05-01' }), - EmberObject.create({ title: 'non valid date string' }) - ]); - assert.ok( - isArray( - controller.get('optionsBootstrapDatepicker') - ), - "it's an array" - ); - assert.equal( - controller.get('optionsBootstrapDatepicker.length'), - 2, - 'array length is correct' - ); - assert.ok( - controller.get('optionsBootstrapDatepicker').every((el) => { - return moment.isDate(el); - }), - 'array elements are date objects' - ); - assert.equal( - controller.get('optionsBootstrapDatepicker.firstObject').toISOString(), - moment('1945-05-09').toISOString(), - 'date is correct' - ); -}); - -test('options having times get mapped to dates as optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { - let controller = this.subject(); - controller.set('options', [ - EmberObject.create({ title: '2014-01-01T12:00:00.00Z' }), - EmberObject.create({ title: '2015-02-02T15:00:00.00Z' }), - EmberObject.create({ title: '2015-02-02T15:00:00.00Z' }), - EmberObject.create({ title: '2016-03-03' }) - ]); - assert.ok( - isArray( - controller.get('optionsBootstrapDatepicker') - ), - "it's an array" - ); - assert.equal( - controller.get('optionsBootstrapDatepicker.length'), - 3, - 'array length is correct' - ); - assert.ok( - controller.get('optionsBootstrapDatepicker').every((el) => { - return moment.isDate(el); - }), - 'array elements are date objects' - ); - assert.deepEqual( - controller.get('optionsBootstrapDatepicker').map((option) => { - return option.toISOString(); - }), - [ - moment('2014-01-01').toISOString(), - moment('2015-02-02').toISOString(), - moment('2016-03-03').toISOString() - ], - 'date is correct' - ); -}); - -test('options get set correctly by optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { - let controller = this.subject(); - run(() => { - controller.set('options', []); - // dates must be in wrong order to test sorting - controller.set('optionsBootstrapDatepicker', [ - moment('1918-11-09').toDate(), - moment('1917-10-25').toDate() - ]); + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); }); - assert.ok( - isArray( - controller.get('options') - ), - 'options is still an array' - ); - assert.equal( - controller.get('options.length'), - 2, - 'array has correct length' - ); - assert.ok( - controller.get('options').every((option) => { - return typeof option.get('title') === 'string'; - }), - 'option.title is a string' - ); - assert.ok( - controller.get('options').every((option) => { - return moment(option.get('title'), 'YYYY-MM-DD', true).isValid(); - }), - 'option.title is an ISO-8601 date string without time' - ); - assert.ok( - controller.get('options').findBy('title', '1918-11-09'), - 'date is correct' - ); - assert.equal( - controller.get('options.firstObject.title'), - '1917-10-25', - 'dates are in correct order' - ); -}); -test('existing times are preserved if new days get selected', function(assert) { - let component; - run(() => { - component = this.subject({ - options: [ - this.store.createFragment('option', { - title: moment('2015-01-01T11:11').toISOString() - }), - this.store.createFragment('option', { - title: moment('2015-01-01T22:22').toISOString() - }), - this.store.createFragment('option', { - title: moment('2015-06-06T08:08').toISOString() - }), - this.store.createFragment('option', { - title: '2016-01-01' - }) - ] + test('options get mapped to dates as optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { + let controller = this.owner.factoryFor('component:create-options-dates').create(); + controller.set('options', [ + EmberObject.create({ title: '1945-05-09' }), + EmberObject.create({ title: '1987-05-01' }), + EmberObject.create({ title: 'non valid date string' }) + ]); + assert.ok( + isArray( + controller.get('optionsBootstrapDatepicker') + ), + "it's an array" + ); + assert.equal( + controller.get('optionsBootstrapDatepicker.length'), + 2, + 'array length is correct' + ); + assert.ok( + controller.get('optionsBootstrapDatepicker').every((el) => { + return moment.isDate(el); + }), + 'array elements are date objects' + ); + assert.equal( + controller.get('optionsBootstrapDatepicker.firstObject').toISOString(), + moment('1945-05-09').toISOString(), + 'date is correct' + ); + }); + + test('options having times get mapped to dates as optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { + let controller = this.owner.factoryFor('component:create-options-dates').create(); + controller.set('options', [ + EmberObject.create({ title: '2014-01-01T12:00:00.00Z' }), + EmberObject.create({ title: '2015-02-02T15:00:00.00Z' }), + EmberObject.create({ title: '2015-02-02T15:00:00.00Z' }), + EmberObject.create({ title: '2016-03-03' }) + ]); + assert.ok( + isArray( + controller.get('optionsBootstrapDatepicker') + ), + "it's an array" + ); + assert.equal( + controller.get('optionsBootstrapDatepicker.length'), + 3, + 'array length is correct' + ); + assert.ok( + controller.get('optionsBootstrapDatepicker').every((el) => { + return moment.isDate(el); + }), + 'array elements are date objects' + ); + assert.deepEqual( + controller.get('optionsBootstrapDatepicker').map((option) => { + return option.toISOString(); + }), + [ + moment('2014-01-01').toISOString(), + moment('2015-02-02').toISOString(), + moment('2016-03-03').toISOString() + ], + 'date is correct' + ); + }); + + test('options get set correctly by optionsBootstrapDatepicker (used by ember-cli-bootstrap-datepicker)', function(assert) { + let controller = this.owner.factoryFor('component:create-options-dates').create(); + run(() => { + controller.set('options', []); + // dates must be in wrong order to test sorting + controller.set('optionsBootstrapDatepicker', [ + moment('1918-11-09').toDate(), + moment('1917-10-25').toDate() + ]); }); + assert.ok( + isArray( + controller.get('options') + ), + 'options is still an array' + ); + assert.equal( + controller.get('options.length'), + 2, + 'array has correct length' + ); + assert.ok( + controller.get('options').every((option) => { + return typeof option.get('title') === 'string'; + }), + 'option.title is a string' + ); + assert.ok( + controller.get('options').every((option) => { + return moment(option.get('title'), 'YYYY-MM-DD', true).isValid(); + }), + 'option.title is an ISO-8601 date string without time' + ); + assert.ok( + controller.get('options').findBy('title', '1918-11-09'), + 'date is correct' + ); + assert.equal( + controller.get('options.firstObject.title'), + '1917-10-25', + 'dates are in correct order' + ); }); - // add another day - run(() => { - component.set('optionsBootstrapDatepicker', [ - moment('2015-01-01').toDate(), - moment('2015-06-06').toDate(), - moment('2016-01-01').toDate(), - moment('2016-06-06').toDate() // new day - ]); + + test('existing times are preserved if new days get selected', function(assert) { + let component; + run(() => { + component = this.owner.factoryFor('component:create-options-dates').create({ + options: [ + this.store.createFragment('option', { + title: moment('2015-01-01T11:11').toISOString() + }), + this.store.createFragment('option', { + title: moment('2015-01-01T22:22').toISOString() + }), + this.store.createFragment('option', { + title: moment('2015-06-06T08:08').toISOString() + }), + this.store.createFragment('option', { + title: '2016-01-01' + }) + ] + }); + }); + // add another day + run(() => { + component.set('optionsBootstrapDatepicker', [ + moment('2015-01-01').toDate(), + moment('2015-06-06').toDate(), + moment('2016-01-01').toDate(), + moment('2016-06-06').toDate() // new day + ]); + }); + assert.deepEqual( + component.get('options').map((option) => option.get('title')), + [ + moment('2015-01-01T11:11').toISOString(), + moment('2015-01-01T22:22').toISOString(), + moment('2015-06-06T08:08').toISOString(), + '2016-01-01', + '2016-06-06' + ], + 'preseve existing times if another day is added' + ); + // delete a day + run(() => { + component.set('optionsBootstrapDatepicker', [ + moment('2015-06-06').toDate(), + moment('2016-01-01').toDate(), + moment('2016-06-06').toDate() + ]); + }); + assert.deepEqual( + component.get('options').map((option) => option.get('title')), + [ + moment('2015-06-06T08:08').toISOString(), + '2016-01-01', + '2016-06-06' + ], + 'preseve existing times if a day is deleted' + ); + // order if multiple days are added + run(() => { + component.set('optionsBootstrapDatepicker', [ + moment('2015-06-06').toDate(), + moment('2016-01-01').toDate(), + moment('2016-06-06').toDate(), + moment('2016-12-12').toDate(), + moment('2015-01-01').toDate(), + moment('2016-03-03').toDate() + ]); + }); + assert.deepEqual( + component.get('options').map((option) => option.get('title')), + [ + '2015-01-01', + moment('2015-06-06T08:08').toISOString(), + '2016-01-01', + '2016-03-03', + '2016-06-06', + '2016-12-12' + ], + 'options are in correct order after multiple days are added' + ); }); - assert.deepEqual( - component.get('options').map((option) => option.get('title')), - [ - moment('2015-01-01T11:11').toISOString(), - moment('2015-01-01T22:22').toISOString(), - moment('2015-06-06T08:08').toISOString(), - '2016-01-01', - '2016-06-06' - ], - 'preseve existing times if another day is added' - ); - // delete a day - run(() => { - component.set('optionsBootstrapDatepicker', [ - moment('2015-06-06').toDate(), - moment('2016-01-01').toDate(), - moment('2016-06-06').toDate() - ]); - }); - assert.deepEqual( - component.get('options').map((option) => option.get('title')), - [ - moment('2015-06-06T08:08').toISOString(), - '2016-01-01', - '2016-06-06' - ], - 'preseve existing times if a day is deleted' - ); - // order if multiple days are added - run(() => { - component.set('optionsBootstrapDatepicker', [ - moment('2015-06-06').toDate(), - moment('2016-01-01').toDate(), - moment('2016-06-06').toDate(), - moment('2016-12-12').toDate(), - moment('2015-01-01').toDate(), - moment('2016-03-03').toDate() - ]); - }); - assert.deepEqual( - component.get('options').map((option) => option.get('title')), - [ - '2015-01-01', - moment('2015-06-06T08:08').toISOString(), - '2016-01-01', - '2016-03-03', - '2016-06-06', - '2016-12-12' - ], - 'options are in correct order after multiple days are added' - ); }); diff --git a/tests/unit/components/create-options-datetime-test.js b/tests/unit/components/create-options-datetime-test.js index 55a144d..c372225 100644 --- a/tests/unit/components/create-options-datetime-test.js +++ b/tests/unit/components/create-options-datetime-test.js @@ -1,255 +1,251 @@ import { run } from '@ember/runloop'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; -moduleForComponent('create-options-datetime', 'Unit | Component | create options datetime', { - unit: true, - needs: [ - 'config:environment', - 'model:option', 'model:poll', 'model:user', - 'service:i18n', - 'validator:alias', 'validator:collection', 'validator:iso8601', 'validator:length', 'validator:presence', 'validator:time', 'validator:unique', 'validator:valid-collection' - ], - beforeEach() { - this.inject.service('store'); - } -}); +module('Unit | Component | create options datetime', function(hooks) { + setupTest(hooks); -test('delete a date', function(assert) { - let component = this.subject(); - let a, b, c, d, e; - run(() => { - a = this.store.createFragment('option', { title: moment('2015-01-01T01:01:00.000').toISOString() }); - b = this.store.createFragment('option', { title: moment('2015-01-01T11:11:00.000').toISOString() }); - c = this.store.createFragment('option', { title: moment('2015-02-02T11:11:00.000').toISOString() }); - d = this.store.createFragment('option', { title: '2015-02-02' }); - e = this.store.createFragment('option', { title: '2015-02-03' }); - component.set('dates', [a, b, c, d, e]); + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); }); - component.send('deleteOption', b); - assert.deepEqual( - component.get('dates').map((date) => date.get('title')), - [ - moment('2015-01-01T01:01:00.000').toISOString(), - moment('2015-02-02T11:11:00.000').toISOString(), - '2015-02-02', - '2015-02-03' - ], - 'date get deleted if there is another date with same day (both having a time)' - ); - component.send('deleteOption', d); - assert.deepEqual( - component.get('dates').map((date) => date.get('title')), - [ - moment('2015-01-01T01:01:00.000').toISOString(), - moment('2015-02-02T11:11:00.000').toISOString(), - '2015-02-03' - ], - 'date get deleted if there is another date with same day (date does not have a time)' - ); - run(() => { - component.send('deleteOption', c); - }); - assert.deepEqual( - component.get('dates').map((date) => date.get('title')), - [ - moment('2015-01-01T01:01:00.000').toISOString(), - '2015-02-02', - '2015-02-03' - ], - 'time is removed from date if there isn\' t any other date with same day' - ); - component.send('deleteOption', d); - assert.deepEqual( - component.get('dates').map((date) => date.get('title')), - [ - moment('2015-01-01T01:01:00.000').toISOString(), - '2015-02-02', - '2015-02-03' - ], - 'nothing changes if it\'s the only date for this day it it doesn\'t have a time' - ); -}); -test('datetimes are grouped by date', function(assert) { - let component = this.subject(); - let a, b, c; - // have to set dates in local time and than convert to ISO 8601 strings - // because otherwise test could fail caused by timezone - run(() => { - a = this.store.createFragment('option', { title: moment('2015-01-01T01:01:00').toISOString() }); - b = this.store.createFragment('option', { title: moment('2015-01-01T11:11:00').toISOString() }); - c = this.store.createFragment('option', { title: moment('2015-02-02T01:01:00').toISOString() }); - component.set('dates', [a, b, c]); - }); - assert.equal( - component.get('groupedDates.length'), - 2, - 'length is correct' - ); - assert.deepEqual( - component.get('groupedDates.firstObject.items').map((item) => { - return item.get('date').toISOString(); - }), - [a.get('title'), b.get('title')], - 'first dates having same day are grouped together' - ); - assert.equal( - component.get('groupedDates.lastObject.items.firstObject.date').toISOString(), - [c.get('title')], - 'last date having another day is in a separate group' - ); -}); - -test('bindings are working on grouped datetimes', function(assert) { - let component = this.subject(); - run(() => { - component.set('dates', [ - this.store.createFragment('option', { - title: moment('2015-01-01T11:11:00.000Z').toISOString() - }) - ]); - }); - assert.equal( - component.get('groupedDates.firstObject.items.firstObject.time'), - moment('2015-01-01T11:11:00.000Z').format('HH:mm'), - 'time is correct before' - ); - run(() => { - component.set( - 'groupedDates.firstObject.items.firstObject.time', - '00:00' + test('delete a date', function(assert) { + let component = this.owner.factoryFor('component:create-options-datetime').create(); + let a, b, c, d, e; + run(() => { + a = this.store.createFragment('option', { title: moment('2015-01-01T01:01:00.000').toISOString() }); + b = this.store.createFragment('option', { title: moment('2015-01-01T11:11:00.000').toISOString() }); + c = this.store.createFragment('option', { title: moment('2015-02-02T11:11:00.000').toISOString() }); + d = this.store.createFragment('option', { title: '2015-02-02' }); + e = this.store.createFragment('option', { title: '2015-02-03' }); + component.set('dates', [a, b, c, d, e]); + }); + component.send('deleteOption', b); + assert.deepEqual( + component.get('dates').map((date) => date.get('title')), + [ + moment('2015-01-01T01:01:00.000').toISOString(), + moment('2015-02-02T11:11:00.000').toISOString(), + '2015-02-02', + '2015-02-03' + ], + 'date get deleted if there is another date with same day (both having a time)' + ); + component.send('deleteOption', d); + assert.deepEqual( + component.get('dates').map((date) => date.get('title')), + [ + moment('2015-01-01T01:01:00.000').toISOString(), + moment('2015-02-02T11:11:00.000').toISOString(), + '2015-02-03' + ], + 'date get deleted if there is another date with same day (date does not have a time)' + ); + run(() => { + component.send('deleteOption', c); + }); + assert.deepEqual( + component.get('dates').map((date) => date.get('title')), + [ + moment('2015-01-01T01:01:00.000').toISOString(), + '2015-02-02', + '2015-02-03' + ], + 'time is removed from date if there isn\' t any other date with same day' + ); + component.send('deleteOption', d); + assert.deepEqual( + component.get('dates').map((date) => date.get('title')), + [ + moment('2015-01-01T01:01:00.000').toISOString(), + '2015-02-02', + '2015-02-03' + ], + 'nothing changes if it\'s the only date for this day it it doesn\'t have a time' ); }); - assert.equal( - component.get('dates.firstObject.title'), - moment('2015-01-01T00:00').toISOString(), - 'option is updated after time changed on grouped datetimes' - ); - run(() => { - component.get('dates').pushObject( - this.store.createFragment('option', { title: moment('2015-01-01T12:12').toISOString() }) + + test('datetimes are grouped by date', function(assert) { + let component = this.owner.factoryFor('component:create-options-datetime').create(); + let a, b, c; + // have to set dates in local time and than convert to ISO 8601 strings + // because otherwise test could fail caused by timezone + run(() => { + a = this.store.createFragment('option', { title: moment('2015-01-01T01:01:00').toISOString() }); + b = this.store.createFragment('option', { title: moment('2015-01-01T11:11:00').toISOString() }); + c = this.store.createFragment('option', { title: moment('2015-02-02T01:01:00').toISOString() }); + component.set('dates', [a, b, c]); + }); + assert.equal( + component.get('groupedDates.length'), + 2, + 'length is correct' + ); + assert.deepEqual( + component.get('groupedDates.firstObject.items').map((item) => { + return item.get('date').toISOString(); + }), + [a.get('title'), b.get('title')], + 'first dates having same day are grouped together' + ); + assert.equal( + component.get('groupedDates.lastObject.items.firstObject.date').toISOString(), + [c.get('title')], + 'last date having another day is in a separate group' ); }); - assert.equal( - component.get('groupedDates.firstObject.items.length'), - 2, - 'grouped datetimes got updated after option was added (same day)' - ); - assert.equal( - component.get('groupedDates.firstObject.items.lastObject.time'), - '12:12', - 'grouped datetimes got updated correctly after option was added (same day)' - ); - run(() => { - component.get('dates').pushObject( - this.store.createFragment('option', { title: moment('2015-02-02T01:01').toISOString() }) + + test('bindings are working on grouped datetimes', function(assert) { + let component = this.owner.factoryFor('component:create-options-datetime').create(); + run(() => { + component.set('dates', [ + this.store.createFragment('option', { + title: moment('2015-01-01T11:11:00.000Z').toISOString() + }) + ]); + }); + assert.equal( + component.get('groupedDates.firstObject.items.firstObject.time'), + moment('2015-01-01T11:11:00.000Z').format('HH:mm'), + 'time is correct before' + ); + run(() => { + component.set( + 'groupedDates.firstObject.items.firstObject.time', + '00:00' + ); + }); + assert.equal( + component.get('dates.firstObject.title'), + moment('2015-01-01T00:00').toISOString(), + 'option is updated after time changed on grouped datetimes' + ); + run(() => { + component.get('dates').pushObject( + this.store.createFragment('option', { title: moment('2015-01-01T12:12').toISOString() }) + ); + }); + assert.equal( + component.get('groupedDates.firstObject.items.length'), + 2, + 'grouped datetimes got updated after option was added (same day)' + ); + assert.equal( + component.get('groupedDates.firstObject.items.lastObject.time'), + '12:12', + 'grouped datetimes got updated correctly after option was added (same day)' + ); + run(() => { + component.get('dates').pushObject( + this.store.createFragment('option', { title: moment('2015-02-02T01:01').toISOString() }) + ); + }); + assert.equal( + component.get('groupedDates.length'), + 2, + 'grouped datetimes got updated after option was added (other day)' + ); + assert.equal( + component.get('groupedDates.lastObject.items.firstObject.time'), + '01:01', + 'grouped datetimes got updated correctly after option was added (same day)' ); }); - assert.equal( - component.get('groupedDates.length'), - 2, - 'grouped datetimes got updated after option was added (other day)' - ); - assert.equal( - component.get('groupedDates.lastObject.items.firstObject.time'), - '01:01', - 'grouped datetimes got updated correctly after option was added (same day)' - ); -}); -test('adopt times of first day - simple', function(assert) { - let component; - let poll; - run(() => { - poll = this.store.createRecord('poll', { - options: [ - { title: moment('2015-01-01T11:11:00.000').toISOString() }, - { title: moment('2015-01-01T22:22:00.000').toISOString() }, - { title: moment('2015-01-02').toISOString() }, - { title: moment('2015-01-03').toISOString() } - ] + test('adopt times of first day - simple', function(assert) { + let component; + let poll; + run(() => { + poll = this.store.createRecord('poll', { + options: [ + { title: moment('2015-01-01T11:11:00.000').toISOString() }, + { title: moment('2015-01-01T22:22:00.000').toISOString() }, + { title: moment('2015-01-02').toISOString() }, + { title: moment('2015-01-03').toISOString() } + ] + }); + component = this.owner.factoryFor('component:create-options-datetime').create({ + dates: poll.get('options') + }); + component.send('adoptTimesOfFirstDay'); }); - component = this.subject({ - dates: poll.get('options') - }); - component.send('adoptTimesOfFirstDay'); + assert.deepEqual( + component.get('dates').map((option) => option.get('title')), + [ + moment('2015-01-01T11:11:00.000').toISOString(), + moment('2015-01-01T22:22:00.000').toISOString(), + moment('2015-01-02T11:11:00.000').toISOString(), + moment('2015-01-02T22:22:00.000').toISOString(), + moment('2015-01-03T11:11:00.000').toISOString(), + moment('2015-01-03T22:22:00.000').toISOString() + ], + 'times adopted correctly' + ); }); - assert.deepEqual( - component.get('dates').map((option) => option.get('title')), - [ - moment('2015-01-01T11:11:00.000').toISOString(), - moment('2015-01-01T22:22:00.000').toISOString(), - moment('2015-01-02T11:11:00.000').toISOString(), - moment('2015-01-02T22:22:00.000').toISOString(), - moment('2015-01-03T11:11:00.000').toISOString(), - moment('2015-01-03T22:22:00.000').toISOString() - ], - 'times adopted correctly' - ); -}); -test('adopt times of first day - having times on the other days', function(assert) { - let component; - let poll; - run(() => { - poll = this.store.createRecord('poll', { - options: [ - { title: moment('2015-01-01T11:11:00.000').toISOString() }, - { title: moment('2015-01-01T22:22:00.000').toISOString() }, - { title: moment('2015-01-02T09:11:00.000').toISOString() }, - { title: moment('2015-01-03T01:11:00.000').toISOString() }, - { title: moment('2015-01-03T11:11:00.000').toISOString() }, - { title: moment('2015-01-04T02:11:00.000').toISOString() }, - { title: moment('2015-01-04T05:11:00.000').toISOString() }, - { title: moment('2015-01-04T12:11:00.000').toISOString() } - ] + test('adopt times of first day - having times on the other days', function(assert) { + let component; + let poll; + run(() => { + poll = this.store.createRecord('poll', { + options: [ + { title: moment('2015-01-01T11:11:00.000').toISOString() }, + { title: moment('2015-01-01T22:22:00.000').toISOString() }, + { title: moment('2015-01-02T09:11:00.000').toISOString() }, + { title: moment('2015-01-03T01:11:00.000').toISOString() }, + { title: moment('2015-01-03T11:11:00.000').toISOString() }, + { title: moment('2015-01-04T02:11:00.000').toISOString() }, + { title: moment('2015-01-04T05:11:00.000').toISOString() }, + { title: moment('2015-01-04T12:11:00.000').toISOString() } + ] + }); + component = this.owner.factoryFor('component:create-options-datetime').create({ + dates: poll.get('options') + }); + component.send('adoptTimesOfFirstDay'); }); - component = this.subject({ - dates: poll.get('options') - }); - component.send('adoptTimesOfFirstDay'); + assert.deepEqual( + component.get('dates').map((option) => option.get('title')), + [ + moment('2015-01-01T11:11:00.000').toISOString(), + moment('2015-01-01T22:22:00.000').toISOString(), + moment('2015-01-02T11:11:00.000').toISOString(), + moment('2015-01-02T22:22:00.000').toISOString(), + moment('2015-01-03T11:11:00.000').toISOString(), + moment('2015-01-03T22:22:00.000').toISOString(), + moment('2015-01-04T11:11:00.000').toISOString(), + moment('2015-01-04T22:22:00.000').toISOString() + ], + 'times adopted correctly' + ); }); - assert.deepEqual( - component.get('dates').map((option) => option.get('title')), - [ - moment('2015-01-01T11:11:00.000').toISOString(), - moment('2015-01-01T22:22:00.000').toISOString(), - moment('2015-01-02T11:11:00.000').toISOString(), - moment('2015-01-02T22:22:00.000').toISOString(), - moment('2015-01-03T11:11:00.000').toISOString(), - moment('2015-01-03T22:22:00.000').toISOString(), - moment('2015-01-04T11:11:00.000').toISOString(), - moment('2015-01-04T22:22:00.000').toISOString() - ], - 'times adopted correctly' - ); -}); -test('adopt times of first day - no times on first day', function(assert) { - let component; - let poll; - run(() => { - poll = this.store.createRecord('poll', { - options: [ - { title: '2015-01-01' }, - { title: '2015-01-02' }, - { title: moment('2015-01-03T11:00:00.000Z').toISOString() }, - { title: moment('2015-01-03T15:00:00.000Z').toISOString() } - ] + test('adopt times of first day - no times on first day', function(assert) { + let component; + let poll; + run(() => { + poll = this.store.createRecord('poll', { + options: [ + { title: '2015-01-01' }, + { title: '2015-01-02' }, + { title: moment('2015-01-03T11:00:00.000Z').toISOString() }, + { title: moment('2015-01-03T15:00:00.000Z').toISOString() } + ] + }); + component = this.owner.factoryFor('component:create-options-datetime').create({ + dates: poll.get('options') + }); + component.send('adoptTimesOfFirstDay'); }); - component = this.subject({ - dates: poll.get('options') - }); - component.send('adoptTimesOfFirstDay'); + assert.deepEqual( + component.get('dates').map((option) => option.get('title')), + [ + '2015-01-01', + '2015-01-02', + '2015-01-03' + ], + 'times are removed from all days' + ); }); - assert.deepEqual( - component.get('dates').map((option) => option.get('title')), - [ - '2015-01-01', - '2015-01-02', - '2015-01-03' - ], - 'times are removed from all days' - ); }); diff --git a/tests/unit/components/create-options-test.js b/tests/unit/components/create-options-test.js index 36146df..d503d2c 100644 --- a/tests/unit/components/create-options-test.js +++ b/tests/unit/components/create-options-test.js @@ -1,5 +1,6 @@ import { run } from '@ember/runloop'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; // validator consumes i18n service // have to register it therefore @@ -7,205 +8,185 @@ import moment from 'moment'; import tHelper from 'ember-i18n/helper'; import localeConfig from 'ember-i18n/config/en'; -moduleForComponent('create-options', 'Unit | Component | create options', { - needs: [ - 'model:option', - 'model:poll', - 'validator:alias', - 'model:user', - 'validator:collection', - 'validator:iso8601', - 'validator:length', - 'validator:presence', - 'validator:time', - 'validator:unique', - 'validator:valid-collection', - 'validator:messages', +module('Unit | Component | create options', function(hooks) { + setupTest(hooks); + + hooks.beforeEach(function() { + this.store = this.owner.lookup('service:store'); // validator consumes i18n service - 'service:i18n', - 'locale:en/translations', - // 'locale:en/config', https://github.com/jamesarosen/ember-i18n/issues/368 - 'util:i18n/missing-message', - 'util:i18n/compile-template', - 'config:environment' - ], - unit: true, - beforeEach() { - this.inject.service('store'); - // validator consumes i18n service - this.container.lookup('service:i18n').set('locale', 'en'); - this.registry.register('locale:en/config', localeConfig); - this.registry.register('helper:t', tHelper); - } -}); - -test('validation for make a poll', function(assert) { - let component = this.subject(); - component.set('options', []); - component.set('isFindADate', false); - component.set('isMakeAPoll', true); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: component.get('isFindADate'), - isMakeAPoll: component.get('isMakeAPoll') - }); - }); - - assert.notOk( - component.get('validations.isValid'), - 'invalid without any options' - ); - run(() => { - let option = this.store.createFragment('option', { - title: 'first option' - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.ok( - component.get('validations.isValid'), - 'valid if there is atleast one valid option' - ); - run(() => { - let option = this.store.createFragment('option', { - title: 'second option' - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.ok( - component.get('validations.isValid'), - 'valid for two options which are not empty strings' - ); - run(() => { - component.set('options.firstObject.title', ''); - }); - assert.notOk( - component.get('validations.isValid'), - 'invalid if atleast one string is empty' - ); -}); - -test('validation for find a date without times', function(assert) { - let component = this.subject(); - component.set('options', []); - component.set('isFindADate', true); - component.set('isMakeAPoll', false); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: component.get('isFindADate'), - isMakeAPoll: component.get('isMakeAPoll') - }); - }); - - assert.notOk( - component.get('validations.isValid'), - 'invalid without any options' - ); - run(() => { - let option = this.store.createFragment('option', { - title: '2015-01-01' - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.ok( - component.get('validations.isValid'), - 'valid if there is atleast one valid date' - ); - run(() => { - let option = this.store.createFragment('option', { - title: '2015-01-02' - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.ok( - component.get('validations.isValid'), - 'valid for two valid dates' - ); - run(() => { - let option = this.store.createFragment('option', { - title: 'foo' - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.notOk( - component.get('validations.isValid'), - 'invalid if atleast one option is not a valid date' - ); - run(() => { - component.set('options.lastObject.title', '2015-01-03'); - }); - assert.ok( - component.get('validations.isValid'), - 'valid again after title is a valid date again' - ); - run(() => { - component.set('options.firstObject.title', '2015-01-01'); - component.set('options.lastObject.title', '2015-01-01'); - }); - assert.ok( - component.get('validations.isInvalid'), - 'invalid if dates are not unique' - ); -}); - -test('validation for find a date with times', function(assert) { - let component = this.subject(); - component.set('options', []); - component.set('isMakeAPoll', false); - - // validation is based on validation of every option fragment - // which validates according to poll model it belongs to - // therefore each option needs to be pushed to poll model to have it as - // it's owner - let poll; - run(() => { - poll = this.store.createRecord('poll', { - isFindADate: component.get('isFindADate'), - isMakeAPoll: component.get('isMakeAPoll') - }); - }); - assert.notOk( - component.get('validations.isValid'), - 'invalid without any options' - ); - run(() => { - let option = this.store.createFragment('option', { - title: moment().add('1', 'day').format('YYYY-MM-DD') - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.ok( - component.get('validations.isValid'), - 'valid if there is atleast one valid date' - ); - /* - Ember.run(() => { - let option = this.store.createFragment('option', { - title: moment().add('1', 'day').hour(22).minute(30).seconds(0).milliseconds(0).toISOString() - }); - poll.get('options').pushObject(option); - component.get('options').pushObject(option); - }); - assert.notOk( - component.get('validations.isValid'), - 'invalid if there is a option without time for a day with has another option with time specified' - ); - */ + this.owner.lookup('service:i18n').set('locale', 'en'); + this.owner.register('locale:en/config', localeConfig); + this.owner.register('helper:t', tHelper); + }); + + test('validation for make a poll', function(assert) { + let component = this.owner.factoryFor('component:create-options').create(); + component.set('options', []); + component.set('isFindADate', false); + component.set('isMakeAPoll', true); + + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: component.get('isFindADate'), + isMakeAPoll: component.get('isMakeAPoll') + }); + }); + + assert.notOk( + component.get('validations.isValid'), + 'invalid without any options' + ); + run(() => { + let option = this.store.createFragment('option', { + title: 'first option' + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.ok( + component.get('validations.isValid'), + 'valid if there is atleast one valid option' + ); + run(() => { + let option = this.store.createFragment('option', { + title: 'second option' + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.ok( + component.get('validations.isValid'), + 'valid for two options which are not empty strings' + ); + run(() => { + component.set('options.firstObject.title', ''); + }); + assert.notOk( + component.get('validations.isValid'), + 'invalid if atleast one string is empty' + ); + }); + + test('validation for find a date without times', function(assert) { + let component = this.owner.factoryFor('component:create-options').create(); + component.set('options', []); + component.set('isFindADate', true); + component.set('isMakeAPoll', false); + + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: component.get('isFindADate'), + isMakeAPoll: component.get('isMakeAPoll') + }); + }); + + assert.notOk( + component.get('validations.isValid'), + 'invalid without any options' + ); + run(() => { + let option = this.store.createFragment('option', { + title: '2015-01-01' + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.ok( + component.get('validations.isValid'), + 'valid if there is atleast one valid date' + ); + run(() => { + let option = this.store.createFragment('option', { + title: '2015-01-02' + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.ok( + component.get('validations.isValid'), + 'valid for two valid dates' + ); + run(() => { + let option = this.store.createFragment('option', { + title: 'foo' + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.notOk( + component.get('validations.isValid'), + 'invalid if atleast one option is not a valid date' + ); + run(() => { + component.set('options.lastObject.title', '2015-01-03'); + }); + assert.ok( + component.get('validations.isValid'), + 'valid again after title is a valid date again' + ); + run(() => { + component.set('options.firstObject.title', '2015-01-01'); + component.set('options.lastObject.title', '2015-01-01'); + }); + assert.ok( + component.get('validations.isInvalid'), + 'invalid if dates are not unique' + ); + }); + + test('validation for find a date with times', function(assert) { + let component = this.owner.factoryFor('component:create-options').create(); + component.set('options', []); + component.set('isMakeAPoll', false); + + // validation is based on validation of every option fragment + // which validates according to poll model it belongs to + // therefore each option needs to be pushed to poll model to have it as + // it's owner + let poll; + run(() => { + poll = this.store.createRecord('poll', { + isFindADate: component.get('isFindADate'), + isMakeAPoll: component.get('isMakeAPoll') + }); + }); + assert.notOk( + component.get('validations.isValid'), + 'invalid without any options' + ); + run(() => { + let option = this.store.createFragment('option', { + title: moment().add('1', 'day').format('YYYY-MM-DD') + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.ok( + component.get('validations.isValid'), + 'valid if there is atleast one valid date' + ); + /* + Ember.run(() => { + let option = this.store.createFragment('option', { + title: moment().add('1', 'day').hour(22).minute(30).seconds(0).milliseconds(0).toISOString() + }); + poll.get('options').pushObject(option); + component.get('options').pushObject(option); + }); + assert.notOk( + component.get('validations.isValid'), + 'invalid if there is a option without time for a day with has another option with time specified' + ); + */ + }); }); diff --git a/tests/unit/components/poll-evaluation-chart-test.js b/tests/unit/components/poll-evaluation-chart-test.js index a4cb0b9..969c1a4 100644 --- a/tests/unit/components/poll-evaluation-chart-test.js +++ b/tests/unit/components/poll-evaluation-chart-test.js @@ -1,141 +1,37 @@ import EmberObject from '@ember/object'; -import { moduleForComponent, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; import tHelper from 'ember-i18n/helper'; import localeConfig from 'ember-i18n/config/en'; -moduleForComponent('poll-evaluation-chart', 'Unit | Component | poll evaluation chart', { - unit: true, - // https://github.com/jamesarosen/ember-i18n/wiki/Doc:-Testing#unit-tests - needs: [ - 'service:i18n', - 'locale:en/translations', - 'util:i18n/missing-message', - 'util:i18n/compile-template', - 'config:environment' - ], - beforeEach() { +module('Unit | Component | poll evaluation chart', function(hooks) { + setupTest(hooks); + + hooks.beforeEach(function() { moment.locale('en'); - this.container.lookup('service:i18n').set('locale', 'en'); - this.registry.register('locale:en/config', localeConfig); - this.registry.register('helper:t', tHelper); - } -}); - -test('data is a valid ChartJS dataset for FindADate using poll timezone', function(assert) { - let options = [ - EmberObject.create({ - title: '2015-01-01' - }), - EmberObject.create({ - title: '2015-02-02' - }), - EmberObject.create({ - title: '2015-03-03T01:00:00.000Z' - }), - EmberObject.create({ - title: '2015-03-03T11:00:00.000Z' - }) - ]; - let users = [ - EmberObject.create({ - id: 1, - selections: [ - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' - }) - ] - }), - EmberObject.create({ - id: 2, - selections: [ - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' - }), - EmberObject.create({ - type: 'no' - }) - ] - }) - ]; - let currentLocale = 'en'; - let momentLongDayFormat = moment.localeData(currentLocale) - .longDateFormat('LLLL') - .replace( - moment.localeData(currentLocale).longDateFormat('LT'), '') - .trim(); - let component = this.subject({ - answerType: 'YesNoMaybe', - currentLocale, - isFindADate: true, - momentLongDayFormat, - options, - timezone: 'Asia/Hong_Kong', - users + this.owner.lookup('service:i18n').set('locale', 'en'); + this.owner.register('locale:en/config', localeConfig); + this.owner.register('helper:t', tHelper); }); - const data = component.get('data'); - assert.deepEqual( - data.labels, - ['Thursday, January 1, 2015', 'Monday, February 2, 2015', 'Tuesday, March 3, 2015 9:00 AM', 'Tuesday, March 3, 2015 7:00 PM'], - 'Labels are correct' - ); - assert.equal( - data.datasets.length, - 2, - 'there are two datasets' - ); - assert.deepEqual( - data.datasets.map((dataset) => dataset.label), - ['Yes', 'Maybe'], - 'datasets having answers as label and are in correct order' - ); - assert.deepEqual( - data.datasets[0].data, - [100, 50, 0, 0], - 'dataset for yes is correct' - ); - assert.deepEqual( - data.datasets[1].data, - [0, 50, 50, 0], - 'dataset for maybe is correct' - ); -}); -test('data is a valid ChartJS dataset for MakeAPoll', function(assert) { - const options = [ - EmberObject.create({ - title: 'first option' - }), - EmberObject.create({ - title: 'second option' - }), - EmberObject.create({ - title: 'third option' - }), - EmberObject.create({ - title: 'fourth option' - }) - ]; - let component = this.subject({ - answerType: 'YesNoMaybe', - options, - users: [ + test('data is a valid ChartJS dataset for FindADate using poll timezone', function(assert) { + let options = [ + EmberObject.create({ + title: '2015-01-01' + }), + EmberObject.create({ + title: '2015-02-02' + }), + EmberObject.create({ + title: '2015-03-03T01:00:00.000Z' + }), + EmberObject.create({ + title: '2015-03-03T11:00:00.000Z' + }) + ]; + let users = [ EmberObject.create({ id: 1, selections: [ @@ -170,149 +66,247 @@ test('data is a valid ChartJS dataset for MakeAPoll', function(assert) { }) ] }) - ] + ]; + let currentLocale = 'en'; + let momentLongDayFormat = moment.localeData(currentLocale) + .longDateFormat('LLLL') + .replace( + moment.localeData(currentLocale).longDateFormat('LT'), '') + .trim(); + let component = this.owner.factoryFor('component:poll-evaluation-chart').create({ + answerType: 'YesNoMaybe', + currentLocale, + isFindADate: true, + momentLongDayFormat, + options, + timezone: 'Asia/Hong_Kong', + users + }); + const data = component.get('data'); + assert.deepEqual( + data.labels, + ['Thursday, January 1, 2015', 'Monday, February 2, 2015', 'Tuesday, March 3, 2015 9:00 AM', 'Tuesday, March 3, 2015 7:00 PM'], + 'Labels are correct' + ); + assert.equal( + data.datasets.length, + 2, + 'there are two datasets' + ); + assert.deepEqual( + data.datasets.map((dataset) => dataset.label), + ['Yes', 'Maybe'], + 'datasets having answers as label and are in correct order' + ); + assert.deepEqual( + data.datasets[0].data, + [100, 50, 0, 0], + 'dataset for yes is correct' + ); + assert.deepEqual( + data.datasets[1].data, + [0, 50, 50, 0], + 'dataset for maybe is correct' + ); }); - const data = component.get('data'); - assert.deepEqual( - data.labels, - options.map((option) => option.get('title')), - 'Labels are correct' - ); - assert.equal( - data.datasets.length, - 2, - 'there are two datasets' - ); - assert.deepEqual( - data.datasets.map((dataset) => dataset.label), - ['Yes', 'Maybe'], - 'datasets having answers as label and are in correct order' - ); - assert.deepEqual( - data.datasets[0].data, - [100, 50, 0, 0], - 'dataset for yes is correct' - ); - assert.deepEqual( - data.datasets[1].data, - [0, 50, 50, 0], - 'dataset for maybe is correct' - ); -}); -test('data is a valid ChartJS dataset for FindADate using poll timezone', function(assert) { - let options = [ - EmberObject.create({ - title: '2015-01-01' - }), - EmberObject.create({ - title: '2015-02-02' - }), - EmberObject.create({ - title: '2015-03-03T01:00:00.000Z' - }), - EmberObject.create({ - title: '2015-03-03T11:00:00.000Z' - }) - ]; - let users = [ - EmberObject.create({ - id: 1, - selections: [ + test('data is a valid ChartJS dataset for MakeAPoll', function(assert) { + const options = [ + EmberObject.create({ + title: 'first option' + }), + EmberObject.create({ + title: 'second option' + }), + EmberObject.create({ + title: 'third option' + }), + EmberObject.create({ + title: 'fourth option' + }) + ]; + let component = this.owner.factoryFor('component:poll-evaluation-chart').create({ + answerType: 'YesNoMaybe', + options, + users: [ EmberObject.create({ - type: 'yes' + id: 1, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }) + ] }), EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' + id: 2, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }), + EmberObject.create({ + type: 'no' + }) + ] }) ] - }), - EmberObject.create({ - id: 2, - selections: [ - EmberObject.create({ - type: 'yes' - }), - EmberObject.create({ - type: 'maybe' - }), - EmberObject.create({ - type: 'no' - }), - EmberObject.create({ - type: 'no' - }) - ] - }) - ]; - let currentLocale = 'en'; - let momentLongDayFormat = moment.localeData(currentLocale) - .longDateFormat('LLLL') - .replace( - moment.localeData(currentLocale).longDateFormat('LT'), '') - .trim(); - let component = this.subject({ - answerType: 'YesNoMaybe', - currentLocale, - isFindADate: true, - momentLongDayFormat, - options, - timezone: 'Asia/Hong_Kong', - users + }); + const data = component.get('data'); + assert.deepEqual( + data.labels, + options.map((option) => option.get('title')), + 'Labels are correct' + ); + assert.equal( + data.datasets.length, + 2, + 'there are two datasets' + ); + assert.deepEqual( + data.datasets.map((dataset) => dataset.label), + ['Yes', 'Maybe'], + 'datasets having answers as label and are in correct order' + ); + assert.deepEqual( + data.datasets[0].data, + [100, 50, 0, 0], + 'dataset for yes is correct' + ); + assert.deepEqual( + data.datasets[1].data, + [0, 50, 50, 0], + 'dataset for maybe is correct' + ); }); - const data = component.get('data'); - assert.deepEqual( - data.labels, - ['Thursday, January 1, 2015', 'Monday, February 2, 2015', 'Tuesday, March 3, 2015 9:00 AM', 'Tuesday, March 3, 2015 7:00 PM'], - 'Labels are correct' - ); - assert.equal( - data.datasets.length, - 2, - 'there are two datasets' - ); - assert.deepEqual( - data.datasets.map((dataset) => dataset.label), - ['Yes', 'Maybe'], - 'datasets having answers as label and are in correct order' - ); - assert.deepEqual( - data.datasets[0].data, - [100, 50, 0, 0], - 'dataset for yes is correct' - ); - assert.deepEqual( - data.datasets[1].data, - [0, 50, 50, 0], - 'dataset for maybe is correct' - ); -}); -test('data is a valid ChartJS dataset for FindADate using locale timezone', function(assert) { - let options = [ - EmberObject.create({ - title: '2015-03-03T01:00:00.000Z' - }) - ]; - let component = this.subject({ - answerType: 'YesNoMaybe', - currentLocale: 'en', - isFindADate: true, - momentLongDayFormat: '', - options, - timezone: undefined, - users: [] + test('data is a valid ChartJS dataset for FindADate using poll timezone', function(assert) { + let options = [ + EmberObject.create({ + title: '2015-01-01' + }), + EmberObject.create({ + title: '2015-02-02' + }), + EmberObject.create({ + title: '2015-03-03T01:00:00.000Z' + }), + EmberObject.create({ + title: '2015-03-03T11:00:00.000Z' + }) + ]; + let users = [ + EmberObject.create({ + id: 1, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }) + ] + }), + EmberObject.create({ + id: 2, + selections: [ + EmberObject.create({ + type: 'yes' + }), + EmberObject.create({ + type: 'maybe' + }), + EmberObject.create({ + type: 'no' + }), + EmberObject.create({ + type: 'no' + }) + ] + }) + ]; + let currentLocale = 'en'; + let momentLongDayFormat = moment.localeData(currentLocale) + .longDateFormat('LLLL') + .replace( + moment.localeData(currentLocale).longDateFormat('LT'), '') + .trim(); + let component = this.owner.factoryFor('component:poll-evaluation-chart').create({ + answerType: 'YesNoMaybe', + currentLocale, + isFindADate: true, + momentLongDayFormat, + options, + timezone: 'Asia/Hong_Kong', + users + }); + const data = component.get('data'); + assert.deepEqual( + data.labels, + ['Thursday, January 1, 2015', 'Monday, February 2, 2015', 'Tuesday, March 3, 2015 9:00 AM', 'Tuesday, March 3, 2015 7:00 PM'], + 'Labels are correct' + ); + assert.equal( + data.datasets.length, + 2, + 'there are two datasets' + ); + assert.deepEqual( + data.datasets.map((dataset) => dataset.label), + ['Yes', 'Maybe'], + 'datasets having answers as label and are in correct order' + ); + assert.deepEqual( + data.datasets[0].data, + [100, 50, 0, 0], + 'dataset for yes is correct' + ); + assert.deepEqual( + data.datasets[1].data, + [0, 50, 50, 0], + 'dataset for maybe is correct' + ); + }); + + test('data is a valid ChartJS dataset for FindADate using locale timezone', function(assert) { + let options = [ + EmberObject.create({ + title: '2015-03-03T01:00:00.000Z' + }) + ]; + let component = this.owner.factoryFor('component:poll-evaluation-chart').create({ + answerType: 'YesNoMaybe', + currentLocale: 'en', + isFindADate: true, + momentLongDayFormat: '', + options, + timezone: undefined, + users: [] + }); + const data = component.get('data'); + assert.deepEqual( + data.labels, + [moment('2015-03-03T01:00:00.000Z').format('LLLL')], + 'Labels are correct' + ); }); - const data = component.get('data'); - assert.deepEqual( - data.labels, - [moment('2015-03-03T01:00:00.000Z').format('LLLL')], - 'Labels are correct' - ); }); diff --git a/tests/unit/controllers/create-test.js b/tests/unit/controllers/create-test.js index 2aaa4a9..5e973ea 100644 --- a/tests/unit/controllers/create-test.js +++ b/tests/unit/controllers/create-test.js @@ -1,12 +1,12 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('controller:create', 'Unit | Controller | create', { - // Specify the other units that are required for this test. - // needs: ['controller:foo'] -}); +module('Unit | Controller | create', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('it exists', function(assert) { - let controller = this.subject(); - assert.ok(controller); + // Replace this with your real tests. + test('it exists', function(assert) { + let controller = this.owner.lookup('controller:create'); + assert.ok(controller); + }); }); diff --git a/tests/unit/controllers/create/options-datetime-test.js b/tests/unit/controllers/create/options-datetime-test.js index 1de601e..c67fe02 100644 --- a/tests/unit/controllers/create/options-datetime-test.js +++ b/tests/unit/controllers/create/options-datetime-test.js @@ -1,58 +1,60 @@ import { run } from '@ember/runloop'; import EmberObject from '@ember/object'; -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; -moduleFor('controller:create/options-datetime', 'Unit | Controller | create/options datetime', { -}); +module('Unit | Controller | create/options datetime', function(hooks) { + setupTest(hooks); -test('normalize options - remove days without time if there is another option with a time for that day', function(assert) { - const dirtyOption = EmberObject.create({ title: '2015-01-01' }); - let controller = this.subject({ - model: { - options: [ - EmberObject.create({ title: '2015-01-01T12:00:00.000Z' }), - dirtyOption, - EmberObject.create({ title: '2017-11-11' }), - EmberObject.create({ title: '2018-04-04T11:11:00.000Z' }) - ] - } + test('normalize options - remove days without time if there is another option with a time for that day', function(assert) { + const dirtyOption = EmberObject.create({ title: '2015-01-01' }); + let controller = this.owner.factoryFor('controller:create/options-datetime').create({ + model: { + options: [ + EmberObject.create({ title: '2015-01-01T12:00:00.000Z' }), + dirtyOption, + EmberObject.create({ title: '2017-11-11' }), + EmberObject.create({ title: '2018-04-04T11:11:00.000Z' }) + ] + } + }); + run(() => { + controller.normalizeOptions(); + }); + assert.equal( + controller.get('options.length'), + 3, + 'one option is removed' + ); + assert.ok( + controller.get('options').indexOf(dirtyOption) === -1, + 'correct option is removed' + ); }); - run(() => { - controller.normalizeOptions(); - }); - assert.equal( - controller.get('options.length'), - 3, - 'one option is removed' - ); - assert.ok( - controller.get('options').indexOf(dirtyOption) === -1, - 'correct option is removed' - ); -}); -test('normalize options - sort them', function(assert) { - const dateA = moment().hour(5).toISOString(); - const dateB = moment().hour(10).toISOString(); - const dateC = moment().hour(22).toISOString(); - const dateD = moment().add(1, 'day').toISOString(); - let controller = this.subject({ - model: { - options: [ - EmberObject.create({ title: dateB }), - EmberObject.create({ title: dateA }), - EmberObject.create({ title: dateC }), - EmberObject.create({ title: dateD }) - ] - } + test('normalize options - sort them', function(assert) { + const dateA = moment().hour(5).toISOString(); + const dateB = moment().hour(10).toISOString(); + const dateC = moment().hour(22).toISOString(); + const dateD = moment().add(1, 'day').toISOString(); + let controller = this.owner.factoryFor('controller:create/options-datetime').create({ + model: { + options: [ + EmberObject.create({ title: dateB }), + EmberObject.create({ title: dateA }), + EmberObject.create({ title: dateC }), + EmberObject.create({ title: dateD }) + ] + } + }); + run(() => { + controller.normalizeOptions(); + }); + assert.deepEqual( + controller.get('options').map((option) => option.get('title')), + [dateA, dateB, dateC, dateD], + 'options are sorted' + ); }); - run(() => { - controller.normalizeOptions(); - }); - assert.deepEqual( - controller.get('options').map((option) => option.get('title')), - [dateA, dateB, dateC, dateD], - 'options are sorted' - ); }); diff --git a/tests/unit/controllers/create/options-test.js b/tests/unit/controllers/create/options-test.js index 30cd501..6232fd5 100644 --- a/tests/unit/controllers/create/options-test.js +++ b/tests/unit/controllers/create/options-test.js @@ -1,12 +1,12 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('controller:create/options', 'Unit | Controller | create/options', { - // Specify the other units that are required for this test. - // needs: ['controller:foo'] -}); +module('Unit | Controller | create/options', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('it exists', function(assert) { - let controller = this.subject(); - assert.ok(controller); + // Replace this with your real tests. + test('it exists', function(assert) { + let controller = this.owner.lookup('controller:create/options'); + assert.ok(controller); + }); }); diff --git a/tests/unit/controllers/error-test.js b/tests/unit/controllers/error-test.js index 83525cf..a4fee5c 100644 --- a/tests/unit/controllers/error-test.js +++ b/tests/unit/controllers/error-test.js @@ -1,12 +1,12 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('controller:error', 'Unit | Controller | error', { - // Specify the other units that are required for this test. - // needs: ['controller:foo'] -}); +module('Unit | Controller | error', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('it exists', function(assert) { - let controller = this.subject(); - assert.ok(controller); + // Replace this with your real tests. + test('it exists', function(assert) { + let controller = this.owner.lookup('controller:error'); + assert.ok(controller); + }); }); diff --git a/tests/unit/controllers/poll-test.js b/tests/unit/controllers/poll-test.js index 13788b3..c2dca03 100644 --- a/tests/unit/controllers/poll-test.js +++ b/tests/unit/controllers/poll-test.js @@ -1,30 +1,31 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; -moduleFor('controller:poll', 'Unit | Controller | poll', { - needs: ['service:encryption', 'service:flashMessages', 'service:i18n'] -}); +module('Unit | Controller | poll', function(hooks) { + setupTest(hooks); -test('#showExpirationWarning', function(assert) { - let controller = this.subject({ - model: { - expirationDate: undefined - } + test('#showExpirationWarning', function(assert) { + let controller = this.owner.factoryFor('controller:poll').create({ + model: { + expirationDate: undefined + } + }); + assert.notOk( + controller.get('showExpirationWarning'), + 'is false if expirationDate is undefined' + ); + + controller.set('model.expirationDate', moment().add(1, 'week').toISOString()); + assert.ok( + controller.get('showExpirationWarning'), + 'is true if expirationDate is less than 2 weeks in future' + ); + + controller.set('model.expirationDate', moment().add(1, 'month').toISOString()); + assert.notOk( + controller.get('showExpirationWarning'), + 'is false if expirationDate is more than 2 weeks in future' + ); }); - assert.notOk( - controller.get('showExpirationWarning'), - 'is false if expirationDate is undefined' - ); - - controller.set('model.expirationDate', moment().add(1, 'week').toISOString()); - assert.ok( - controller.get('showExpirationWarning'), - 'is true if expirationDate is less than 2 weeks in future' - ); - - controller.set('model.expirationDate', moment().add(1, 'month').toISOString()); - assert.notOk( - controller.get('showExpirationWarning'), - 'is false if expirationDate is more than 2 weeks in future' - ); }); diff --git a/tests/unit/controllers/poll/participation-test.js b/tests/unit/controllers/poll/participation-test.js index 12716b1..e7d3d32 100644 --- a/tests/unit/controllers/poll/participation-test.js +++ b/tests/unit/controllers/poll/participation-test.js @@ -1,16 +1,12 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('controller:poll/participation', 'Unit | Controller | poll/participation', { - needs: [ - 'config:environment', - 'controller:poll', - 'service:encryption', 'service:i18n', - 'validator:collection', 'validator:presence', 'validator:unique' - ] -}); +module('Unit | Controller | poll/participation', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('it exists', function(assert) { - let controller = this.subject(); - assert.ok(controller); + // Replace this with your real tests. + test('it exists', function(assert) { + let controller = this.owner.lookup('controller:poll/participation'); + assert.ok(controller); + }); }); diff --git a/tests/unit/mixins/autofocus-support-test.js b/tests/unit/mixins/autofocus-support-test.js index ed35443..f62c5c7 100644 --- a/tests/unit/mixins/autofocus-support-test.js +++ b/tests/unit/mixins/autofocus-support-test.js @@ -2,11 +2,11 @@ import EmberObject from '@ember/object'; import AutofocusSupportMixin from 'croodle/mixins/autofocus-support'; import { module, test } from 'qunit'; -module('Unit | Mixin | autofocus support'); - -// Replace this with your real tests. -test('it works', function(assert) { - let AutofocusSupportObject = EmberObject.extend(AutofocusSupportMixin); - let subject = AutofocusSupportObject.create(); - assert.ok(subject); +module('Unit | Mixin | autofocus support', function() { + // Replace this with your real tests. + test('it works', function(assert) { + let AutofocusSupportObject = EmberObject.extend(AutofocusSupportMixin); + let subject = AutofocusSupportObject.create(); + assert.ok(subject); + }); }); diff --git a/tests/unit/models/option-test.js b/tests/unit/models/option-test.js index 5c0f1f8..17a6030 100644 --- a/tests/unit/models/option-test.js +++ b/tests/unit/models/option-test.js @@ -1,6 +1,7 @@ import { run } from '@ember/runloop'; import Service from '@ember/service'; -import { moduleForModel, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; import moment from 'moment'; const i18nStub = Service.extend({ @@ -10,356 +11,347 @@ const i18nStub = Service.extend({ locale: 'en' }); -moduleForModel('option', 'Unit | Model | option', { - needs: [ - 'validator:alias', - 'validator:iso8601', - 'validator:unique', - 'validator:presence', - 'validator:messages', - 'validator:time', - 'model:poll', - 'model:user' - ], +module('Unit | Model | option', function(hooks) { + setupTest(hooks); - beforeEach() { - this.register('service:i18n', i18nStub); - this.inject.service('i18n', { as: 'i18n' }); + hooks.beforeEach(function() { + this.owner.register('service:i18n', i18nStub); + this.i18n = this.owner.lookup('service:i18n'); moment.locale('en'); - } -}); - -test('date property (get)', function(assert) { - let option = this.subject({ - title: '2015-01-01' - }); - assert.ok( - moment.isMoment(option.get('date')), - 'returns a moment instance if title is an ISO 8601 day string' - ); - assert.equal( - option.get('date').format('YYYY-MM-DD HH:mm:ss.SSS'), - '2015-01-01 00:00:00.000', - 'string to date conversion is correct for ISO 8601 day string' - ); - - run(() => { - option.set('title', '2015-01-01T11:11:00.000Z'); - }); - assert.ok( - moment.isMoment(option.get('date')), - 'returns a moment instance if title is an ISO 8601 datetime string' - ); - assert.equal( - option.get('date').toISOString(), - '2015-01-01T11:11:00.000Z', - 'string to date conversion is correct for ISO 8601 datetime string' - ); - - run(() => { - option.set('title', null); - }); - assert.equal( - option.get('date'), - undefined, - 'returns undefined if title is empty' - ); - - run(() => { - option.set('title', 'abc'); - }); - assert.equal( - option.get('date'), - undefined, - 'returns undefined if title is not a valid ISO 8601 date string' - ); - - run(() => { - option.set('title', '2015'); - }); - assert.equal( - option.get('date'), - undefined, - 'returns undefined if title ISO 8601 string only contains a year' - ); - - run(() => { - option.set('title', '2015-01'); - }); - assert.equal( - option.get('date'), - undefined, - 'returns undefined if title ISO 8601 string only contains a year and a month' - ); - - run(() => { - option.set('title', '2013W06'); - }); - assert.equal( - option.get('date'), - undefined, - 'returns undefined if title ISO 8601 string only contains a year and a week' - ); -}); - -test('day property (get)', function(assert) { - let option = this.subject({ - title: '2015-01-01' - }); - assert.equal( - option.get('day'), - '2015-01-01', - 'returns ISO 8601 day string if title is ISO 8601 day string' - ); - - run(() => { - option.set('title', '2015-01-01T11:11:00.000Z'); - }); - assert.equal( - option.get('day'), - moment('2015-01-01T11:11:00.000Z').format('YYYY-MM-DD'), - 'returns ISO 8601 day string if title is ISO 8601 datetime string' - ); - - run(() => { - option.set('title', 'abc'); - }); - assert.equal( - option.get('day'), - undefined, - 'returns undefined if title is not a valid ISO 8601 string' - ); - - run(() => { - option.set('title', null); - }); - assert.equal( - option.get('day'), - undefined, - 'returns undefined if title is null' - ); -}); - -test('dayFormatted property (get)', function(assert) { - let option = this.subject({ - title: '2015-01-01' - }); - assert.equal( - option.get('dayFormatted'), - 'Thursday, January 1, 2015', - 'returns formatted date if title is ISO 8601 day string' - ); - - run(() => { - option.set('title', moment('2015-01-01').toISOString()); - }); - assert.equal( - option.get('dayFormatted'), - 'Thursday, January 1, 2015', - 'returns formatted date if title is ISO 8601 datetime string' - ); - - run(() => { - option.set('i18n.locale', 'de'); - }); - assert.equal( - option.get('dayFormatted'), - 'Donnerstag, 1. Januar 2015', - 'observes locale changes' - ); - - run(() => { - option.set('title', 'abc'); - }); - assert.equal( - option.get('dayFormatted'), - undefined, - 'returns undfined if title is not a valid ISO 8601 string' - ); -}); - -test('hasTime property', function(assert) { - let option = this.subject({ - title: '2015-01-01T11:11:00.000Z' - }); - assert.ok(option.get('hasTime')); - run(() => { - option.set('title', '2015-01-01'); - }); - assert.notOk(option.get('hasTime')); - run(() => { - option.set('title', 'foo'); - }); - assert.notOk(option.get('hasTime')); -}); - -test('time property (get)', function(assert) { - let option = this.subject({ - title: '2015-01-01T11:11:00.000Z' - }); - assert.equal( - option.get('time'), - moment('2015-01-01T11:11:00.000Z').format('HH:mm'), - 'returns time if title is ISO 8601 datetime string' - ); - - run(() => { - option.set('title', '2015-01-01'); - }); - assert.equal( - option.get('time'), - undefined, - 'returns undefined if title is ISO 8601 day string' - ); - - run(() => { - option.set('title', 'abc'); - }); - assert.equal( - option.get('time'), - undefined, - 'returns undefined if title is not an ISO 8601 date string' - ); -}); - -test('time property (set)', function(assert) { - let option = this.subject({ - title: '2015-01-01' }); - run(() => { - option.set('time', '11:00'); - }); - assert.equal( - option.get('title'), - moment('2015-01-01T11:00').toISOString(), - 'sets title according to time' - ); - - run(() => { - option.set('time', null); - }); - assert.equal( - option.get('title'), - '2015-01-01', - 'removes time from option if value is false' - ); - - const before = option.get('title'); - run(() => { - option.set('time', 'abc'); - }); - assert.equal( - option.get('title'), - before, - 'does not set title if time is invalid' - ); - - run(() => { - option.set('title', 'abc'); - }); - assert.throws( - () => { - option.set('time', '11:11'); - }, - 'throws if attempt to set a time if title is not a date string' - ); -}); - -test('validation for MakeAPoll', function(assert) { - run(() => { - let store = this.store(); - let poll = store.createRecord('poll', { - pollType: 'MakeAPoll' - }); - let option = store.createFragment('option'); - poll.get('options').pushObject(option); - option.validate(); - assert.notOk( - option.get('validations.isValid'), - 'default value is not valid' + test('date property (get)', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01' + })); + assert.ok( + moment.isMoment(option.get('date')), + 'returns a moment instance if title is an ISO 8601 day string' ); + assert.equal( + option.get('date').format('YYYY-MM-DD HH:mm:ss.SSS'), + '2015-01-01 00:00:00.000', + 'string to date conversion is correct for ISO 8601 day string' + ); + run(() => { - option.set('title', 'Spasibo!'); + option.set('title', '2015-01-01T11:11:00.000Z'); }); assert.ok( - option.get('validations.isValid'), - 'is valid for a non empty string' + moment.isMoment(option.get('date')), + 'returns a moment instance if title is an ISO 8601 datetime string' ); - run(() => { - option.set('title', '!'); - }); - assert.ok( - option.get('validations.isValid'), - 'is invalid if set to empty string again' + assert.equal( + option.get('date').toISOString(), + '2015-01-01T11:11:00.000Z', + 'string to date conversion is correct for ISO 8601 datetime string' ); - }); -}); -test('validation for FindADate', function(assert) { - run(() => { - let store = this.store(); - let poll = store.createRecord('poll', { - isDateTime: false, - pollType: 'FindADate' - }); - let option = store.createFragment('option'); - poll.get('options').pushObject(option); - option.validate(); - assert.notOk( - option.get('validations.isValid'), - 'default value is not valid' - ); run(() => { - option.set('title', '1945-05-08'); + option.set('title', null); }); - assert.ok( - option.get('validations.isValid'), - 'iso 8601 date string is valid' + assert.equal( + option.get('date'), + undefined, + 'returns undefined if title is empty' ); - run(() => { - option.set('title', 'Spasibo!'); - }); - assert.notOk( - option.get('validations.isValid'), - 'random string is not valid' - ); - }); -}); -test('validation for FindADate', function(assert) { - run(() => { - let store = this.store(); - let poll = store.createRecord('poll', { - pollType: 'FindADate' - }); - let option = store.createFragment('option'); - poll.get('options').pushObject(option); - option.validate(); - assert.notOk( - option.get('validations.isValid'), - 'default value is not valid' - ); run(() => { - option.set('title', '1945-05-08T00:00:00.000Z'); + option.set('title', 'abc'); }); - assert.ok( - option.get('validations.isValid'), - 'iso 8601 datetime string is valid' + assert.equal( + option.get('date'), + undefined, + 'returns undefined if title is not a valid ISO 8601 date string' ); + run(() => { - option.set('title', 'Spasibo!'); + option.set('title', '2015'); }); - assert.notOk( - option.get('validations.isValid'), - 'random string is not valid' + assert.equal( + option.get('date'), + undefined, + 'returns undefined if title ISO 8601 string only contains a year' ); + run(() => { - option.set('title', '1945-05-08'); + option.set('title', '2015-01'); }); - assert.ok( - option.get('validations.isValid'), - 'iso 8601 date string is valid' + assert.equal( + option.get('date'), + undefined, + 'returns undefined if title ISO 8601 string only contains a year and a month' + ); + + run(() => { + option.set('title', '2013W06'); + }); + assert.equal( + option.get('date'), + undefined, + 'returns undefined if title ISO 8601 string only contains a year and a week' ); }); + + test('day property (get)', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01' + })); + assert.equal( + option.get('day'), + '2015-01-01', + 'returns ISO 8601 day string if title is ISO 8601 day string' + ); + + run(() => { + option.set('title', '2015-01-01T11:11:00.000Z'); + }); + assert.equal( + option.get('day'), + moment('2015-01-01T11:11:00.000Z').format('YYYY-MM-DD'), + 'returns ISO 8601 day string if title is ISO 8601 datetime string' + ); + + run(() => { + option.set('title', 'abc'); + }); + assert.equal( + option.get('day'), + undefined, + 'returns undefined if title is not a valid ISO 8601 string' + ); + + run(() => { + option.set('title', null); + }); + assert.equal( + option.get('day'), + undefined, + 'returns undefined if title is null' + ); + }); + + test('dayFormatted property (get)', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01' + })); + assert.equal( + option.get('dayFormatted'), + 'Thursday, January 1, 2015', + 'returns formatted date if title is ISO 8601 day string' + ); + + run(() => { + option.set('title', moment('2015-01-01').toISOString()); + }); + assert.equal( + option.get('dayFormatted'), + 'Thursday, January 1, 2015', + 'returns formatted date if title is ISO 8601 datetime string' + ); + + run(() => { + option.set('i18n.locale', 'de'); + }); + assert.equal( + option.get('dayFormatted'), + 'Donnerstag, 1. Januar 2015', + 'observes locale changes' + ); + + run(() => { + option.set('title', 'abc'); + }); + assert.equal( + option.get('dayFormatted'), + undefined, + 'returns undfined if title is not a valid ISO 8601 string' + ); + }); + + test('hasTime property', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01T11:11:00.000Z' + })); + assert.ok(option.get('hasTime')); + run(() => { + option.set('title', '2015-01-01'); + }); + assert.notOk(option.get('hasTime')); + run(() => { + option.set('title', 'foo'); + }); + assert.notOk(option.get('hasTime')); + }); + + test('time property (get)', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01T11:11:00.000Z' + })); + assert.equal( + option.get('time'), + moment('2015-01-01T11:11:00.000Z').format('HH:mm'), + 'returns time if title is ISO 8601 datetime string' + ); + + run(() => { + option.set('title', '2015-01-01'); + }); + assert.equal( + option.get('time'), + undefined, + 'returns undefined if title is ISO 8601 day string' + ); + + run(() => { + option.set('title', 'abc'); + }); + assert.equal( + option.get('time'), + undefined, + 'returns undefined if title is not an ISO 8601 date string' + ); + }); + + test('time property (set)', function(assert) { + let option = run(() => this.owner.lookup('service:store').createRecord('option', { + title: '2015-01-01' + })); + + run(() => { + option.set('time', '11:00'); + }); + assert.equal( + option.get('title'), + moment('2015-01-01T11:00').toISOString(), + 'sets title according to time' + ); + + run(() => { + option.set('time', null); + }); + assert.equal( + option.get('title'), + '2015-01-01', + 'removes time from option if value is false' + ); + + const before = option.get('title'); + run(() => { + option.set('time', 'abc'); + }); + assert.equal( + option.get('title'), + before, + 'does not set title if time is invalid' + ); + + run(() => { + option.set('title', 'abc'); + }); + assert.throws( + () => { + option.set('time', '11:11'); + }, + 'throws if attempt to set a time if title is not a date string' + ); + }); + + test('validation for MakeAPoll', function(assert) { + run(() => { + let store = this.owner.lookup('service:store'); + let poll = store.createRecord('poll', { + pollType: 'MakeAPoll' + }); + let option = store.createFragment('option'); + poll.get('options').pushObject(option); + option.validate(); + assert.notOk( + option.get('validations.isValid'), + 'default value is not valid' + ); + run(() => { + option.set('title', 'Spasibo!'); + }); + assert.ok( + option.get('validations.isValid'), + 'is valid for a non empty string' + ); + run(() => { + option.set('title', '!'); + }); + assert.ok( + option.get('validations.isValid'), + 'is invalid if set to empty string again' + ); + }); + }); + + test('validation for FindADate', function(assert) { + run(() => { + let store = this.owner.lookup('service:store'); + let poll = store.createRecord('poll', { + isDateTime: false, + pollType: 'FindADate' + }); + let option = store.createFragment('option'); + poll.get('options').pushObject(option); + option.validate(); + assert.notOk( + option.get('validations.isValid'), + 'default value is not valid' + ); + run(() => { + option.set('title', '1945-05-08'); + }); + assert.ok( + option.get('validations.isValid'), + 'iso 8601 date string is valid' + ); + run(() => { + option.set('title', 'Spasibo!'); + }); + assert.notOk( + option.get('validations.isValid'), + 'random string is not valid' + ); + }); + }); + + test('validation for FindADate', function(assert) { + run(() => { + let store = this.owner.lookup('service:store'); + let poll = store.createRecord('poll', { + pollType: 'FindADate' + }); + let option = store.createFragment('option'); + poll.get('options').pushObject(option); + option.validate(); + assert.notOk( + option.get('validations.isValid'), + 'default value is not valid' + ); + run(() => { + option.set('title', '1945-05-08T00:00:00.000Z'); + }); + assert.ok( + option.get('validations.isValid'), + 'iso 8601 datetime string is valid' + ); + run(() => { + option.set('title', 'Spasibo!'); + }); + assert.notOk( + option.get('validations.isValid'), + 'random string is not valid' + ); + run(() => { + option.set('title', '1945-05-08'); + }); + assert.ok( + option.get('validations.isValid'), + 'iso 8601 date string is valid' + ); + }); + }); }); diff --git a/tests/unit/routes/create/options-datetime-test.js b/tests/unit/routes/create/options-datetime-test.js index b801266..e841705 100644 --- a/tests/unit/routes/create/options-datetime-test.js +++ b/tests/unit/routes/create/options-datetime-test.js @@ -1,11 +1,11 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('route:create/options-datetime', 'Unit | Route | create/options datetime', { - // Specify the other units that are required for this test. - // needs: ['controller:foo'] -}); +module('Unit | Route | create/options datetime', function(hooks) { + setupTest(hooks); -test('it exists', function(assert) { - let route = this.subject(); - assert.ok(route); + test('it exists', function(assert) { + let route = this.owner.lookup('route:create/options-datetime'); + assert.ok(route); + }); }); diff --git a/tests/unit/services/encryption-test.js b/tests/unit/services/encryption-test.js index 6786548..c8d681b 100644 --- a/tests/unit/services/encryption-test.js +++ b/tests/unit/services/encryption-test.js @@ -1,12 +1,12 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('service:encryption', 'Unit | Service | encryption', { - // Specify the other units that are required for this test. - // needs: ['service:foo'] -}); +module('Unit | Service | encryption', function(hooks) { + setupTest(hooks); -// Replace this with your real tests. -test('it exists', function(assert) { - let service = this.subject(); - assert.ok(service); + // Replace this with your real tests. + test('it exists', function(assert) { + let service = this.owner.lookup('service:encryption'); + assert.ok(service); + }); }); diff --git a/tests/unit/validators/iso8601-test.js b/tests/unit/validators/iso8601-test.js index 81ce67b..582b27c 100644 --- a/tests/unit/validators/iso8601-test.js +++ b/tests/unit/validators/iso8601-test.js @@ -1,96 +1,98 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('validator:iso8601', 'Unit | Validator | iso8601', { -}); +module('Unit | Validator | iso8601', function(hooks) { + setupTest(hooks); -test('default validation is correct', function(assert) { - let validator = this.subject(); - assert.equal( - validator.validate('1945-05-08T23:01:00.000Z'), - true, - 'iso 8601 datetime string with milliseconds in UTC is valid by default' - ); - assert.notOk( - validator.validate(null) === true, - 'null is invalid' - ); - assert.notOk( - validator.validate(undefined) === true, - 'undefined is invalid' - ); - assert.notOk( - validator.validate('') === true, - 'empty string is invalid' - ); - assert.notOk( - validator.validate('abc123') === true, - 'random string is invalid' - ); -}); + test('default validation is correct', function(assert) { + let validator = this.owner.lookup('validator:iso8601'); + assert.equal( + validator.validate('1945-05-08T23:01:00.000Z'), + true, + 'iso 8601 datetime string with milliseconds in UTC is valid by default' + ); + assert.notOk( + validator.validate(null) === true, + 'null is invalid' + ); + assert.notOk( + validator.validate(undefined) === true, + 'undefined is invalid' + ); + assert.notOk( + validator.validate('') === true, + 'empty string is invalid' + ); + assert.notOk( + validator.validate('abc123') === true, + 'random string is invalid' + ); + }); -test('option.active disables validation on false', function(assert) { - let validator = this.subject(); - const buildOptions = validator.buildOptions({ active: false }, {}); - assert.notOk( - validator.validate(null) === true, - 'is validated on default' - ); - assert.equal( - validator.validate(null, buildOptions), - true, - 'validation is disabled on active === false' - ); -}); + test('option.active disables validation on false', function(assert) { + let validator = this.owner.lookup('validator:iso8601'); + const buildOptions = validator.buildOptions({ active: false }, {}); + assert.notOk( + validator.validate(null) === true, + 'is validated on default' + ); + assert.equal( + validator.validate(null, buildOptions), + true, + 'validation is disabled on active === false' + ); + }); -test('option.active could be a function', function(assert) { - let validator = this.subject(); - const buildOptions = validator.buildOptions({ - active() { - return false; - } - }, {}); - assert.equal( - validator.validate(null, buildOptions), - true, - 'validation is dislabed if function returns false' - ); -}); + test('option.active could be a function', function(assert) { + let validator = this.owner.lookup('validator:iso8601'); + const buildOptions = validator.buildOptions({ + active() { + return false; + } + }, {}); + assert.equal( + validator.validate(null, buildOptions), + true, + 'validation is dislabed if function returns false' + ); + }); -test('valid iso8601 string formats could be defined by options.validFormats', function(assert) { - let validator = this.subject(); - const buildOptions = validator.buildOptions({ - validFormats: [ - 'YYYY-MM-DD', - 'YYYY-MM-DDTHH:mmZ', - 'YYYY-MM-DDTHH:mm:ssZ' - ] - }, {}); - assert.notOk( - validator.validate('1945-05-08') === true, - 'iso 8601 date string is invalid by default' - ); - assert.equal( - validator.validate('1945-05-08', buildOptions), - true, - 'iso 8601 date string is valid if it\'s in validFormats options' - ); - assert.notOk( - validator.validate('1945-05-08T23:01Z') === true, - 'iso 8601 datetime string in UTC is invalid by default' - ); - assert.equal( - validator.validate('1945-05-08T23:01Z', buildOptions), - true, - 'iso 8601 datetime string in UTC is valid if it\'s in validFormats options' - ); - assert.notOk( - validator.validate('1945-05-08T23:01:00Z') === true, - true, - 'iso 8601 datetime string with seconds in UTC is invalid by default' - ); - assert.equal( - validator.validate('1945-05-08T23:01:00Z', buildOptions), - true, - 'iso 8601 datetime string with seconds in UTC is valid if it\'s in validFormats options' - ); + test('valid iso8601 string formats could be defined by options.validFormats', function(assert) { + let validator = this.owner.lookup('validator:iso8601'); + const buildOptions = validator.buildOptions({ + validFormats: [ + 'YYYY-MM-DD', + 'YYYY-MM-DDTHH:mmZ', + 'YYYY-MM-DDTHH:mm:ssZ' + ] + }, {}); + assert.notOk( + validator.validate('1945-05-08') === true, + 'iso 8601 date string is invalid by default' + ); + assert.equal( + validator.validate('1945-05-08', buildOptions), + true, + 'iso 8601 date string is valid if it\'s in validFormats options' + ); + assert.notOk( + validator.validate('1945-05-08T23:01Z') === true, + 'iso 8601 datetime string in UTC is invalid by default' + ); + assert.equal( + validator.validate('1945-05-08T23:01Z', buildOptions), + true, + 'iso 8601 datetime string in UTC is valid if it\'s in validFormats options' + ); + assert.notOk( + validator.validate('1945-05-08T23:01:00Z') === true, + true, + 'iso 8601 datetime string with seconds in UTC is invalid by default' + ); + assert.equal( + validator.validate('1945-05-08T23:01:00Z', buildOptions), + true, + 'iso 8601 datetime string with seconds in UTC is valid if it\'s in validFormats options' + ); + }); }); diff --git a/tests/unit/validators/time-test.js b/tests/unit/validators/time-test.js index 4568400..f191061 100644 --- a/tests/unit/validators/time-test.js +++ b/tests/unit/validators/time-test.js @@ -1,47 +1,49 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('validator:time', 'Unit | Validator | time', { -}); - -test('HH:mm is treated as valid', function(assert) { - let validator = this.subject(); - - assert.equal(validator.validate('00:00'), true); - assert.equal(validator.validate('23:59'), true); -}); - -test('24:00 is invalid', function(assert) { - let validator = this.subject(); - - assert.ok(typeof validator.validate('24:00') === 'string'); -}); - -test('00:60 is invalid', function(assert) { - let validator = this.subject(); - - assert.ok(typeof validator.validate('00:60') === 'string'); -}); - -test('an empty string is invalid', function(assert) { - let validator = this.subject(); - - assert.ok(typeof validator.validate('') === 'string'); -}); - -test('null is invalid', function(assert) { - let validator = this.subject(); - - assert.ok(typeof validator.validate(null) === 'string'); -}); - -test('undefined is invalid', function(assert) { - let validator = this.subject(); - - assert.ok(typeof validator.validate(undefined) === 'string'); -}); - -test('a valid time wrapped by spaces is valid', function(assert) { - let validator = this.subject(); - - assert.equal(validator.validate(' 10:00 '), true); +module('Unit | Validator | time', function(hooks) { + setupTest(hooks); + + test('HH:mm is treated as valid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.equal(validator.validate('00:00'), true); + assert.equal(validator.validate('23:59'), true); + }); + + test('24:00 is invalid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.ok(typeof validator.validate('24:00') === 'string'); + }); + + test('00:60 is invalid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.ok(typeof validator.validate('00:60') === 'string'); + }); + + test('an empty string is invalid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.ok(typeof validator.validate('') === 'string'); + }); + + test('null is invalid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.ok(typeof validator.validate(null) === 'string'); + }); + + test('undefined is invalid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.ok(typeof validator.validate(undefined) === 'string'); + }); + + test('a valid time wrapped by spaces is valid', function(assert) { + let validator = this.owner.lookup('validator:time'); + + assert.equal(validator.validate(' 10:00 '), true); + }); }); diff --git a/tests/unit/validators/unique-test.js b/tests/unit/validators/unique-test.js index e975314..02468e6 100644 --- a/tests/unit/validators/unique-test.js +++ b/tests/unit/validators/unique-test.js @@ -1,88 +1,90 @@ import { A } from '@ember/array'; import EmberObject from '@ember/object'; -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('validator:unique', 'Unit | Validator | unique', { -}); +module('Unit | Validator | unique', function(hooks) { + setupTest(hooks); -test('throws if required option is missing', function(assert) { - const validator = this.subject(); - assert.throws( - function() { - validator.validate(null, { - parent: 'foo', - dependentKeys: ['foo'] - }); - }, - 'throws if attributeInParrent is not defined' - ); - assert.throws( - function() { - validator.validate(null, { - attributeInParent: 'foo', - dependentKeys: ['foo'] - }); - }, - 'throws if parent is not defined' - ); - assert.throws( - function() { - validator.validate(null, { - parent: 'foo', - attributeInParent: 'foo' - }); - }, - 'throws if dependentKeys is not defined' - ); -}); - -test('validation', function(assert) { - const validator = this.subject(); - const parent = EmberObject.create({ - collection: A([]) + test('throws if required option is missing', function(assert) { + const validator = this.owner.lookup('validator:unique'); + assert.throws( + function() { + validator.validate(null, { + parent: 'foo', + dependentKeys: ['foo'] + }); + }, + 'throws if attributeInParrent is not defined' + ); + assert.throws( + function() { + validator.validate(null, { + attributeInParent: 'foo', + dependentKeys: ['foo'] + }); + }, + 'throws if parent is not defined' + ); + assert.throws( + function() { + validator.validate(null, { + parent: 'foo', + attributeInParent: 'foo' + }); + }, + 'throws if dependentKeys is not defined' + ); }); - const childObject = EmberObject.extend({ - parent + + test('validation', function(assert) { + const validator = this.owner.lookup('validator:unique'); + const parent = EmberObject.create({ + collection: A([]) + }); + const childObject = EmberObject.extend({ + parent + }); + const options = { + parent: 'parent', + attributeInParent: 'collection', + dependentKeys: ['parent.collection.@each.value'] + }; + const child1 = childObject.create({ value: 'foo' }); + const child2 = childObject.create({ value: 'bar' }); + const child3 = childObject.create({ value: 'foo' }); + + parent.get('collection').push(child1); + assert.ok( + validator.validate( + child1.get('value'), + options, + child1, + 'value' + ) === true, + 'valid for only one element' + ); + + parent.get('collection').push(child2); + assert.ok( + validator.validate( + child2.get('value'), + options, + child2, + 'value' + ) === true, + 'still valid after pushing another element with different value' + ); + + parent.get('collection').push(child3); + assert.ok( + typeof validator.validate( + child3.get('value'), + options, + child3, + 'value' + ) === 'string', + 'invalid after pushing element with same value' + ); }); - const options = { - parent: 'parent', - attributeInParent: 'collection', - dependentKeys: ['parent.collection.@each.value'] - }; - const child1 = childObject.create({ value: 'foo' }); - const child2 = childObject.create({ value: 'bar' }); - const child3 = childObject.create({ value: 'foo' }); - - parent.get('collection').push(child1); - assert.ok( - validator.validate( - child1.get('value'), - options, - child1, - 'value' - ) === true, - 'valid for only one element' - ); - - parent.get('collection').push(child2); - assert.ok( - validator.validate( - child2.get('value'), - options, - child2, - 'value' - ) === true, - 'still valid after pushing another element with different value' - ); - - parent.get('collection').push(child3); - assert.ok( - typeof validator.validate( - child3.get('value'), - options, - child3, - 'value' - ) === 'string', - 'invalid after pushing element with same value' - ); }); diff --git a/tests/unit/validators/valid-collection-test.js b/tests/unit/validators/valid-collection-test.js index a20ee32..7415f0a 100644 --- a/tests/unit/validators/valid-collection-test.js +++ b/tests/unit/validators/valid-collection-test.js @@ -1,9 +1,11 @@ -import { moduleFor, test } from 'ember-qunit'; +import { module, test } from 'qunit'; +import { setupTest } from 'ember-qunit'; -moduleFor('validator:valid-collection', 'Unit | Validator | valid-collection', { -}); +module('Unit | Validator | valid-collection', function(hooks) { + setupTest(hooks); -test('it works', function(assert) { - let validator = this.subject(); - assert.ok(validator); + test('it works', function(assert) { + let validator = this.owner.lookup('validator:valid-collection'); + assert.ok(validator); + }); }); diff --git a/yarn.lock b/yarn.lock index 29f3088..7f22fc8 100644 --- a/yarn.lock +++ b/yarn.lock @@ -591,6 +591,38 @@ lodash "^4.17.10" to-fast-properties "^2.0.0" +"@ember/jquery@^0.5.2": + version "0.5.2" + resolved "https://registry.yarnpkg.com/@ember/jquery/-/jquery-0.5.2.tgz#fe312c03ada0022fa092d23f7cd7e2eb0374b53a" + integrity sha1-/jEsA62gAi+gktI/fNfi6wN0tTo= + dependencies: + broccoli-funnel "^2.0.1" + ember-cli-babel "^6.6.0" + jquery "^3.3.1" + resolve "^1.7.1" + +"@ember/optional-features@^0.6.3": + version "0.6.4" + resolved "https://registry.yarnpkg.com/@ember/optional-features/-/optional-features-0.6.4.tgz#8199f853c1781234fcb1f05090cddd0b822bff69" + integrity sha512-nKmKxMk+Q/BGE8cmfq8KTHnYHVgrU3GHhy/eZ/OTj/fUvzXZhxaEVFOfAXssiOzV3FOQDJjznpbua2TEtHaQRw== + dependencies: + chalk "^2.3.0" + co "^4.6.0" + ember-cli-version-checker "^2.1.0" + glob "^7.1.2" + inquirer "^3.3.0" + mkdirp "^0.5.1" + silent-error "^1.1.0" + util.promisify "^1.0.0" + +"@ember/ordered-set@^2.0.0": + version "2.0.3" + resolved "https://registry.yarnpkg.com/@ember/ordered-set/-/ordered-set-2.0.3.tgz#2ac1ca73b3bd116063cae814898832ef434a57f9" + integrity sha512-F4yfVk6WMc4AUHxeZsC3CaKyTvO0qSZJy7WWHCFTlVDQw6vubn+FvnGdhzpN1F00EiXMI4Tv1tJdSquHcCnYrA== + dependencies: + ember-cli-babel "^6.16.0" + ember-compatibility-helpers "^1.1.1" + "@ember/test-helpers@^0.7.26": version "0.7.27" resolved "https://registry.yarnpkg.com/@ember/test-helpers/-/test-helpers-0.7.27.tgz#c622cabd0cbb95b34efc1e1b6274ab5a14edc138" @@ -601,11 +633,28 @@ ember-cli-babel "^6.12.0" ember-cli-htmlbars-inline-precompile "^1.0.0" +"@glimmer/compiler@^0.36.2": + version "0.36.5" + resolved "https://registry.yarnpkg.com/@glimmer/compiler/-/compiler-0.36.5.tgz#ea2ac9aa1a5c3ada7f8d93cd295fdc14f1c1ccc4" + integrity sha512-C6fs3uejZwxB32c+XSmMvu3r4oesLILETRQcd+LKazY9YdCUy8S4QfnSdCW/gnfEmtB0qgLTxyMiHqMpzT9KHw== + dependencies: + "@glimmer/interfaces" "^0.36.5" + "@glimmer/syntax" "^0.36.5" + "@glimmer/util" "^0.36.5" + "@glimmer/wire-format" "^0.36.5" + "@glimmer/di@^0.2.0": version "0.2.1" resolved "https://registry.yarnpkg.com/@glimmer/di/-/di-0.2.1.tgz#5286b6b32040232b751138f6d006130c728d4b3d" integrity sha512-0D53YVuEgGdHfTl9LGWDZqVzGhn4cT0CXqyAuOYkKFLvqboJXz6SnkRhQNPhhA2hLVrPnvUz3+choQmPhHLGGQ== +"@glimmer/interfaces@^0.36.5": + version "0.36.5" + resolved "https://registry.yarnpkg.com/@glimmer/interfaces/-/interfaces-0.36.5.tgz#b9ef4a6756745dc41927ab01d6c23cdf7ece4158" + integrity sha512-IhoGEP0Awe9bTOMcLF9dUgEV3xguI6m2vFer7SHYX1vuugthA6NEJb83hqUe9FqOd1cNxJE8nAsX0JInx8gn+A== + dependencies: + "@glimmer/wire-format" "^0.36.5" + "@glimmer/resolver@^0.4.1": version "0.4.3" resolved "https://registry.yarnpkg.com/@glimmer/resolver/-/resolver-0.4.3.tgz#b1baae5c3291b4621002ccf8d7870466097e841d" @@ -613,6 +662,63 @@ dependencies: "@glimmer/di" "^0.2.0" +"@glimmer/syntax@^0.36.5": + version "0.36.5" + resolved "https://registry.yarnpkg.com/@glimmer/syntax/-/syntax-0.36.5.tgz#603099a0bf2019dc497e3b858eb6fc84abda805a" + integrity sha512-62BcnXtej4oBEMYSCBezSCOvlZ+1gLAJ/zVXwDgTmin56wKUL2bChScw332OeIL+brvcExAlwZ/hB1UoldMgwQ== + dependencies: + "@glimmer/interfaces" "^0.36.5" + "@glimmer/util" "^0.36.5" + handlebars "^4.0.6" + simple-html-tokenizer "^0.5.6" + +"@glimmer/util@^0.36.5": + version "0.36.5" + resolved "https://registry.yarnpkg.com/@glimmer/util/-/util-0.36.5.tgz#829f393ef0bf791df5b287f104f0fd76e456182c" + integrity sha512-RcDsxxuKGnIc6Ro6wZGFMUZ/E8L3Rbcd5E5F2WOSa59RYHel146fhQtctGrpGxQUZwfxMEMs91GJIaKeukd84g== + +"@glimmer/wire-format@^0.36.5": + version "0.36.5" + resolved "https://registry.yarnpkg.com/@glimmer/wire-format/-/wire-format-0.36.5.tgz#6713c95fbdc23c2e4dcc946e16452ded5cc17447" + integrity sha512-wt+H4iNsGPkW/b/POP21DmTM4cYYYcDmaI54RkEgtMRoeBP6hyi7Y4awbRPMWal6QKIxFepMUY4vnbq345m00w== + dependencies: + "@glimmer/util" "^0.36.5" + +"@mrmlnc/readdir-enhanced@^2.2.1": + version "2.2.1" + resolved "https://registry.yarnpkg.com/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz#524af240d1a360527b730475ecfa1344aa540dde" + integrity sha512-bPHp6Ji8b41szTOcaP63VlnbbO5Ny6dwAATtY6JTjh5N2OLrb5Qk/Th5cRkRQhkWCt+EJsYrNB0MiL+Gpn6e3g== + dependencies: + call-me-maybe "^1.0.1" + glob-to-regexp "^0.3.0" + +"@nodelib/fs.stat@^1.1.2": + version "1.1.3" + resolved "https://registry.yarnpkg.com/@nodelib/fs.stat/-/fs.stat-1.1.3.tgz#2b5a3ab3f918cca48a8c754c08168e3f03eba61b" + integrity sha512-shAmDyaQC4H92APFoIaVDHCx5bStIocgvbwQyxPRrbUY20V1EYTbSDchWbuwlMG3V17cprZhA6+78JfB+3DTPw== + +"@types/acorn@^4.0.3": + version "4.0.4" + resolved "https://registry.yarnpkg.com/@types/acorn/-/acorn-4.0.4.tgz#b3ee72dcd81d1daeea03fed67d7ca7c2574c313b" + integrity sha512-/qLQgGw/hzbpWpEiSrnNDqiVtw7J/wBEfWMWN8HPhOHUMINkL7ggOtj8VSyjfzXlNkoUbStomzKsLEATXcMSzg== + dependencies: + "@types/estree" "*" + +"@types/estree@*": + version "0.0.39" + resolved "https://registry.yarnpkg.com/@types/estree/-/estree-0.0.39.tgz#e177e699ee1b8c22d23174caaa7422644389509f" + integrity sha512-EYNwp3bU+98cpU4lAWYYL7Zz+2gryWH1qbdDTidVd6hkiR6weksdbMadyXKXNPEkQFhXM+hVO9ZygomHXp+AIw== + +"@types/estree@0.0.38": + version "0.0.38" + resolved "https://registry.yarnpkg.com/@types/estree/-/estree-0.0.38.tgz#c1be40aa933723c608820a99a373a16d215a1ca2" + integrity sha512-F/v7t1LwS4vnXuPooJQGBRKRGIoxWUTmA4VHfqjOccFsNDThD5bfUNpITive6s352O7o384wcpEaDV8rHCehDA== + +"@types/node@^9.6.0": + version "9.6.41" + resolved "https://registry.yarnpkg.com/@types/node/-/node-9.6.41.tgz#e57c3152eb2e7ec748c733cebd0c095b437c5d37" + integrity sha512-sPZWEbFMz6qAy9SLY7jh5cgepmsiwqUUHjvEm8lpU6kug2hmmcyuTnwhoGw/GWpI5Npue4EqvsiQQI0eWjW/ZA== + "@xg-wang/whatwg-fetch@^3.0.0": version "3.0.0" resolved "https://registry.yarnpkg.com/@xg-wang/whatwg-fetch/-/whatwg-fetch-3.0.0.tgz#f7b222c012a238e7d6e89ed3d72a1e0edb58453d" @@ -636,7 +742,7 @@ abbrev@1: resolved "https://registry.yarnpkg.com/abbrev/-/abbrev-1.1.1.tgz#f8f2c887ad10bf67f634f005b6987fed3179aac8" integrity sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q== -accepts@~1.3.3, accepts@~1.3.4, accepts@~1.3.5: +accepts@~1.3.4, accepts@~1.3.5: version "1.3.5" resolved "https://registry.yarnpkg.com/accepts/-/accepts-1.3.5.tgz#eb777df6011723a3b14e8a72c0805c8e86746bd2" integrity sha1-63d99gEXI6OxTopywIBcjoZ0a9I= @@ -644,6 +750,13 @@ accepts@~1.3.3, accepts@~1.3.4, accepts@~1.3.5: mime-types "~2.1.18" negotiator "0.6.1" +acorn-dynamic-import@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/acorn-dynamic-import/-/acorn-dynamic-import-3.0.0.tgz#901ceee4c7faaef7e07ad2a47e890675da50a278" + integrity sha512-zVWV8Z8lislJoOKKqdNMOB+s6+XV5WERty8MnKBeFgwA+19XJjJHs2RP5dzM57FftIs+jQnRToLiWazKr6sSWg== + dependencies: + acorn "^5.0.0" + acorn-dynamic-import@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/acorn-dynamic-import/-/acorn-dynamic-import-4.0.0.tgz#482210140582a36b83c3e342e1cfebcaa9240948" @@ -689,7 +802,7 @@ acorn@^4.0.3: resolved "https://registry.yarnpkg.com/acorn/-/acorn-4.0.13.tgz#105495ae5361d697bd195c825192e1ad7f253787" integrity sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c= -acorn@^5.0.3, acorn@^5.2.1, acorn@^5.5.0, acorn@^5.5.3: +acorn@^5.0.0, acorn@^5.0.3, acorn@^5.2.1, acorn@^5.5.0, acorn@^5.5.3: version "5.7.3" resolved "https://registry.yarnpkg.com/acorn/-/acorn-5.7.3.tgz#67aa231bf8812974b85235a96771eb6bd07ea279" integrity sha512-T/zvzYRfbVojPWahDsE5evJdHb3oJoQfFbsrKM7w5Zcs++Tr257tia3BmMP8XYVjp1S9RZXQMh7gao96BlqZOw== @@ -759,27 +872,6 @@ align-text@^0.1.1, align-text@^0.1.3: longest "^1.0.1" repeat-string "^1.5.2" -alter@~0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/alter/-/alter-0.2.0.tgz#c7588808617572034aae62480af26b1d4d1cb3cd" - integrity sha1-x1iICGF1cgNKrmJICvJrHU0cs80= - dependencies: - stable "~0.1.3" - -amd-name-resolver@0.0.7: - version "0.0.7" - resolved "https://registry.yarnpkg.com/amd-name-resolver/-/amd-name-resolver-0.0.7.tgz#814301adfe8a2f109f6e84d5e935196efb669615" - integrity sha1-gUMBrf6KLxCfboTV6TUZbvtmlhU= - dependencies: - ensure-posix-path "^1.0.1" - -amd-name-resolver@1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/amd-name-resolver/-/amd-name-resolver-1.0.0.tgz#0e593b28d6fa3326ab1798107edaea961046e8d8" - integrity sha1-Dlk7KNb6MyarF5gQftrqlhBG6Ng= - dependencies: - ensure-posix-path "^1.0.1" - amd-name-resolver@1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/amd-name-resolver/-/amd-name-resolver-1.2.0.tgz#fc41b3848824b557313897d71f8d5a0184fbe679" @@ -787,7 +879,7 @@ amd-name-resolver@1.2.0: dependencies: ensure-posix-path "^1.0.1" -amd-name-resolver@^1.2.1: +amd-name-resolver@^1.2.0, amd-name-resolver@^1.2.1: version "1.2.1" resolved "https://registry.yarnpkg.com/amd-name-resolver/-/amd-name-resolver-1.2.1.tgz#cea40abff394268307df647ce340c83eda6e9cfc" integrity sha512-cm0sUV2S8L6pwq0wpu0cHdA2KeEAmCVKy+R/qeZl/VxEn3JmU8WMM0IQrKyrnMXLXbULkZ7ptTaX8vKA0NhNvQ== @@ -854,14 +946,6 @@ ansicolors@~0.2.1: resolved "https://registry.yarnpkg.com/ansicolors/-/ansicolors-0.2.1.tgz#be089599097b74a5c9c4a84a0cdbcdb62bd87aef" integrity sha1-vgiVmQl7dKXJxKhKDNvNtivYeu8= -anymatch@^1.3.0: - version "1.3.2" - resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-1.3.2.tgz#553dcb8f91e3c889845dfdba34c77721b90b9d7a" - integrity sha512-0XNayC8lTHQ2OI8aljNCN3sSx6hsr/1+rlcDAotXJR7C1oZZHCNsfpbKwMjRA3Uqb5tF1Rae2oloTr4xpq+WjA== - dependencies: - micromatch "^2.1.5" - normalize-path "^2.0.0" - anymatch@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-2.0.0.tgz#bcb24b4f37934d9aa7ac17b4adaf89e7c76ef2eb" @@ -1015,7 +1099,7 @@ arraybuffer.slice@~0.0.7: resolved "https://registry.yarnpkg.com/arraybuffer.slice/-/arraybuffer.slice-0.0.7.tgz#3bbc4275dd584cc1b10809b89d4e8b63a69e7675" integrity sha512-wGUIVQXuehL5TCqQun8OW81jGzAWycqzFF8lFp+GOM5BXLYj3bKNsYC4daB7n6XjCqxQA/qgTJ+8ANR3acjrog== -arrify@^1.0.0: +arrify@^1.0.0, arrify@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/arrify/-/arrify-1.0.1.tgz#898508da2226f380df904728456849c1501a4b0d" integrity sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0= @@ -1063,26 +1147,11 @@ assign-symbols@^1.0.0: resolved "https://registry.yarnpkg.com/assign-symbols/-/assign-symbols-1.0.0.tgz#59667f41fadd4f20ccbc2bb96b8d4f7f78ec0367" integrity sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c= -ast-traverse@~0.1.1: - version "0.1.1" - resolved "https://registry.yarnpkg.com/ast-traverse/-/ast-traverse-0.1.1.tgz#69cf2b8386f19dcda1bb1e05d68fe359d8897de6" - integrity sha1-ac8rg4bxnc2hux4F1o/jWdiJfeY= - ast-types@0.10.1: version "0.10.1" resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.10.1.tgz#f52fca9715579a14f841d67d7f8d25432ab6a3dd" integrity sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ== -ast-types@0.8.12: - version "0.8.12" - resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.8.12.tgz#a0d90e4351bb887716c83fd637ebf818af4adfcc" - integrity sha1-oNkOQ1G7iHcWyD/WN+v4GK9K38w= - -ast-types@0.8.15: - version "0.8.15" - resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.8.15.tgz#8eef0827f04dff0ec8857ba925abe3fea6194e52" - integrity sha1-ju8IJ/BN/w7IhXupJavj/qYZTlI= - ast-types@0.9.6: version "0.9.6" resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.9.6.tgz#102c9e9e9005d3e7e3829bf0c4fa24ee862ee9b9" @@ -1133,7 +1202,7 @@ async@^2.0.0, async@^2.1.2: dependencies: lodash "^4.14.0" -async@^2.4.1: +async@^2.4.1, async@^2.5.0: version "2.6.1" resolved "https://registry.yarnpkg.com/async/-/async-2.6.1.tgz#b245a23ca71930044ec53fa46aa00a3e87c6a610" integrity sha512-fNEiL2+AZt6AlAw/29Cr0UDe4sRAHCpEHh54WMz+Bb7QfNcFw4h3loofyJpLeQs4Yx7yuqu/2dLgM5hKOs6HlQ== @@ -1179,58 +1248,6 @@ babel-code-frame@^6.22.0, babel-code-frame@^6.26.0: esutils "^2.0.2" js-tokens "^3.0.2" -babel-core@^5.0.0: - version "5.8.38" - resolved "https://registry.yarnpkg.com/babel-core/-/babel-core-5.8.38.tgz#1fcaee79d7e61b750b00b8e54f6dfc9d0af86558" - integrity sha1-H8ruedfmG3ULALjlT238nQr4ZVg= - dependencies: - babel-plugin-constant-folding "^1.0.1" - babel-plugin-dead-code-elimination "^1.0.2" - babel-plugin-eval "^1.0.1" - babel-plugin-inline-environment-variables "^1.0.1" - babel-plugin-jscript "^1.0.4" - babel-plugin-member-expression-literals "^1.0.1" - babel-plugin-property-literals "^1.0.1" - babel-plugin-proto-to-assign "^1.0.3" - babel-plugin-react-constant-elements "^1.0.3" - babel-plugin-react-display-name "^1.0.3" - babel-plugin-remove-console "^1.0.1" - babel-plugin-remove-debugger "^1.0.1" - babel-plugin-runtime "^1.0.7" - babel-plugin-undeclared-variables-check "^1.0.2" - babel-plugin-undefined-to-void "^1.1.6" - babylon "^5.8.38" - bluebird "^2.9.33" - chalk "^1.0.0" - convert-source-map "^1.1.0" - core-js "^1.0.0" - debug "^2.1.1" - detect-indent "^3.0.0" - esutils "^2.0.0" - fs-readdir-recursive "^0.1.0" - globals "^6.4.0" - home-or-tmp "^1.0.0" - is-integer "^1.0.4" - js-tokens "1.0.1" - json5 "^0.4.0" - lodash "^3.10.0" - minimatch "^2.0.3" - output-file-sync "^1.1.0" - path-exists "^1.0.0" - path-is-absolute "^1.0.0" - private "^0.1.6" - regenerator "0.8.40" - regexpu "^1.3.0" - repeating "^1.1.2" - resolve "^1.1.6" - shebang-regex "^1.0.0" - slash "^1.0.0" - source-map "^0.5.0" - source-map-support "^0.2.10" - to-fast-properties "^1.0.0" - trim-right "^1.0.0" - try-resolve "^1.0.0" - babel-core@^6.24.1, babel-core@^6.26.0: version "6.26.3" resolved "https://registry.yarnpkg.com/babel-core/-/babel-core-6.26.3.tgz#b2e2f09e342d0f0c88e2f02e067794125e75c207" @@ -1397,16 +1414,6 @@ babel-plugin-check-es2015-constants@^6.22.0: dependencies: babel-runtime "^6.22.0" -babel-plugin-constant-folding@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-constant-folding/-/babel-plugin-constant-folding-1.0.1.tgz#8361d364c98e449c3692bdba51eff0844290aa8e" - integrity sha1-g2HTZMmORJw2kr26Ue/whEKQqo4= - -babel-plugin-dead-code-elimination@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/babel-plugin-dead-code-elimination/-/babel-plugin-dead-code-elimination-1.0.2.tgz#5f7c451274dcd7cccdbfbb3e0b85dd28121f0f65" - integrity sha1-X3xFEnTc18zNv7s+C4XdKBIfD2U= - babel-plugin-debug-macros@^0.1.10: version "0.1.11" resolved "https://registry.yarnpkg.com/babel-plugin-debug-macros/-/babel-plugin-debug-macros-0.1.11.tgz#6c562bf561fccd406ce14ab04f42c218cf956605" @@ -1414,20 +1421,13 @@ babel-plugin-debug-macros@^0.1.10: dependencies: semver "^5.3.0" -babel-plugin-debug-macros@^0.2.0-beta.6: +babel-plugin-debug-macros@^0.2.0, babel-plugin-debug-macros@^0.2.0-beta.6: version "0.2.0" resolved "https://registry.yarnpkg.com/babel-plugin-debug-macros/-/babel-plugin-debug-macros-0.2.0.tgz#0120ac20ce06ccc57bf493b667cf24b85c28da7a" integrity sha512-Wpmw4TbhR3Eq2t3W51eBAQSdKlr+uAyF0GI4GtPfMCD12Y4cIdpKC9l0RjNTH/P9isFypSqqewMPm7//fnZlNA== dependencies: semver "^5.3.0" -babel-plugin-ember-modules-api-polyfill@^1.4.2: - version "1.6.0" - resolved "https://registry.yarnpkg.com/babel-plugin-ember-modules-api-polyfill/-/babel-plugin-ember-modules-api-polyfill-1.6.0.tgz#abd1afa4237b3121cb51222f9bf3283cad8990aa" - integrity sha512-HIOU4QBiselFqEvx6QaKrS/zxnfRQygQyA8wGdVUd42zO26G0jUqbEr1IE/NkTAbP4zsF0sY/ZLtVpjYiVB3VQ== - dependencies: - ember-rfc176-data "^0.2.0" - babel-plugin-ember-modules-api-polyfill@^2.5.0, babel-plugin-ember-modules-api-polyfill@^2.6.0: version "2.6.0" resolved "https://registry.yarnpkg.com/babel-plugin-ember-modules-api-polyfill/-/babel-plugin-ember-modules-api-polyfill-2.6.0.tgz#9524a65ef0c31ee82536a19c243fbaec1b977cbb" @@ -1435,11 +1435,6 @@ babel-plugin-ember-modules-api-polyfill@^2.5.0, babel-plugin-ember-modules-api-p dependencies: ember-rfc176-data "^0.3.6" -babel-plugin-eval@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-eval/-/babel-plugin-eval-1.0.1.tgz#a2faed25ce6be69ade4bfec263f70169195950da" - integrity sha1-ovrtJc5r5preS/7CY/cBaRlZUNo= - babel-plugin-feature-flags@^0.3.1: version "0.3.1" resolved "https://registry.yarnpkg.com/babel-plugin-feature-flags/-/babel-plugin-feature-flags-0.3.1.tgz#9c827cf9a4eb9a19f725ccb239e85cab02036fc1" @@ -1450,31 +1445,11 @@ babel-plugin-filter-imports@^0.3.1: resolved "https://registry.yarnpkg.com/babel-plugin-filter-imports/-/babel-plugin-filter-imports-0.3.1.tgz#e7859b56886b175dd2616425d277b219e209ea8b" integrity sha1-54WbVohrF13SYWQl0neyGeIJ6os= -babel-plugin-htmlbars-inline-precompile@^0.1.0: - version "0.1.1" - resolved "https://registry.yarnpkg.com/babel-plugin-htmlbars-inline-precompile/-/babel-plugin-htmlbars-inline-precompile-0.1.1.tgz#a878c1771224429dd6e546ba6d39c2c35073be92" - integrity sha512-uG5QNBSmVOXwgOKo1pHXxTS47GppolC9FOzpiAcU5BbD/P/SrJ08XUY6PBttul4DvfmyhdYdh6cTCBxDTB7Etw== - babel-plugin-htmlbars-inline-precompile@^0.2.5: version "0.2.6" resolved "https://registry.yarnpkg.com/babel-plugin-htmlbars-inline-precompile/-/babel-plugin-htmlbars-inline-precompile-0.2.6.tgz#c00b8a3f4b32ca04bf0f0d5169fcef3b5a66d69d" integrity sha512-H4H75TKGUFij8ukwEYWEERAgrUf16R8NSK1uDPe3QwxT8mnE1K8+/s6DVjUqbM5Pv6lSIcE4XufXdlSX+DTB6g== -babel-plugin-inline-environment-variables@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-inline-environment-variables/-/babel-plugin-inline-environment-variables-1.0.1.tgz#1f58ce91207ad6a826a8bf645fafe68ff5fe3ffe" - integrity sha1-H1jOkSB61qgmqL9kX6/mj/X+P/4= - -babel-plugin-jscript@^1.0.4: - version "1.0.4" - resolved "https://registry.yarnpkg.com/babel-plugin-jscript/-/babel-plugin-jscript-1.0.4.tgz#8f342c38276e87a47d5fa0a8bd3d5eb6ccad8fcc" - integrity sha1-jzQsOCduh6R9X6CovT1etsytj8w= - -babel-plugin-member-expression-literals@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-member-expression-literals/-/babel-plugin-member-expression-literals-1.0.1.tgz#cc5edb0faa8dc927170e74d6d1c02440021624d3" - integrity sha1-zF7bD6qNyScXDnTW0cAkQAIWJNM= - babel-plugin-module-resolver@^3.1.1: version "3.1.1" resolved "https://registry.yarnpkg.com/babel-plugin-module-resolver/-/babel-plugin-module-resolver-3.1.1.tgz#881cf67e3d4b8400d5eaaefc1be44d2dc1fe404f" @@ -1486,43 +1461,6 @@ babel-plugin-module-resolver@^3.1.1: reselect "^3.0.1" resolve "^1.4.0" -babel-plugin-property-literals@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-property-literals/-/babel-plugin-property-literals-1.0.1.tgz#0252301900192980b1c118efea48ce93aab83336" - integrity sha1-AlIwGQAZKYCxwRjv6kjOk6q4MzY= - -babel-plugin-proto-to-assign@^1.0.3: - version "1.0.4" - resolved "https://registry.yarnpkg.com/babel-plugin-proto-to-assign/-/babel-plugin-proto-to-assign-1.0.4.tgz#c49e7afd02f577bc4da05ea2df002250cf7cd123" - integrity sha1-xJ56/QL1d7xNoF6i3wAiUM980SM= - dependencies: - lodash "^3.9.3" - -babel-plugin-react-constant-elements@^1.0.3: - version "1.0.3" - resolved "https://registry.yarnpkg.com/babel-plugin-react-constant-elements/-/babel-plugin-react-constant-elements-1.0.3.tgz#946736e8378429cbc349dcff62f51c143b34e35a" - integrity sha1-lGc26DeEKcvDSdz/YvUcFDs041o= - -babel-plugin-react-display-name@^1.0.3: - version "1.0.3" - resolved "https://registry.yarnpkg.com/babel-plugin-react-display-name/-/babel-plugin-react-display-name-1.0.3.tgz#754fe38926e8424a4e7b15ab6ea6139dee0514fc" - integrity sha1-dU/jiSboQkpOexWrbqYTne4FFPw= - -babel-plugin-remove-console@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-remove-console/-/babel-plugin-remove-console-1.0.1.tgz#d8f24556c3a05005d42aaaafd27787f53ff013a7" - integrity sha1-2PJFVsOgUAXUKqqv0neH9T/wE6c= - -babel-plugin-remove-debugger@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/babel-plugin-remove-debugger/-/babel-plugin-remove-debugger-1.0.1.tgz#fd2ea3cd61a428ad1f3b9c89882ff4293e8c14c7" - integrity sha1-/S6jzWGkKK0fO5yJiC/0KT6MFMc= - -babel-plugin-runtime@^1.0.7: - version "1.0.7" - resolved "https://registry.yarnpkg.com/babel-plugin-runtime/-/babel-plugin-runtime-1.0.7.tgz#bf7c7d966dd56ecd5c17fa1cb253c9acb7e54aaf" - integrity sha1-v3x9lm3Vbs1cF/ocslPJrLflSq8= - babel-plugin-syntax-async-functions@^6.8.0: version "6.13.0" resolved "https://registry.yarnpkg.com/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz#cad9cad1191b5ad634bf30ae0872391e0647be95" @@ -1561,7 +1499,7 @@ babel-plugin-transform-es2015-block-scoped-functions@^6.22.0: dependencies: babel-runtime "^6.22.0" -babel-plugin-transform-es2015-block-scoping@^6.23.0, babel-plugin-transform-es2015-block-scoping@^6.24.1: +babel-plugin-transform-es2015-block-scoping@^6.23.0, babel-plugin-transform-es2015-block-scoping@^6.26.0: version "6.26.0" resolved "https://registry.yarnpkg.com/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz#d70f5299c1308d05c12f463813b0a09e73b1895f" integrity sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8= @@ -1761,18 +1699,6 @@ babel-plugin-transform-strict-mode@^6.24.1: babel-runtime "^6.22.0" babel-types "^6.24.1" -babel-plugin-undeclared-variables-check@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/babel-plugin-undeclared-variables-check/-/babel-plugin-undeclared-variables-check-1.0.2.tgz#5cf1aa539d813ff64e99641290af620965f65dee" - integrity sha1-XPGqU52BP/ZOmWQSkK9iCWX2Xe4= - dependencies: - leven "^1.0.2" - -babel-plugin-undefined-to-void@^1.1.6: - version "1.1.6" - resolved "https://registry.yarnpkg.com/babel-plugin-undefined-to-void/-/babel-plugin-undefined-to-void-1.1.6.tgz#7f578ef8b78dfae6003385d8417a61eda06e2f81" - integrity sha1-f1eO+LeN+uYAM4XYQXph7aBuL4E= - babel-polyfill@^6.26.0: version "6.26.0" resolved "https://registry.yarnpkg.com/babel-polyfill/-/babel-polyfill-6.26.0.tgz#379937abc67d7895970adc621f284cd966cf2153" @@ -1885,11 +1811,6 @@ babel6-plugin-strip-heimdall@^6.0.1: resolved "https://registry.yarnpkg.com/babel6-plugin-strip-heimdall/-/babel6-plugin-strip-heimdall-6.0.1.tgz#35f80eddec1f7fffdc009811dfbd46d9965072b6" integrity sha1-NfgO3ewff//cAJgR371G2ZZQcrY= -babylon@^5.8.38: - version "5.8.38" - resolved "https://registry.yarnpkg.com/babylon/-/babylon-5.8.38.tgz#ec9b120b11bf6ccd4173a18bf217e60b79859ffd" - integrity sha1-7JsSCxG/bM1Bc6GL8hfmC3mFn/0= - babylon@^6.18.0: version "6.18.0" resolved "https://registry.yarnpkg.com/babylon/-/babylon-6.18.0.tgz#af2f3b88fa6f5c1e4c634d1a0f8eac4f55b395e3" @@ -1940,10 +1861,12 @@ base@^0.11.1: mixin-deep "^1.2.0" pascalcase "^0.1.1" -basic-auth@~1.1.0: - version "1.1.0" - resolved "https://registry.yarnpkg.com/basic-auth/-/basic-auth-1.1.0.tgz#45221ee429f7ee1e5035be3f51533f1cdfd29884" - integrity sha1-RSIe5Cn37h5QNb4/UVM/HN/SmIQ= +basic-auth@~2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/basic-auth/-/basic-auth-2.0.1.tgz#b998279bf47ce38344b4f3cf916d4679bbf51e3a" + integrity sha512-NF+epuEdnUYVlGuhaxbbq+dvJttwLnGY+YixlXlME5KpQ5W3CnXA5cVTneY3SPbPDRkcjMbifrwmFYcClgOZeg== + dependencies: + safe-buffer "5.1.2" bcrypt-pbkdf@^1.0.0: version "1.0.2" @@ -1981,11 +1904,6 @@ blob@0.0.5: resolved "https://registry.yarnpkg.com/blob/-/blob-0.0.5.tgz#d680eeef25f8cd91ad533f5b01eed48e64caf683" integrity sha512-gaqbzQPqOoamawKg0LGVd7SzLgXS+JH61oWprSLH+P+abTczqJbhTR8CmJ2u9/bUYNmHTGJx/UEmn6doAvvuig== -bluebird@^2.9.33: - version "2.11.0" - resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-2.11.0.tgz#534b9033c022c9579c56ba3b3e5a5caafbb650e1" - integrity sha1-U0uQM8AiyVecVro7Plpcqvu2UOE= - bluebird@^3.1.1, bluebird@^3.4.6: version "3.5.3" resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.5.3.tgz#7d01c6f9616c9a51ab0f8c549a79dfe6ec33efa7" @@ -2073,7 +1991,7 @@ bower-endpoint-parser@0.2.2: resolved "https://registry.yarnpkg.com/bower-endpoint-parser/-/bower-endpoint-parser-0.2.2.tgz#00b565adbfab6f2d35addde977e97962acbcb3f6" integrity sha1-ALVlrb+rby01rd3pd+l5Yqy8s/Y= -brace-expansion@^1.0.0, brace-expansion@^1.1.7: +brace-expansion@^1.1.7: version "1.1.11" resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== @@ -2106,28 +2024,15 @@ braces@^2.3.1: split-string "^3.0.2" to-regex "^3.0.1" -breakable@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/breakable/-/breakable-1.0.0.tgz#784a797915a38ead27bad456b5572cb4bbaa78c1" - integrity sha1-eEp5eRWjjq0nutRWtVcstLuqeME= - -broccoli-babel-transpiler@^5.6.2: - version "5.7.4" - resolved "https://registry.yarnpkg.com/broccoli-babel-transpiler/-/broccoli-babel-transpiler-5.7.4.tgz#2b0611ce9e5d98b8d8d2b49ae1219af2f52767e3" - integrity sha512-gI14Pqc4qbmn5RW4SuAmybLiOoYW59D+HzQyhY6WdaGMAjikKBwJN0p17phyvafQ+kvG0mUiMd83lgHLeATnEA== +broccoli-amd-funnel@^1.3.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/broccoli-amd-funnel/-/broccoli-amd-funnel-1.3.0.tgz#c4426b4fce976e44295bd74f34725f53bdeb08e3" + integrity sha512-QLjCWblDW//a/5/ivDikVPRHiA+d/1K45meHZA6lAlpHC1c216rcZQYpdlo9PiOJiI4T3tKqDaaM1CDeFDCoVQ== dependencies: - babel-core "^5.0.0" - broccoli-funnel "^1.0.0" - broccoli-merge-trees "^1.0.0" - broccoli-persistent-filter "^1.4.2" - clone "^0.2.0" - hash-for-dep "^1.0.2" - heimdalljs-logger "^0.1.7" - json-stable-stringify "^1.0.0" - rsvp "^3.5.0" - workerpool "^2.3.0" + broccoli-plugin "^1.3.0" + symlink-or-copy "^1.2.0" -broccoli-babel-transpiler@^6.0.0, broccoli-babel-transpiler@^6.5.0: +broccoli-babel-transpiler@^6.5.0: version "6.5.1" resolved "https://registry.yarnpkg.com/broccoli-babel-transpiler/-/broccoli-babel-transpiler-6.5.1.tgz#a4afc8d3b59b441518eb9a07bd44149476e30738" integrity sha512-w6GcnkxvHcNCte5FcLGEG1hUdQvlfvSN/6PtGWU/otg69Ugk8rUk51h41R0Ugoc+TNxyeFG1opRt2RlA87XzNw== @@ -2159,18 +2064,12 @@ broccoli-babel-transpiler@^7.1.0: rsvp "^4.8.3" workerpool "^2.3.1" -broccoli-brocfile-loader@^0.18.0: - version "0.18.0" - resolved "https://registry.yarnpkg.com/broccoli-brocfile-loader/-/broccoli-brocfile-loader-0.18.0.tgz#2e86021c805c34ffc8d29a2fb721cf273e819e4b" - integrity sha1-LoYCHIBcNP/I0povtyHPJz6Bnks= - dependencies: - findup-sync "^0.4.2" - -broccoli-builder@^0.18.8: - version "0.18.8" - resolved "https://registry.yarnpkg.com/broccoli-builder/-/broccoli-builder-0.18.8.tgz#fe54694d544c3cdfdb01028e802eeca65749a879" - integrity sha1-/lRpTVRMPN/bAQKOgC7spldJqHk= +broccoli-builder@^0.18.14: + version "0.18.14" + resolved "https://registry.yarnpkg.com/broccoli-builder/-/broccoli-builder-0.18.14.tgz#4b79e2f844de11a4e1b816c3f49c6df4776c312d" + integrity sha1-S3ni+ETeEaThuBbD9Jxt9HdsMS0= dependencies: + broccoli-node-info "^1.1.0" heimdalljs "^0.2.0" promise-map-series "^0.2.1" quick-temp "^0.1.2" @@ -2178,7 +2077,7 @@ broccoli-builder@^0.18.8: rsvp "^3.0.17" silent-error "^1.0.1" -broccoli-caching-writer@^2.0.4, broccoli-caching-writer@^2.2.0, broccoli-caching-writer@^2.3.1: +broccoli-caching-writer@^2.2.0, broccoli-caching-writer@^2.3.1: version "2.3.1" resolved "https://registry.yarnpkg.com/broccoli-caching-writer/-/broccoli-caching-writer-2.3.1.tgz#b93cf58f9264f003075868db05774f4e7f25bd07" integrity sha1-uTz1j5Jk8AMHWGjbBXdPTn8lvQc= @@ -2230,12 +2129,30 @@ broccoli-concat@^3.2.2: lodash.uniq "^4.2.0" walk-sync "^0.3.1" -broccoli-config-loader@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/broccoli-config-loader/-/broccoli-config-loader-1.0.0.tgz#c3cf5ecfaffc04338c6f1d5d38dc36baeaa131ba" - integrity sha1-w89ez6/8BDOMbx1dONw2uuqhMbo= +broccoli-concat@^3.5.1, broccoli-concat@^3.7.1: + version "3.7.3" + resolved "https://registry.yarnpkg.com/broccoli-concat/-/broccoli-concat-3.7.3.tgz#0dca01311567ffb13180e6b4eb111824628e4885" + integrity sha512-2Ma9h81EJ0PRb9n4sW0i8KZlcnpTQfKxcj87zvi5DFe1fd8CTDEdseHDotK2beuA2l+LbgVPfd8EHaBJKm/Y8g== dependencies: - broccoli-caching-writer "^2.0.4" + broccoli-debug "^0.6.5" + broccoli-kitchen-sink-helpers "^0.3.1" + broccoli-plugin "^1.3.0" + ensure-posix-path "^1.0.2" + fast-sourcemap-concat "^1.4.0" + find-index "^1.1.0" + fs-extra "^4.0.3" + fs-tree-diff "^0.5.7" + lodash.merge "^4.3.1" + lodash.omit "^4.1.0" + lodash.uniq "^4.2.0" + walk-sync "^0.3.2" + +broccoli-config-loader@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/broccoli-config-loader/-/broccoli-config-loader-1.0.1.tgz#d10aaf8ebc0cb45c1da5baa82720e1d88d28c80a" + integrity sha512-MDKYQ50rxhn+g17DYdfzfEM9DjTuSGu42Db37A8TQHQe8geYEcUZ4SQqZRgzdAI3aRQNlA1yBHJfOeGmOjhLIg== + dependencies: + broccoli-caching-writer "^3.0.3" broccoli-config-replace@^1.1.2: version "1.1.2" @@ -2247,7 +2164,7 @@ broccoli-config-replace@^1.1.2: debug "^2.2.0" fs-extra "^0.24.0" -broccoli-debug@^0.6.1, broccoli-debug@^0.6.2, broccoli-debug@^0.6.3, broccoli-debug@^0.6.4, broccoli-debug@^0.6.5: +broccoli-debug@^0.6.1, broccoli-debug@^0.6.3, broccoli-debug@^0.6.4, broccoli-debug@^0.6.5: version "0.6.5" resolved "https://registry.yarnpkg.com/broccoli-debug/-/broccoli-debug-0.6.5.tgz#164a5cdafd8936e525e702bf8f91f39d758e2e78" integrity sha512-RIVjHvNar9EMCLDW/FggxFRXqpjhncM/3qq87bn/y+/zR9tqEkHvTqbyOc4QnB97NO2m6342w4wGkemkaeOuWg== @@ -2259,7 +2176,7 @@ broccoli-debug@^0.6.1, broccoli-debug@^0.6.2, broccoli-debug@^0.6.3, broccoli-de symlink-or-copy "^1.1.8" tree-sync "^1.2.2" -broccoli-file-creator@^1.0.0, broccoli-file-creator@^1.1.1: +broccoli-file-creator@^1.1.1: version "1.2.0" resolved "https://registry.yarnpkg.com/broccoli-file-creator/-/broccoli-file-creator-1.2.0.tgz#27f1b25b1b00e7bb7bf3d5d7abed5f4d5388df4d" integrity sha512-l9zthHg6bAtnOfRr/ieZ1srRQEsufMZID7xGYRW3aBDv3u/3Eux+Iawl10tAGYE5pL9YB4n5X4vxkp6iNOoZ9g== @@ -2280,7 +2197,7 @@ broccoli-funnel-reducer@^1.0.0: resolved "https://registry.yarnpkg.com/broccoli-funnel-reducer/-/broccoli-funnel-reducer-1.0.0.tgz#11365b2a785aec9b17972a36df87eef24c5cc0ea" integrity sha1-ETZbKnha7JsXlyo234fu8kxcwOo= -broccoli-funnel@^1.0.0, broccoli-funnel@^1.0.1, broccoli-funnel@^1.0.2, broccoli-funnel@^1.1.0, broccoli-funnel@^1.2.0: +broccoli-funnel@^1.0.0, broccoli-funnel@^1.0.1, broccoli-funnel@^1.0.2, broccoli-funnel@^1.1.0: version "1.2.0" resolved "https://registry.yarnpkg.com/broccoli-funnel/-/broccoli-funnel-1.2.0.tgz#cddc3afc5ff1685a8023488fff74ce6fb5a51296" integrity sha1-zdw6/F/xaFqAI0iP/3TOb7WlEpY= @@ -2389,22 +2306,47 @@ broccoli-merge-trees@^3.0.0, broccoli-merge-trees@^3.0.1: broccoli-plugin "^1.3.0" merge-trees "^2.0.0" -broccoli-middleware@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/broccoli-middleware/-/broccoli-middleware-1.0.0.tgz#92f4e1fb9a791ea986245a7077f35cc648dab097" - integrity sha1-kvTh+5p5HqmGJFpwd/NcxkjasJc= +broccoli-middleware@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/broccoli-middleware/-/broccoli-middleware-2.0.1.tgz#093314f13e52fad7fa8c4254a4e4a4560c857a65" + integrity sha512-V/K5uozcEH/XJ09ZAL8aJt/W2UwJU8I8fA2FAg3u9gzs5dQrehHDtgSoKS2QjPjurRC1GSiYLcsMp36sezaQQg== dependencies: handlebars "^4.0.4" - mime "^1.2.11" + mime-types "^2.1.18" -broccoli-persistent-filter@^1.0.3, broccoli-persistent-filter@^1.1.6, broccoli-persistent-filter@^1.4.2, broccoli-persistent-filter@^1.4.3: - version "1.4.6" - resolved "https://registry.yarnpkg.com/broccoli-persistent-filter/-/broccoli-persistent-filter-1.4.6.tgz#80762d19000880a77da33c34373299c0f6a3e615" - integrity sha512-0RejLwoC95kv4kta8KAa+FmECJCK78Qgm8SRDEK7YyU0N9Cx6KpY3UCDy9WELl3mCXLN8TokNxc7/hp3lL4lfw== +broccoli-module-normalizer@^1.3.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/broccoli-module-normalizer/-/broccoli-module-normalizer-1.3.0.tgz#f9982d9cbb776b4ed754161cc6547784d3eb19de" + integrity sha512-0idZCOtdVG6xXoQ36Psc1ApMCr3lW5DB+WEAOEwHcUoESIBHzwcRPQTxheGIjZ5o0hxpsRYAUH5x0ErtNezbrQ== + dependencies: + broccoli-plugin "^1.3.0" + merge-trees "^1.0.1" + rimraf "^2.6.2" + symlink-or-copy "^1.1.8" + +broccoli-module-unification-reexporter@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/broccoli-module-unification-reexporter/-/broccoli-module-unification-reexporter-1.0.0.tgz#031909c5d3f159ec11d5f9e2346f2861db8acb3e" + integrity sha512-HTi9ua520M20aBZomaiBopsSt3yjL7J/paR3XPjieygK7+ShATBiZdn0B+ZPiniBi4I8JuMn1q0fNFUevtP//A== + dependencies: + broccoli-plugin "^1.3.0" + mkdirp "^0.5.1" + walk-sync "^0.3.2" + +broccoli-node-info@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/broccoli-node-info/-/broccoli-node-info-1.1.0.tgz#3aa2e31e07e5bdb516dd25214f7c45ba1c459412" + integrity sha1-OqLjHgflvbUW3SUhT3xFuhxFlBI= + +broccoli-persistent-filter@^1.1.5: + version "1.4.2" + resolved "https://registry.yarnpkg.com/broccoli-persistent-filter/-/broccoli-persistent-filter-1.4.2.tgz#17af1278a25ff2556f9d7d23e115accfad3a7ce7" + integrity sha1-F68SeKJf8lVvnX0j4RWsz606fOc= dependencies: async-disk-cache "^1.2.1" async-promise-queue "^1.0.3" broccoli-plugin "^1.0.0" + crypto "0.0.3" fs-tree-diff "^0.5.2" hash-for-dep "^1.0.2" heimdalljs "^0.2.1" @@ -2416,15 +2358,14 @@ broccoli-persistent-filter@^1.0.3, broccoli-persistent-filter@^1.1.6, broccoli-p symlink-or-copy "^1.0.1" walk-sync "^0.3.1" -broccoli-persistent-filter@^1.1.5: - version "1.4.2" - resolved "https://registry.yarnpkg.com/broccoli-persistent-filter/-/broccoli-persistent-filter-1.4.2.tgz#17af1278a25ff2556f9d7d23e115accfad3a7ce7" - integrity sha1-F68SeKJf8lVvnX0j4RWsz606fOc= +broccoli-persistent-filter@^1.1.6, broccoli-persistent-filter@^1.4.3: + version "1.4.6" + resolved "https://registry.yarnpkg.com/broccoli-persistent-filter/-/broccoli-persistent-filter-1.4.6.tgz#80762d19000880a77da33c34373299c0f6a3e615" + integrity sha512-0RejLwoC95kv4kta8KAa+FmECJCK78Qgm8SRDEK7YyU0N9Cx6KpY3UCDy9WELl3mCXLN8TokNxc7/hp3lL4lfw== dependencies: async-disk-cache "^1.2.1" async-promise-queue "^1.0.3" broccoli-plugin "^1.0.0" - crypto "0.0.3" fs-tree-diff "^0.5.2" hash-for-dep "^1.0.2" heimdalljs "^0.2.1" @@ -2485,20 +2426,20 @@ broccoli-plugin@^1.2.0: rimraf "^2.3.4" symlink-or-copy "^1.1.8" -broccoli-rollup@^1.2.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/broccoli-rollup/-/broccoli-rollup-1.3.0.tgz#43a0a7798555bab54217009eb470a4ff5a056df0" - integrity sha1-Q6CneYVVurVCFwCetHCk/1oFbfA= +broccoli-rollup@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/broccoli-rollup/-/broccoli-rollup-2.1.1.tgz#0b77dc4b7560a53e998ea85f3b56772612d4988d" + integrity sha512-aky/Ovg5DbsrsJEx2QCXxHLA6ZR+9u1TNVTf85soP4gL8CjGGKQ/JU8R3BZ2ntkWzo6/83RCKzX6O+nlNKR5MQ== dependencies: + "@types/node" "^9.6.0" + amd-name-resolver "^1.2.0" broccoli-plugin "^1.2.1" - es6-map "^0.1.4" - fs-extra "^0.30.0" fs-tree-diff "^0.5.2" heimdalljs "^0.2.1" heimdalljs-logger "^0.1.7" - md5-hex "^1.3.0" + magic-string "^0.24.0" node-modules-path "^1.0.1" - rollup "^0.41.4" + rollup "^0.57.1" symlink-or-copy "^1.1.8" walk-sync "^0.3.1" @@ -2525,7 +2466,7 @@ broccoli-sri-hash@^2.1.0: sri-toolbox "^0.2.0" symlink-or-copy "^1.0.1" -broccoli-stew@^1.2.0, broccoli-stew@^1.3.3: +broccoli-stew@^1.3.3: version "1.4.0" resolved "https://registry.yarnpkg.com/broccoli-stew/-/broccoli-stew-1.4.0.tgz#1bdb0a1804d62a419d190abc26acb3c91878154d" integrity sha1-G9sKGATWKkGdGQq8JqyzyRh4FU0= @@ -2765,13 +2706,6 @@ browserslist@^4.3.4: electron-to-chromium "^1.3.92" node-releases "^1.1.1" -bser@1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/bser/-/bser-1.0.2.tgz#381116970b2a6deea5646dd15dd7278444b56169" - integrity sha1-OBEWlwsqbe6lZG3RXdcnhES1YWk= - dependencies: - node-int64 "^0.4.0" - bser@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/bser/-/bser-2.0.0.tgz#9ac78d3ed5d915804fd87acb158bc797147a1719" @@ -2779,11 +2713,29 @@ bser@^2.0.0: dependencies: node-int64 "^0.4.0" +buffer-alloc-unsafe@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz#bd7dc26ae2972d0eda253be061dba992349c19f0" + integrity sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg== + +buffer-alloc@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/buffer-alloc/-/buffer-alloc-1.2.0.tgz#890dd90d923a873e08e10e5fd51a57e5b7cce0ec" + integrity sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow== + dependencies: + buffer-alloc-unsafe "^1.1.0" + buffer-fill "^1.0.0" + buffer-crc32@^0.2.1: version "0.2.13" resolved "https://registry.yarnpkg.com/buffer-crc32/-/buffer-crc32-0.2.13.tgz#0d333e3f00eac50aa1454abd30ef8c2a5d9a7242" integrity sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI= +buffer-fill@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/buffer-fill/-/buffer-fill-1.0.0.tgz#f8f78b76789888ef39f205cd637f68e702122b2c" + integrity sha1-+PeLdniYiO858gXNY39o5wISKyw= + buffer-from@^1.0.0: version "1.1.1" resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.1.tgz#32713bc028f75c02fdb710d7c7bcec1f2c6070ef" @@ -2823,11 +2775,6 @@ bytes@1: resolved "https://registry.yarnpkg.com/bytes/-/bytes-1.0.0.tgz#3569ede8ba34315fab99c3e92cb04c7220de1fa8" integrity sha1-NWnt6Lo0MV+rmcPpLLBMciDeH6g= -bytes@2.3.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/bytes/-/bytes-2.3.0.tgz#d5b680a165b6201739acb611542aabc2d8ceb070" - integrity sha1-1baAoWW2IBc5rLYRVCqrwtjOsHA= - bytes@2.4.0: version "2.4.0" resolved "https://registry.yarnpkg.com/bytes/-/bytes-2.4.0.tgz#7d97196f9d5baf7f6935e25985549edd2a6c2339" @@ -2858,13 +2805,18 @@ cached-path-relative@^1.0.0: resolved "https://registry.yarnpkg.com/cached-path-relative/-/cached-path-relative-1.0.2.tgz#a13df4196d26776220cc3356eb147a52dba2c6db" integrity sha512-5r2GqsoEb4qMTTN9J+WzXfjov+hjxT+j3u5K+kIVNIwAd99DLCJE9pBIMP1qVeybV6JiijL385Oz0DcYxfbOIg== -calculate-cache-key-for-tree@^1.0.0, calculate-cache-key-for-tree@^1.1.0: +calculate-cache-key-for-tree@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/calculate-cache-key-for-tree/-/calculate-cache-key-for-tree-1.1.0.tgz#0c3e42c9c134f3c9de5358c0f16793627ea976d6" integrity sha1-DD5CycE088neU1jA8WeTYn6pdtY= dependencies: json-stable-stringify "^1.0.1" +call-me-maybe@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/call-me-maybe/-/call-me-maybe-1.0.1.tgz#26d208ea89e37b5cbde60250a15f031c16a4d66b" + integrity sha1-JtII6onje1y95gJQoV8DHBak1ms= + caller-path@^0.1.0: version "0.1.0" resolved "https://registry.yarnpkg.com/caller-path/-/caller-path-0.1.0.tgz#94085ef63581ecd3daa92444a8fe94e82577751f" @@ -2890,7 +2842,7 @@ camelcase-keys@^2.0.0: camelcase "^2.0.0" map-obj "^1.0.0" -camelcase@^1.0.2, camelcase@^1.2.1: +camelcase@^1.0.2: version "1.2.1" resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-1.2.1.tgz#9bb5304d2e0b56698b2c758b08a3eaa9daa58a39" integrity sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk= @@ -2917,7 +2869,7 @@ caniuse-lite@^1.0.30000844, caniuse-lite@^1.0.30000921: resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30000925.tgz#f1a3b9aae2a83071b1eccfa39959d72440409b08" integrity sha512-zcYupoUxtW46rOikuDF7vfL9N1Qe9ZuUBTz3n3q8fFsoJIs/h9UN6Vg/0QpjsmvImXw9mVc3g+ZBfqvUz/iALA== -capture-exit@^1.1.0, capture-exit@^1.2.0: +capture-exit@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/capture-exit/-/capture-exit-1.2.0.tgz#1c5fcc489fd0ab00d4f1ac7ae1072e3173fbab6f" integrity sha1-HF/MSJ/QqwDU8ax64QcuMXP7q28= @@ -3026,6 +2978,11 @@ chownr@^1.1.1: resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.1.tgz#54726b8b8fff4df053c42187e801fb4412df1494" integrity sha512-j38EvO5+LHX84jlo6h4UzmOwi0UgW61WRyPtJz4qaadK5eY3BTS5TY/S1Stc3Uk2lIM6TPevAlULiEJwie860g== +ci-info@^1.1.3: + version "1.6.0" + resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-1.6.0.tgz#2ca20dbb9ceb32d4524a683303313f0304b1e497" + integrity sha512-vsGdkwSCDpWmP80ncATX7iea5DWQemg1UgCW5J8tqjU3lYw4FBYuj89J0CTVomA7BEfvSZd84GmHko+MxFQU2A== + cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3: version "1.0.4" resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de" @@ -3095,16 +3052,6 @@ cli-spinners@^1.1.0: resolved "https://registry.yarnpkg.com/cli-spinners/-/cli-spinners-1.3.1.tgz#002c1990912d0d59580c93bd36c056de99e4259a" integrity sha512-1QL4544moEsDVH9T/l6Cemov/37iv1RtoKf7NJ04A60+4MREXNfx/QvavbH6QoGdsD4N4Mwy49cmaINR/o2mdg== -cli-table2@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/cli-table2/-/cli-table2-0.2.0.tgz#2d1ef7f218a0e786e214540562d4bd177fe32d97" - integrity sha1-LR738hig54biFFQFYtS9F3/jLZc= - dependencies: - lodash "^3.10.1" - string-width "^1.0.1" - optionalDependencies: - colors "^1.1.2" - cli-table@^0.3.1: version "0.3.1" resolved "https://registry.yarnpkg.com/cli-table/-/cli-table-0.3.1.tgz#f53b05266a8b1a0b934b3d0821e6e2dc5914ae23" @@ -3144,11 +3091,6 @@ cliui@^3.2.0: strip-ansi "^3.0.1" wrap-ansi "^2.0.0" -clone@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/clone/-/clone-0.2.0.tgz#c6126a90ad4f72dbf5acdb243cc37724fe93fc1f" - integrity sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8= - clone@^1.0.2: version "1.0.4" resolved "https://registry.yarnpkg.com/clone/-/clone-1.0.4.tgz#da309cc263df15994c688ca902179ca3c7cd7c7e" @@ -3204,11 +3146,6 @@ colors@1.0.3: resolved "https://registry.yarnpkg.com/colors/-/colors-1.0.3.tgz#0433f44d809680fdeb60ed260f1b0c262e82a40b" integrity sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs= -colors@^1.1.2: - version "1.3.3" - resolved "https://registry.yarnpkg.com/colors/-/colors-1.3.3.tgz#39e005d546afe01e01f9c4ca8fa50f686a01205d" - integrity sha512-mmGt/1pZqYRjMxB1axhTo16/snVZ5krrKkcmMeVKxzECMMXoCgnvTPp10QgHfcbQZw8Dq2jMNG6je4JlWU0gWg== - combine-source-map@^0.8.0, combine-source-map@~0.8.0: version "0.8.0" resolved "https://registry.yarnpkg.com/combine-source-map/-/combine-source-map-0.8.0.tgz#a58d0df042c186fcf822a8e8015f5450d2d79a8b" @@ -3238,7 +3175,7 @@ commander@2.8.x: dependencies: graceful-readlink ">= 1.0.0" -commander@^2.5.0, commander@^2.6.0: +commander@^2.6.0: version "2.19.0" resolved "https://registry.yarnpkg.com/commander/-/commander-2.19.0.tgz#f6198aa84e5b83c46054b94ddedbfed5ee9ff12a" integrity sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg== @@ -3258,21 +3195,6 @@ common-tags@^1.4.0: resolved "https://registry.yarnpkg.com/common-tags/-/common-tags-1.8.0.tgz#8e3153e542d4a39e9b10554434afaaf98956a937" integrity sha512-6P6g0uetGpW/sdyUy/iQQCbFF0kWVMSIVSyYz7Zgjcgh8mgw8PQzDNZeyZ5DQ2gM7LBoZPHmnjz8rUthkBG5tw== -commoner@~0.10.3: - version "0.10.8" - resolved "https://registry.yarnpkg.com/commoner/-/commoner-0.10.8.tgz#34fc3672cd24393e8bb47e70caa0293811f4f2c5" - integrity sha1-NPw2cs0kOT6LtH5wyqApOBH08sU= - dependencies: - commander "^2.5.0" - detective "^4.3.1" - glob "^5.0.15" - graceful-fs "^4.1.2" - iconv-lite "^0.4.5" - mkdirp "^0.5.0" - private "^0.1.6" - q "^1.1.2" - recast "^0.11.17" - component-bind@1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/component-bind/-/component-bind-1.0.0.tgz#00c608ab7dcd93897c0009651b1d3a8e1e73bbd1" @@ -3298,24 +3220,25 @@ compress-commons@^1.2.0: normalize-path "^2.0.0" readable-stream "^2.0.0" -compressible@~2.0.8: - version "2.0.10" - resolved "https://registry.yarnpkg.com/compressible/-/compressible-2.0.10.tgz#feda1c7f7617912732b29bf8cf26252a20b9eecd" - integrity sha1-/tocf3YXkScyspv4zyYlKiC57s0= +compressible@~2.0.14: + version "2.0.15" + resolved "https://registry.yarnpkg.com/compressible/-/compressible-2.0.15.tgz#857a9ab0a7e5a07d8d837ed43fe2defff64fe212" + integrity sha512-4aE67DL33dSW9gw4CI2H/yTxqHLNcxp0yS6jB+4h+wr3e43+1z7vm0HU9qXOH8j+qjKuL8+UtkOxYQSMq60Ylw== dependencies: - mime-db ">= 1.27.0 < 2" + mime-db ">= 1.36.0 < 2" -compression@^1.4.4: - version "1.6.2" - resolved "https://registry.yarnpkg.com/compression/-/compression-1.6.2.tgz#cceb121ecc9d09c52d7ad0c3350ea93ddd402bc3" - integrity sha1-zOsSHsydCcUtetDDNQ6pPd1AK8M= +compression@^1.7.3: + version "1.7.3" + resolved "https://registry.yarnpkg.com/compression/-/compression-1.7.3.tgz#27e0e176aaf260f7f2c2813c3e440adb9f1993db" + integrity sha512-HSjyBG5N1Nnz7tF2+O7A9XUhyjru71/fwgNb7oIsEVHR0WShfs2tIS/EySLgiTe98aOK18YDlMXpzjCXY/n9mg== dependencies: - accepts "~1.3.3" - bytes "2.3.0" - compressible "~2.0.8" - debug "~2.2.0" + accepts "~1.3.5" + bytes "3.0.0" + compressible "~2.0.14" + debug "2.6.9" on-headers "~1.0.1" - vary "~1.1.0" + safe-buffer "5.1.2" + vary "~1.1.2" concat-map@0.0.1: version "0.0.1" @@ -3341,10 +3264,10 @@ concat-stream@^1.4.7, concat-stream@~1.5.0, concat-stream@~1.5.1: readable-stream "~2.0.0" typedarray "~0.0.5" -configstore@^3.0.0: - version "3.1.1" - resolved "https://registry.yarnpkg.com/configstore/-/configstore-3.1.1.tgz#094ee662ab83fad9917678de114faaea8fcdca90" - integrity sha512-5oNkD/L++l0O6xGXxb1EWS7SivtjfGQlRyxJsYgE0Z495/L81e2h4/d3r969hoPXuFItzNOKMtsXgYG4c7dYvw== +configstore@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/configstore/-/configstore-4.0.0.tgz#5933311e95d3687efb592c528b922d9262d227e7" + integrity sha512-CmquAXFBocrzaSM8mtGPMM/HiWmyIpr4CcJl/rgY2uCObZ/S7cKU0silxslqJejl+t/T9HS8E0PUNQD81JGUEQ== dependencies: dot-prop "^4.1.0" graceful-fs "^4.1.2" @@ -3365,7 +3288,7 @@ console-control-strings@^1.0.0, console-control-strings@~1.1.0: resolved "https://registry.yarnpkg.com/console-control-strings/-/console-control-strings-1.1.0.tgz#3d7cf4464db6446ea644bf4b39507f9851008e8e" integrity sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4= -console-ui@^2.0.0: +console-ui@^2.2.2: version "2.2.2" resolved "https://registry.yarnpkg.com/console-ui/-/console-ui-2.2.2.tgz#b294a2934de869dd06789ab4be69555411edef29" integrity sha1-spSik03oad0GeJq0vmlVVBHt7yk= @@ -3431,11 +3354,6 @@ copy-descriptor@^0.1.0: resolved "https://registry.yarnpkg.com/copy-descriptor/-/copy-descriptor-0.1.1.tgz#676f6eb3c39997c2ee1ac3a924fd6124748f578d" integrity sha1-Z29us8OZl8LuGsOpJP1hJHSPV40= -core-js@^1.0.0: - version "1.2.7" - resolved "https://registry.yarnpkg.com/core-js/-/core-js-1.2.7.tgz#652294c14651db28fa93bd2d5ff2983a4f08c636" - integrity sha1-ZSKUwUZR2yj6k70tX/KYOk8IxjY= - core-js@^2.4.0, core-js@^2.4.1, core-js@^2.5.0, core-js@^2.5.7: version "2.6.1" resolved "https://registry.yarnpkg.com/core-js/-/core-js-2.6.1.tgz#87416ae817de957a3f249b3b5ca475d4aaed6042" @@ -3446,12 +3364,12 @@ core-object@^1.1.0: resolved "https://registry.yarnpkg.com/core-object/-/core-object-1.1.0.tgz#86d63918733cf9da1a5aae729e62c0a88e66ad0a" integrity sha1-htY5GHM8+doaWq5ynmLAqI5mrQo= -core-object@^3.1.3: - version "3.1.3" - resolved "https://registry.yarnpkg.com/core-object/-/core-object-3.1.3.tgz#df399b3311bdb0c909e8aae8929fc3c1c4b25880" - integrity sha1-3zmbMxG9sMkJ6Krokp/DwcSyWIA= +core-object@^3.1.5: + version "3.1.5" + resolved "https://registry.yarnpkg.com/core-object/-/core-object-3.1.5.tgz#fa627b87502adc98045e44678e9a8ec3b9c0d2a9" + integrity sha512-sA2/4+/PZ/KV6CKgjrVrrUVBKCkdDO02CUlQ0YKTQoYUwPYNOtOAcWlbYhd5v/1JqYaA6oZ4sDlOU4ppVw6Wbg== dependencies: - chalk "^1.1.3" + chalk "^2.0.0" core-util-is@1.0.2, core-util-is@~1.0.0: version "1.0.2" @@ -3502,7 +3420,7 @@ create-hmac@^1.1.0, create-hmac@^1.1.2, create-hmac@^1.1.4: safe-buffer "^5.0.1" sha.js "^2.4.8" -cross-spawn@^5.0.1, cross-spawn@^5.1.0: +cross-spawn@^5.1.0: version "5.1.0" resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-5.1.0.tgz#e8bd0efee58fcff6f8f94510a0a554bbfa235449" integrity sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk= @@ -3608,20 +3526,20 @@ date-now@^0.1.4: resolved "https://registry.yarnpkg.com/date-now/-/date-now-0.1.4.tgz#eaf439fd4d4848ad74e5cc7dbef200672b9e345b" integrity sha1-6vQ5/U1ISK105cx9vvIAZyueNFs= -debug@2, debug@2.6.8, debug@~2.6.7: +date-time@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/date-time/-/date-time-2.1.0.tgz#0286d1b4c769633b3ca13e1e62558d2dbdc2eba2" + integrity sha512-/9+C44X7lot0IeiyfgJmETtRMhBidBYM2QFFIkGa0U1k+hSyY87Nw7PY3eDqpvCBm7I3WCSfPeZskW/YYq6m4g== + dependencies: + time-zone "^1.0.0" + +debug@2: version "2.6.8" resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.8.tgz#e731531ca2ede27d188222427da17821d68ff4fc" integrity sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw= dependencies: ms "2.0.0" -debug@2.6.1, debug@^2.1.0: - version "2.6.1" - resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.1.tgz#79855090ba2c4e3115cc7d8769491d58f0491351" - integrity sha1-eYVQkLosTjEVzH2HaUkdWPBJE1E= - dependencies: - ms "0.7.2" - debug@2.6.7: version "2.6.7" resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.7.tgz#92bad1f6d05bbb6bba22cca88bcd0ec894c2861e" @@ -3643,6 +3561,13 @@ debug@=3.1.0, debug@~3.1.0: dependencies: ms "2.0.0" +debug@^2.1.0: + version "2.6.1" + resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.1.tgz#79855090ba2c4e3115cc7d8769491d58f0491351" + integrity sha1-eYVQkLosTjEVzH2HaUkdWPBJE1E= + dependencies: + ms "0.7.2" + debug@^3.1.0: version "3.2.6" resolved "https://registry.yarnpkg.com/debug/-/debug-3.2.6.tgz#e83d17de16d8a7efb7717edbe5fb10135eee629b" @@ -3657,13 +3582,6 @@ debug@^4.1.0, debug@~4.1.0: dependencies: ms "^2.1.1" -debug@~2.2.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/debug/-/debug-2.2.0.tgz#f87057e995b1a1f6ae6a4960664137bc56f039da" - integrity sha1-+HBX6ZWxofauaklgZkE3vFbwOdo= - dependencies: - ms "0.7.1" - decamelize@^1.0.0, decamelize@^1.1.1, decamelize@^1.1.2: version "1.2.0" resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290" @@ -3691,6 +3609,13 @@ defaults@^1.0.3: dependencies: clone "^1.0.2" +define-properties@^1.1.2: + version "1.1.3" + resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.1.3.tgz#cf88da6cbee26fe6db7094f61d870cbd84cee9f1" + integrity sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ== + dependencies: + object-keys "^1.0.12" + define-property@^0.2.5: version "0.2.5" resolved "https://registry.yarnpkg.com/define-property/-/define-property-0.2.5.tgz#c35b1ef918ec3c990f9a5bc57be04aacec5c8116" @@ -3718,22 +3643,6 @@ defined@^1.0.0: resolved "https://registry.yarnpkg.com/defined/-/defined-1.0.0.tgz#c98d9bcef75674188e110969151199e39b1fa693" integrity sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM= -defs@~1.1.0: - version "1.1.1" - resolved "https://registry.yarnpkg.com/defs/-/defs-1.1.1.tgz#b22609f2c7a11ba7a3db116805c139b1caffa9d2" - integrity sha1-siYJ8sehG6ej2xFoBcE5scr/qdI= - dependencies: - alter "~0.2.0" - ast-traverse "~0.1.1" - breakable "~1.0.0" - esprima-fb "~15001.1001.0-dev-harmony-fb" - simple-fmt "~0.1.0" - simple-is "~0.2.0" - stringmap "~0.2.2" - stringset "~0.2.1" - tryor "~0.1.2" - yargs "~3.27.0" - del@^2.0.2: version "2.2.2" resolved "https://registry.yarnpkg.com/del/-/del-2.2.2.tgz#c12c981d067846c84bcaf862cff930d907ffd1a8" @@ -3801,27 +3710,11 @@ destroy@~1.0.4: resolved "https://registry.yarnpkg.com/destroy/-/destroy-1.0.4.tgz#978857442c44749e4206613e37946205826abd80" integrity sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA= -detect-file@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/detect-file/-/detect-file-0.1.0.tgz#4935dedfd9488648e006b0129566e9386711ea63" - integrity sha1-STXe39lIhkjgBrASlWbpOGcR6mM= - dependencies: - fs-exists-sync "^0.1.0" - detect-file@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/detect-file/-/detect-file-1.0.0.tgz#f0d66d03672a825cb1b73bdb3fe62310c8e552b7" integrity sha1-8NZtA2cqglyxtzvbP+YjEMjlUrc= -detect-indent@^3.0.0: - version "3.0.1" - resolved "https://registry.yarnpkg.com/detect-indent/-/detect-indent-3.0.1.tgz#9dc5e5ddbceef8325764b9451b02bc6d54084f75" - integrity sha1-ncXl3bzu+DJXZLlFGwK8bVQIT3U= - dependencies: - get-stdin "^4.0.1" - minimist "^1.1.0" - repeating "^1.1.0" - detect-indent@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/detect-indent/-/detect-indent-4.0.0.tgz#f76d064352cdf43a1cb6ce619c4ee3a9475de208" @@ -3829,12 +3722,17 @@ detect-indent@^4.0.0: dependencies: repeating "^2.0.0" +detect-indent@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/detect-indent/-/detect-indent-5.0.0.tgz#3871cc0a6a002e8c3e5b3cf7f336264675f06b9d" + integrity sha1-OHHMCmoALow+Wzz38zYmRnXwa50= + detect-libc@^1.0.2: version "1.0.3" resolved "https://registry.yarnpkg.com/detect-libc/-/detect-libc-1.0.3.tgz#fa137c4bd698edf55cd5cd02ac559f91a4c4ba9b" integrity sha1-+hN8S9aY7fVc1c0CrFWfkaTEups= -detective@^4.0.0, detective@^4.3.1: +detective@^4.0.0: version "4.7.1" resolved "https://registry.yarnpkg.com/detective/-/detective-4.7.1.tgz#0eca7314338442febb6d65da54c10bb1c82b246e" integrity sha512-H6PmeeUcZloWtdt4DAkFyzFL94arpHr3NOwwmVILFiy+9Qd4JTxxXrzfyGk/lmct2qVGBwTSwSXagqu2BxmWig== @@ -3842,10 +3740,10 @@ detective@^4.0.0, detective@^4.3.1: acorn "^5.2.1" defined "^1.0.0" -diff@^3.2.0: - version "3.3.0" - resolved "https://registry.yarnpkg.com/diff/-/diff-3.3.0.tgz#056695150d7aa93237ca7e378ac3b1682b7963b9" - integrity sha512-w0XZubFWn0Adlsapj9EAWX0FqWdO4tz8kc3RiYdWLh4k/V8PTb6i0SMgXt0vRM3zyKnT8tKO7mUlieRQHIjMNg== +diff@^3.5.0: + version "3.5.0" + resolved "https://registry.yarnpkg.com/diff/-/diff-3.5.0.tgz#800c0dd1e0a8bfbc95835c202ad220fe317e5a12" + integrity sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA== diffie-hellman@^5.0.0: version "5.0.3" @@ -3856,6 +3754,14 @@ diffie-hellman@^5.0.0: miller-rabin "^4.0.0" randombytes "^2.0.0" +dir-glob@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-2.0.0.tgz#0b205d2b6aef98238ca286598a8204d29d0a0034" + integrity sha512-37qirFDz8cA5fimp9feo43fSuRo2gHwaIn6dXL8Ber1dGwUosDrGZeCCXq57WnIqE4aQ+u3eQZzsk1yOzhdwag== + dependencies: + arrify "^1.0.1" + path-type "^3.0.0" + doctrine@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-2.1.0.tgz#5cd01fc101621b42c4cd7f5d1a66243716d3f39d" @@ -3925,10 +3831,10 @@ elliptic@^6.0.0: minimalistic-assert "^1.0.0" minimalistic-crypto-utils "^1.0.0" -ember-ajax@^3.0.0: - version "3.1.3" - resolved "https://registry.yarnpkg.com/ember-ajax/-/ember-ajax-3.1.3.tgz#f51b8e3e36765575a2698c8660e377d4d6371642" - integrity sha512-C+BmWxXECGWuv7T17OHSQySpVuoCalmxI/NLUr+3eSlBeCD0xwI3mRRL1CbmAWXdyNwzK3je+lFCSuMaJu2miA== +ember-ajax@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/ember-ajax/-/ember-ajax-4.0.1.tgz#2a33e10857019637f9ab574bbfc3c42ba21b4cf1" + integrity sha512-HbcXTltsxeIhfzwKBOMOE7PBsmVkbqLoenKThoPODMIiiJLtQ46NJztgIcKk5Hgw6zSDOtjHv8YG0nPkO379Aw== dependencies: ember-cli-babel "^6.16.0" najax "^1.0.3" @@ -4035,7 +3941,7 @@ ember-cli-acceptance-test-helpers@^1.0.0: dependencies: ember-cli-babel "^6.12.0" -ember-cli-app-version@^3.0.0: +ember-cli-app-version@^3.2.0: version "3.2.0" resolved "https://registry.yarnpkg.com/ember-cli-app-version/-/ember-cli-app-version-3.2.0.tgz#7b9ad0e1b63ae0518648356ee24c703e922bc26e" integrity sha512-fHWOJElSw8JL03FNCHrT0RdWhGpWEQ4VQ10unEwwhVZ+OANNcOLz8O2dA3D5iuB4bb0fMLwjEwYZGM62+TBs1Q== @@ -4043,28 +3949,6 @@ ember-cli-app-version@^3.0.0: ember-cli-babel "^6.12.0" git-repo-version "^1.0.2" -ember-cli-babel@^5.1.3: - version "5.2.4" - resolved "https://registry.yarnpkg.com/ember-cli-babel/-/ember-cli-babel-5.2.4.tgz#5ce4f46b08ed6f6d21e878619fb689719d6e8e13" - integrity sha1-XOT0awjtb20h6Hhhn7aJcZ1ujhM= - dependencies: - broccoli-babel-transpiler "^5.6.2" - broccoli-funnel "^1.0.0" - clone "^2.0.0" - ember-cli-version-checker "^1.0.2" - resolve "^1.1.2" - -ember-cli-babel@^5.1.5: - version "5.2.8" - resolved "https://registry.yarnpkg.com/ember-cli-babel/-/ember-cli-babel-5.2.8.tgz#0356b03cc3fdff5d0f2ecaa46a0e1cfaebffd876" - integrity sha512-Mt9OOB5RaZwjde+LYef8EgwNVCAzsYDv4ktshblaXxr4m/Xm5/7/rxEu42RNrYkoy/qWpT9uhaD+JKK4riMf+w== - dependencies: - broccoli-babel-transpiler "^5.6.2" - broccoli-funnel "^1.0.0" - clone "^2.0.0" - ember-cli-version-checker "^1.0.2" - resolve "^1.1.2" - ember-cli-babel@^6.0.0, ember-cli-babel@^6.0.0-beta.4, ember-cli-babel@^6.0.0-beta.7, ember-cli-babel@^6.1.0, ember-cli-babel@^6.10.0, ember-cli-babel@^6.11.0, ember-cli-babel@^6.12.0, ember-cli-babel@^6.16.0, ember-cli-babel@^6.3.0, ember-cli-babel@^6.4.1, ember-cli-babel@^6.6.0, ember-cli-babel@^6.7.2, ember-cli-babel@^6.8.0, ember-cli-babel@^6.8.2, ember-cli-babel@^6.9.0, ember-cli-babel@^6.9.2: version "6.18.0" resolved "https://registry.yarnpkg.com/ember-cli-babel/-/ember-cli-babel-6.18.0.tgz#3f6435fd275172edeff2b634ee7b29ce74318957" @@ -4135,23 +4019,24 @@ ember-cli-bootstrap-datepicker@^0.6.1: broccoli-merge-trees "^2.0.0" ember-cli-babel "^6.6.0" -ember-cli-broccoli-sane-watcher@^2.0.4: - version "2.0.4" - resolved "https://registry.yarnpkg.com/ember-cli-broccoli-sane-watcher/-/ember-cli-broccoli-sane-watcher-2.0.4.tgz#f43f42f75b7509c212fb926cd9aea86ae19264c6" - integrity sha1-9D9C91t1CcIS+5Js2a6oauGSZMY= +ember-cli-broccoli-sane-watcher@^2.1.1: + version "2.2.2" + resolved "https://registry.yarnpkg.com/ember-cli-broccoli-sane-watcher/-/ember-cli-broccoli-sane-watcher-2.2.2.tgz#9bb1b04ddeb2c086aecd8693cbaeca1d88dc160c" + integrity sha512-9OLy8x3pdNKC/6xR00IjTL8XyiQU3rb2HLyQSAqHuaZpZcSTKkbAse2ERTsELSINoo/zi/W7qPP5vd5SsHsraw== dependencies: broccoli-slow-trees "^3.0.1" heimdalljs "^0.2.1" heimdalljs-logger "^0.1.7" rsvp "^3.0.18" - sane "^1.1.1" + sane "^2.4.1" -ember-cli-browser-navigation-button-test-helper@^0.0.4: - version "0.0.4" - resolved "https://registry.yarnpkg.com/ember-cli-browser-navigation-button-test-helper/-/ember-cli-browser-navigation-button-test-helper-0.0.4.tgz#58363924a32da68e3662db09bf71b5b944bfe2eb" - integrity sha1-WDY5JKMtpo42YtsJv3G1uUS/4us= +ember-cli-browser-navigation-button-test-helper@^0.1.1: + version "0.1.1" + resolved "https://registry.yarnpkg.com/ember-cli-browser-navigation-button-test-helper/-/ember-cli-browser-navigation-button-test-helper-0.1.1.tgz#1df21df6e864d4afec3eecc7aa66571cac50a73b" + integrity sha512-8aPL5Fa2s9LPKUKzOdN/fUyyFFmoiGf1qqgrkaRtfBdcsxGcJmkdWID9Rqyc/JJXu/LLnk6XARJbGClDV32+XA== dependencies: - ember-cli-babel "^6.3.0" + ember-cli-babel "^6.6.0" + ember-router-service-polyfill "^1.0.3" ember-cli-build-config-editor@0.5.0: version "0.5.0" @@ -4189,10 +4074,10 @@ ember-cli-content-security-policy@^0.6.2: body-parser "^1.12.3" chalk "^1.0.0" -ember-cli-dependency-checker@^2.0.0: - version "2.2.1" - resolved "https://registry.yarnpkg.com/ember-cli-dependency-checker/-/ember-cli-dependency-checker-2.2.1.tgz#1eb728258dc7d528951c391d39b365e1beedecca" - integrity sha512-DmxayycdIPx6wZLpfwXq+MOtKtxhFbCw05kdGaQEyKKNSMeSdywsUjZyxneEpGb8Ztrm+kBwFW3eseydnYLWyw== +ember-cli-dependency-checker@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/ember-cli-dependency-checker/-/ember-cli-dependency-checker-3.0.0.tgz#61245f5f79f881dece043303111d5f41efb8621f" + integrity sha512-Fq9PXFaZfpSHssJwt20cpHMT0AKHMKMBMGiz+Y8BsIvvY1ILaM5bzpUP8V6czm0RU5y7VxM+z7zTN9Cn1iotOA== dependencies: chalk "^2.3.0" find-yarn-workspace-root "^1.1.0" @@ -4212,7 +4097,7 @@ ember-cli-deprecation-workflow@^0.2.3: quick-temp "^0.1.5" rimraf "^2.5.2" -ember-cli-eslint@^4.2.1: +ember-cli-eslint@^4.2.3: version "4.2.3" resolved "https://registry.yarnpkg.com/ember-cli-eslint/-/ember-cli-eslint-4.2.3.tgz#2844d3f5e8184f19b2d7132ba99eb0b370b55598" integrity sha512-1fqRz9QVLTT790Zr07aDFmAprZ1vVsaBGJOGQgDEFmBpogq8BeaQopaxogWFp748hol8nGC4QP5tbzhVD6KQHw== @@ -4236,11 +4121,6 @@ ember-cli-get-component-path-option@^1.0.0: resolved "https://registry.yarnpkg.com/ember-cli-get-component-path-option/-/ember-cli-get-component-path-option-1.0.0.tgz#0d7b595559e2f9050abed804f1d8eff1b08bc771" integrity sha1-DXtZVVni+QUKvtgE8djv8bCLx3E= -ember-cli-get-dependency-depth@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/ember-cli-get-dependency-depth/-/ember-cli-get-dependency-depth-1.0.0.tgz#e0afecf82a2d52f00f28ab468295281aec368d11" - integrity sha1-4K/s+CotUvAPKKtGgpUoGuw2jRE= - ember-cli-head@^0.3.1: version "0.3.1" resolved "https://registry.yarnpkg.com/ember-cli-head/-/ember-cli-head-0.3.1.tgz#a407df4880f235280371c437bb5b0b5cbdaea646" @@ -4249,20 +4129,7 @@ ember-cli-head@^0.3.1: ember-cli-babel "^6.1.0" ember-cli-htmlbars "^2.0.1" -ember-cli-htmlbars-inline-precompile@^0.3.1: - version "0.3.11" - resolved "https://registry.yarnpkg.com/ember-cli-htmlbars-inline-precompile/-/ember-cli-htmlbars-inline-precompile-0.3.11.tgz#55f6858acf5576d9773678a674566b9ad9c79cbe" - integrity sha1-VfaFis9Vdtl3NnimdFZrmtnHnL4= - dependencies: - babel-plugin-htmlbars-inline-precompile "^0.1.0" - ember-cli-babel "^5.1.3" - ember-cli-htmlbars "^1.0.0" - hash-for-dep "^1.0.2" - resolve "^1.3.3" - semver "^5.3.0" - silent-error "^1.1.0" - -ember-cli-htmlbars-inline-precompile@^1.0.0: +ember-cli-htmlbars-inline-precompile@^1.0.0, ember-cli-htmlbars-inline-precompile@^1.0.3: version "1.0.5" resolved "https://registry.yarnpkg.com/ember-cli-htmlbars-inline-precompile/-/ember-cli-htmlbars-inline-precompile-1.0.5.tgz#312e050c9e3dd301c55fb399fd706296cd0b1d6a" integrity sha512-/CNEqPxroIcbY6qejrt704ZaghHLCntZKYLizFfJ2esirXoJx6fuYKBY1YyJ8GOgjfbHHKjBZuK4vFFJpkGqkQ== @@ -4273,28 +4140,6 @@ ember-cli-htmlbars-inline-precompile@^1.0.0: heimdalljs-logger "^0.1.9" silent-error "^1.1.0" -ember-cli-htmlbars@^1.0.0: - version "1.3.5" - resolved "https://registry.yarnpkg.com/ember-cli-htmlbars/-/ember-cli-htmlbars-1.3.5.tgz#65be9678b274b5e7861d7f75c188780af7ef9d13" - integrity sha512-Qur/anb0Vk57qmIhGLkSzl8X1QIMoae6pLa14MRQ8+YD2N5fNs3qdhEFf0SDBquPOH1QxQtraiNQvji47QBJyg== - dependencies: - broccoli-persistent-filter "^1.0.3" - ember-cli-version-checker "^1.0.2" - hash-for-dep "^1.0.2" - json-stable-stringify "^1.0.0" - strip-bom "^2.0.0" - -ember-cli-htmlbars@^1.0.1: - version "1.3.3" - resolved "https://registry.yarnpkg.com/ember-cli-htmlbars/-/ember-cli-htmlbars-1.3.3.tgz#06815262c1577736235bd42ce99db559ce5ebfd1" - integrity sha1-BoFSYsFXdzYjW9Qs6Z21Wc5ev9E= - dependencies: - broccoli-persistent-filter "^1.0.3" - ember-cli-version-checker "^1.0.2" - hash-for-dep "^1.0.2" - json-stable-stringify "^1.0.0" - strip-bom "^2.0.0" - ember-cli-htmlbars@^2.0.1, ember-cli-htmlbars@^2.0.2, ember-cli-htmlbars@^2.0.3: version "2.0.5" resolved "https://registry.yarnpkg.com/ember-cli-htmlbars/-/ember-cli-htmlbars-2.0.5.tgz#b5a105429a6bce4f7c9c97b667e3b8926e31397f" @@ -4320,7 +4165,7 @@ ember-cli-import-polyfill@^0.2.0: resolved "https://registry.yarnpkg.com/ember-cli-import-polyfill/-/ember-cli-import-polyfill-0.2.0.tgz#c1a08a8affb45c97b675926272fe78cf4ca166f2" integrity sha1-waCKiv+0XJe2dZJicv54z0yhZvI= -ember-cli-inject-live-reload@^1.4.1: +ember-cli-inject-live-reload@^1.8.2: version "1.10.2" resolved "https://registry.yarnpkg.com/ember-cli-inject-live-reload/-/ember-cli-inject-live-reload-1.10.2.tgz#43c59f7f1d1e717772da32e5e81d948fb9fe7c94" integrity sha512-yFvZE4WFyWjzMJ6MTYIyjCXpcJNFMTaZP61JXITMkXhSkhuDkzMD/XfwR5+fr004TYcwrbNWpg1oGX5DbOgcaQ== @@ -4333,29 +4178,6 @@ ember-cli-is-package-missing@^1.0.0: resolved "https://registry.yarnpkg.com/ember-cli-is-package-missing/-/ember-cli-is-package-missing-1.0.0.tgz#6e6184cafb92635dd93ca6c946b104292d4e3390" integrity sha1-bmGEyvuSY13ZPKbJRrEEKS1OM5A= -ember-cli-legacy-blueprints@^0.2.0: - version "0.2.1" - resolved "https://registry.yarnpkg.com/ember-cli-legacy-blueprints/-/ember-cli-legacy-blueprints-0.2.1.tgz#480f37cb83f1eda2d46bbc7d07c59ea2e8ce9b84" - integrity sha1-SA83y4Px7aLUa7x9B8WeoujOm4Q= - dependencies: - chalk "^2.3.0" - ember-cli-get-component-path-option "^1.0.0" - ember-cli-get-dependency-depth "^1.0.0" - ember-cli-is-package-missing "^1.0.0" - ember-cli-lodash-subset "^2.0.1" - ember-cli-normalize-entity-name "^1.0.0" - ember-cli-path-utils "^1.0.0" - ember-cli-string-utils "^1.0.0" - ember-cli-test-info "^1.0.0" - ember-cli-valid-component-name "^1.0.0" - ember-cli-version-checker "^2.1.0" - ember-router-generator "^1.0.0" - exists-sync "0.0.3" - fs-extra "^4.0.0" - inflection "^1.7.1" - rsvp "^4.7.0" - silent-error "^1.0.0" - ember-cli-less@^1.5.3: version "1.5.7" resolved "https://registry.yarnpkg.com/ember-cli-less/-/ember-cli-less-1.5.7.tgz#2420ae4b10cb4b6923f61782a9060ff31232e8ac" @@ -4452,21 +4274,20 @@ ember-cli-path-utils@^1.0.0: resolved "https://registry.yarnpkg.com/ember-cli-path-utils/-/ember-cli-path-utils-1.0.0.tgz#4e39af8b55301cddc5017739b77a804fba2071ed" integrity sha1-Tjmvi1UwHN3FAXc5t3qAT7ogce0= -ember-cli-preprocess-registry@^3.1.0: - version "3.1.1" - resolved "https://registry.yarnpkg.com/ember-cli-preprocess-registry/-/ember-cli-preprocess-registry-3.1.1.tgz#38456c21c4d2b64945850cf9ec68db6ba769288a" - integrity sha1-OEVsIcTStklFhQz57Gjba6dpKIo= +ember-cli-preprocess-registry@^3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/ember-cli-preprocess-registry/-/ember-cli-preprocess-registry-3.1.2.tgz#083efb21fd922c021ceba9e08f4d9278249fc4db" + integrity sha512-YJfcDHMBEjtD505CIhM8dtu5FO2Ku+0OTs/0kdLlj9mhXlbzC+k0JAS5c/0AQ+Nh2f+qZZJ8G19ySdzWwTLSCQ== dependencies: broccoli-clean-css "^1.1.0" broccoli-funnel "^1.0.0" broccoli-merge-trees "^1.0.0" debug "^2.2.0" ember-cli-lodash-subset "^1.0.7" - exists-sync "0.0.3" process-relative-require "^1.0.0" silent-error "^1.0.0" -ember-cli-qunit@^4.1.1: +ember-cli-qunit@^4.3.2: version "4.4.0" resolved "https://registry.yarnpkg.com/ember-cli-qunit/-/ember-cli-qunit-4.4.0.tgz#0edd7d651001d0d7ea200b9236a4733a5b7420f1" integrity sha512-+gkx380AV4WXYjQeIuQi675STL9K12fHFtxs8B9u3EFbw45vJKrnYR4Vph3FujxhE/1pr/Je8kZEPAuezZAVLw== @@ -4498,18 +4319,7 @@ ember-cli-sauce@^1.6.0: rsvp "^3.1.0" saucie "^2.1.1" -ember-cli-shims@^1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/ember-cli-shims/-/ember-cli-shims-1.2.0.tgz#0f53aff0aab80b5f29da3a9731bac56169dd941f" - integrity sha1-D1Ov8Kq4C18p2jqXMbrFYWndlB8= - dependencies: - broccoli-file-creator "^1.1.1" - broccoli-merge-trees "^2.0.0" - ember-cli-version-checker "^2.0.0" - ember-rfc176-data "^0.3.1" - silent-error "^1.0.1" - -ember-cli-sri@^2.1.0: +ember-cli-sri@^2.1.1: version "2.1.1" resolved "https://registry.yarnpkg.com/ember-cli-sri/-/ember-cli-sri-2.1.1.tgz#971620934a4b9183cf7923cc03e178b83aa907fd" integrity sha1-lxYgk0pLkYPPeSPMA+F4uDqpB/0= @@ -4521,6 +4331,23 @@ ember-cli-string-utils@^1.0.0, ember-cli-string-utils@^1.1.0: resolved "https://registry.yarnpkg.com/ember-cli-string-utils/-/ember-cli-string-utils-1.1.0.tgz#39b677fc2805f55173735376fcef278eaa4452a1" integrity sha1-ObZ3/CgF9VFzc1N2/O8njqpEUqE= +ember-cli-template-lint@^1.0.0-beta.1: + version "1.0.0-beta.2" + resolved "https://registry.yarnpkg.com/ember-cli-template-lint/-/ember-cli-template-lint-1.0.0-beta.2.tgz#0ebd2f8c1f9ca47f9ee3b42755d66262440c14f6" + integrity sha512-i37mJhz+dll7eP/Y3Yh8oLw5aRqfdnIiutqdLsrvTSLb4VphDXbujXCO8XravvZtGeGBVYKXGsjTxobbPXgsgw== + dependencies: + aot-test-generators "^0.1.0" + broccoli-concat "^3.7.1" + broccoli-persistent-filter "^1.4.3" + chalk "^2.4.1" + debug "^3.1.0" + ember-cli-version-checker "^2.1.2" + ember-template-lint "^1.0.0-beta.5" + json-stable-stringify "^1.0.1" + md5-hex "^2.0.0" + strip-ansi "^4.0.0" + walk-sync "^0.3.3" + ember-cli-test-info@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/ember-cli-test-info/-/ember-cli-test-info-1.0.0.tgz#ed4e960f249e97523cf891e4aed2072ce84577b4" @@ -4535,7 +4362,7 @@ ember-cli-test-loader@^2.2.0: dependencies: ember-cli-babel "^6.8.1" -ember-cli-uglify@^2.0.0: +ember-cli-uglify@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/ember-cli-uglify/-/ember-cli-uglify-2.1.0.tgz#4a0641fe4768d7ab7d4807aca9924cc77c544184" integrity sha512-lDzdAUfhGx5AMBsgyR54ibENVp/LRQuHNWNaP2SDjkAXDyuYFgW0iXIAfGbxF6+nYaesJ9Tr9AKOfTPlwxZDSg== @@ -4550,14 +4377,14 @@ ember-cli-valid-component-name@^1.0.0: dependencies: silent-error "^1.0.0" -ember-cli-version-checker@^1.0.2, ember-cli-version-checker@^1.1.4, ember-cli-version-checker@^1.1.6: +ember-cli-version-checker@^1.1.4: version "1.3.1" resolved "https://registry.yarnpkg.com/ember-cli-version-checker/-/ember-cli-version-checker-1.3.1.tgz#0bc2d134c830142da64bf9627a0eded10b61ae72" integrity sha1-C8LRNMgwFC2mS/lieg7e0QthrnI= dependencies: semver "^5.3.0" -ember-cli-version-checker@^2.0.0, ember-cli-version-checker@^2.1.0, ember-cli-version-checker@^2.1.2: +ember-cli-version-checker@^2.0.0, ember-cli-version-checker@^2.1.0, ember-cli-version-checker@^2.1.1, ember-cli-version-checker@^2.1.2: version "2.1.2" resolved "https://registry.yarnpkg.com/ember-cli-version-checker/-/ember-cli-version-checker-2.1.2.tgz#305ce102390c66e4e0f1432dea9dc5c7c19fed98" integrity sha512-sjkHGr4IGXnO3EUcY21380Xo9Qf6bC8HWH4D62bVnrQop/8uha5XgMQRoAflMCeH6suMrezQL287JUoYc2smEw== @@ -4565,95 +4392,107 @@ ember-cli-version-checker@^2.0.0, ember-cli-version-checker@^2.1.0, ember-cli-ve resolve "^1.3.3" semver "^5.3.0" -ember-cli@~2.18.2: - version "2.18.2" - resolved "https://registry.yarnpkg.com/ember-cli/-/ember-cli-2.18.2.tgz#bb15313a15139a85248a86d203643f918ba40f57" - integrity sha1-uxUxOhUTmoUkiobSA2Q/kYukD1c= +ember-cli@~3.4.4: + version "3.4.4" + resolved "https://registry.yarnpkg.com/ember-cli/-/ember-cli-3.4.4.tgz#8d25b223b2ef3b863310099192da92ab1feeef6b" + integrity sha512-opbdqt9AbNRPr/amemwqi9ENbx/HcqcprxJAW/y8nZAV1gAku+xPY4WNBF6KuClVEKkddbNi4jITLU59rlJcDA== dependencies: - amd-name-resolver "1.0.0" - babel-plugin-transform-es2015-modules-amd "^6.24.0" + amd-name-resolver "^1.2.0" + babel-plugin-transform-es2015-modules-amd "^6.24.1" bower-config "^1.3.0" bower-endpoint-parser "0.2.2" - broccoli-babel-transpiler "^6.0.0" - broccoli-brocfile-loader "^0.18.0" - broccoli-builder "^0.18.8" - broccoli-concat "^3.2.2" - broccoli-config-loader "^1.0.0" + broccoli-amd-funnel "^1.3.0" + broccoli-babel-transpiler "^6.5.0" + broccoli-builder "^0.18.14" + broccoli-concat "^3.5.1" + broccoli-config-loader "^1.0.1" broccoli-config-replace "^1.1.2" - broccoli-debug "^0.6.3" - broccoli-funnel "^2.0.0" + broccoli-debug "^0.6.4" + broccoli-funnel "^2.0.1" broccoli-funnel-reducer "^1.0.0" - broccoli-merge-trees "^2.0.0" - broccoli-middleware "^1.0.0" + broccoli-merge-trees "^3.0.0" + broccoli-middleware "^2.0.1" + broccoli-module-normalizer "^1.3.0" + broccoli-module-unification-reexporter "^1.0.0" broccoli-source "^1.1.0" - broccoli-stew "^1.2.0" - calculate-cache-key-for-tree "^1.0.0" - capture-exit "^1.1.0" - chalk "^2.0.1" + broccoli-stew "^2.0.0" + calculate-cache-key-for-tree "^1.1.0" + capture-exit "^1.2.0" + chalk "^2.4.1" + ci-info "^1.1.3" clean-base-url "^1.0.0" - compression "^1.4.4" - configstore "^3.0.0" - console-ui "^2.0.0" - core-object "^3.1.3" + compression "^1.7.3" + configstore "^4.0.0" + console-ui "^2.2.2" + core-object "^3.1.5" dag-map "^2.0.2" - diff "^3.2.0" - ember-cli-broccoli-sane-watcher "^2.0.4" + diff "^3.5.0" + ember-cli-broccoli-sane-watcher "^2.1.1" ember-cli-is-package-missing "^1.0.0" - ember-cli-legacy-blueprints "^0.2.0" ember-cli-lodash-subset "^2.0.1" ember-cli-normalize-entity-name "^1.0.0" - ember-cli-preprocess-registry "^3.1.0" - ember-cli-string-utils "^1.0.0" - ember-try "^0.2.15" + ember-cli-preprocess-registry "^3.1.2" + ember-cli-string-utils "^1.1.0" ensure-posix-path "^1.0.2" - execa "^0.8.0" - exists-sync "0.0.4" + execa "^0.10.0" exit "^0.1.2" - express "^4.12.3" - filesize "^3.1.3" - find-up "^2.1.0" - fs-extra "^4.0.0" - fs-tree-diff "^0.5.2" + express "^4.16.3" + filesize "^3.6.1" + find-up "^3.0.0" + find-yarn-workspace-root "^1.1.0" + fixturify-project "^1.5.3" + fs-extra "^7.0.0" + fs-tree-diff "^0.5.7" get-caller-file "^1.0.0" - git-repo-info "^1.4.1" - glob "7.1.1" - heimdalljs "^0.2.3" - heimdalljs-fs-monitor "^0.1.0" - heimdalljs-graph "^0.3.1" - heimdalljs-logger "^0.1.7" - http-proxy "^1.9.0" - inflection "^1.7.0" + git-repo-info "^2.0.0" + glob "^7.1.2" + heimdalljs "^0.2.5" + heimdalljs-fs-monitor "^0.2.2" + heimdalljs-graph "^0.3.4" + heimdalljs-logger "^0.1.9" + http-proxy "^1.17.0" + inflection "^1.12.0" is-git-url "^1.0.0" - isbinaryfile "^3.0.0" - js-yaml "^3.6.1" + isbinaryfile "^3.0.3" + js-yaml "^3.12.0" json-stable-stringify "^1.0.1" leek "0.0.24" - lodash.template "^4.2.5" - markdown-it "^8.3.0" + lodash.template "^4.4.0" + markdown-it "^8.4.2" markdown-it-terminal "0.1.0" - minimatch "^3.0.0" - morgan "^1.8.1" - node-modules-path "^1.0.0" + minimatch "^3.0.4" + morgan "^1.9.0" + node-modules-path "^1.0.1" nopt "^3.0.6" - npm-package-arg "^6.0.0" - portfinder "^1.0.7" - promise-map-series "^0.2.1" + npm-package-arg "^6.1.0" + portfinder "^1.0.15" + promise-map-series "^0.2.3" quick-temp "^0.1.8" - resolve "^1.3.0" - rsvp "^4.7.0" - sane "^2.2.0" - semver "^5.1.1" - silent-error "^1.0.0" - sort-package-json "^1.4.0" - symlink-or-copy "^1.1.8" + resolve "^1.8.1" + rsvp "^4.8.3" + sane "^3.0.0" + semver "^5.5.0" + silent-error "^1.1.0" + sort-package-json "^1.15.0" + symlink-or-copy "^1.2.0" temp "0.8.3" - testem "^2.0.0" - tiny-lr "^1.0.3" - tree-sync "^1.2.1" - uuid "^3.0.0" + testem "^2.9.2" + tiny-lr "^1.1.1" + tree-sync "^1.2.2" + uuid "^3.3.2" validate-npm-package-name "^3.0.0" - walk-sync "^0.3.0" - yam "0.0.22" + walk-sync "^0.3.2" + watch-detector "^0.1.0" + yam "^0.0.24" + +ember-compatibility-helpers@^1.1.1: + version "1.1.2" + resolved "https://registry.yarnpkg.com/ember-compatibility-helpers/-/ember-compatibility-helpers-1.1.2.tgz#ae0ee4a7a2858b5ffdf79b428c23aee85c47d93d" + integrity sha512-yN163MzERpotO8M0b+q+kXs4i3Nx6aIriiZHWv+yXQzr2TAtYlVwg9V7/3+jcurOa3oDEYDpN7y9UZ6q3mnoTg== + dependencies: + babel-plugin-debug-macros "^0.2.0" + ember-cli-version-checker "^2.1.1" + semver "^5.4.1" ember-composable-helpers@^2.1.0: version "2.1.0" @@ -4672,6 +4511,13 @@ ember-concurrency@^0.8.7: ember-cli-babel "^6.8.2" ember-maybe-import-regenerator "^0.1.5" +ember-copy@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/ember-copy/-/ember-copy-1.0.0.tgz#426554ba6cf65920f31d24d0a3ca2cb1be16e4aa" + integrity sha512-aiZNAvOmdemHdvZNn0b5b/0d9g3JFpcOsrDgfhYEbfd7SzE0b69YiaVK2y3wjqfjuuiA54vOllGN4pjSzECNSw== + dependencies: + ember-cli-babel "^6.6.0" + ember-cp-validations@^3.5.0: version "3.5.4" resolved "https://registry.yarnpkg.com/ember-cp-validations/-/ember-cp-validations-3.5.4.tgz#95c09d30071958972600d63e659b65fc05062c84" @@ -4686,52 +4532,50 @@ ember-cp-validations@^3.5.0: exists-sync "0.0.4" walk-sync "^0.3.1" -ember-data-model-fragments@^2.14.0: - version "2.14.0" - resolved "https://registry.yarnpkg.com/ember-data-model-fragments/-/ember-data-model-fragments-2.14.0.tgz#f31a03cdcf2449eaaaf84e0996324bf6af6c7b8e" - integrity sha512-U8AKBjqKrjAMNv1FfeqrIua2iHh7fUnhOAzG5zAVhLqFxqPBYXf3owU1bL0thZnBW0JdwiS/F5edBTxwMCV18g== +ember-data-model-fragments@^3.3.0: + version "3.3.0" + resolved "https://registry.yarnpkg.com/ember-data-model-fragments/-/ember-data-model-fragments-3.3.0.tgz#93e3ddba6fab2150435f995e07d25a4d88694886" + integrity sha512-fzBGYCSooaF7sqhxrv08TqG7okye7btYjefGq0ATucaAqSVMkjDkmM9/304nQYHWbKpzWeAzX/qJKSMYaWpN6g== dependencies: - broccoli-file-creator "^1.1.1" - broccoli-merge-trees "^2.0.0" - ember-cli-babel "^6.0.0" - exists-sync "^0.0.4" - git-repo-info "^1.4.1" + broccoli-file-creator "^2.1.1" + broccoli-merge-trees "^3.0.0" + calculate-cache-key-for-tree "^1.1.0" + ember-cli-babel "^6.8.0" + ember-copy "1.0.0" + git-repo-info "^2.0.0" npm-git-info "^1.0.3" -ember-data@~2.18.0: - version "2.18.5" - resolved "https://registry.yarnpkg.com/ember-data/-/ember-data-2.18.5.tgz#cb6509161883db7be3a0859349142f664bb83495" - integrity sha512-WWZVIaMESZ+RgGOW6AsmuuJdKhmbWZMpGoLfZDHmypK45X5Fg7lKG6kJeqrzB/Ilg8r5KlyEpteDBiYXQshSQQ== +ember-data@~3.4.0: + version "3.4.4" + resolved "https://registry.yarnpkg.com/ember-data/-/ember-data-3.4.4.tgz#a201c2db1d7ca2cbe59a23ddf3cb96281fce216f" + integrity sha512-5DE1CxR1Eobue0y2WCkGSRUaOuE8ebktNElhcyPUcrksbnILxniPsKPVRq15X+5wLjaEb+XiscH68NLBGbjUvQ== dependencies: - amd-name-resolver "0.0.7" - babel-plugin-ember-modules-api-polyfill "^1.4.2" + "@ember/ordered-set" "^2.0.0" babel-plugin-feature-flags "^0.3.1" babel-plugin-filter-imports "^0.3.1" - babel-plugin-transform-es2015-block-scoping "^6.24.1" + babel-plugin-transform-es2015-block-scoping "^6.26.0" babel6-plugin-strip-class-callcheck "^6.0.0" babel6-plugin-strip-heimdall "^6.0.1" - broccoli-babel-transpiler "^6.0.0" - broccoli-debug "^0.6.2" - broccoli-file-creator "^1.0.0" - broccoli-funnel "^1.2.0" - broccoli-merge-trees "^2.0.0" - broccoli-rollup "^1.2.0" + broccoli-debug "^0.6.4" + broccoli-file-creator "^2.1.1" + broccoli-funnel "^2.0.1" + broccoli-merge-trees "^3.0.0" + broccoli-rollup "^2.1.1" calculate-cache-key-for-tree "^1.1.0" - chalk "^1.1.1" - ember-cli-babel "^6.8.2" + chalk "^2.4.1" + ember-cli-babel "^6.16.0" ember-cli-path-utils "^1.0.0" - ember-cli-string-utils "^1.0.0" + ember-cli-string-utils "^1.1.0" ember-cli-test-info "^1.0.0" - ember-cli-version-checker "^2.1.0" - ember-inflector "^2.0.0" - ember-runtime-enumerable-includes-polyfill "^2.0.0" - exists-sync "0.0.3" - git-repo-info "^1.1.2" + ember-cli-version-checker "^2.1.2" + ember-inflector "^3.0.0" + git-repo-info "^2.0.0" heimdalljs "^0.3.0" - inflection "^1.8.0" - npm-git-info "^1.0.0" - semver "^5.1.0" - silent-error "^1.0.0" + inflection "^1.12.0" + npm-git-info "^1.0.3" + resolve "^1.8.1" + semver "^5.5.0" + silent-error "^1.1.0" ember-debug-handlers-polyfill@^1.0.2: version "1.1.1" @@ -4795,21 +4639,14 @@ ember-in-element-polyfill@^0.1.2: ember-cli-version-checker "^2.1.0" ember-wormhole "^0.5.4" -ember-inflector@^2.0.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/ember-inflector/-/ember-inflector-2.3.0.tgz#94797eba0eea98d902aa1e5da0f0aeef6053317f" - integrity sha1-lHl+ug7qmNkCqh5doPCu72BTMX8= - dependencies: - ember-cli-babel "^6.0.0" - -"ember-inflector@^2.0.0 || ^3.0.0": +"ember-inflector@^2.0.0 || ^3.0.0", ember-inflector@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/ember-inflector/-/ember-inflector-3.0.0.tgz#7e1ee8aaa0fa773ba0905d8b7c0786354d890ee1" integrity sha512-tLWfYolZAkLnkTvvBkjizy4Wmj8yI8wqHZFK+leh0iScHiC3r1Yh5C4qO+OMGiBTMLwfTy+YqVoE/Nu3hGNkcA== dependencies: ember-cli-babel "^6.6.0" -ember-load-initializers@^1.0.0: +ember-load-initializers@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/ember-load-initializers/-/ember-load-initializers-1.1.0.tgz#4edacc0f3a14d9f53d241ac3e5561804c8377978" integrity sha512-WiciFi8IXOqjyJ65M4iBNIthqcy4uXXQq5n3WxeMMhvJVk5JNSd9hynNECNz3nqfEYuZQ9c04UWkmFIQXRfl4Q== @@ -4857,7 +4694,7 @@ ember-math-helpers@^2.8.1: ember-cli-babel "^6.16.0" ember-cli-htmlbars "^3.0.0" -ember-maybe-import-regenerator@^0.1.5: +ember-maybe-import-regenerator@^0.1.5, ember-maybe-import-regenerator@^0.1.6: version "0.1.6" resolved "https://registry.yarnpkg.com/ember-maybe-import-regenerator/-/ember-maybe-import-regenerator-0.1.6.tgz#35d41828afa6d6a59bc0da3ce47f34c573d776ca" integrity sha1-NdQYKK+m1qWbwNo85H80xXPXdso= @@ -4891,14 +4728,6 @@ ember-native-dom-helpers@^0.5.3: broccoli-funnel "^1.1.0" ember-cli-babel "^6.6.0" -ember-native-dom-helpers@^0.6.2: - version "0.6.2" - resolved "https://registry.yarnpkg.com/ember-native-dom-helpers/-/ember-native-dom-helpers-0.6.2.tgz#ad1f82d64ac9abdd612022f4f390bdb6653b3d39" - integrity sha512-J4SfukTITFFsCYbOxG/sjGBTcZVrxgbMyFKrrTcB2cKfrglyTZSwqs9jBUpF91FEwetzmYP02Nh9N4WzcJ8cRQ== - dependencies: - broccoli-funnel "^1.1.0" - ember-cli-babel "^6.6.0" - ember-page-title@^3.0.6: version "3.2.2" resolved "https://registry.yarnpkg.com/ember-page-title/-/ember-page-title-3.2.2.tgz#241effbc8228ecfb75e33540f6707003fdf6db31" @@ -4957,25 +4786,20 @@ ember-require-module@0.1.3, ember-require-module@^0.1.2: dependencies: ember-cli-babel "^6.9.2" -ember-resolver@^4.0.0: - version "4.5.6" - resolved "https://registry.yarnpkg.com/ember-resolver/-/ember-resolver-4.5.6.tgz#61cecc683fbe3464d759e6d0c2bab97b3914ee4b" - integrity sha512-v+VfQKkYCzdI49cGhPAWlvkjnyYEk1x7/CBKH9xakd8qyByNh6996/EgN0Wzew7B2Gj+cFXii0cEGI8iFAxj6g== +ember-resolver@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/ember-resolver/-/ember-resolver-5.0.1.tgz#21740b92e1e4a65f94018de22aa1c73434dc3b2f" + integrity sha512-Svhs/eseIVQ6Yik+4mFpixT639FREZW2UkIYo7197bRuSL63tofKDMfE+gOXUSSudQlQSaFHFeKDr9oD+0C2GQ== dependencies: "@glimmer/resolver" "^0.4.1" babel-plugin-debug-macros "^0.1.10" - broccoli-funnel "^1.1.0" - broccoli-merge-trees "^2.0.0" + broccoli-funnel "^2.0.1" + broccoli-merge-trees "^3.0.0" ember-cli-babel "^6.8.1" ember-cli-version-checker "^2.0.0" resolve "^1.3.3" -ember-rfc176-data@^0.2.0: - version "0.2.7" - resolved "https://registry.yarnpkg.com/ember-rfc176-data/-/ember-rfc176-data-0.2.7.tgz#bd355bc9b473e08096b518784170a23388bc973b" - integrity sha512-pJE2w+sI22UDsYmudI4nCp3WcImpUzXwe9qHfpOcEu3yM/HD1nGpDRt6kZD0KUnDmqkLeik/nYyzEwN/NU6xxA== - -ember-rfc176-data@^0.3.1, ember-rfc176-data@^0.3.5, ember-rfc176-data@^0.3.6: +ember-rfc176-data@^0.3.5, ember-rfc176-data@^0.3.6: version "0.3.6" resolved "https://registry.yarnpkg.com/ember-rfc176-data/-/ember-rfc176-data-0.3.6.tgz#7138db8dfccec39c9a832adfbd4c49d670028907" integrity sha512-kPY94VCukPUPj+/6sZ9KvphD42KnpX2IS31p5z07OFVIviDogR0cQuld5c7Irzfgq7a0YACj0HlToROFn7dLYQ== @@ -4988,13 +4812,20 @@ ember-route-action-helper@^2.0.6: ember-cli-babel "^6.8.1" ember-getowner-polyfill "^2.0.0" -ember-router-generator@^1.0.0, ember-router-generator@^1.2.3: +ember-router-generator@^1.2.3: version "1.2.3" resolved "https://registry.yarnpkg.com/ember-router-generator/-/ember-router-generator-1.2.3.tgz#8ed2ca86ff323363120fc14278191e9e8f1315ee" integrity sha1-jtLKhv8yM2MSD8FCeBkeno8TFe4= dependencies: recast "^0.11.3" +ember-router-service-polyfill@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/ember-router-service-polyfill/-/ember-router-service-polyfill-1.0.3.tgz#506d7fbd7179951410b7ffe8db171540601d88b1" + integrity sha1-UG1/vXF5lRQQt//o2xcVQGAdiLE= + dependencies: + ember-cli-babel "^6.8.2" + ember-runtime-enumerable-includes-polyfill@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/ember-runtime-enumerable-includes-polyfill/-/ember-runtime-enumerable-includes-polyfill-2.1.0.tgz#dc6d4a028471e4acc350dfd2a149874fb20913f5" @@ -5003,34 +4834,33 @@ ember-runtime-enumerable-includes-polyfill@^2.0.0: ember-cli-babel "^6.9.0" ember-cli-version-checker "^2.1.0" -ember-simple-select@^0.6.1: +ember-simple-select@jelhan/ember-simple-select#ember-3.4: version "0.6.1" - resolved "https://registry.yarnpkg.com/ember-simple-select/-/ember-simple-select-0.6.1.tgz#a5110f2e8d9c72661eb0e990bb6049fc952afdf0" - integrity sha1-pREPLo2ccmYesOmQu2BJ/JUq/fA= + resolved "https://codeload.github.com/jelhan/ember-simple-select/tar.gz/a86208766a6bcd52ec065a1c1e3cd3e5517d7926" dependencies: - ember-cli-babel "^5.1.5" - ember-cli-htmlbars "^1.0.1" - ember-cli-htmlbars-inline-precompile "^0.3.1" + ember-cli-babel "^6.16.0" + ember-cli-htmlbars "^3.0.0" + ember-cli-htmlbars-inline-precompile "^1.0.3" -ember-source@~2.18.0: - version "2.18.2" - resolved "https://registry.yarnpkg.com/ember-source/-/ember-source-2.18.2.tgz#75d00eef5488bfe504044b025c752ba924eaf87f" - integrity sha1-ddAO71SIv+UEBEsCXHUrqSTq+H8= +ember-source@~3.4.0: + version "3.4.7" + resolved "https://registry.yarnpkg.com/ember-source/-/ember-source-3.4.7.tgz#c819337c62fcc6a10ca8aee28abc703c15a57d9e" + integrity sha512-+4yhFZHsjSucSd0bJGErJUly0kdkutMR06AWHLR0b0VRcdYUCbMcFlEvfc2g2B5YR0GY4enSy4gt7PZgYQOrQw== dependencies: broccoli-funnel "^2.0.1" broccoli-merge-trees "^2.0.0" + chalk "^2.3.0" ember-cli-get-component-path-option "^1.0.0" ember-cli-is-package-missing "^1.0.0" ember-cli-normalize-entity-name "^1.0.0" ember-cli-path-utils "^1.0.0" ember-cli-string-utils "^1.1.0" - ember-cli-test-info "^1.0.0" ember-cli-valid-component-name "^1.0.0" ember-cli-version-checker "^2.1.0" ember-router-generator "^1.2.3" inflection "^1.12.0" - jquery "^3.2.1" - resolve "^1.3.3" + jquery "^3.3.1" + resolve "^1.6.0" ember-string-ishtmlsafe-polyfill@^2.0.0: version "2.0.2" @@ -5039,6 +4869,18 @@ ember-string-ishtmlsafe-polyfill@^2.0.0: dependencies: ember-cli-version-checker "^2.1.0" +ember-template-lint@^1.0.0-beta.5: + version "1.0.0-beta.6" + resolved "https://registry.yarnpkg.com/ember-template-lint/-/ember-template-lint-1.0.0-beta.6.tgz#a49d6a37beb3fd7bdae17472efc8ec298d739aa9" + integrity sha512-QeP0GB0oFLvtZXszCTHILlHO5RdVybkdhFdoXSST7IdJHdSIourYjhtgkVVdpw9SOP2SV4xLLTev/tXfNyNZXQ== + dependencies: + "@glimmer/compiler" "^0.36.2" + chalk "^2.0.0" + globby "^8.0.1" + minimatch "^3.0.4" + resolve "^1.1.3" + strip-bom "^3.0.0" + ember-transition-helper@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/ember-transition-helper/-/ember-transition-helper-1.0.0.tgz#a0cdefc1080c2c37944f8f0a23de514eae617769" @@ -5053,35 +4895,6 @@ ember-truth-helpers@^2.1.0: dependencies: ember-cli-babel "^6.6.0" -ember-try-config@^2.0.1: - version "2.1.0" - resolved "https://registry.yarnpkg.com/ember-try-config/-/ember-try-config-2.1.0.tgz#e0e156229a542346a58ee6f6ad605104c98edfe0" - integrity sha1-4OFWIppUI0aljub2rWBRBMmO3+A= - dependencies: - lodash "^4.6.1" - node-fetch "^1.3.3" - rsvp "^3.2.1" - semver "^5.1.0" - -ember-try@^0.2.15: - version "0.2.16" - resolved "https://registry.yarnpkg.com/ember-try/-/ember-try-0.2.16.tgz#cf7092d8a8fea9701d7faa73cbdbff37a8ada330" - integrity sha512-AQZEwMv6BIrVq/ysRcWULvw5tr6RQtUfSYuCpvtdxxJWho74d16YKhGyWAdID+QSmWHrVVGx+O1kDgjf7YKu9A== - dependencies: - chalk "^1.0.0" - cli-table2 "^0.2.0" - core-object "^1.1.0" - debug "^2.2.0" - ember-cli-version-checker "^1.1.6" - ember-try-config "^2.0.1" - extend "^3.0.0" - fs-extra "^0.26.0" - promise-map-series "^0.2.1" - resolve "^1.1.6" - rimraf "^2.3.2" - rsvp "^3.0.17" - semver "^5.1.0" - ember-validators@1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/ember-validators/-/ember-validators-1.0.4.tgz#7d89c2511945c52bd20c5384e715138f902133bb" @@ -5107,18 +4920,11 @@ ember-wormhole@^0.5.4: ember-cli-babel "^6.10.0" ember-cli-htmlbars "^2.0.1" -encodeurl@~1.0.1, encodeurl@~1.0.2: +encodeurl@~1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.2.tgz#ad3ff4c86ec2d029322f5a02c3a9a606c95b3f59" integrity sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k= -encoding@^0.1.11: - version "0.1.12" - resolved "https://registry.yarnpkg.com/encoding/-/encoding-0.1.12.tgz#538b66f3ee62cd1ab51ec323829d1f9480c74beb" - integrity sha1-U4tm8+5izRq1HsMjgp0flIDHS+s= - dependencies: - iconv-lite "~0.4.13" - end-of-stream@^1.0.0: version "1.4.0" resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.0.tgz#7a90d833efda6cfa6eac0f4949dbb0fad3a63206" @@ -5205,6 +5011,26 @@ error@^7.0.0: string-template "~0.2.1" xtend "~4.0.0" +es-abstract@^1.5.1: + version "1.12.0" + resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.12.0.tgz#9dbbdd27c6856f0001421ca18782d786bf8a6165" + integrity sha512-C8Fx/0jFmV5IPoMOFPA9P9G5NtqW+4cOPit3MIuvR2t7Ag2K15EJTpxnHAYTzL+aYQJIESYeXZmDBfOBE1HcpA== + dependencies: + es-to-primitive "^1.1.1" + function-bind "^1.1.1" + has "^1.0.1" + is-callable "^1.1.3" + is-regex "^1.0.4" + +es-to-primitive@^1.1.1: + version "1.2.0" + resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.0.tgz#edf72478033456e8dda8ef09e00ad9650707f377" + integrity sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg== + dependencies: + is-callable "^1.1.4" + is-date-object "^1.0.1" + is-symbol "^1.0.2" + es5-ext@^0.10.14, es5-ext@^0.10.35, es5-ext@^0.10.9, es5-ext@~0.10.14: version "0.10.46" resolved "https://registry.yarnpkg.com/es5-ext/-/es5-ext-0.10.46.tgz#efd99f67c5a7ec789baa3daa7f79870388f7f572" @@ -5223,7 +5049,7 @@ es6-iterator@^2.0.1, es6-iterator@~2.0.1, es6-iterator@~2.0.3: es5-ext "^0.10.35" es6-symbol "^3.1.1" -es6-map@^0.1.3, es6-map@^0.1.4: +es6-map@^0.1.3: version "0.1.5" resolved "https://registry.yarnpkg.com/es6-map/-/es6-map-0.1.5.tgz#9136e0503dcc06a301690f0bb14ff4e364e949f0" integrity sha1-kTbgUD3MBqMBaQ8LsU/042TpSfA= @@ -5296,7 +5122,7 @@ escope@^3.6.0: esrecurse "^4.1.0" estraverse "^4.1.1" -eslint-plugin-ember@^5.0.0: +eslint-plugin-ember@^5.2.0: version "5.4.0" resolved "https://registry.yarnpkg.com/eslint-plugin-ember/-/eslint-plugin-ember-5.4.0.tgz#2980a4389119b37d0450fff8e82d59c9aab126d0" integrity sha512-tYMuxUrTad4f7Dq9gY9GUs9lXwKY+fZklzCJ0JoYbzK2PwSfdrPInr2Y4tHornc9dzPvNbRxsn5b26PrWp2iZg== @@ -5369,16 +5195,6 @@ espree@^3.5.4: acorn "^5.5.0" acorn-jsx "^3.0.0" -esprima-fb@~15001.1001.0-dev-harmony-fb: - version "15001.1001.0-dev-harmony-fb" - resolved "https://registry.yarnpkg.com/esprima-fb/-/esprima-fb-15001.1001.0-dev-harmony-fb.tgz#43beb57ec26e8cf237d3dd8b33e42533577f2659" - integrity sha1-Q761fsJujPI3092LM+QlM1d/Jlk= - -esprima@^2.6.0: - version "2.7.3" - resolved "https://registry.yarnpkg.com/esprima/-/esprima-2.7.3.tgz#96e3b70d5779f6ad49cd032673d1c312767ba581" - integrity sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE= - esprima@^3.1.3, esprima@~3.1.0: version "3.1.3" resolved "https://registry.yarnpkg.com/esprima/-/esprima-3.1.3.tgz#fdca51cee6133895e3c88d535ce49dbff62a4633" @@ -5418,12 +5234,17 @@ estraverse@^4.0.0, estraverse@^4.1.0, estraverse@^4.1.1, estraverse@^4.2.0: resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.2.0.tgz#0dee3fed31fcd469618ce7342099fc1afa0bdb13" integrity sha1-De4/7TH81GlhjOc0IJn8GvoL2xM= -esutils@^2.0.0, esutils@^2.0.2: +estree-walker@^0.5.2: + version "0.5.2" + resolved "https://registry.yarnpkg.com/estree-walker/-/estree-walker-0.5.2.tgz#d3850be7529c9580d815600b53126515e146dd39" + integrity sha512-XpCnW/AE10ws/kDAs37cngSkvgIR8aN3G0MS85m7dUpuK2EREo9VJ00uvw6Dg/hXEpfsE1I1TvJOJr+Z+TL+ig== + +esutils@^2.0.2: version "2.0.2" resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.2.tgz#0abf4f1caa5bcb1f7a9d8acc6dea4faaa04bac9b" integrity sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs= -etag@~1.8.0, etag@~1.8.1: +etag@~1.8.1: version "1.8.1" resolved "https://registry.yarnpkg.com/etag/-/etag-1.8.1.tgz#41ae2eeb65efa62268aebfea83ac7d79299b0887" integrity sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc= @@ -5436,11 +5257,6 @@ event-emitter@~0.3.5: d "1" es5-ext "~0.10.14" -eventemitter3@1.x.x: - version "1.2.0" - resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-1.2.0.tgz#1c86991d816ad1e504750e73874224ecf3bec508" - integrity sha1-HIaZHYFq0eUEdQ5zh0Ik7PO+xQg= - eventemitter3@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/eventemitter3/-/eventemitter3-3.1.0.tgz#090b4d6cdbd645ed10bf750d4b5407942d7ba163" @@ -5480,12 +5296,12 @@ exec-sh@^0.2.0: dependencies: merge "^1.1.3" -execa@^0.8.0: - version "0.8.0" - resolved "https://registry.yarnpkg.com/execa/-/execa-0.8.0.tgz#d8d76bbc1b55217ed190fd6dd49d3c774ecfc8da" - integrity sha1-2NdrvBtVIX7RkP1t1J08d07PyNo= +execa@^0.10.0: + version "0.10.0" + resolved "https://registry.yarnpkg.com/execa/-/execa-0.10.0.tgz#ff456a8f53f90f8eccc71a96d11bdfc7f082cb50" + integrity sha512-7XOMnz8Ynx1gGo/3hyV9loYNPWM94jG3+3T3Y8tsfSstFmETmENCMU/A/zj8Lyaj1lkgEepKepvd6240tBRvlw== dependencies: - cross-spawn "^5.0.1" + cross-spawn "^6.0.0" get-stream "^3.0.0" is-stream "^1.1.0" npm-run-path "^2.0.0" @@ -5511,12 +5327,7 @@ exists-stat@1.0.0: resolved "https://registry.yarnpkg.com/exists-stat/-/exists-stat-1.0.0.tgz#0660e3525a2e89d9e446129440c272edfa24b529" integrity sha1-BmDjUlouidnkRhKUQMJy7foktSk= -exists-sync@0.0.3: - version "0.0.3" - resolved "https://registry.yarnpkg.com/exists-sync/-/exists-sync-0.0.3.tgz#b910000bedbb113b378b82f5f5a7638107622dcf" - integrity sha1-uRAAC+27ETs3i4L19adjgQdiLc8= - -exists-sync@0.0.4, exists-sync@^0.0.4: +exists-sync@0.0.4: version "0.0.4" resolved "https://registry.yarnpkg.com/exists-sync/-/exists-sync-0.0.4.tgz#9744c2c428cc03b01060db454d4b12f0ef3c8879" integrity sha1-l0TCxCjMA7AQYNtFTUsS8O88iHk= @@ -5558,13 +5369,6 @@ expand-range@^1.8.1: dependencies: fill-range "^2.1.0" -expand-tilde@^1.2.2: - version "1.2.2" - resolved "https://registry.yarnpkg.com/expand-tilde/-/expand-tilde-1.2.2.tgz#0b81eba897e5a3d31d1c3d102f8f01441e559449" - integrity sha1-C4HrqJflo9MdHD0QL48BRB5VlEk= - dependencies: - os-homedir "^1.0.1" - expand-tilde@^2.0.0, expand-tilde@^2.0.2: version "2.0.2" resolved "https://registry.yarnpkg.com/expand-tilde/-/expand-tilde-2.0.2.tgz#97e801aa052df02454de46b02bf621642cdc8502" @@ -5572,7 +5376,7 @@ expand-tilde@^2.0.0, expand-tilde@^2.0.2: dependencies: homedir-polyfill "^1.0.1" -express@^4.10.7: +express@^4.10.7, express@^4.16.3: version "4.16.4" resolved "https://registry.yarnpkg.com/express/-/express-4.16.4.tgz#fddef61926109e24c515ea97fd2f1bdbf62df12e" integrity sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg== @@ -5608,40 +5412,6 @@ express@^4.10.7: utils-merge "1.0.1" vary "~1.1.2" -express@^4.12.3: - version "4.15.2" - resolved "https://registry.yarnpkg.com/express/-/express-4.15.2.tgz#af107fc148504457f2dca9a6f2571d7129b97b35" - integrity sha1-rxB/wUhQRFfy3Kmm8lcdcSm5ezU= - dependencies: - accepts "~1.3.3" - array-flatten "1.1.1" - content-disposition "0.5.2" - content-type "~1.0.2" - cookie "0.3.1" - cookie-signature "1.0.6" - debug "2.6.1" - depd "~1.1.0" - encodeurl "~1.0.1" - escape-html "~1.0.3" - etag "~1.8.0" - finalhandler "~1.0.0" - fresh "0.5.0" - merge-descriptors "1.0.1" - methods "~1.1.2" - on-finished "~2.3.0" - parseurl "~1.3.1" - path-to-regexp "0.1.7" - proxy-addr "~1.1.3" - qs "6.4.0" - range-parser "~1.2.0" - send "0.15.1" - serve-static "1.12.1" - setprototypeof "1.0.3" - statuses "~1.3.1" - type-is "~1.6.14" - utils-merge "1.0.0" - vary "~1.1.0" - extend-shallow@^2.0.1: version "2.0.1" resolved "https://registry.yarnpkg.com/extend-shallow/-/extend-shallow-2.0.1.tgz#51af7d614ad9a9f610ea1bafbb989d6b1c56890f" @@ -5736,6 +5506,18 @@ fast-deep-equal@^2.0.1: resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz#7b05218ddf9667bf7f370bf7fdb2cb15fdd0aa49" integrity sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk= +fast-glob@^2.0.2: + version "2.2.4" + resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-2.2.4.tgz#e54f4b66d378040e0e4d6a68ec36bbc5b04363c0" + integrity sha512-FjK2nCGI/McyzgNtTESqaWP3trPvHyRyoyY70hxjc3oKPNmDe8taohLZpoVKoUjW85tbU5txaYUZCNtVzygl1g== + dependencies: + "@mrmlnc/readdir-enhanced" "^2.2.1" + "@nodelib/fs.stat" "^1.1.2" + glob-parent "^3.1.0" + is-glob "^4.0.0" + merge2 "^1.2.3" + micromatch "^3.1.10" + fast-json-stable-stringify@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz#d5142c0caee6b1189f87d3a76111064f86c8bbf2" @@ -5767,6 +5549,20 @@ fast-sourcemap-concat@^1.0.1: source-map "^0.4.2" source-map-url "^0.3.0" +fast-sourcemap-concat@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/fast-sourcemap-concat/-/fast-sourcemap-concat-1.4.0.tgz#122c330d4a2afaff16ad143bc9674b87cd76c8ad" + integrity sha512-x90Wlx/2C83lfyg7h4oguTZN4MyaVfaiUSJQNpU+YEA0Odf9u659Opo44b0LfoVg9G/bOE++GdID/dkyja+XcA== + dependencies: + chalk "^2.0.0" + fs-extra "^5.0.0" + heimdalljs-logger "^0.1.9" + memory-streams "^0.1.3" + mkdirp "^0.5.0" + source-map "^0.4.2" + source-map-url "^0.3.0" + sourcemap-validator "^1.1.0" + fastboot-transform@0.1.1: version "0.1.1" resolved "https://registry.yarnpkg.com/fastboot-transform/-/fastboot-transform-0.1.1.tgz#de55550d85644ec94cb11264c2ba883e3ea3b255" @@ -5789,13 +5585,6 @@ faye-websocket@~0.10.0: dependencies: websocket-driver ">=0.5.1" -fb-watchman@^1.8.0: - version "1.9.2" - resolved "https://registry.yarnpkg.com/fb-watchman/-/fb-watchman-1.9.2.tgz#a24cf47827f82d38fb59a69ad70b76e3b6ae7383" - integrity sha1-okz0eCf4LTj7Waaa1wt247auc4M= - dependencies: - bser "1.0.2" - fb-watchman@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/fb-watchman/-/fb-watchman-2.0.0.tgz#54e9abf7dfa2f26cd9b1636c588c1afc05de5d58" @@ -5823,10 +5612,10 @@ filename-regex@^2.0.0: resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26" integrity sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY= -filesize@^3.1.3: - version "3.5.6" - resolved "https://registry.yarnpkg.com/filesize/-/filesize-3.5.6.tgz#5fd98f3eac94ec9516ef8ed5782fad84a01a0a1a" - integrity sha1-X9mPPqyU7JUW747VeC+thKAaCho= +filesize@^3.6.1: + version "3.6.1" + resolved "https://registry.yarnpkg.com/filesize/-/filesize-3.6.1.tgz#090bb3ee01b6f801a8a8be99d31710b3422bb317" + integrity sha512-7KjR1vv6qnicaPMi1iiTcI85CyYwRO/PSFCu6SvqL8jN2Wjt/NIYQTFtFs7fSDCYOstUkEWIQGFUg5YZQfjlcg== fill-range@^2.1.0: version "2.2.4" @@ -5862,19 +5651,6 @@ finalhandler@1.1.1: statuses "~1.4.0" unpipe "~1.0.0" -finalhandler@~1.0.0: - version "1.0.6" - resolved "https://registry.yarnpkg.com/finalhandler/-/finalhandler-1.0.6.tgz#007aea33d1a4d3e42017f624848ad58d212f814f" - integrity sha1-AHrqM9Gk0+QgF/YkhIrVjSEvgU8= - dependencies: - debug "2.6.9" - encodeurl "~1.0.1" - escape-html "~1.0.3" - on-finished "~2.3.0" - parseurl "~1.3.2" - statuses "~1.3.1" - unpipe "~1.0.0" - find-babel-config@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/find-babel-config/-/find-babel-config-1.1.0.tgz#acc01043a6749fec34429be6b64f542ebb5d6355" @@ -5903,6 +5679,13 @@ find-up@^2.1.0: dependencies: locate-path "^2.0.0" +find-up@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-3.0.0.tgz#49169f1d7993430646da61ecc5ae355c21c97b73" + integrity sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg== + dependencies: + locate-path "^3.0.0" + find-yarn-workspace-root@^1.1.0: version "1.2.1" resolved "https://registry.yarnpkg.com/find-yarn-workspace-root/-/find-yarn-workspace-root-1.2.1.tgz#40eb8e6e7c2502ddfaa2577c176f221422f860db" @@ -5921,16 +5704,6 @@ findup-sync@2.0.0, findup-sync@^2.0.0: micromatch "^3.0.4" resolve-dir "^1.0.1" -findup-sync@^0.4.2: - version "0.4.3" - resolved "https://registry.yarnpkg.com/findup-sync/-/findup-sync-0.4.3.tgz#40043929e7bc60adf0b7f4827c4c6e75a0deca12" - integrity sha1-QAQ5Kee8YK3wt/SCfExudaDeyhI= - dependencies: - detect-file "^0.1.0" - is-glob "^2.0.1" - micromatch "^2.3.7" - resolve-dir "^0.1.0" - fireworm@^0.7.0: version "0.7.1" resolved "https://registry.yarnpkg.com/fireworm/-/fireworm-0.7.1.tgz#ccf20f7941f108883fcddb99383dbe6e1861c758" @@ -5942,6 +5715,22 @@ fireworm@^0.7.0: lodash.flatten "^3.0.2" minimatch "^3.0.2" +fixturify-project@^1.5.3: + version "1.5.3" + resolved "https://registry.yarnpkg.com/fixturify-project/-/fixturify-project-1.5.3.tgz#2ba4ffec59c1d79ae6638f818c0847eb974d179b" + integrity sha512-vgH+Uo+pC6jHg7mt+FDz+j08bKFugnP6guBWeumYllQDbvxT7NQ/sf6zO4nC0XKRRsSNWsOHkO0AppaHvwF69A== + dependencies: + fixturify "^0.3.4" + tmp "^0.0.33" + +fixturify@^0.3.4: + version "0.3.4" + resolved "https://registry.yarnpkg.com/fixturify/-/fixturify-0.3.4.tgz#c676de404a7f8ee8e64d0b76118e62ec95ab7b25" + integrity sha512-Gx+KSB25b6gMc4bf7UFRTA85uE0iZR+RYur0JHh6dg4AGBh0EksOv4FCHyM7XpGmiJO7Bc7oV7vxENQBT+2WEQ== + dependencies: + fs-extra "^0.30.0" + matcher-collection "^1.0.4" + flat-cache@^1.2.1: version "1.2.2" resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-1.2.2.tgz#fa86714e72c21db88601761ecf2f555d1abc6b96" @@ -5994,7 +5783,7 @@ form-data@~2.3.2: combined-stream "^1.0.6" mime-types "^2.1.12" -forwarded@~0.1.0, forwarded@~0.1.2: +forwarded@~0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/forwarded/-/forwarded-0.1.2.tgz#98c23dab1175657b8c0573e8ceccd91b0ff18c84" integrity sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ= @@ -6006,21 +5795,11 @@ fragment-cache@^0.2.1: dependencies: map-cache "^0.2.2" -fresh@0.5.0: - version "0.5.0" - resolved "https://registry.yarnpkg.com/fresh/-/fresh-0.5.0.tgz#f474ca5e6a9246d6fd8e0953cfa9b9c805afa78e" - integrity sha1-9HTKXmqSRtb9jglTz6m5yAWvp44= - fresh@0.5.2: version "0.5.2" resolved "https://registry.yarnpkg.com/fresh/-/fresh-0.5.2.tgz#3d8cadd90d976569fa835ab1f8e4b23a105605a7" integrity sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac= -fs-exists-sync@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/fs-exists-sync/-/fs-exists-sync-0.1.0.tgz#982d6893af918e72d08dec9e8673ff2b5a8d6add" - integrity sha1-mC1ok6+RjnLQjeyehnP/K1qNat0= - fs-extra@^0.24.0: version "0.24.0" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.24.0.tgz#d4e4342a96675cb7846633a6099249332b539952" @@ -6031,17 +5810,6 @@ fs-extra@^0.24.0: path-is-absolute "^1.0.0" rimraf "^2.2.8" -fs-extra@^0.26.0: - version "0.26.7" - resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.26.7.tgz#9ae1fdd94897798edab76d0918cf42d0c3184fa9" - integrity sha1-muH92UiXeY7at20JGM9C0MMYT6k= - dependencies: - graceful-fs "^4.1.2" - jsonfile "^2.1.0" - klaw "^1.0.0" - path-is-absolute "^1.0.0" - rimraf "^2.2.8" - fs-extra@^0.30.0: version "0.30.0" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.30.0.tgz#f233ffcc08d4da7d432daa449776989db1df93f0" @@ -6062,7 +5830,7 @@ fs-extra@^1.0.0: jsonfile "^2.1.0" klaw "^1.0.0" -fs-extra@^4.0.0, fs-extra@^4.0.3: +fs-extra@^4.0.2, fs-extra@^4.0.3: version "4.0.3" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-4.0.3.tgz#0d852122e5bc5beb453fb028e9c0c9bf36340c94" integrity sha512-q6rbdDd1o2mAnQreO7YADIxf/Whx4AHBiRf6d+/cVT8h44ss+lHgxf1FemcqDnQt9X3ct4McHr+JMGlYSsK7Cg== @@ -6089,7 +5857,7 @@ fs-extra@^6.0.1: jsonfile "^4.0.0" universalify "^0.1.0" -fs-extra@^7.0.1: +fs-extra@^7.0.0, fs-extra@^7.0.1: version "7.0.1" resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== @@ -6105,12 +5873,7 @@ fs-minipass@^1.2.5: dependencies: minipass "^2.2.1" -fs-readdir-recursive@^0.1.0: - version "0.1.2" - resolved "https://registry.yarnpkg.com/fs-readdir-recursive/-/fs-readdir-recursive-0.1.2.tgz#315b4fb8c1ca5b8c47defef319d073dad3568059" - integrity sha1-MVtPuMHKW4xH3v7zGdBz2tNWgFk= - -fs-tree-diff@^0.5.0, fs-tree-diff@^0.5.2, fs-tree-diff@^0.5.3, fs-tree-diff@^0.5.4, fs-tree-diff@^0.5.6: +fs-tree-diff@^0.5.0, fs-tree-diff@^0.5.2, fs-tree-diff@^0.5.3, fs-tree-diff@^0.5.4, fs-tree-diff@^0.5.6, fs-tree-diff@^0.5.7: version "0.5.9" resolved "https://registry.yarnpkg.com/fs-tree-diff/-/fs-tree-diff-0.5.9.tgz#a4ec6182c2f5bd80b9b83c8e23e4522e6f5fd946" integrity sha512-872G8ax0kHh01m9n/2KDzgYwouKza0Ad9iFltBpNykvROvf2AGtoOzPJgGx125aolGPER3JuC7uZFrQ7bG1AZw== @@ -6232,11 +5995,16 @@ getpass@^0.1.1: dependencies: assert-plus "^1.0.0" -git-repo-info@^1.1.2, git-repo-info@^1.4.1: +git-repo-info@^1.4.1: version "1.4.1" resolved "https://registry.yarnpkg.com/git-repo-info/-/git-repo-info-1.4.1.tgz#2a072823254aaf62fcf0766007d7b6651bd41943" integrity sha1-KgcoIyVKr2L88HZgB9e2ZRvUGUM= +git-repo-info@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/git-repo-info/-/git-repo-info-2.1.0.tgz#13d1f753c75bc2994432e65a71e35377ff563813" + integrity sha512-+kigfDB7j3W80f74BoOUX+lKOmf4pR3/i2Ww6baKTCPe2hD4FRdjhV3s4P5Dy0Tak1uY1891QhKoYNtnyX2VvA== + git-repo-version@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/git-repo-version/-/git-repo-version-1.0.2.tgz#2c8e9bee5d970cafc0dd58480f9dc56d9afe8e4f" @@ -6266,7 +6034,31 @@ glob-parent@^2.0.0: dependencies: is-glob "^2.0.0" -glob@7.1.1, glob@^7.0.0: +glob-parent@^3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-3.1.0.tgz#9e6af6299d8d3bd2bd40430832bd113df906c5ae" + integrity sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4= + dependencies: + is-glob "^3.1.0" + path-dirname "^1.0.0" + +glob-to-regexp@^0.3.0: + version "0.3.0" + resolved "https://registry.yarnpkg.com/glob-to-regexp/-/glob-to-regexp-0.3.0.tgz#8c5a1494d2066c570cc3bfe4496175acc4d502ab" + integrity sha1-jFoUlNIGbFcMw7/kSWF1rMTVAqs= + +glob@^5.0.10: + version "5.0.15" + resolved "https://registry.yarnpkg.com/glob/-/glob-5.0.15.tgz#1bc936b9e02f4a603fcc222ecf7633d30b8b93b1" + integrity sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E= + dependencies: + inflight "^1.0.4" + inherits "2" + minimatch "2 || 3" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^7.0.0: version "7.1.1" resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.1.tgz#805211df04faaf1c63a3600306cdf5ade50b2ec8" integrity sha1-gFIR3wT6rxxjo2ADBs31reULLsg= @@ -6278,17 +6070,6 @@ glob@7.1.1, glob@^7.0.0: once "^1.3.0" path-is-absolute "^1.0.0" -glob@^5.0.10, glob@^5.0.15: - version "5.0.15" - resolved "https://registry.yarnpkg.com/glob/-/glob-5.0.15.tgz#1bc936b9e02f4a603fcc222ecf7633d30b8b93b1" - integrity sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E= - dependencies: - inflight "^1.0.4" - inherits "2" - minimatch "2 || 3" - once "^1.3.0" - path-is-absolute "^1.0.0" - glob@^7.0.3: version "7.1.2" resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.2.tgz#c19c9df9a028702d678612384a6552404c636d15" @@ -6313,14 +6094,6 @@ glob@^7.0.4, glob@^7.0.5, glob@^7.1.0, glob@^7.1.2: once "^1.3.0" path-is-absolute "^1.0.0" -global-modules@^0.2.3: - version "0.2.3" - resolved "https://registry.yarnpkg.com/global-modules/-/global-modules-0.2.3.tgz#ea5a3bed42c6d6ce995a4f8a1269b5dae223828d" - integrity sha1-6lo77ULG1s6ZWk+KEmm12uIjgo0= - dependencies: - global-prefix "^0.1.4" - is-windows "^0.2.0" - global-modules@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/global-modules/-/global-modules-1.0.0.tgz#6d770f0eb523ac78164d72b5e71a8877265cc3ea" @@ -6330,16 +6103,6 @@ global-modules@^1.0.0: is-windows "^1.0.1" resolve-dir "^1.0.0" -global-prefix@^0.1.4: - version "0.1.5" - resolved "https://registry.yarnpkg.com/global-prefix/-/global-prefix-0.1.5.tgz#8d3bc6b8da3ca8112a160d8d496ff0462bfef78f" - integrity sha1-jTvGuNo8qBEqFg2NSW/wRiv+948= - dependencies: - homedir-polyfill "^1.0.0" - ini "^1.3.4" - is-windows "^0.2.0" - which "^1.2.12" - global-prefix@^1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/global-prefix/-/global-prefix-1.0.2.tgz#dbf743c6c14992593c655568cb66ed32c0122ebe" @@ -6356,11 +6119,6 @@ globals@^11.0.1, globals@^11.1.0: resolved "https://registry.yarnpkg.com/globals/-/globals-11.9.0.tgz#bde236808e987f290768a93d065060d78e6ab249" integrity sha512-5cJVtyXWH8PiJPVLZzzoIizXx944O4OmRro5MWKx5fT4MgcN7OfaMutPeaTdJCCURwbWdhhcCWcKIffPnmTzBg== -globals@^6.4.0: - version "6.4.1" - resolved "https://registry.yarnpkg.com/globals/-/globals-6.4.1.tgz#8498032b3b6d1cc81eebc5f79690d8fe29fabf4f" - integrity sha1-hJgDKzttHMge68X3lpDY/in6v08= - globals@^9.18.0: version "9.18.0" resolved "https://registry.yarnpkg.com/globals/-/globals-9.18.0.tgz#aa3896b3e69b487f17e31ed2143d69a8e30c2d8a" @@ -6378,6 +6136,19 @@ globby@^5.0.0: pify "^2.0.0" pinkie-promise "^2.0.0" +globby@^8.0.1: + version "8.0.1" + resolved "https://registry.yarnpkg.com/globby/-/globby-8.0.1.tgz#b5ad48b8aa80b35b814fc1281ecc851f1d2b5b50" + integrity sha512-oMrYrJERnKBLXNLVTqhm3vPEdJ/b2ZE28xN4YARiix1NOIOBPEpOUnm844K1iu/BkphCaf2WNFwMszv8Soi1pw== + dependencies: + array-union "^1.0.1" + dir-glob "^2.0.0" + fast-glob "^2.0.2" + glob "^7.1.2" + ignore "^3.3.5" + pify "^3.0.0" + slash "^1.0.0" + good-listener@^1.2.2: version "1.2.2" resolved "https://registry.yarnpkg.com/good-listener/-/good-listener-1.2.2.tgz#d53b30cdf9313dffb7dc9a0d477096aa6d145c50" @@ -6390,7 +6161,7 @@ graceful-fs@^4.1.0, graceful-fs@^4.1.11, graceful-fs@^4.1.3: resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.1.11.tgz#0e8bdfe4d1ddb8854d64e04ea7c00e2a026e5658" integrity sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg= -graceful-fs@^4.1.2, graceful-fs@^4.1.4, graceful-fs@^4.1.6, graceful-fs@^4.1.9: +graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.1.9: version "4.1.15" resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.1.15.tgz#ffb703e1066e8a0eeaa4c8b80ba9253eeefbfb00" integrity sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA== @@ -6416,6 +6187,17 @@ handlebars@^4.0.4: optionalDependencies: uglify-js "^2.6" +handlebars@^4.0.6: + version "4.0.12" + resolved "https://registry.yarnpkg.com/handlebars/-/handlebars-4.0.12.tgz#2c15c8a96d46da5e266700518ba8cb8d919d5bc5" + integrity sha512-RhmTekP+FZL+XNhwS1Wf+bTTZpdLougwt5pcgA1tuz6Jcx0fpH/7z0qd71RKnZHBCxIRBHfBOnio4gViPemNzA== + dependencies: + async "^2.5.0" + optimist "^0.6.1" + source-map "^0.6.1" + optionalDependencies: + uglify-js "^3.1.4" + har-schema@^1.0.5: version "1.0.5" resolved "https://registry.yarnpkg.com/har-schema/-/har-schema-1.0.5.tgz#d263135f43307c02c602afc8fe95970c0151369e" @@ -6483,6 +6265,11 @@ has-flag@^3.0.0: resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" integrity sha1-tdRU3CGZriJWmfNGfloH87lVuv0= +has-symbols@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.0.0.tgz#ba1a8f1af2a0fc39650f5c850367704122063b44" + integrity sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q= + has-unicode@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/has-unicode/-/has-unicode-2.0.1.tgz#e0e6fe6a28cf51138855e086d1691e771de2a8b9" @@ -6519,7 +6306,7 @@ has-values@^1.0.0: is-number "^3.0.0" kind-of "^4.0.0" -has@^1.0.0: +has@^1.0.0, has@^1.0.1: version "1.0.3" resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== @@ -6562,18 +6349,18 @@ hawk@~3.1.3: hoek "2.x.x" sntp "1.x.x" -heimdalljs-fs-monitor@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/heimdalljs-fs-monitor/-/heimdalljs-fs-monitor-0.1.0.tgz#d404a65688c6714c485469ed3495da4853440272" - integrity sha1-1ASmVojGcUxIVGntNJXaSFNEAnI= +heimdalljs-fs-monitor@^0.2.2: + version "0.2.2" + resolved "https://registry.yarnpkg.com/heimdalljs-fs-monitor/-/heimdalljs-fs-monitor-0.2.2.tgz#a76d98f52dbf3aa1b7c20cebb0132e2f5eeb9204" + integrity sha512-R/VhkWs8tm4x+ekLIp+oieR8b3xYK0oFDumEraGnwNMixpiKwO3+Ms5MJzDP5W5Ui1+H/57nGW5L3lHbxi20GA== dependencies: - heimdalljs "^0.2.0" + heimdalljs "^0.2.3" heimdalljs-logger "^0.1.7" -heimdalljs-graph@^0.3.1: - version "0.3.3" - resolved "https://registry.yarnpkg.com/heimdalljs-graph/-/heimdalljs-graph-0.3.3.tgz#ea801dbba659c8d522fe1cb83b2d605726e4918f" - integrity sha1-6oAdu6ZZyNUi/hy4Oy1gVybkkY8= +heimdalljs-graph@^0.3.4: + version "0.3.5" + resolved "https://registry.yarnpkg.com/heimdalljs-graph/-/heimdalljs-graph-0.3.5.tgz#420fbbc8fc3aec5963ddbbf1a5fb47921c4a5927" + integrity sha512-szOy9WZUc7eUInEBQEsoa1G2d+oYHrn6ndZPf76eh8A9ID1zWUCEEsxP3F+CvQx9+EDrg1srdyLUmfVAr8EB4g== heimdalljs-logger@^0.1.7, heimdalljs-logger@^0.1.9: version "0.1.10" @@ -6611,14 +6398,6 @@ hoek@2.x.x: resolved "https://registry.yarnpkg.com/hoek/-/hoek-2.16.3.tgz#20bb7403d3cea398e91dc4710a8ff1b8274a25ed" integrity sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0= -home-or-tmp@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/home-or-tmp/-/home-or-tmp-1.0.0.tgz#4b9f1e40800c3e50c6c27f781676afcce71f3985" - integrity sha1-S58eQIAMPlDGwn94FnavzOcfOYU= - dependencies: - os-tmpdir "^1.0.1" - user-home "^1.1.1" - home-or-tmp@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/home-or-tmp/-/home-or-tmp-2.0.0.tgz#e36c3f2d2cae7d746a857e38d18d5f32a7882db8" @@ -6627,7 +6406,7 @@ home-or-tmp@^2.0.0: os-homedir "^1.0.0" os-tmpdir "^1.0.1" -homedir-polyfill@^1.0.0, homedir-polyfill@^1.0.1: +homedir-polyfill@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz#4c2bbc8a758998feebf5ed68580f76d46768b4bc" integrity sha1-TCu8inWJmP7r9e1oWA921GdotLw= @@ -6661,7 +6440,7 @@ http-errors@1.6.3, http-errors@~1.6.1, http-errors@~1.6.2, http-errors@~1.6.3: setprototypeof "1.1.0" statuses ">= 1.4.0 < 2" -http-proxy@^1.13.1: +http-proxy@^1.13.1, http-proxy@^1.17.0: version "1.17.0" resolved "https://registry.yarnpkg.com/http-proxy/-/http-proxy-1.17.0.tgz#7ad38494658f84605e2f6db4436df410f4e5be9a" integrity sha512-Taqn+3nNvYRfJ3bGvKfBSRwy1v6eePlm3oc/aWVxZp57DQr5Eq3xhKJi7Z4hZpS8PC3H4qI+Yly5EmFacGuA/g== @@ -6670,14 +6449,6 @@ http-proxy@^1.13.1: follow-redirects "^1.0.0" requires-port "^1.0.0" -http-proxy@^1.9.0: - version "1.16.2" - resolved "https://registry.yarnpkg.com/http-proxy/-/http-proxy-1.16.2.tgz#06dff292952bf64dbe8471fa9df73066d4f37742" - integrity sha1-Bt/ykpUr9k2+hHH6nfcwZtTzd0I= - dependencies: - eventemitter3 "1.x.x" - requires-port "1.x.x" - http-signature@~1.1.0: version "1.1.1" resolved "https://registry.yarnpkg.com/http-signature/-/http-signature-1.1.1.tgz#df72e267066cd0ac67fb76adf8e134a8fbcf91bf" @@ -6722,7 +6493,7 @@ iconv-lite@0.4.23: dependencies: safer-buffer ">= 2.1.2 < 3" -iconv-lite@0.4.24, iconv-lite@^0.4.17, iconv-lite@^0.4.4, iconv-lite@^0.4.5, iconv-lite@~0.4.13: +iconv-lite@0.4.24, iconv-lite@^0.4.17, iconv-lite@^0.4.4: version "0.4.24" resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== @@ -6741,7 +6512,7 @@ ignore-walk@^3.0.1: dependencies: minimatch "^3.0.4" -ignore@^3.3.3: +ignore@^3.3.3, ignore@^3.3.5: version "3.3.10" resolved "https://registry.yarnpkg.com/ignore/-/ignore-3.3.10.tgz#0a97fb876986e8081c631160f8f9f389157f0043" integrity sha512-Pgs951kaMm5GXP7MOvxERINe3gsaVjUWFm+UZPSq9xYriQAksyhg0csnS0KXSNRD5NmNdapXEpjxG49+AKh/ug== @@ -6773,7 +6544,7 @@ indexof@0.0.1: resolved "https://registry.yarnpkg.com/indexof/-/indexof-0.0.1.tgz#82dc336d232b9062179d05ab3293a66059fd435d" integrity sha1-gtwzbSMrkGIXnQWrMpOmYFn9Q10= -inflection@^1.12.0, inflection@^1.7.0, inflection@^1.7.1, inflection@^1.8.0: +inflection@^1.12.0: version "1.12.0" resolved "https://registry.yarnpkg.com/inflection/-/inflection-1.12.0.tgz#a200935656d6f5f6bc4dc7502e1aecb703228416" integrity sha1-ogCTVlbW9fa8TcdQLhrstwMihBY= @@ -6839,7 +6610,7 @@ inquirer@^2: strip-ansi "^3.0.0" through "^2.3.6" -inquirer@^3.0.6: +inquirer@^3.0.6, inquirer@^3.3.0: version "3.3.0" resolved "https://registry.yarnpkg.com/inquirer/-/inquirer-3.3.0.tgz#9dd2f2ad765dcab1ff0443b491442a20ba227dc9" integrity sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ== @@ -6887,11 +6658,6 @@ invert-kv@^1.0.0: resolved "https://registry.yarnpkg.com/invert-kv/-/invert-kv-1.0.0.tgz#104a8e4aaca6d3d8cd157a8ef8bfab2d7a3ffdb6" integrity sha1-EEqOSqym09jNFXqO+L+rLXo//bY= -ipaddr.js@1.4.0: - version "1.4.0" - resolved "https://registry.yarnpkg.com/ipaddr.js/-/ipaddr.js-1.4.0.tgz#296aca878a821816e5b85d0a285a99bcff4582f0" - integrity sha1-KWrKh4qCGBbluF0KKFqZvP9FgvA= - ipaddr.js@1.8.0: version "1.8.0" resolved "https://registry.yarnpkg.com/ipaddr.js/-/ipaddr.js-1.8.0.tgz#eaa33d6ddd7ace8f7f6fe0c9ca0440e706738b1e" @@ -6928,6 +6694,11 @@ is-builtin-module@^1.0.0: dependencies: builtin-modules "^1.0.0" +is-callable@^1.1.3, is-callable@^1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/is-callable/-/is-callable-1.1.4.tgz#1e1adf219e1eeb684d691f9d6a05ff0d30a24d75" + integrity sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA== + is-data-descriptor@^0.1.4: version "0.1.4" resolved "https://registry.yarnpkg.com/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz#0b5ee648388e2c860282e793f1856fec3f301b56" @@ -6942,6 +6713,11 @@ is-data-descriptor@^1.0.0: dependencies: kind-of "^6.0.0" +is-date-object@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.1.tgz#9aa20eb6aeebbff77fbd33e74ca01b33581d3a16" + integrity sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY= + is-descriptor@^0.1.0: version "0.1.6" resolved "https://registry.yarnpkg.com/is-descriptor/-/is-descriptor-0.1.6.tgz#366d8240dde487ca51823b1ab9f07a10a78251ca" @@ -6989,7 +6765,7 @@ is-extglob@^1.0.0: resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-1.0.0.tgz#ac468177c4943405a092fc8f29760c6ffc6206c0" integrity sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA= -is-extglob@^2.1.0: +is-extglob@^2.1.0, is-extglob@^2.1.1: version "2.1.1" resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" integrity sha1-qIwCU1eR8C7TfHahueqXc8gz+MI= @@ -7032,12 +6808,12 @@ is-glob@^3.1.0: dependencies: is-extglob "^2.1.0" -is-integer@^1.0.4: - version "1.0.7" - resolved "https://registry.yarnpkg.com/is-integer/-/is-integer-1.0.7.tgz#6bde81aacddf78b659b6629d629cadc51a886d5c" - integrity sha1-a96Bqs3feLZZtmKdYpytxRqIbVw= +is-glob@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.0.tgz#9521c76845cc2610a85203ddf080a958c2ffabc0" + integrity sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A= dependencies: - is-finite "^1.0.0" + is-extglob "^2.1.1" is-my-json-valid@^2.12.4: version "2.16.0" @@ -7119,6 +6895,20 @@ is-property@^1.0.0: resolved "https://registry.yarnpkg.com/is-property/-/is-property-1.0.2.tgz#57fe1c4e48474edd65b09911f26b1cd4095dda84" integrity sha1-V/4cTkhHTt1lsJkR8msc1Ald2oQ= +is-reference@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/is-reference/-/is-reference-1.1.0.tgz#50e6ef3f64c361e2c53c0416cdc9420037f2685b" + integrity sha512-h37O/IX4efe56o9k41II1ECMqKwtqHa7/12dLDEzJIFux2x15an4WCDb0/eKdmUgRpLJ3bR0DrzDc7vOrVgRDw== + dependencies: + "@types/estree" "0.0.38" + +is-regex@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-regex/-/is-regex-1.0.4.tgz#5517489b547091b0930e095654ced25ee97e9491" + integrity sha1-VRdIm1RwkbCTDglWVM7SXul+lJE= + dependencies: + has "^1.0.1" + is-resolvable@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-resolvable/-/is-resolvable-1.0.0.tgz#8df57c61ea2e3c501408d100fb013cf8d6e0cc62" @@ -7126,11 +6916,18 @@ is-resolvable@^1.0.0: dependencies: tryit "^1.0.1" -is-stream@^1.0.1, is-stream@^1.1.0: +is-stream@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44" integrity sha1-EtSj3U5o4Lec6428hBc66A2RykQ= +is-symbol@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.2.tgz#a055f6ae57192caee329e7a860118b497a950f38" + integrity sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw== + dependencies: + has-symbols "^1.0.0" + is-type@0.0.1: version "0.0.1" resolved "https://registry.yarnpkg.com/is-type/-/is-type-0.0.1.tgz#f651d85c365d44955d14a51d8d7061f3f6b4779c" @@ -7148,11 +6945,6 @@ is-utf8@^0.2.0: resolved "https://registry.yarnpkg.com/is-utf8/-/is-utf8-0.2.1.tgz#4b0da1442104d1b336340e80797e865cf39f7d72" integrity sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI= -is-windows@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-0.2.0.tgz#de1aa6d63ea29dd248737b69f1ff8b8002d2108c" - integrity sha1-3hqm1j6indJIc3tp8f+LgALSEIw= - is-windows@^1.0.1, is-windows@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d" @@ -7178,10 +6970,12 @@ isarray@^2.0.4: resolved "https://registry.yarnpkg.com/isarray/-/isarray-2.0.4.tgz#38e7bcbb0f3ba1b7933c86ba1894ddfc3781bbb7" integrity sha512-GMxXOiUirWg1xTKRipM0Ek07rX+ubx4nNVElTJdNLYmNO/2YrDkgJGw9CljXn+r4EWiDQg/8lsRdHyg2PJuUaA== -isbinaryfile@^3.0.0: - version "3.0.2" - resolved "https://registry.yarnpkg.com/isbinaryfile/-/isbinaryfile-3.0.2.tgz#4a3e974ec0cba9004d3fc6cde7209ea69368a621" - integrity sha1-Sj6XTsDLqQBNP8bN5yCeppNopiE= +isbinaryfile@^3.0.3: + version "3.0.3" + resolved "https://registry.yarnpkg.com/isbinaryfile/-/isbinaryfile-3.0.3.tgz#5d6def3edebf6e8ca8cae9c30183a804b5f8be80" + integrity sha512-8cJBL5tTd2OS0dM4jz07wQd5g0dCCqIhUxPIGtZfa5L6hWlvV5MHTITy/DBAsF+Oe2LS1X3krBUhNwaGUWpWxw== + dependencies: + buffer-alloc "^1.2.0" isexe@^2.0.0: version "2.0.0" @@ -7219,7 +7013,7 @@ jquery-deferred@^0.3.0: resolved "https://registry.yarnpkg.com/jquery-deferred/-/jquery-deferred-0.3.1.tgz#596eca1caaff54f61b110962b23cafea74c35355" integrity sha1-WW7KHKr/VPYbEQlisjyv6nTDU1U= -"jquery@>=1.7.1 <4.0.0": +"jquery@>=1.7.1 <4.0.0", jquery@^3.3.1: version "3.3.1" resolved "https://registry.yarnpkg.com/jquery/-/jquery-3.3.1.tgz#958ce29e81c9790f31be7792df5d4d95fc57fbca" integrity sha512-Ubldcmxp5np52/ENotGxlLe6aGMvmF4R8S6tZjsP6Knsaxd/xp3Zrh50cG93lR6nPXyUFwzN3ZSOQI0wRJNdGg== @@ -7239,11 +7033,6 @@ js-reporters@1.2.1: resolved "https://registry.yarnpkg.com/js-reporters/-/js-reporters-1.2.1.tgz#f88c608e324a3373a95bcc45ad305e5c979c459b" integrity sha1-+IxgjjJKM3OpW8xFrTBeXJecRZs= -js-tokens@1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-1.0.1.tgz#cc435a5c8b94ad15acb7983140fc80182c89aeae" - integrity sha1-zENaXIuUrRWst5gxQPyAGCyJrq4= - "js-tokens@^3.0.0 || ^4.0.0", js-tokens@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499" @@ -7254,7 +7043,7 @@ js-tokens@^3.0.2: resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-3.0.2.tgz#9866df395102130e38f7f996bceb65443209c25b" integrity sha1-mGbfOVECEw449/mWvOtlRDIJwls= -js-yaml@^3.2.5, js-yaml@^3.2.7, js-yaml@^3.9.1: +js-yaml@^3.12.0, js-yaml@^3.2.5, js-yaml@^3.2.7, js-yaml@^3.9.1: version "3.12.0" resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.12.0.tgz#eaed656ec8344f10f527c6bfa1b6e2244de167d1" integrity sha512-PIt2cnwmPfL4hKNwqeiuz4bKfnzHTBv6HyVgjahA6mPLwPDzjDWrplJBMjHUFxku/N3FlmrbyPclad+I+4mJ3A== @@ -7262,14 +7051,6 @@ js-yaml@^3.2.5, js-yaml@^3.2.7, js-yaml@^3.9.1: argparse "^1.0.7" esprima "^4.0.0" -js-yaml@^3.6.1: - version "3.9.0" - resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.9.0.tgz#4ffbbf25c2ac963b8299dc74da7e3740de1c18ce" - integrity sha512-0LoUNELX4S+iofCT8f4uEHIiRBR+c2AINyC8qRWfC6QNruLtxVZRJaPcu/xwMgFIgDxF25tGHaDjvxzJCNE9yw== - dependencies: - argparse "^1.0.7" - esprima "^4.0.0" - jsbn@~0.1.0: version "0.1.1" resolved "https://registry.yarnpkg.com/jsbn/-/jsbn-0.1.1.tgz#a5e654c2e5a2deb5f201d96cefbca80c0ef2f513" @@ -7322,6 +7103,11 @@ jsesc@^2.5.1: resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-2.5.2.tgz#80564d2e483dacf6e8ef209650a67df3f0c283a4" integrity sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA== +jsesc@~0.3.x: + version "0.3.0" + resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-0.3.0.tgz#1bf5ee63b4539fe2e26d0c1e99c240b97a457972" + integrity sha1-G/XuY7RTn+LibQwemcJAuXpFeXI= + jsesc@~0.5.0: version "0.5.0" resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-0.5.0.tgz#e7dee66e35d6fc16f710fe91d5cf69f70f08911d" @@ -7366,11 +7152,6 @@ json-stringify-safe@~5.0.1: resolved "https://registry.yarnpkg.com/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz#1296a2d58fd45f19a0f6ce01d65701e2c735b6eb" integrity sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus= -json5@^0.4.0: - version "0.4.0" - resolved "https://registry.yarnpkg.com/json5/-/json5-0.4.0.tgz#054352e4c4c80c86c0923877d449de176a732c8d" - integrity sha1-BUNS5MTIDIbAkjh31EneF2pzLI0= - json5@^0.5.1: version "0.5.1" resolved "https://registry.yarnpkg.com/json5/-/json5-0.5.1.tgz#1eade7acc012034ad84e2396767ead9fa5495821" @@ -7509,11 +7290,6 @@ less@^2.5.0: request "2.81.0" source-map "^0.5.3" -leven@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/leven/-/leven-1.0.2.tgz#9144b6eebca5f1d0680169f1a6770dcea60b75c3" - integrity sha1-kUS27ryl8dBoAWnxpncNzqYLdcM= - levn@^0.3.0, levn@~0.3.0: version "0.3.0" resolved "https://registry.yarnpkg.com/levn/-/levn-0.3.0.tgz#3b09924edf9f083c0490fdd4c0bc4421e04764ee" @@ -7529,10 +7305,10 @@ linkify-it@^2.0.0: dependencies: uc.micro "^1.0.1" -livereload-js@^2.2.2: - version "2.2.2" - resolved "https://registry.yarnpkg.com/livereload-js/-/livereload-js-2.2.2.tgz#6c87257e648ab475bc24ea257457edcc1f8d0bc2" - integrity sha1-bIclfmSKtHW8JOoldFftzB+NC8I= +livereload-js@^2.3.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/livereload-js/-/livereload-js-2.4.0.tgz#447c31cf1ea9ab52fc20db615c5ddf678f78009c" + integrity sha512-XPQH8Z2GDP/Hwz2PCDrh2mth4yFejwA1OZ/81Ti3LgKyhDcEjsSsqFWZojHG0va/duGd+WyosY7eXLDoOyqcPw== load-json-file@^1.0.0: version "1.1.0" @@ -7545,11 +7321,16 @@ load-json-file@^1.0.0: pinkie-promise "^2.0.0" strip-bom "^2.0.0" -loader.js@^4.2.3: +loader.js@^4.7.0: version "4.7.0" resolved "https://registry.yarnpkg.com/loader.js/-/loader.js-4.7.0.tgz#a1a52902001c83631efde9688b8ab3799325ef1f" integrity sha512-9M2KvGT6duzGMgkOcTkWb+PR/Q2Oe54df/tLgHGVmFpAmtqJ553xJh6N63iFYI2yjo2PeJXbS5skHi/QpJq4vA== +locate-character@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/locate-character/-/locate-character-2.0.5.tgz#f2d2614d49820ecb3c92d80d193b8db755f74c0f" + integrity sha512-n2GmejDXtOPBAZdIiEFy5dJ5N38xBCXLNOtw2WpB9kGh6pnrEuKlwYI+Tkpofc4wDtVXHtoAOJaMRlYG/oYaxg== + locate-path@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" @@ -7558,6 +7339,14 @@ locate-path@^2.0.0: p-locate "^2.0.0" path-exists "^3.0.0" +locate-path@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-3.0.0.tgz#dbec3b3ab759758071b58fe59fc41871af21400e" + integrity sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A== + dependencies: + p-locate "^3.0.0" + path-exists "^3.0.0" + lodash-es@^4.17.4: version "4.17.4" resolved "https://registry.yarnpkg.com/lodash-es/-/lodash-es-4.17.4.tgz#dcc1d7552e150a0640073ba9cb31d70f032950e7" @@ -7581,11 +7370,49 @@ lodash._baseassign@^3.0.0: lodash._basecopy "^3.0.0" lodash.keys "^3.0.0" +lodash._basebind@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basebind/-/lodash._basebind-2.3.0.tgz#2b5bc452a0e106143b21869f233bdb587417d248" + integrity sha1-K1vEUqDhBhQ7IYafIzvbWHQX0kg= + dependencies: + lodash._basecreate "~2.3.0" + lodash._setbinddata "~2.3.0" + lodash.isobject "~2.3.0" + lodash._basecopy@^3.0.0: version "3.0.1" resolved "https://registry.yarnpkg.com/lodash._basecopy/-/lodash._basecopy-3.0.1.tgz#8da0e6a876cf344c0ad8a54882111dd3c5c7ca36" integrity sha1-jaDmqHbPNEwK2KVIghEd08XHyjY= +lodash._basecreate@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreate/-/lodash._basecreate-2.3.0.tgz#9b88a86a4dcff7b7f3c61d83a2fcfc0671ec9de0" + integrity sha1-m4ioak3P97fzxh2Dovz8BnHsneA= + dependencies: + lodash._renative "~2.3.0" + lodash.isobject "~2.3.0" + lodash.noop "~2.3.0" + +lodash._basecreatecallback@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreatecallback/-/lodash._basecreatecallback-2.3.0.tgz#37b2ab17591a339e988db3259fcd46019d7ac362" + integrity sha1-N7KrF1kaM56YjbMln81GAZ16w2I= + dependencies: + lodash._setbinddata "~2.3.0" + lodash.bind "~2.3.0" + lodash.identity "~2.3.0" + lodash.support "~2.3.0" + +lodash._basecreatewrapper@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._basecreatewrapper/-/lodash._basecreatewrapper-2.3.0.tgz#aa0c61ad96044c3933376131483a9759c3651247" + integrity sha1-qgxhrZYETDkzN2ExSDqXWcNlEkc= + dependencies: + lodash._basecreate "~2.3.0" + lodash._setbinddata "~2.3.0" + lodash._slice "~2.3.0" + lodash.isobject "~2.3.0" + lodash._baseflatten@^3.0.0: version "3.1.4" resolved "https://registry.yarnpkg.com/lodash._baseflatten/-/lodash._baseflatten-3.1.4.tgz#0770ff80131af6e34f3b511796a7ba5214e65ff7" @@ -7613,21 +7440,90 @@ lodash._createassigner@^3.0.0: lodash._isiterateecall "^3.0.0" lodash.restparam "^3.0.0" +lodash._createwrapper@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._createwrapper/-/lodash._createwrapper-2.3.0.tgz#d1aae1102dadf440e8e06fc133a6edd7fe146075" + integrity sha1-0arhEC2t9EDo4G/BM6bt1/4UYHU= + dependencies: + lodash._basebind "~2.3.0" + lodash._basecreatewrapper "~2.3.0" + lodash.isfunction "~2.3.0" + +lodash._escapehtmlchar@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._escapehtmlchar/-/lodash._escapehtmlchar-2.3.0.tgz#d03da6bd82eedf38dc0a5b503d740ecd0e894592" + integrity sha1-0D2mvYLu3zjcCltQPXQOzQ6JRZI= + dependencies: + lodash._htmlescapes "~2.3.0" + +lodash._escapestringchar@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._escapestringchar/-/lodash._escapestringchar-2.3.0.tgz#cce73ae60fc6da55d2bf8a0679c23ca2bab149fc" + integrity sha1-zOc65g/G2lXSv4oGecI8orqxSfw= + lodash._getnative@^3.0.0: version "3.9.1" resolved "https://registry.yarnpkg.com/lodash._getnative/-/lodash._getnative-3.9.1.tgz#570bc7dede46d61cdcde687d65d3eecbaa3aaff5" integrity sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U= +lodash._htmlescapes@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._htmlescapes/-/lodash._htmlescapes-2.3.0.tgz#1ca98863cadf1fa1d82c84f35f31e40556a04f3a" + integrity sha1-HKmIY8rfH6HYLITzXzHkBVagTzo= + lodash._isiterateecall@^3.0.0: version "3.0.9" resolved "https://registry.yarnpkg.com/lodash._isiterateecall/-/lodash._isiterateecall-3.0.9.tgz#5203ad7ba425fae842460e696db9cf3e6aac057c" integrity sha1-UgOte6Ql+uhCRg5pbbnPPmqsBXw= +lodash._objecttypes@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._objecttypes/-/lodash._objecttypes-2.3.0.tgz#6a3ea3987dd6eeb8021b2d5c9c303549cc2bae1e" + integrity sha1-aj6jmH3W7rgCGy1cnDA1Scwrrh4= + +lodash._reinterpolate@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._reinterpolate/-/lodash._reinterpolate-2.3.0.tgz#03ee9d85c0e55cbd590d71608a295bdda51128ec" + integrity sha1-A+6dhcDlXL1ZDXFgiilb3aURKOw= + lodash._reinterpolate@~3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz#0ccf2d89166af03b3663c796538b75ac6e114d9d" integrity sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0= +lodash._renative@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._renative/-/lodash._renative-2.3.0.tgz#77d8edd4ced26dd5971f9e15a5f772e4e317fbd3" + integrity sha1-d9jt1M7SbdWXH54Vpfdy5OMX+9M= + +lodash._reunescapedhtml@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._reunescapedhtml/-/lodash._reunescapedhtml-2.3.0.tgz#db920b55ac7f3ff825939aceb9ba2c231713d24d" + integrity sha1-25ILVax/P/glk5rOubosIxcT0k0= + dependencies: + lodash._htmlescapes "~2.3.0" + lodash.keys "~2.3.0" + +lodash._setbinddata@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._setbinddata/-/lodash._setbinddata-2.3.0.tgz#e5610490acd13277d59858d95b5f2727f1508f04" + integrity sha1-5WEEkKzRMnfVmFjZW18nJ/FQjwQ= + dependencies: + lodash._renative "~2.3.0" + lodash.noop "~2.3.0" + +lodash._shimkeys@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._shimkeys/-/lodash._shimkeys-2.3.0.tgz#611f93149e3e6c721096b48769ef29537ada8ba9" + integrity sha1-YR+TFJ4+bHIQlrSHae8pU3rai6k= + dependencies: + lodash._objecttypes "~2.3.0" + +lodash._slice@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash._slice/-/lodash._slice-2.3.0.tgz#147198132859972e4680ca29a5992c855669aa5c" + integrity sha1-FHGYEyhZly5GgMoppZkshVZpqlw= + lodash.assign@^3.2.0: version "3.2.0" resolved "https://registry.yarnpkg.com/lodash.assign/-/lodash.assign-3.2.0.tgz#3ce9f0234b4b2223e296b8fa0ac1fee8ebca64fa" @@ -7642,6 +7538,15 @@ lodash.assignin@^4.1.0: resolved "https://registry.yarnpkg.com/lodash.assignin/-/lodash.assignin-4.2.0.tgz#ba8df5fb841eb0a3e8044232b0e263a8dc6a28a2" integrity sha1-uo31+4QesKPoBEIysOJjqNxqKKI= +lodash.bind@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.bind/-/lodash.bind-2.3.0.tgz#c2a8e18b68e5ecc152e2b168266116fea5b016cc" + integrity sha1-wqjhi2jl7MFS4rFoJmEW/qWwFsw= + dependencies: + lodash._createwrapper "~2.3.0" + lodash._renative "~2.3.0" + lodash._slice "~2.3.0" + lodash.castarray@^4.4.0: version "4.4.0" resolved "https://registry.yarnpkg.com/lodash.castarray/-/lodash.castarray-4.4.0.tgz#c02513515e309daddd4c24c60cfddcf5976d9115" @@ -7664,11 +7569,28 @@ lodash.defaults@^4.2.0: resolved "https://registry.yarnpkg.com/lodash.defaults/-/lodash.defaults-4.2.0.tgz#d09178716ffea4dde9e5fb7b37f6f0802274580c" integrity sha1-0JF4cW/+pN3p5ft7N/bwgCJ0WAw= +lodash.defaults@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.defaults/-/lodash.defaults-2.3.0.tgz#a832b001f138f3bb9721c2819a2a7cc5ae21ed25" + integrity sha1-qDKwAfE487uXIcKBmip8xa4h7SU= + dependencies: + lodash._objecttypes "~2.3.0" + lodash.keys "~2.3.0" + lodash.defaultsdeep@^4.6.0: version "4.6.0" resolved "https://registry.yarnpkg.com/lodash.defaultsdeep/-/lodash.defaultsdeep-4.6.0.tgz#bec1024f85b1bd96cbea405b23c14ad6443a6f81" integrity sha1-vsECT4WxvZbL6kBbI8FK1kQ6b4E= +lodash.escape@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.escape/-/lodash.escape-2.3.0.tgz#844c38c58f844e1362ebe96726159b62cf5f2a58" + integrity sha1-hEw4xY+EThNi6+lnJhWbYs9fKlg= + dependencies: + lodash._escapehtmlchar "~2.3.0" + lodash._reunescapedhtml "~2.3.0" + lodash.keys "~2.3.0" + lodash.find@^4.5.1: version "4.6.0" resolved "https://registry.yarnpkg.com/lodash.find/-/lodash.find-4.6.0.tgz#cb0704d47ab71789ffa0de8b97dd926fb88b13b1" @@ -7682,6 +7604,28 @@ lodash.flatten@^3.0.2: lodash._baseflatten "^3.0.0" lodash._isiterateecall "^3.0.0" +lodash.foreach@~2.3.x: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.foreach/-/lodash.foreach-2.3.0.tgz#083404c91e846ee77245fdf9d76519c68b2af168" + integrity sha1-CDQEyR6EbudyRf3512UZxosq8Wg= + dependencies: + lodash._basecreatecallback "~2.3.0" + lodash.forown "~2.3.0" + +lodash.forown@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.forown/-/lodash.forown-2.3.0.tgz#24fb4aaf800d45fc2dc60bfec3ce04c836a3ad7f" + integrity sha1-JPtKr4ANRfwtxgv+w84EyDajrX8= + dependencies: + lodash._basecreatecallback "~2.3.0" + lodash._objecttypes "~2.3.0" + lodash.keys "~2.3.0" + +lodash.identity@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.identity/-/lodash.identity-2.3.0.tgz#6b01a210c9485355c2a913b48b6711219a173ded" + integrity sha1-awGiEMlIU1XCqRO0i2cRIZoXPe0= + lodash.isarguments@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz#2f573d85c6a24289ff00663b491c1d338ff3458a" @@ -7692,6 +7636,18 @@ lodash.isarray@^3.0.0: resolved "https://registry.yarnpkg.com/lodash.isarray/-/lodash.isarray-3.0.4.tgz#79e4eb88c36a8122af86f844aa9bcd851b5fbb55" integrity sha1-eeTriMNqgSKvhvhEqpvNhRtfu1U= +lodash.isfunction@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.isfunction/-/lodash.isfunction-2.3.0.tgz#6b2973e47a647cf12e70d676aea13643706e5267" + integrity sha1-aylz5HpkfPEucNZ2rqE2Q3BuUmc= + +lodash.isobject@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.isobject/-/lodash.isobject-2.3.0.tgz#2e16d3fc583da9831968953f2d8e6d73434f6799" + integrity sha1-LhbT/Fg9qYMZaJU/LY5tc0NPZ5k= + dependencies: + lodash._objecttypes "~2.3.0" + lodash.isplainobject@^3.0.0: version "3.2.0" resolved "https://registry.yarnpkg.com/lodash.isplainobject/-/lodash.isplainobject-3.2.0.tgz#9a8238ae16b200432960cd7346512d0123fbf4c5" @@ -7715,6 +7671,15 @@ lodash.keys@^3.0.0: lodash.isarguments "^3.0.0" lodash.isarray "^3.0.0" +lodash.keys@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.keys/-/lodash.keys-2.3.0.tgz#b350f4f92caa9f45a4a2ecf018454cf2f28ae253" + integrity sha1-s1D0+Syqn0WkouzwGEVM8vKK4lM= + dependencies: + lodash._renative "~2.3.0" + lodash._shimkeys "~2.3.0" + lodash.isobject "~2.3.0" + lodash.keysin@^3.0.0: version "3.0.8" resolved "https://registry.yarnpkg.com/lodash.keysin/-/lodash.keysin-3.0.8.tgz#22c4493ebbedb1427962a54b445b2c8a767fb47f" @@ -7745,11 +7710,21 @@ lodash.merge@^3.3.2: lodash.keysin "^3.0.0" lodash.toplainobject "^3.0.0" -lodash.merge@^4.3.0, lodash.merge@^4.4.0, lodash.merge@^4.6.0: +lodash.merge@^4.3.0, lodash.merge@^4.6.0: version "4.6.0" resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.0.tgz#69884ba144ac33fe699737a6086deffadd0f89c5" integrity sha1-aYhLoUSsM/5plzemCG3v+t0PicU= +lodash.merge@^4.3.1: + version "4.6.1" + resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.1.tgz#adc25d9cb99b9391c59624f379fbba60d7111d54" + integrity sha512-AOYza4+Hf5z1/0Hztxpm2/xiPZgi/cjMqdnKTUWTBSKchJlxXXuUSxCCl8rJlf4g6yww/j6mA8nC8Hw/EZWxKQ== + +lodash.noop@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.noop/-/lodash.noop-2.3.0.tgz#3059d628d51bbf937cd2a0b6fc3a7f212a669c2c" + integrity sha1-MFnWKNUbv5N80qC2/Dp/ISpmnCw= + lodash.omit@^4.1.0: version "4.5.0" resolved "https://registry.yarnpkg.com/lodash.omit/-/lodash.omit-4.5.0.tgz#6eb19ae5a1ee1dd9df0b969e66ce0b7fa30b5e60" @@ -7765,7 +7740,14 @@ lodash.sortby@^4.7.0: resolved "https://registry.yarnpkg.com/lodash.sortby/-/lodash.sortby-4.7.0.tgz#edd14c824e2cc9c1e0b0a1b42bb5210516a42438" integrity sha1-7dFMgk4sycHgsKG0K7UhBRakJDg= -lodash.template@^4.2.5: +lodash.support@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.support/-/lodash.support-2.3.0.tgz#7eaf038af4f0d6aab776b44aa6dcfc80334c9bfd" + integrity sha1-fq8DivTw1qq3drRKptz8gDNMm/0= + dependencies: + lodash._renative "~2.3.0" + +lodash.template@^4.4.0: version "4.4.0" resolved "https://registry.yarnpkg.com/lodash.template/-/lodash.template-4.4.0.tgz#e73a0385c8355591746e020b99679c690e68fba0" integrity sha1-5zoDhcg1VZF0bgILmWecaQ5o+6A= @@ -7773,6 +7755,19 @@ lodash.template@^4.2.5: lodash._reinterpolate "~3.0.0" lodash.templatesettings "^4.0.0" +lodash.template@~2.3.x: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.template/-/lodash.template-2.3.0.tgz#4e3e29c433b4cfea675ec835e6f12391c61fd22b" + integrity sha1-Tj4pxDO0z+pnXsg15vEjkcYf0is= + dependencies: + lodash._escapestringchar "~2.3.0" + lodash._reinterpolate "~2.3.0" + lodash.defaults "~2.3.0" + lodash.escape "~2.3.0" + lodash.keys "~2.3.0" + lodash.templatesettings "~2.3.0" + lodash.values "~2.3.0" + lodash.templatesettings@^4.0.0: version "4.1.0" resolved "https://registry.yarnpkg.com/lodash.templatesettings/-/lodash.templatesettings-4.1.0.tgz#2b4d4e95ba440d915ff08bc899e4553666713316" @@ -7780,6 +7775,14 @@ lodash.templatesettings@^4.0.0: dependencies: lodash._reinterpolate "~3.0.0" +lodash.templatesettings@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.templatesettings/-/lodash.templatesettings-2.3.0.tgz#303d132c342710040d5a18efaa2d572fd03f8cdc" + integrity sha1-MD0TLDQnEAQNWhjvqi1XL9A/jNw= + dependencies: + lodash._reinterpolate "~2.3.0" + lodash.escape "~2.3.0" + lodash.toplainobject@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/lodash.toplainobject/-/lodash.toplainobject-3.0.0.tgz#28790ad942d293d78aa663a07ecf7f52ca04198d" @@ -7798,17 +7801,19 @@ lodash.uniqby@^4.7.0: resolved "https://registry.yarnpkg.com/lodash.uniqby/-/lodash.uniqby-4.7.0.tgz#d99c07a669e9e6d24e1362dfe266c67616af1302" integrity sha1-2ZwHpmnp5tJOE2Lf4mbGdhavEwI= +lodash.values@~2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/lodash.values/-/lodash.values-2.3.0.tgz#ca96fbe60a20b0b0ec2ba2ba5fc6a765bd14a3ba" + integrity sha1-ypb75gogsLDsK6K6X8anZb0Uo7o= + dependencies: + lodash.keys "~2.3.0" + lodash@4.16.2: version "4.16.2" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.16.2.tgz#3e626db827048a699281a8a125226326cfc0e652" integrity sha1-PmJtuCcEimmSgaihJSJjJs/A5lI= -lodash@^3.10.0, lodash@^3.10.1, lodash@^3.9.3: - version "3.10.1" - resolved "https://registry.yarnpkg.com/lodash/-/lodash-3.10.1.tgz#5bf45e8e49ba4189e17d482789dfd15bd140b7b6" - integrity sha1-W/Rejkm6QYnhfUgnid/RW9FAt7Y= - -lodash@^4.13.1, lodash@^4.14.0, lodash@^4.17.10, lodash@^4.17.4, lodash@^4.5.1, lodash@^4.6.1: +lodash@^4.13.1, lodash@^4.14.0, lodash@^4.17.10, lodash@^4.17.4, lodash@^4.5.1: version "4.17.11" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.11.tgz#b39ea6229ef607ecd89e2c8df12536891cac9b8d" integrity sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg== @@ -7858,6 +7863,13 @@ lru-cache@^4.0.1: pseudomap "^1.0.2" yallist "^2.1.2" +magic-string@^0.24.0: + version "0.24.1" + resolved "https://registry.yarnpkg.com/magic-string/-/magic-string-0.24.1.tgz#7e38e5f126cae9f15e71f0cf8e450818ca7d5a8f" + integrity sha512-YBfNxbJiixMzxW40XqJEIldzHyh5f7CZKalo1uZffevyrPEX8Qgo9s0dmcORLHdV47UyvJg8/zD+6hQG3qvJrA== + dependencies: + sourcemap-codec "^1.4.1" + make-array@^0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/make-array/-/make-array-0.1.2.tgz#335e36ebb0c5a43154d21213a1ecaeae2a1bb3ef" @@ -7905,7 +7917,7 @@ markdown-it-terminal@0.1.0: lodash.merge "^4.6.0" markdown-it "^8.3.1" -markdown-it@^8.3.0, markdown-it@^8.3.1: +markdown-it@^8.3.1: version "8.3.1" resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-8.3.1.tgz#2f4b622948ccdc193d66f3ca2d43125ac4ac7323" integrity sha1-L0tiKUjM3Bk9ZvPKLUMSWsSscyM= @@ -7916,7 +7928,18 @@ markdown-it@^8.3.0, markdown-it@^8.3.1: mdurl "^1.0.1" uc.micro "^1.0.3" -matcher-collection@^1.0.0, matcher-collection@^1.0.5: +markdown-it@^8.4.2: + version "8.4.2" + resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-8.4.2.tgz#386f98998dc15a37722aa7722084f4020bdd9b54" + integrity sha512-GcRz3AWTqSUphY3vsUqQSFMbgR38a4Lh3GWlHRh/7MRwz8mcu9n2IO7HOh+bXHrR9kOPDl5RNCaEsrneb+xhHQ== + dependencies: + argparse "^1.0.7" + entities "~1.1.1" + linkify-it "^2.0.0" + mdurl "^1.0.1" + uc.micro "^1.0.5" + +matcher-collection@^1.0.0, matcher-collection@^1.0.4, matcher-collection@^1.0.5: version "1.0.5" resolved "https://registry.yarnpkg.com/matcher-collection/-/matcher-collection-1.0.5.tgz#2ee095438372cb8884f058234138c05c644ec339" integrity sha512-nUCmzKipcJEwYsBVAFh5P+d7JBuhJaW1xs85Hara9xuMLqtCVUrW6DSC0JVIkluxEH2W45nPBM/wjHtBXa/tYA== @@ -7973,6 +7996,13 @@ memory-streams@^0.1.0: dependencies: readable-stream "~1.0.2" +memory-streams@^0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/memory-streams/-/memory-streams-0.1.3.tgz#d9b0017b4b87f1d92f55f2745c9caacb1dc93ceb" + integrity sha512-qVQ/CjkMyMInPaaRMrwWNDvf6boRZXaT/DbQeMYcCWuXPEBf1v8qChOc9OlEVQp2uOvRXa1Qu30fLmKhY6NipA== + dependencies: + readable-stream "~1.0.2" + meow@^3.4.0: version "3.7.0" resolved "https://registry.yarnpkg.com/meow/-/meow-3.7.0.tgz#72cb668b425228290abbfa856892587308a801fb" @@ -8014,6 +8044,11 @@ merge-trees@^2.0.0: fs-updater "^1.0.4" heimdalljs "^0.2.5" +merge2@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.2.3.tgz#7ee99dbd69bb6481689253f018488a1b902b0ed5" + integrity sha512-gdUU1Fwj5ep4kplwcmftruWofEFt6lfpkkr3h860CXbAB9c3hGb55EOL2ali0Td5oebvW0E1+3Sr+Ur7XfKpRA== + merge@^1.1.3, merge@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/merge/-/merge-1.2.0.tgz#7531e39d4949c281a66b8c5a6e0265e8b05894da" @@ -8024,7 +8059,7 @@ methods@~1.1.2: resolved "https://registry.yarnpkg.com/methods/-/methods-1.1.2.tgz#5529a4d67654134edcc5266656835b0f851afcee" integrity sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4= -micromatch@^2.1.5, micromatch@^2.3.7: +micromatch@^2.3.11: version "2.3.11" resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-2.3.11.tgz#86677c97d1720b363431d04d0d15293bd38c1565" integrity sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU= @@ -8043,7 +8078,7 @@ micromatch@^2.1.5, micromatch@^2.3.7: parse-glob "^3.0.4" regex-cache "^0.4.2" -micromatch@^3.0.4, micromatch@^3.1.4: +micromatch@^3.0.4, micromatch@^3.1.10, micromatch@^3.1.4: version "3.1.10" resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-3.1.10.tgz#70859bc95c9840952f359a068a3fc49f9ecfac23" integrity sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg== @@ -8070,22 +8105,17 @@ miller-rabin@^4.0.0: bn.js "^4.0.0" brorand "^1.0.1" -"mime-db@>= 1.27.0 < 2": - version "1.27.0" - resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.27.0.tgz#820f572296bbd20ec25ed55e5b5de869e5436eb1" - integrity sha1-gg9XIpa70g7CXtVeW13oaeVDbrE= +"mime-db@>= 1.36.0 < 2", mime-db@~1.37.0: + version "1.37.0" + resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.37.0.tgz#0b6a0ce6fdbe9576e25f1f2d2fde8830dc0ad0d8" + integrity sha512-R3C4db6bgQhlIhPU48fUtdVmKnflq+hRdad7IyKhtFj06VPNVdk2RhiYL3UjQIlso8L+YxAtFkobT0VK+S/ybg== mime-db@~1.29.0: version "1.29.0" resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.29.0.tgz#48d26d235589651704ac5916ca06001914266878" integrity sha1-SNJtI1WJZRcErFkWygYAGRQmaHg= -mime-db@~1.37.0: - version "1.37.0" - resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.37.0.tgz#0b6a0ce6fdbe9576e25f1f2d2fde8830dc0ad0d8" - integrity sha512-R3C4db6bgQhlIhPU48fUtdVmKnflq+hRdad7IyKhtFj06VPNVdk2RhiYL3UjQIlso8L+YxAtFkobT0VK+S/ybg== - -mime-types@^2.1.12, mime-types@~2.1.18, mime-types@~2.1.19, mime-types@~2.1.7: +mime-types@^2.1.12, mime-types@^2.1.18, mime-types@~2.1.18, mime-types@~2.1.19, mime-types@~2.1.7: version "2.1.21" resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.21.tgz#28995aa1ecb770742fe6ae7e58f9181c744b3f96" integrity sha512-3iL6DbwpyLzjR3xHSFNFeb9Nz/M8WDkX33t1GFQnFOllWk8pOrh/LSrB5OXlnlW5P9LH73X6loW/eogc+F5lJg== @@ -8099,11 +8129,6 @@ mime-types@~2.1.15: dependencies: mime-db "~1.29.0" -mime@1.3.4: - version "1.3.4" - resolved "https://registry.yarnpkg.com/mime/-/mime-1.3.4.tgz#115f9e3b6b3daf2959983cb38f149a2d40eb5d53" - integrity sha1-EV+eO2s9rylZmDyzjxSaLUDrXVM= - mime@1.4.1: version "1.4.1" resolved "https://registry.yarnpkg.com/mime/-/mime-1.4.1.tgz#121f9ebc49e3766f311a76e1fa1c8003c4b03aa6" @@ -8136,13 +8161,6 @@ minimalistic-crypto-utils@^1.0.0, minimalistic-crypto-utils@^1.0.1: dependencies: brace-expansion "^1.1.7" -minimatch@^2.0.3: - version "2.0.10" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-2.0.10.tgz#8d087c39c6b38c001b97fca7ce6d0e1e80afbac7" - integrity sha1-jQh8OcazjAAbl/ynzm0OHoCvusc= - dependencies: - brace-expansion "^1.0.0" - minimist@0.0.8, minimist@~0.0.1: version "0.0.8" resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.0.8.tgz#857fcabfc3397d2625b8228262e86aa7a011b05d" @@ -8233,14 +8251,14 @@ moment@^2.10.2, moment@^2.19.3: resolved "https://registry.yarnpkg.com/moment/-/moment-2.23.0.tgz#759ea491ac97d54bac5ad776996e2a58cc1bc225" integrity sha512-3IE39bHVqFbWWaPOMHZF98Q9c3LDKGTmypMiTM2QygGXXElkFWIH7GxfmlwmY2vwa+wmNsoYZmG2iusf1ZjJoA== -morgan@^1.8.1: - version "1.8.2" - resolved "https://registry.yarnpkg.com/morgan/-/morgan-1.8.2.tgz#784ac7734e4a453a9c6e6e8680a9329275c8b687" - integrity sha1-eErHc05KRTqcbm6GgKkyknXItoc= +morgan@^1.9.0: + version "1.9.1" + resolved "https://registry.yarnpkg.com/morgan/-/morgan-1.9.1.tgz#0a8d16734a1d9afbc824b99df87e738e58e2da59" + integrity sha512-HQStPIV4y3afTiCYVxirakhlCfGkI161c76kKFca7Fk1JusM//Qeo1ej2XaMniiNeaZklMVrh3vTtIzpzwbpmA== dependencies: - basic-auth "~1.1.0" - debug "2.6.8" - depd "~1.1.0" + basic-auth "~2.0.0" + debug "2.6.9" + depd "~1.1.2" on-finished "~2.3.0" on-headers "~1.0.1" @@ -8249,11 +8267,6 @@ mout@^1.0.0: resolved "https://registry.yarnpkg.com/mout/-/mout-1.0.0.tgz#9bdf1d4af57d66d47cb353a6335a3281098e1501" integrity sha1-m98dSvV9ZtR8s1OmM1oygQmOFQE= -ms@0.7.1: - version "0.7.1" - resolved "https://registry.yarnpkg.com/ms/-/ms-0.7.1.tgz#9cd13c03adbff25b65effde7ce864ee952017098" - integrity sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg= - ms@0.7.2: version "0.7.2" resolved "https://registry.yarnpkg.com/ms/-/ms-0.7.2.tgz#ae25cf2512b3885a1d95d7f037868d8431124765" @@ -8351,14 +8364,6 @@ no-case@^2.2.0: dependencies: lower-case "^1.1.1" -node-fetch@^1.3.3: - version "1.7.3" - resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-1.7.3.tgz#980f6f72d85211a5347c6b2bc18c5b84c3eb47ef" - integrity sha512-NhZ4CsKx7cYm2vSrBAr2PvFOe6sWDf0UYLRqA6svUYg7+/TSfVAu49jYC4BvQ4Sms9SZgdqGBgroqfDhJdTyKQ== - dependencies: - encoding "^0.1.11" - is-stream "^1.0.1" - node-int64@^0.4.0: version "0.4.0" resolved "https://registry.yarnpkg.com/node-int64/-/node-int64-0.4.0.tgz#87a9065cdb355d3182d8f94ce11188b825c68a3b" @@ -8444,12 +8449,12 @@ npm-bundled@^1.0.1: resolved "https://registry.yarnpkg.com/npm-bundled/-/npm-bundled-1.0.5.tgz#3c1732b7ba936b3a10325aef616467c0ccbcc979" integrity sha512-m/e6jgWu8/v5niCUKQi9qQl8QdeEduFA96xHDDzFGqly0OOjI7c+60KM/2sppfnUU9JJagf+zs+yGhqSOFj71g== -npm-git-info@^1.0.0, npm-git-info@^1.0.3: +npm-git-info@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/npm-git-info/-/npm-git-info-1.0.3.tgz#a933c42ec321e80d3646e0d6e844afe94630e1d5" integrity sha1-qTPELsMh6A02RuDW6ESv6UYw4dU= -npm-package-arg@^6.0.0: +npm-package-arg@^6.1.0: version "6.1.0" resolved "https://registry.yarnpkg.com/npm-package-arg/-/npm-package-arg-6.1.0.tgz#15ae1e2758a5027efb4c250554b85a737db7fcc1" integrity sha512-zYbhP2k9DbJhA0Z3HKUePUgdB1x7MfIfKssC+WLPFMKTBZKpZh5m13PgexJjCq6KW7j17r0jHWcCpxEqnnncSA== @@ -8528,6 +8533,11 @@ object-hash@^1.3.1: resolved "https://registry.yarnpkg.com/object-hash/-/object-hash-1.3.1.tgz#fde452098a951cb145f039bb7d455449ddc126df" integrity sha512-OSuu/pU4ENM9kmREg0BdNrUDIl1heYa4mBZacJc+vVWz4GtAwu7jO8s4AIt2aGRUTqxykpWzI3Oqnsm13tTMDA== +object-keys@^1.0.12: + version "1.0.12" + resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.0.12.tgz#09c53855377575310cca62f55bb334abff7b3ed2" + integrity sha512-FTMyFUm2wBcGHnH2eXmz7tC6IwlqQZ6mVZ+6dm6vZ4IQIHjs6FdNsQBuKGPuUUUY6NfJw2PshC08Tn6LzLDOag== + object-visit@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/object-visit/-/object-visit-1.0.1.tgz#f79c4493af0c5377b59fe39d395e41042dd045bb" @@ -8535,6 +8545,14 @@ object-visit@^1.0.0: dependencies: isobject "^3.0.0" +object.getownpropertydescriptors@^2.0.3: + version "2.0.3" + resolved "https://registry.yarnpkg.com/object.getownpropertydescriptors/-/object.getownpropertydescriptors-2.0.3.tgz#8758c846f5b407adab0f236e0986f14b051caa16" + integrity sha1-h1jIRvW0B62rDyNuCYbxSwUcqhY= + dependencies: + define-properties "^1.1.2" + es-abstract "^1.5.1" + object.omit@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/object.omit/-/object.omit-2.0.1.tgz#1a9c744829f39dbb858c76ca3579ae2a54ebd1fa" @@ -8656,15 +8674,6 @@ osenv@^0.1.4, osenv@^0.1.5: os-homedir "^1.0.0" os-tmpdir "^1.0.0" -output-file-sync@^1.1.0: - version "1.1.2" - resolved "https://registry.yarnpkg.com/output-file-sync/-/output-file-sync-1.1.2.tgz#d0a33eefe61a205facb90092e826598d5245ce76" - integrity sha1-0KM+7+YaIF+suQCS6CZZjVJFznY= - dependencies: - graceful-fs "^4.1.4" - mkdirp "^0.5.1" - object-assign "^4.1.0" - p-finally@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/p-finally/-/p-finally-1.0.0.tgz#3fbcfb15b899a44123b34b6dcc18b724336a2cae" @@ -8675,6 +8684,13 @@ p-limit@^1.1.0: resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.1.0.tgz#b07ff2d9a5d88bec806035895a2bab66a27988bc" integrity sha1-sH/y2aXYi+yAYDWJWiurZqJ5iLw= +p-limit@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-2.1.0.tgz#1d5a0d20fb12707c758a655f6bbc4386b5930d68" + integrity sha512-NhURkNcrVB+8hNfLuysU8enY5xn2KXphsHBaC2YmRNTZRc7RWusw6apSpdEj3jo4CMb6W9nrF6tTnsJsJeyu6g== + dependencies: + p-try "^2.0.0" + p-locate@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" @@ -8682,6 +8698,18 @@ p-locate@^2.0.0: dependencies: p-limit "^1.1.0" +p-locate@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-3.0.0.tgz#322d69a05c0264b25997d9f40cd8a891ab0064a4" + integrity sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ== + dependencies: + p-limit "^2.0.0" + +p-try@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-2.0.0.tgz#85080bb87c64688fa47996fe8f7dfbe8211760b1" + integrity sha512-hMp0onDKIajHfIkdRk3P4CdCmErkYAxxDtP3Wx/4nZ3aGlau2VKh3mZpcuFkH27WQkL/3WBCPOktzA9ZOAnMQQ== + pako@~0.2.0: version "0.2.9" resolved "https://registry.yarnpkg.com/pako/-/pako-0.2.9.tgz#f3f7522f4ef782348da8161bad9ecfd51bf83a75" @@ -8722,6 +8750,11 @@ parse-json@^2.2.0: dependencies: error-ex "^1.2.0" +parse-ms@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/parse-ms/-/parse-ms-1.0.1.tgz#56346d4749d78f23430ca0c713850aef91aa361d" + integrity sha1-VjRtR0nXjyNDDKDHE4UK75GqNh0= + parse-passwd@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/parse-passwd/-/parse-passwd-1.0.0.tgz#6d5b934a456993b23d37f40a382d6f1666a8e5c6" @@ -8746,7 +8779,7 @@ parseuri@0.0.5: dependencies: better-assert "~1.0.0" -parseurl@~1.3.1, parseurl@~1.3.2: +parseurl@~1.3.2: version "1.3.2" resolved "https://registry.yarnpkg.com/parseurl/-/parseurl-1.3.2.tgz#fc289d4ed8993119460c156253262cdc8de65bf3" integrity sha1-/CidTtiZMRlGDBViUyYs3I3mW/M= @@ -8768,10 +8801,10 @@ path-browserify@~0.0.0: resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-0.0.1.tgz#e6c4ddd7ed3aa27c68a20cc4e50e1a4ee83bbc4a" integrity sha512-BapA40NHICOS+USX9SN4tyhq+A2RrN/Ws5F0Z5aMHDp98Fl86lX8Oti8B7uN93L4Ifv4fHOEA+pQw87gmMO/lQ== -path-exists@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-1.0.0.tgz#d5a8998eb71ef37a74c34eb0d9eba6e878eea081" - integrity sha1-1aiZjrce83p0w06w2eum6HjuoIE= +path-dirname@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/path-dirname/-/path-dirname-1.0.2.tgz#cc33d24d525e099a5388c0336c6e32b9160609e0" + integrity sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA= path-exists@^2.0.0: version "2.1.0" @@ -8829,6 +8862,13 @@ path-type@^1.0.0: pify "^2.0.0" pinkie-promise "^2.0.0" +path-type@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-type/-/path-type-3.0.0.tgz#cef31dc8e0a1a3bb0d105c0cd97cf3bf47f4e36f" + integrity sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg== + dependencies: + pify "^3.0.0" + pbkdf2@^3.0.3: version "3.0.17" resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.0.17.tgz#976c206530617b14ebb32114239f7b09336e93a6" @@ -8855,6 +8895,11 @@ pify@^2.0.0, pify@^2.3.0: resolved "https://registry.yarnpkg.com/pify/-/pify-2.3.0.tgz#ed141a6ac043a849ea588498e7dca8b15330e90c" integrity sha1-7RQaasBDqEnqWISY59yosVMw6Qw= +pify@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/pify/-/pify-3.0.0.tgz#e5a4acd2c101fdf3d9a4d07f0dbc4db49dd28176" + integrity sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY= + pinkie-promise@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/pinkie-promise/-/pinkie-promise-2.0.1.tgz#2135d6dfa7a358c069ac9b178776288228450ffa" @@ -8889,10 +8934,10 @@ popper.js@^1.14.1: resolved "https://registry.yarnpkg.com/popper.js/-/popper.js-1.14.6.tgz#ab20dd4edf9288b8b3b6531c47c361107b60b4b0" integrity sha512-AGwHGQBKumlk/MDfrSOf0JHhJCImdDMcGNoqKmKkU+68GFazv3CQ6q9r7Ja1sKDZmYWTckY/uLyEznheTDycnA== -portfinder@^1.0.7: - version "1.0.13" - resolved "https://registry.yarnpkg.com/portfinder/-/portfinder-1.0.13.tgz#bb32ecd87c27104ae6ee44b5a3ccbf0ebb1aede9" - integrity sha1-uzLs2HwnEErm7kS1o8y/Drsa7ek= +portfinder@^1.0.15: + version "1.0.20" + resolved "https://registry.yarnpkg.com/portfinder/-/portfinder-1.0.20.tgz#bea68632e54b2e13ab7b0c4775e9b41bf270e44a" + integrity sha512-Yxe4mTyDzTd59PZJY4ojZR8F+E5e97iq2ZOHPz3HDgSvYC5siNad2tLooQ5y5QHyQhc3xVqvyk/eNA3wuoa7Sw== dependencies: async "^1.5.2" debug "^2.2.0" @@ -8922,6 +8967,13 @@ pretender@2.1.0: fake-xml-http-request "^2.0.0" route-recognizer "^0.3.3" +pretty-ms@^3.1.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/pretty-ms/-/pretty-ms-3.2.0.tgz#87a8feaf27fc18414d75441467d411d6e6098a25" + integrity sha512-ZypexbfVUGTFxb0v+m1bUyy92DHe5SyYlnyY0msyms5zd3RwyvNgyxZZsXXgoyzlxjx5MiqtXUdhUfvQbe0A2Q== + dependencies: + parse-ms "^1.0.0" + printf@^0.5.1: version "0.5.1" resolved "https://registry.yarnpkg.com/printf/-/printf-0.5.1.tgz#e0466788260859ed153006dc6867f09ddf240cf3" @@ -8959,7 +9011,7 @@ progress@^2.0.0: resolved "https://registry.yarnpkg.com/progress/-/progress-2.0.3.tgz#7e8cf8d8f5b8f239c1bc68beb4eb78567d572ef8" integrity sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA== -promise-map-series@^0.2.0, promise-map-series@^0.2.1: +promise-map-series@^0.2.0, promise-map-series@^0.2.1, promise-map-series@^0.2.3: version "0.2.3" resolved "https://registry.yarnpkg.com/promise-map-series/-/promise-map-series-0.2.3.tgz#c2d377afc93253f6bd03dbb77755eb88ab20a847" integrity sha1-wtN3r8kyU/a9A9u3d1XriKsgqEc= @@ -8973,14 +9025,6 @@ promise@^7.1.1: dependencies: asap "~2.0.3" -proxy-addr@~1.1.3: - version "1.1.5" - resolved "https://registry.yarnpkg.com/proxy-addr/-/proxy-addr-1.1.5.tgz#71c0ee3b102de3f202f3b64f608d173fcba1a918" - integrity sha1-ccDuOxAt4/IC87ZPYI0XP8uhqRg= - dependencies: - forwarded "~0.1.0" - ipaddr.js "1.4.0" - proxy-addr@~2.0.4: version "2.0.4" resolved "https://registry.yarnpkg.com/proxy-addr/-/proxy-addr-2.0.4.tgz#ecfc733bf22ff8c6f407fa275327b9ab67e48b93" @@ -9044,11 +9088,6 @@ q@1.4.1: resolved "https://registry.yarnpkg.com/q/-/q-1.4.1.tgz#55705bcd93c5f3673530c2c2cbc0c2b3addc286e" integrity sha1-VXBbzZPF82c1MMLCy8DCs63cKG4= -q@^1.1.2: - version "1.5.1" - resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7" - integrity sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc= - qs@6.4.0, qs@~6.4.0: version "6.4.0" resolved "https://registry.yarnpkg.com/qs/-/qs-6.4.0.tgz#13e26d28ad6b0ffaa91312cd3bf708ed351e7233" @@ -9093,6 +9132,14 @@ quick-temp@^0.1.2, quick-temp@^0.1.3, quick-temp@^0.1.5, quick-temp@^0.1.8: rimraf "^2.5.4" underscore.string "~3.3.4" +qunit-dom@^0.7.1: + version "0.7.1" + resolved "https://registry.yarnpkg.com/qunit-dom/-/qunit-dom-0.7.1.tgz#2e6ad4a6453c034f88ef415250b37e82572460b9" + integrity sha512-8mwF7taWSqDrVRYHgp98nJmoTeE2z37K7RmHjV18pX0YoGxaJSYg+y1bRE0h3tsjSMs85W9gL/WR62yfoQN3VA== + dependencies: + broccoli-funnel "^2.0.0" + broccoli-merge-trees "^2.0.0" + qunit@~2.6.0: version "2.6.2" resolved "https://registry.yarnpkg.com/qunit/-/qunit-2.6.2.tgz#551210c5cf857258a4fe39a7fe15d9e14dfef22c" @@ -9244,26 +9291,6 @@ readable-stream@~2.0.0: string_decoder "~0.10.x" util-deprecate "~1.0.1" -recast@0.10.33: - version "0.10.33" - resolved "https://registry.yarnpkg.com/recast/-/recast-0.10.33.tgz#942808f7aa016f1fa7142c461d7e5704aaa8d697" - integrity sha1-lCgI96oBbx+nFCxGHX5XBKqo1pc= - dependencies: - ast-types "0.8.12" - esprima-fb "~15001.1001.0-dev-harmony-fb" - private "~0.1.5" - source-map "~0.5.0" - -recast@^0.10.10: - version "0.10.43" - resolved "https://registry.yarnpkg.com/recast/-/recast-0.10.43.tgz#b95d50f6d60761a5f6252e15d80678168491ce7f" - integrity sha1-uV1Q9tYHYaX2JS4V2AZ4FoSRzn8= - dependencies: - ast-types "0.8.15" - esprima-fb "~15001.1001.0-dev-harmony-fb" - private "~0.1.5" - source-map "~0.5.0" - recast@^0.11.17, recast@^0.11.3: version "0.11.23" resolved "https://registry.yarnpkg.com/recast/-/recast-0.11.23.tgz#451fd3004ab1e4df9b4e4b66376b2a21912462d3" @@ -9348,18 +9375,6 @@ regenerator-transform@^0.13.3: dependencies: private "^0.1.6" -regenerator@0.8.40: - version "0.8.40" - resolved "https://registry.yarnpkg.com/regenerator/-/regenerator-0.8.40.tgz#a0e457c58ebdbae575c9f8cd75127e93756435d8" - integrity sha1-oORXxY69uuV1yfjNdRJ+k3VkNdg= - dependencies: - commoner "~0.10.3" - defs "~1.1.0" - esprima-fb "~15001.1001.0-dev-harmony-fb" - private "~0.1.5" - recast "0.10.33" - through "~2.3.8" - regex-cache@^0.4.2: version "0.4.4" resolved "https://registry.yarnpkg.com/regex-cache/-/regex-cache-0.4.4.tgz#75bdc58a2a1496cec48a12835bc54c8d562336dd" @@ -9401,17 +9416,6 @@ regexpu-core@^4.1.3, regexpu-core@^4.2.0: unicode-match-property-ecmascript "^1.0.4" unicode-match-property-value-ecmascript "^1.0.2" -regexpu@^1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/regexpu/-/regexpu-1.3.0.tgz#e534dc991a9e5846050c98de6d7dd4a55c9ea16d" - integrity sha1-5TTcmRqeWEYFDJjebX3UpVyeoW0= - dependencies: - esprima "^2.6.0" - recast "^0.10.10" - regenerate "^1.2.1" - regjsgen "^0.2.0" - regjsparser "^0.1.4" - regjsgen@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/regjsgen/-/regjsgen-0.2.0.tgz#6c016adeac554f75823fe37ac05b92d5a4edb1f7" @@ -9451,13 +9455,6 @@ repeat-string@^1.5.2, repeat-string@^1.6.1: resolved "https://registry.yarnpkg.com/repeat-string/-/repeat-string-1.6.1.tgz#8dcae470e1c88abc2d600fff4a776286da75e637" integrity sha1-jcrkcOHIirwtYA//Sndihtp15jc= -repeating@^1.1.0, repeating@^1.1.2: - version "1.1.3" - resolved "https://registry.yarnpkg.com/repeating/-/repeating-1.1.3.tgz#3d4114218877537494f97f77f9785fab810fa4ac" - integrity sha1-PUEUIYh3U3SU+X93+Xhfq4EPpKw= - dependencies: - is-finite "^1.0.0" - repeating@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/repeating/-/repeating-2.0.1.tgz#5214c53a926d3552707527fbab415dbc08d06dda" @@ -9571,6 +9568,11 @@ require-main-filename@^1.0.1: resolved "https://registry.yarnpkg.com/require-main-filename/-/require-main-filename-1.0.1.tgz#97f717b69d48784f5f526a6c5aa8ffdda055a4d1" integrity sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE= +require-relative@^0.8.7: + version "0.8.7" + resolved "https://registry.yarnpkg.com/require-relative/-/require-relative-0.8.7.tgz#7999539fc9e047a37928fa196f8e1563dabd36de" + integrity sha1-eZlTn8ngR6N5KPoZb44VY9q9Nt4= + require-uncached@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/require-uncached/-/require-uncached-1.0.3.tgz#4e0d56d6c9662fd31e43011c4b95aa49955421d3" @@ -9579,7 +9581,7 @@ require-uncached@^1.0.3: caller-path "^0.1.0" resolve-from "^1.0.0" -requires-port@1.x.x, requires-port@^1.0.0: +requires-port@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/requires-port/-/requires-port-1.0.0.tgz#925d2601d39ac485e091cf0da5c6e694dc3dcaff" integrity sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8= @@ -9589,14 +9591,6 @@ reselect@^3.0.1: resolved "https://registry.yarnpkg.com/reselect/-/reselect-3.0.1.tgz#efdaa98ea7451324d092b2b2163a6a1d7a9a2147" integrity sha1-79qpjqdFEyTQkrKyFjpqHXqaIUc= -resolve-dir@^0.1.0: - version "0.1.1" - resolved "https://registry.yarnpkg.com/resolve-dir/-/resolve-dir-0.1.1.tgz#b219259a5602fac5c5c496ad894a6e8cc430261e" - integrity sha1-shklmlYC+sXFxJatiUpujMQwJh4= - dependencies: - expand-tilde "^1.2.2" - global-modules "^0.2.3" - resolve-dir@^1.0.0, resolve-dir@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/resolve-dir/-/resolve-dir-1.0.1.tgz#79a40644c362be82f26effe739c9bb5382046f43" @@ -9627,20 +9621,13 @@ resolve@1.5.0: dependencies: path-parse "^1.0.5" -resolve@^1.1.2, resolve@^1.1.3, resolve@^1.1.4, resolve@^1.1.6, resolve@^1.1.7, resolve@^1.3.2, resolve@^1.3.3, resolve@^1.4.0, resolve@^1.5.0, resolve@^1.8.1: +resolve@^1.1.3, resolve@^1.1.4, resolve@^1.1.6, resolve@^1.1.7, resolve@^1.3.2, resolve@^1.3.3, resolve@^1.4.0, resolve@^1.5.0, resolve@^1.6.0, resolve@^1.7.1, resolve@^1.8.1: version "1.9.0" resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.9.0.tgz#a14c6fdfa8f92a7df1d996cb7105fa744658ea06" integrity sha512-TZNye00tI67lwYvzxCxHGjwTNlUV70io54/Ed4j6PscB8xVfuBJpRenI/o6dVk0cY0PYTY27AgCoGGxRnYuItQ== dependencies: path-parse "^1.0.6" -resolve@^1.3.0: - version "1.4.0" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.4.0.tgz#a75be01c53da25d934a98ebd0e4c4a7312f92a86" - integrity sha512-aW7sVKPufyHqOmyyLzg/J+8606v5nevBgaliIlV7nUpVMsDnoBGV/cbSLNjZAg9q0Cfd/+easKVKQ8vOu8fn1Q== - dependencies: - path-parse "^1.0.5" - restore-cursor@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/restore-cursor/-/restore-cursor-1.0.1.tgz#34661f46886327fed2991479152252df92daa541" @@ -9669,7 +9656,7 @@ right-align@^0.1.1: dependencies: align-text "^0.1.1" -rimraf@^2.2.8, rimraf@^2.3.2, rimraf@^2.3.4, rimraf@^2.4.3, rimraf@^2.4.4, rimraf@^2.5.2, rimraf@^2.5.3, rimraf@^2.5.4, rimraf@^2.6.1, rimraf@^2.6.2: +rimraf@^2.2.8, rimraf@^2.3.4, rimraf@^2.4.3, rimraf@^2.4.4, rimraf@^2.5.2, rimraf@^2.5.3, rimraf@^2.5.4, rimraf@^2.6.1, rimraf@^2.6.2: version "2.6.2" resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.2.tgz#2ed8150d24a16ea8651e6d6ef0f47c4158ce7a36" integrity sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w== @@ -9689,12 +9676,30 @@ ripemd160@^2.0.0, ripemd160@^2.0.1: hash-base "^3.0.0" inherits "^2.0.1" -rollup@^0.41.4: - version "0.41.6" - resolved "https://registry.yarnpkg.com/rollup/-/rollup-0.41.6.tgz#e0d05497877a398c104d816d2733a718a7a94e2a" - integrity sha1-4NBUl4d6OYwQTYFtJzOnGKepTio= +rollup-pluginutils@^2.0.1: + version "2.3.3" + resolved "https://registry.yarnpkg.com/rollup-pluginutils/-/rollup-pluginutils-2.3.3.tgz#3aad9b1eb3e7fe8262820818840bf091e5ae6794" + integrity sha512-2XZwja7b6P5q4RZ5FhyX1+f46xi1Z3qBKigLRZ6VTZjwbN0K1IFGMlwm06Uu0Emcre2Z63l77nq/pzn+KxIEoA== dependencies: - source-map-support "^0.4.0" + estree-walker "^0.5.2" + micromatch "^2.3.11" + +rollup@^0.57.1: + version "0.57.1" + resolved "https://registry.yarnpkg.com/rollup/-/rollup-0.57.1.tgz#0bb28be6151d253f67cf4a00fea48fb823c74027" + integrity sha512-I18GBqP0qJoJC1K1osYjreqA8VAKovxuI3I81RSk0Dmr4TgloI0tAULjZaox8OsJ+n7XRrhH6i0G2By/pj1LCA== + dependencies: + "@types/acorn" "^4.0.3" + acorn "^5.5.3" + acorn-dynamic-import "^3.0.0" + date-time "^2.1.0" + is-reference "^1.1.0" + locate-character "^2.0.5" + pretty-ms "^3.1.0" + require-relative "^0.8.7" + rollup-pluginutils "^2.0.1" + signal-exit "^3.0.2" + sourcemap-codec "^1.4.1" route-recognizer@^0.3.3: version "0.3.3" @@ -9706,7 +9711,7 @@ route-recognizer@^0.3.4: resolved "https://registry.yarnpkg.com/route-recognizer/-/route-recognizer-0.3.4.tgz#39ab1ffbce1c59e6d2bdca416f0932611e4f3ca3" integrity sha512-2+MhsfPhvauN1O8KaXpXAOfR/fwe8dnUXVM+xw7yt40lJRfPVQxV6yryZm0cgRvAj5fMF/mdRZbL2ptwbs5i2g== -rsvp@^3.0.14, rsvp@^3.0.16, rsvp@^3.0.17, rsvp@^3.0.18, rsvp@^3.2.1, rsvp@^3.3.3, rsvp@^3.5.0: +rsvp@^3.0.14, rsvp@^3.0.16, rsvp@^3.0.17, rsvp@^3.0.18, rsvp@^3.3.3: version "3.6.2" resolved "https://registry.yarnpkg.com/rsvp/-/rsvp-3.6.2.tgz#2e96491599a96cde1b515d5674a8f7a91452926a" integrity sha512-OfWGQTb9vnwRjwtA2QwpG2ICclHC3pgXZO5xt8H2EfgDquO0qVdSb5T88L4qJVAEugbS56pAuV4XZM58UX8ulw== @@ -9772,20 +9777,7 @@ safe-regex@^1.1.0: resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== -sane@^1.1.1: - version "1.6.0" - resolved "https://registry.yarnpkg.com/sane/-/sane-1.6.0.tgz#9610c452307a135d29c1fdfe2547034180c46775" - integrity sha1-lhDEUjB6E10pwf3+JUcDQYDEZ3U= - dependencies: - anymatch "^1.3.0" - exec-sh "^0.2.0" - fb-watchman "^1.8.0" - minimatch "^3.0.2" - minimist "^1.1.1" - walker "~1.0.5" - watch "~0.10.0" - -sane@^2.2.0, sane@^2.5.2: +sane@^2.4.1, sane@^2.5.2: version "2.5.2" resolved "https://registry.yarnpkg.com/sane/-/sane-2.5.2.tgz#b4dc1861c21b427e929507a3e751e2a2cb8ab3fa" integrity sha1-tNwYYcIbQn6SlQej51HiosuKs/o= @@ -9801,6 +9793,23 @@ sane@^2.2.0, sane@^2.5.2: optionalDependencies: fsevents "^1.2.3" +sane@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/sane/-/sane-3.1.0.tgz#995193b7dc1445ef1fe41ddfca2faf9f111854c6" + integrity sha512-G5GClRRxT1cELXfdAq7UKtUsv8q/ZC5k8lQGmjEm4HcAl3HzBy68iglyNCmw4+0tiXPCBZntslHlRhbnsSws+Q== + dependencies: + anymatch "^2.0.0" + capture-exit "^1.2.0" + exec-sh "^0.2.0" + execa "^1.0.0" + fb-watchman "^2.0.0" + micromatch "^3.1.4" + minimist "^1.1.1" + walker "~1.0.5" + watch "~0.18.0" + optionalDependencies: + fsevents "^1.2.3" + sauce-connect-launcher@^1.1.0: version "1.2.2" resolved "https://registry.yarnpkg.com/sauce-connect-launcher/-/sauce-connect-launcher-1.2.2.tgz#7346cc8fbdc443191323439b0733451f5f3521f2" @@ -9834,7 +9843,7 @@ select@^1.1.2: resolved "https://registry.yarnpkg.com/select/-/select-1.1.2.tgz#0e7350acdec80b1108528786ec1d4418d11b396d" integrity sha1-DnNQrN7ICxEIUoeG7B1EGNEbOW0= -"semver@2 || 3 || 4 || 5", semver@^5.1.0, semver@^5.3.0, semver@^5.4.1, semver@^5.5.0: +"semver@2 || 3 || 4 || 5", semver@^5.3.0, semver@^5.4.1, semver@^5.5.0: version "5.6.0" resolved "https://registry.yarnpkg.com/semver/-/semver-5.6.0.tgz#7e74256fbaa49c75aa7c7a205cc22799cac80004" integrity sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg== @@ -9844,35 +9853,11 @@ semver@^4.3.1: resolved "https://registry.yarnpkg.com/semver/-/semver-4.3.6.tgz#300bc6e0e86374f7ba61068b5b1ecd57fc6532da" integrity sha1-MAvG4OhjdPe6YQaLWx7NV/xlMto= -semver@^5.1.1: - version "5.3.0" - resolved "https://registry.yarnpkg.com/semver/-/semver-5.3.0.tgz#9b2ce5d3de02d17c6012ad326aa6b4d0cf54f94f" - integrity sha1-myzl094C0XxgEq0yaqa00M9U+U8= - semver@~5.0.1: version "5.0.3" resolved "https://registry.yarnpkg.com/semver/-/semver-5.0.3.tgz#77466de589cd5d3c95f138aa78bc569a3cb5d27a" integrity sha1-d0Zt5YnNXTyV8TiqeLxWmjy10no= -send@0.15.1: - version "0.15.1" - resolved "https://registry.yarnpkg.com/send/-/send-0.15.1.tgz#8a02354c26e6f5cca700065f5f0cdeba90ec7b5f" - integrity sha1-igI1TCbm9cynAAZfXwzeupDse18= - dependencies: - debug "2.6.1" - depd "~1.1.0" - destroy "~1.0.4" - encodeurl "~1.0.1" - escape-html "~1.0.3" - etag "~1.8.0" - fresh "0.5.0" - http-errors "~1.6.1" - mime "1.3.4" - ms "0.7.2" - on-finished "~2.3.0" - range-parser "~1.2.0" - statuses "~1.3.1" - send@0.16.2: version "0.16.2" resolved "https://registry.yarnpkg.com/send/-/send-0.16.2.tgz#6ecca1e0f8c156d141597559848df64730a6bbc1" @@ -9892,16 +9877,6 @@ send@0.16.2: range-parser "~1.2.0" statuses "~1.4.0" -serve-static@1.12.1: - version "1.12.1" - resolved "https://registry.yarnpkg.com/serve-static/-/serve-static-1.12.1.tgz#7443a965e3ced647aceb5639fa06bf4d1bbe0039" - integrity sha1-dEOpZePO1kes61Y5+ga/TRu+ADk= - dependencies: - encodeurl "~1.0.1" - escape-html "~1.0.3" - parseurl "~1.3.1" - send "0.15.1" - serve-static@1.13.2: version "1.13.2" resolved "https://registry.yarnpkg.com/serve-static/-/serve-static-1.13.2.tgz#095e8472fd5b46237db50ce486a43f4b86c6cec1" @@ -9937,11 +9912,6 @@ set-value@^2.0.0: is-plain-object "^2.0.3" split-string "^3.0.1" -setprototypeof@1.0.3: - version "1.0.3" - resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.0.3.tgz#66567e37043eeb4f04d91bd658c0cbefb55b8e04" - integrity sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ= - setprototypeof@1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.1.0.tgz#d0bd85536887b6fe7c0d818cb962d9d91c54e656" @@ -10007,15 +9977,10 @@ simple-concat@^1.0.0: resolved "https://registry.yarnpkg.com/simple-concat/-/simple-concat-1.0.0.tgz#7344cbb8b6e26fb27d66b2fc86f9f6d5997521c6" integrity sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY= -simple-fmt@~0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/simple-fmt/-/simple-fmt-0.1.0.tgz#191bf566a59e6530482cb25ab53b4a8dc85c3a6b" - integrity sha1-GRv1ZqWeZTBILLJatTtKjchcOms= - -simple-is@~0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/simple-is/-/simple-is-0.2.0.tgz#2abb75aade39deb5cc815ce10e6191164850baf0" - integrity sha1-Krt1qt453rXMgVzhDmGRFkhQuvA= +simple-html-tokenizer@^0.5.6: + version "0.5.7" + resolved "https://registry.yarnpkg.com/simple-html-tokenizer/-/simple-html-tokenizer-0.5.7.tgz#8eca336ecfbe2b3c6166cbb31b2682088de79f40" + integrity sha512-APW9iYbkJ5cijjX4Ljhf3VG8SwYPUJT5gZrwci/wieMabQxWFiV5VwsrP5c6GMRvXKEQMGkAB1d9dvW66dTqpg== slash@^1.0.0: version "1.0.0" @@ -10124,17 +10089,18 @@ socket.io@^2.1.0: socket.io-client "2.2.0" socket.io-parser "~3.3.0" -sort-object-keys@^1.1.1: +sort-object-keys@^1.1.2: version "1.1.2" resolved "https://registry.yarnpkg.com/sort-object-keys/-/sort-object-keys-1.1.2.tgz#d3a6c48dc2ac97e6bc94367696e03f6d09d37952" integrity sha1-06bEjcKsl+a8lDZ2luA/bQnTeVI= -sort-package-json@^1.4.0: - version "1.7.0" - resolved "https://registry.yarnpkg.com/sort-package-json/-/sort-package-json-1.7.0.tgz#13b362ff6400c5b4eaa9ba220f9ea7c3d6644b5f" - integrity sha1-E7Ni/2QAxbTqqboiD56nw9ZkS18= +sort-package-json@^1.15.0: + version "1.17.1" + resolved "https://registry.yarnpkg.com/sort-package-json/-/sort-package-json-1.17.1.tgz#ab8d7ba8c8e2bbe1805e0650829256f64191c203" + integrity sha512-IxcHMpJF2ksT2cTtY3scXErmxbpp79bA7nlToENHCn0ZhoX7fMJk97z9sHDyubRoKzbwzq4r6TZz9DHL5V0LXA== dependencies: - sort-object-keys "^1.1.1" + detect-indent "^5.0.0" + sort-object-keys "^1.1.2" source-map-resolve@^0.5.0: version "0.5.2" @@ -10147,14 +10113,7 @@ source-map-resolve@^0.5.0: source-map-url "^0.4.0" urix "^0.1.0" -source-map-support@^0.2.10: - version "0.2.10" - resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.2.10.tgz#ea5a3900a1c1cb25096a0ae8cc5c2b4b10ded3dc" - integrity sha1-6lo5AKHByyUJagrozFwrSxDe09w= - dependencies: - source-map "0.1.32" - -source-map-support@^0.4.0, source-map-support@^0.4.15: +source-map-support@^0.4.15: version "0.4.18" resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.4.18.tgz#0286a6de8be42641338594e97ccea75f0a2c585f" integrity sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA== @@ -10179,13 +10138,6 @@ source-map-url@^0.4.0: resolved "https://registry.yarnpkg.com/source-map-url/-/source-map-url-0.4.0.tgz#3e935d7ddd73631b97659956d55128e87b5084a3" integrity sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM= -source-map@0.1.32: - version "0.1.32" - resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.1.32.tgz#c8b6c167797ba4740a8ea33252162ff08591b266" - integrity sha1-yLbBZ3l7pHQKjqMyUhYv8IWRsmY= - dependencies: - amdefine ">=0.0.4" - source-map@0.4.x, source-map@^0.4.2, source-map@^0.4.4: version "0.4.4" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.4.4.tgz#eba4f5da9c0dc999de68032d8b4f76173652036b" @@ -10198,16 +10150,38 @@ source-map@^0.5.0, source-map@^0.5.3, source-map@^0.5.6, source-map@^0.5.7, sour resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.7.tgz#8a039d2d1021d22d1ea14c80d8ea468ba2ef3fcc" integrity sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w= -source-map@^0.6.0, source-map@~0.6.1: +source-map@^0.6.0, source-map@^0.6.1, source-map@~0.6.1: version "0.6.1" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== +source-map@~0.1.x: + version "0.1.43" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.1.43.tgz#c24bc146ca517c1471f5dacbe2571b2b7f9e3346" + integrity sha1-wkvBRspRfBRx9drL4lcbK3+eM0Y= + dependencies: + amdefine ">=0.0.4" + source-map@~0.5.1: version "0.5.6" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.6.tgz#75ce38f52bf0733c5a7f0c118d81334a2bb5f412" integrity sha1-dc449SvwczxafwwRjYEzSiu19BI= +sourcemap-codec@^1.4.1: + version "1.4.4" + resolved "https://registry.yarnpkg.com/sourcemap-codec/-/sourcemap-codec-1.4.4.tgz#c63ea927c029dd6bd9a2b7fa03b3fec02ad56e9f" + integrity sha512-CYAPYdBu34781kLHkaW3m6b/uUSyMOC2R61gcYMWooeuaGtjof86ZA/8T+qVPPt7np1085CR9hmMGrySwEc8Xg== + +sourcemap-validator@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/sourcemap-validator/-/sourcemap-validator-1.1.0.tgz#00454547d1682186e1498a7208e022e8dfa8738f" + integrity sha512-Hmdu39KL+EoAAZ69OTk7RXXJdPRRizJvOZOWhCW9jLGfEQflCNPTlSoCXFPdKWFwwf0uzLcGR/fc7EP/PT8vRQ== + dependencies: + jsesc "~0.3.x" + lodash.foreach "~2.3.x" + lodash.template "~2.3.x" + source-map "~0.1.x" + spawn-args@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/spawn-args/-/spawn-args-0.2.0.tgz#fb7d0bd1d70fd4316bd9e3dec389e65f9d6361bb" @@ -10289,11 +10263,6 @@ sshpk@^1.7.0: safer-buffer "^2.0.2" tweetnacl "~0.14.0" -stable@~0.1.3: - version "0.1.8" - resolved "https://registry.yarnpkg.com/stable/-/stable-0.1.8.tgz#836eb3c8382fe2936feaf544631017ce7d47a3cf" - integrity sha512-ji9qxRnOVfcuLDySj9qzhGSEFVobyt1kIOSkj1qZzYLzq7Tos/oUUWvotUPQLlrsidqsK6tBH89Bc9kL5zHA6w== - static-extend@^0.1.1: version "0.1.2" resolved "https://registry.yarnpkg.com/static-extend/-/static-extend-0.1.2.tgz#60809c39cbff55337226fd5e0b520f341f1fb5c6" @@ -10307,11 +10276,6 @@ static-extend@^0.1.1: resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.5.0.tgz#161c7dac177659fd9811f43771fa99381478628c" integrity sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow= -statuses@~1.3.1: - version "1.3.1" - resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.3.1.tgz#faf51b9eb74aaef3b3acf4ad5f61abf24cb7b93e" - integrity sha1-+vUbnrdKrvOzrPStX2Gr8ky3uT4= - statuses@~1.4.0: version "1.4.0" resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.4.0.tgz#bb73d446da2796106efcc1b601a253d6c46bd087" @@ -10398,16 +10362,6 @@ string_decoder@~1.1.1: dependencies: safe-buffer "~5.1.0" -stringmap@~0.2.2: - version "0.2.2" - resolved "https://registry.yarnpkg.com/stringmap/-/stringmap-0.2.2.tgz#556c137b258f942b8776f5b2ef582aa069d7d1b1" - integrity sha1-VWwTeyWPlCuHdvWy71gqoGnX0bE= - -stringset@~0.2.1: - version "0.2.1" - resolved "https://registry.yarnpkg.com/stringset/-/stringset-0.2.1.tgz#ef259c4e349344377fcd1c913dd2e848c9c042b5" - integrity sha1-7yWcTjSTRDd/zRyRPdLoSMnAQrU= - stringstream@~0.0.4: version "0.0.6" resolved "https://registry.yarnpkg.com/stringstream/-/stringstream-0.0.6.tgz#7880225b0d4ad10e30927d167a1d6f2fd3b33a72" @@ -10577,7 +10531,7 @@ terser@^3.7.5: source-map "~0.6.1" source-map-support "~0.5.6" -testem@^2.0.0: +testem@^2.9.2: version "2.14.0" resolved "https://registry.yarnpkg.com/testem/-/testem-2.14.0.tgz#418a9a15843f68381659c6a486abb4ea48d06c29" integrity sha512-tldpNPCzXfibmxOoTMGOfr8ztUiHf9292zSXCu7SitBx9dCK83k7vEoa77qJBS9t3RGCQCRF+GNMUuiFw//Mbw== @@ -10629,11 +10583,16 @@ through2@^2.0.0: readable-stream "~2.3.6" xtend "~4.0.1" -"through@>=2.2.7 <3", through@^2.3.6, through@^2.3.8, through@~2.3.8: +"through@>=2.2.7 <3", through@^2.3.6, through@^2.3.8: version "2.3.8" resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" integrity sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU= +time-zone@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/time-zone/-/time-zone-1.0.0.tgz#99c5bf55958966af6d06d83bdf3800dc82faec5d" + integrity sha1-mcW/VZWJZq9tBtg73zgA3IL67F0= + timers-browserify@^1.0.1: version "1.4.2" resolved "https://registry.yarnpkg.com/timers-browserify/-/timers-browserify-1.4.2.tgz#c9c58b575be8407375cb5e2462dacee74359f41d" @@ -10646,15 +10605,15 @@ tiny-emitter@^2.0.0: resolved "https://registry.yarnpkg.com/tiny-emitter/-/tiny-emitter-2.0.2.tgz#82d27468aca5ade8e5fd1e6d22b57dd43ebdfb7c" integrity sha512-2NM0auVBGft5tee/OxP4PI3d8WItkDM+fPnaRAVo6xTDI2knbz9eC5ArWGqtGlYqiH3RU5yMpdyTTO7MguC4ow== -tiny-lr@^1.0.3: - version "1.0.5" - resolved "https://registry.yarnpkg.com/tiny-lr/-/tiny-lr-1.0.5.tgz#21f40bf84ebd1f853056680375eef1670c334112" - integrity sha512-YrxUSiMgOVh3PnAqtdAUQuUVEVRnqcRCxJ3BHrl/aaWV2fplKKB60oClM0GH2Gio2hcXvkxMUxsC/vXZrQePlg== +tiny-lr@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/tiny-lr/-/tiny-lr-1.1.1.tgz#9fa547412f238fedb068ee295af8b682c98b2aab" + integrity sha512-44yhA3tsaRoMOjQQ+5v5mVdqef+kH6Qze9jTpqtVufgYjYt08zyZAwNwwVBj3i1rJMnR52IxOW0LK0vBzgAkuA== dependencies: body "^5.1.0" - debug "~2.6.7" + debug "^3.1.0" faye-websocket "~0.10.0" - livereload-js "^2.2.2" + livereload-js "^2.3.0" object-assign "^4.1.0" qs "^6.4.0" @@ -10694,7 +10653,7 @@ to-arraybuffer@^1.0.0: resolved "https://registry.yarnpkg.com/to-arraybuffer/-/to-arraybuffer-1.0.1.tgz#7d229b1fcc637e466ca081180836a7aabff83f43" integrity sha1-fSKbH8xjfkZsoIEYCDanqr/4P0M= -to-fast-properties@^1.0.0, to-fast-properties@^1.0.3: +to-fast-properties@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/to-fast-properties/-/to-fast-properties-1.0.3.tgz#b83571fa4d8c25b82e231b06e3a3055de4ca1a47" integrity sha1-uDVx+k2MJbguIxsG46MFXeTKGkc= @@ -10759,17 +10718,6 @@ tr46@^1.0.1: dependencies: punycode "^2.1.0" -tree-sync@^1.2.1: - version "1.2.2" - resolved "https://registry.yarnpkg.com/tree-sync/-/tree-sync-1.2.2.tgz#2cf76b8589f59ffedb58db5a3ac7cb013d0158b7" - integrity sha1-LPdrhYn1n/7bWNtaOsfLAT0BWLc= - dependencies: - debug "^2.2.0" - fs-tree-diff "^0.5.6" - mkdirp "^0.5.1" - quick-temp "^0.1.5" - walk-sync "^0.2.7" - tree-sync@^1.2.2: version "1.4.0" resolved "https://registry.yarnpkg.com/tree-sync/-/tree-sync-1.4.0.tgz#314598d13abaf752547d9335b8f95d9a137100d6" @@ -10786,26 +10734,16 @@ trim-newlines@^1.0.0: resolved "https://registry.yarnpkg.com/trim-newlines/-/trim-newlines-1.0.0.tgz#5887966bb582a4503a41eb524f7d35011815a613" integrity sha1-WIeWa7WCpFA6QetST301ARgVphM= -trim-right@^1.0.0, trim-right@^1.0.1: +trim-right@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/trim-right/-/trim-right-1.0.1.tgz#cb2e1203067e0c8de1f614094b9fe45704ea6003" integrity sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM= -try-resolve@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/try-resolve/-/try-resolve-1.0.1.tgz#cfde6fabd72d63e5797cfaab873abbe8e700e912" - integrity sha1-z95vq9ctY+V5fPqrhzq76OcA6RI= - tryit@^1.0.1: version "1.0.3" resolved "https://registry.yarnpkg.com/tryit/-/tryit-1.0.3.tgz#393be730a9446fd1ead6da59a014308f36c289cb" integrity sha1-OTvnMKlEb9Hq1tpZoBQwjzbCics= -tryor@~0.1.2: - version "0.1.2" - resolved "https://registry.yarnpkg.com/tryor/-/tryor-0.1.2.tgz#8145e4ca7caff40acde3ccf946e8b8bb75b4172b" - integrity sha1-gUXkynyv9ArN48z5Rui4u3W0Fys= - tty-browserify@~0.0.0: version "0.0.1" resolved "https://registry.yarnpkg.com/tty-browserify/-/tty-browserify-0.0.1.tgz#3f05251ee17904dfd0677546670db9651682b811" @@ -10835,14 +10773,6 @@ type-check@~0.3.2: dependencies: prelude-ls "~1.1.2" -type-is@~1.6.14, type-is@~1.6.16: - version "1.6.16" - resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.16.tgz#f89ce341541c672b25ee7ae3c73dee3b2be50194" - integrity sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q== - dependencies: - media-typer "0.3.0" - mime-types "~2.1.18" - type-is@~1.6.15: version "1.6.15" resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.15.tgz#cab10fb4909e441c82842eafe1ad646c81804410" @@ -10851,6 +10781,14 @@ type-is@~1.6.15: media-typer "0.3.0" mime-types "~2.1.15" +type-is@~1.6.16: + version "1.6.16" + resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.16.tgz#f89ce341541c672b25ee7ae3c73dee3b2be50194" + integrity sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q== + dependencies: + media-typer "0.3.0" + mime-types "~2.1.18" + typedarray@^0.0.6, typedarray@~0.0.5: version "0.0.6" resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" @@ -10861,6 +10799,11 @@ uc.micro@^1.0.1, uc.micro@^1.0.3: resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.3.tgz#7ed50d5e0f9a9fb0a573379259f2a77458d50192" integrity sha1-ftUNXg+an7ClczeSWfKndFjVAZI= +uc.micro@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.5.tgz#0c65f15f815aa08b560a61ce8b4db7ffc3f45376" + integrity sha512-JoLI4g5zv5qNyT09f4YAvEZIIV1oOjqnewYg5D38dkQljIzpPT296dbIGvKro3digYI1bkb7W6EP1y4uDlmzLg== + uglify-js@^2.6: version "2.8.18" resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-2.8.18.tgz#925d14bae48ab62d1883b41afe6e2261662adb8e" @@ -10871,6 +10814,14 @@ uglify-js@^2.6: optionalDependencies: uglify-to-browserify "~1.0.0" +uglify-js@^3.1.4: + version "3.4.9" + resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.4.9.tgz#af02f180c1207d76432e473ed24a28f4a782bae3" + integrity sha512-8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q== + dependencies: + commander "~2.17.1" + source-map "~0.6.1" + uglify-to-browserify@~1.0.0: version "1.0.2" resolved "https://registry.yarnpkg.com/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz#6e0924d6bda6b5afe349e39a6d632850a0f882b7" @@ -11002,11 +10953,6 @@ use@^3.1.0: resolved "https://registry.yarnpkg.com/use/-/use-3.1.1.tgz#d50c8cac79a19fbc20f2911f56eb973f4e10070f" integrity sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ== -user-home@^1.1.1: - version "1.1.1" - resolved "https://registry.yarnpkg.com/user-home/-/user-home-1.1.1.tgz#2b5be23a32b63a7c9deb8d0f28d485724a3df190" - integrity sha1-K1viOjK2Onyd640PKNSFcko98ZA= - user-info@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/user-info/-/user-info-1.0.0.tgz#81c82b7ed63e674c2475667653413b3c76fde239" @@ -11033,6 +10979,14 @@ util-deprecate@^1.0.2, util-deprecate@~1.0.1: resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8= +util.promisify@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/util.promisify/-/util.promisify-1.0.0.tgz#440f7165a459c9a16dc145eb8e72f35687097030" + integrity sha512-i+6qA2MPhvoKLuxnJNpXAGhg7HphQOSUq2LKMZD0m15EiskXUkMvKdF4Uui0WYeCUGea+o2cw/ZuwehtfsrNkA== + dependencies: + define-properties "^1.1.2" + object.getownpropertydescriptors "^2.0.3" + util@0.10.3: version "0.10.3" resolved "https://registry.yarnpkg.com/util/-/util-0.10.3.tgz#7afb1afe50805246489e3db7fe0ed379336ac0f9" @@ -11047,11 +11001,6 @@ util@~0.10.1: dependencies: inherits "2.0.3" -utils-merge@1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/utils-merge/-/utils-merge-1.0.0.tgz#0294fb922bb9375153541c4f7096231f287c8af8" - integrity sha1-ApT7kiu5N1FTVBxPcJYjHyh8ivg= - utils-merge@1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/utils-merge/-/utils-merge-1.0.1.tgz#9f95710f50a267947b2ccc124741c1028427e713" @@ -11082,7 +11031,7 @@ vargs@0.1.0: resolved "https://registry.yarnpkg.com/vargs/-/vargs-0.1.0.tgz#6b6184da6520cc3204ce1b407cac26d92609ebff" integrity sha1-a2GE2mUgzDIEzhtAfKwm2SYJ6/8= -vary@~1.1.0, vary@~1.1.2: +vary@~1.1.2: version "1.1.2" resolved "https://registry.yarnpkg.com/vary/-/vary-1.1.2.tgz#2299f02c6ded30d4a5961b0b9f74524a18f634fc" integrity sha1-IpnwLG3tMNSllhsLn3RSShj2NPw= @@ -11146,10 +11095,16 @@ walker@~1.0.5: dependencies: makeerror "1.0.x" -watch@~0.10.0: - version "0.10.0" - resolved "https://registry.yarnpkg.com/watch/-/watch-0.10.0.tgz#77798b2da0f9910d595f1ace5b0c2258521f21dc" - integrity sha1-d3mLLaD5kQ1ZXxrOWwwiWFIfIdw= +watch-detector@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/watch-detector/-/watch-detector-0.1.0.tgz#e37b410d149e2a8bf263a4f8b71e2f667633dbf8" + integrity sha512-vfzMMfpjQc88xjETwl2HuE6PjEuxCBeyC4bQmqrHrofdfYWi/4mEJklYbNgSzpqM9PxubsiPIrE5SZ1FDyiQ2w== + dependencies: + heimdalljs-logger "^0.1.9" + quick-temp "^0.1.8" + rsvp "^4.7.0" + semver "^5.4.1" + silent-error "^1.1.0" watch@~0.18.0: version "0.18.0" @@ -11232,7 +11187,7 @@ which-module@^1.0.0: resolved "https://registry.yarnpkg.com/which-module/-/which-module-1.0.0.tgz#bba63ca861948994ff307736089e3b96026c2a4f" integrity sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8= -which@^1.2.12, which@^1.2.14, which@^1.2.9, which@^1.3.0: +which@^1.2.14, which@^1.2.9, which@^1.3.0: version "1.3.1" resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a" integrity sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ== @@ -11251,11 +11206,6 @@ window-size@0.1.0: resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.0.tgz#5438cd2ea93b202efa3a19fe8887aee7c94f9c9d" integrity sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0= -window-size@^0.1.2: - version "0.1.4" - resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.4.tgz#f8e1aa1ee5a53ec5bf151ffa09742a6ad7697876" - integrity sha1-+OGqHuWlPsW/FR/6CXQqatdpeHY= - wordwrap@0.0.2: version "0.0.2" resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-0.0.2.tgz#b79669bb42ecb409f83d583cad52ca17eaa1643f" @@ -11346,7 +11296,7 @@ xtend@^4.0.0, xtend@^4.0.1, xtend@~4.0.0, xtend@~4.0.1: resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.1.tgz#a5c6d532be656e23db820efb943a1f04998d63af" integrity sha1-pcbVMr5lbiPbgg77lDofBJmNY68= -y18n@^3.2.0, y18n@^3.2.1: +y18n@^3.2.1: version "3.2.1" resolved "https://registry.yarnpkg.com/y18n/-/y18n-3.2.1.tgz#6d15fba884c08679c0d77e88e7759e811e07fa41" integrity sha1-bRX7qITAhnnA136I53WegR4H+kE= @@ -11361,13 +11311,13 @@ yallist@^3.0.0, yallist@^3.0.2: resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.0.3.tgz#b4b049e314be545e3ce802236d6cd22cd91c3de9" integrity sha512-S+Zk8DEWE6oKpV+vI3qWkaK+jSbIK86pCwe2IF/xwIpQ8jEuxpw9NyaGjmp9+BoJv5FV2piqCDcoCtStppiq2A== -yam@0.0.22: - version "0.0.22" - resolved "https://registry.yarnpkg.com/yam/-/yam-0.0.22.tgz#38a76cb79a19284d9206ed49031e359a1340bd06" - integrity sha1-OKdst5oZKE2SBu1JAx41mhNAvQY= +yam@^0.0.24: + version "0.0.24" + resolved "https://registry.yarnpkg.com/yam/-/yam-0.0.24.tgz#11e9630444735f66a561d29221407de6d037cd95" + integrity sha512-llPF60oFLV8EQimNPR6+KorSaj59L32C4c1db4cr72GaWVWapnhTS2VZeK2K2xLyEOveWtRcNa+dLJBW7EfhYQ== dependencies: - fs-extra "^0.30.0" - lodash.merge "^4.4.0" + fs-extra "^4.0.2" + lodash.merge "^4.6.0" yargs-parser@^4.2.0: version "4.2.1" @@ -11405,18 +11355,6 @@ yargs@~3.10.0: decamelize "^1.0.0" window-size "0.1.0" -yargs@~3.27.0: - version "3.27.0" - resolved "https://registry.yarnpkg.com/yargs/-/yargs-3.27.0.tgz#21205469316e939131d59f2da0c6d7f98221ea40" - integrity sha1-ISBUaTFuk5Ex1Z8toMbX+YIh6kA= - dependencies: - camelcase "^1.2.1" - cliui "^2.1.0" - decamelize "^1.0.0" - os-locale "^1.4.0" - window-size "^0.1.2" - y18n "^3.2.0" - yeast@0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/yeast/-/yeast-0.1.2.tgz#008e06d8094320c372dbc2f8ed76a0ca6c8ac419"