Browse Source

[ADD] data sincronizer

robert 6 years ago
parent
commit
6be81861c2

+ 3 - 1
__openerp__.py

@@ -13,7 +13,9 @@
         'multi_store',
         # 'multi_store_stock',
         # 'multi_store_partner',
-        'sale'
+        'sale',
+        'eiru_sidebar_toggler',
+        'eiru_topbar_toggler'
     ],
     'data': [
         'templates.xml',

+ 24 - 22
controllers/main.py

@@ -153,17 +153,6 @@ class PosSales(http.Controller):
 
         # Imports
         from server_datetime import get_date, get_datetime
-
-        # Parameters
-        date_now = get_date()
-        mode = kw.get('mode', 'sale')
-        journal_id = kw.get('journalId', None)
-        customer_id = kw.get('customerId', None)
-        cart_items = kw.get('items', [])
-        payment_term_id = kw.get('paymentTermId', None)
-        payment = float(kw.get('payment'))
-        payment_method = kw.get('paymentMethod', 'Efectivo')
-        bank_payment_data = kw.get('bankPaymentData', {})
         
         '''
         ╔═╗╦╔╗╔╦╔═╗╦ ╦  ╔╗ ╦ ╦╔╦╗╔═╗╔═╗╔╦╗  ╔═╗╔═╗╔═╗  ╔═╗╦═╗╔═╗╔═╗╔═╗╔╦╗╦ ╦╦═╗╔═╗
@@ -284,20 +273,33 @@ class PosSales(http.Controller):
         ╠═╝╠╦╝║ ║║  ║╣ ╚═╗╚═╗  ╠╣ ║║║║║╚═╗╠═╣   ║║║╣ ║  ║╚═╗║║ ║║║║
         ╩  ╩╚═╚═╝╚═╝╚═╝╚═╝╚═╝  ╚  ╩╝╚╝╩╚═╝╩ ╩  ═╩╝╚═╝╚═╝╩╚═╝╩╚═╝╝╚╝
         '''
-        if mode == 'budget':
-            finish_budget_pos(journal_id, customer_id, cart_items, date_now, currency_id, payment_term_id)
+        data = kw.get('data', [])
+        date_now = get_date()
 
-        if mode == 'sale':
-            finish_sale_pos(journal_id, customer_id, cart_items, date_now, payment_term_id, payment, payment_method, bank_payment_data)
+        for row in data:
+            mode = row.get('mode', 'sale')
+            journal_id = row.get('journalId', None)
+            customer_id = row.get('customerId', None)
+            cart_items = row.get('items', [])
+            payment_term_id = row.get('paymentTermId', None)
+            payment = float(row.get('payment'))
+            payment_method = row.get('paymentMethod', 'Efectivo')
+            bank_payment_data = row.get('bankPaymentData', {})
 
-        if mode == 'product_picking':
-            finish_process_picking(journal_id, customer_id, cart_items, date_now, payment_term_id)
+            if mode == 'budget':
+                finish_budget_pos(journal_id, customer_id, cart_items, date_now, currency_id, payment_term_id)
 
-        if mode == 'payment':
-            finish_payment()
-        
-        if mode == 'product_delivery':
-            finish_product_delivery()
+            if mode == 'sale':
+                finish_sale_pos(journal_id, customer_id, cart_items, date_now, payment_term_id, payment, payment_method, bank_payment_data)
+
+            if mode == 'product_picking':
+                finish_process_picking(journal_id, customer_id, cart_items, date_now, payment_term_id)
+
+            if mode == 'payment':
+                finish_payment()
+            
+            if mode == 'product_delivery':
+                finish_product_delivery()
 
         return {
             'process': True,

+ 1 - 0
package.json

@@ -13,6 +13,7 @@
 		"babel-loader": "^7.1.2",
 		"babel-preset-env": "^1.6.1",
 		"babel-preset-stage-2": "^6.24.1",
+		"copy-webpack-plugin": "^4.5.2",
 		"css-loader": "^0.28.9",
 		"extract-text-webpack-plugin": "^3.0.2",
 		"file-loader": "^1.1.6",

+ 48 - 14
src/store/actions.js

@@ -1,5 +1,4 @@
 import axios from 'axios'
-import { Db } from '../utils'
 
 const actions = {
     notify(_, message) {
@@ -13,6 +12,11 @@ const actions = {
         commit('setLoading', true)
         commit('setCompleted', false)
 
+        if (!getters.isWired) {
+            commit('setLoading', false)
+            return
+        }
+ 
         return axios.get('/eiru_sales/init', {
             params: {
                 mode: getters.mode
@@ -27,8 +31,6 @@ const actions = {
         })
     },
     explodeData({ dispatch, commit }, data) {
-        Db.create(data)
-
         for (let value in data) {
             if (value === 'settings') {
                 commit('updateSettings', data[value])
@@ -91,7 +93,7 @@ const actions = {
     toggleSettingsVisibility({ commit }) {
         commit('setSettingsVisibility')
     },
-    changeSetting({dispatch, commit}, setting) {
+    changeSetting({dispatch, commit, getters}, setting) {
         commit('setLoading', true)
 
         return axios.post('/eiru_sales/save_settings', {
@@ -126,7 +128,6 @@ const actions = {
     endProcess({ getters, commit, dispatch }) {
         const mode = getters.mode
 
-        // Check variables
         if (mode == 'sale') {
             if (getters.paymentType === 'cash' && getters.initialPayment < getters.amountToPay) {
                 return dispatch('notify', 'El monto recibido no puede ser menor al monto a pagar')
@@ -139,7 +140,6 @@ const actions = {
 
         commit('setLoading', true)
 
-        // Collect data
         const data = {
             mode,
             items: getters.cartItems.map(item => {
@@ -161,22 +161,36 @@ const actions = {
             }
         }
 
-        // Send data to server endpoint
+        dispatch('storeData', data)
+
+        if (getters.isWired) {
+            dispatch('syncData')
+        }
+
+        dispatch('printDocument').then(() => {
+            commit('setLoading', false)
+            commit('setCompleted', true)
+        })
+    },
+    storeData({ commit }, data) {
+        commit('storeData', data)
+    },
+    syncData({ getters, dispatch, commit }) {
+        if (getters.data.length == 0) {
+            return
+        }
+
         axios.post('/eiru_sales/finish', {
             jsonrpc: '2.0',
             method: 'call',
             params: {
-                ...data
+                data: getters.data
             }
         }).catch(() => {
             dispatch('notify', 'La transacción no terminó correctamente')
         })
 
-        // Print document
-        dispatch('printDocument').then(() => {
-            commit('setLoading', false)
-            commit('setCompleted', true)
-        })
+        commit('resetData')
     },
     printDocument({ getters, dispatch }) {
         if (getters.mode === 'sale') {
@@ -259,13 +273,33 @@ const actions = {
             
             key = key.replace('Module', '')
 
+            console.log(key)
+
             dispatch(`reset${key[0].toUpperCase()}${key.slice(1)}`)
         }
 
         dispatch('initProcess')
     },
-    changeNetStatus({ commit }, isWired) {
+    changeNetStatus({ commit, dispatch }, isWired) {
+        dispatch('hideTopbar', isWired)
         commit('setNetStatus', isWired)
+
+        if (isWired) {
+            dispatch('syncData')
+        }
+    },
+    hideTopbar(_, isWired) {
+        if (!openerp.eiru_topbar_toggler) {
+            return
+        }
+
+        setTimeout(() => {
+            if (isWired) {
+                openerp.eiru_topbar_toggler.show()
+            } else {
+                openerp.eiru_topbar_toggler.hide()
+            }
+        }, 3000)
     }
 }
 

+ 3 - 0
src/store/getters.js

@@ -2,6 +2,9 @@ const getters = {
     mode(state) {
         return state.mode
     },
+    data(state) {
+        return state.data
+    },
     isSale(state) {
         return state.mode === 'sale'
     },

+ 6 - 3
src/store/modules/bank.js

@@ -51,9 +51,12 @@ const actions = {
     changeBank({ commit }, bankId) {
         commit('setSelectedBank', bankId)
     },
-    resetBank ({ commit }) {
-        commit('setLoadingBanks', true)
-        commit('setBanks', [])
+    resetBank ({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingBanks', true)
+            commit('setBanks', [])
+        }
+        
         commit('setSelectedBank', null)
     }
 }

+ 6 - 3
src/store/modules/bankPaymentType.js

@@ -51,9 +51,12 @@ const actions = {
     changeBankPaymentType({ commit }, id) {
         commit('setSelectedBankPaymentType', id)
     },
-    resetBankPaymentType ({ commit }) {
-        commit('setLoadingBankPaymentTypes', true)
-        commit('setBankPaymentTypes', [])
+    resetBankPaymentType ({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingBankPaymentTypes', true)
+            commit('setBankPaymentTypes', [])
+        }
+        
         commit('setSelectedBankPaymentType')
     }
 }

+ 6 - 3
src/store/modules/chequeType.js

@@ -47,9 +47,12 @@ const actions = {
     changeChequeType({ commit }, id) {
         commit('setSelectedChequeType', id)
     },
-    resetChequeType({ commit }) {
-        commit('setLoadingChequeTypes')
-        commit('setChequeTypes', [])
+    resetChequeType({ getters, commit }) {
+        if (!getters.isWired) {
+            commit('setLoadingChequeTypes')
+            commit('setChequeTypes', [])
+        }
+
         commit('setSelectedChequeType')
     }
 }

+ 8 - 4
src/store/modules/currency.js

@@ -56,10 +56,6 @@ const actions = {
         commit('setSelectedCurrency')
         commit('setLoadingCurrencies')
     },
-    resetCurrency({ commit }) {
-        commit('setLoadingCurrencies', true)
-        commit('setCurrencies', [])
-    },
     changeCurrency({ commit, dispatch, getters }, currencySymbol) {
         commit('computePaymentInCurrency', {
             fromSymbol: getters.currencySymbol,
@@ -75,6 +71,14 @@ const actions = {
         }
 
         dispatch('autoSelectJournal')
+    },
+    resetCurrency({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingCurrencies', true)
+            commit('setCurrencies', [])
+        }
+        
+        commit('setSelectedCurrency')
     }
 }
 

+ 6 - 3
src/store/modules/customer.js

@@ -78,9 +78,12 @@ const actions = {
     selectCustomer({ commit }, payload) {
         commit('setSelectedCustomer', payload)
     },
-    resetCustomer({ commit }) {
-        commit('setLoadingCustomers', true)
-        commit('setCustomers', [])
+    resetCustomer({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingCustomers', true)
+            commit('setCustomers', [])
+        }
+        
         commit('setFilteredCustomers', [])
         commit('setSelectedCustomer', null)
     }

+ 5 - 1
src/store/modules/date.js

@@ -31,7 +31,11 @@ const actions = {
         commit('setDate', payload)
         commit('setLoadingDate')
     },
-    resetDate({ commit }) {
+    resetDate({ getters, commit }) {
+        if (!getters.isWired) {
+            return
+        }
+
         commit('setLoadingDate', true)
         commit('setDate', null)
     }

+ 7 - 3
src/store/modules/journal.js

@@ -61,10 +61,14 @@ const actions = {
     selectJournal ({ commit }, journalId) {
         commit('setSelectedJournal', journalId)
     },
-    resetJournal ({ commit }) {
-        commit('setLoadingJournals', true)
-        commit('setJournals', [])
+    resetJournal ({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingJournals', true)
+            commit('setJournals', [])
+        }
+
         commit('setSelectedJournal', null)
+        commit('autoSelectJournal')
     }
 }
 

+ 9 - 3
src/store/modules/payment.js

@@ -246,15 +246,21 @@ const actions = {
             total: getters.amountToPay
         })
     },
-    resetPayment({ commit }) {
-        commit('setLoadingPaymentTerms', true)
-        commit('setPaymentTerms', [])
+    resetPayment({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingPaymentTerms', true)
+            commit('setPaymentTerms', [])
+
+        }
+        
         commit('setPaymentTerm', null)
         commit('setPaymentType', 'cash')
         commit('setPaymentMethod', 'Efectivo')
         commit('setAmountToPay', 0)
         commit('setInitialPayment', 0)
         commit('setAmountResidual')
+
+        commit('autoSelectPaymentTerm')
     }
 }
 

+ 6 - 3
src/store/modules/product.js

@@ -90,9 +90,12 @@ const actions = {
             dispatch('addToCart', payload.variants[0])
         }
     },
-    resetProduct({ commit }) {
-        commit('setLoadingProducts', true)
-        commit('setProducts', [])
+    resetProduct({ getters, commit }) {
+        if (getters.isWired) {
+            commit('setLoadingProducts', true)
+            commit('setProducts', [])
+        }
+        
         commit('setFilteredProducts', [])
     }
 }

+ 5 - 1
src/store/modules/user.js

@@ -38,7 +38,11 @@ const actions = {
         commit('setUser', payload)
         commit('setLoadingUser')
     },
-    resetUser({ commit }) {
+    resetUser({ getters, commit }) {
+        if (!getters.isWired) {
+            return
+        }
+
         commit('setLoadingUser', true)
         commit('setUser', null)
     }

+ 6 - 0
src/store/mutations.js

@@ -25,6 +25,12 @@ const mutations = {
     },
     setNetStatus(state, isWired) {
         state.isWired = isWired
+    },
+    storeData(state, data) {
+        state.data.push(data)
+    },
+    resetData(state) {
+        state.data = []
     }
 }
 

+ 1 - 0
src/store/state.js

@@ -1,5 +1,6 @@
 const state = {
     mode: 'sale',
+    data: [],
     settings: null,
     footerButtonsVisibility: false,
     settingsVisibility: false,

+ 0 - 12
src/utils/db.js

@@ -1,12 +0,0 @@
-const storageId = 'pos-storage'
-
-/**
- * 
- * @param {*} data 
- */
-const create = data => {
-}
-
-export default {
-    create
-}

+ 0 - 5
src/utils/index.js

@@ -1,5 +0,0 @@
-import Db from './db'
-
-export {
-    Db
-}

+ 20 - 13
webpack.config.js

@@ -2,6 +2,7 @@ var Path = require('path');
 var LiveReloadPlugin = require('webpack-livereload-plugin')
 var HardSourceWebpackPlugin = require('hard-source-webpack-plugin')
 var ExtractTextPlugin = require('extract-text-webpack-plugin')
+var CopyWebpackPlugin = require('copy-webpack-plugin')
 
 var prod = process.env.NODE_ENV === 'production'
 
@@ -23,19 +24,25 @@ module.exports = {
         new LiveReloadPlugin({
             appendScriptTag: true
         }),
-        // new HardSourceWebpackPlugin({
-        //     cacheDirectory: 'node_modules/.cache/hard-source/[confighash]',
-        //     recordsPath: 'node_modules/.cache/hard-source/[confighash]/records.json',
-        //     configHash: function(webpackConfig) {
-        //         return require('node-object-hash')({sort: false}).hash(webpackConfig)
-        //     },
-        //     environmentHash: {
-        //         root: process.cwd(),
-        //         directories: [],
-        //         files: ['package-lock.json', 'yarn.lock'],
-        //     }
-        // }),
-        new ExtractTextPlugin('main.css')
+        new HardSourceWebpackPlugin({
+            cacheDirectory: 'node_modules/.cache/hard-source/[confighash]',
+            recordsPath: 'node_modules/.cache/hard-source/[confighash]/records.json',
+            configHash: function(webpackConfig) {
+                return require('node-object-hash')({sort: false}).hash(webpackConfig)
+            },
+            environmentHash: {
+                root: process.cwd(),
+                directories: [],
+                files: ['package-lock.json', 'yarn.lock'],
+            }
+        }),
+        new ExtractTextPlugin('main.css'),
+        new CopyWebpackPlugin([
+            {
+                from: 'src/sw.js',
+                to: '.'
+            }
+        ])
     ],
     module: {
         rules: [

+ 319 - 4
yarn.lock

@@ -99,6 +99,10 @@ aproba@^1.0.3:
   version "1.1.2"
   resolved "https://registry.yarnpkg.com/aproba/-/aproba-1.1.2.tgz#45c6629094de4e96f693ef7eab74ae079c240fc1"
 
+aproba@^1.1.1:
+  version "1.2.0"
+  resolved "https://registry.yarnpkg.com/aproba/-/aproba-1.2.0.tgz#6802e6264efd18c790a1b0d517f0f2627bf2c94a"
+
 are-we-there-yet@~1.1.2:
   version "1.1.4"
   resolved "https://registry.yarnpkg.com/are-we-there-yet/-/are-we-there-yet-1.1.4.tgz#bb5dca382bb94f05e15194373d16fd3ba1ca110d"
@@ -126,11 +130,21 @@ array-find-index@^1.0.1:
   version "1.0.2"
   resolved "https://registry.yarnpkg.com/array-find-index/-/array-find-index-1.0.2.tgz#df010aa1287e164bbda6f9723b0a96a1ec4187a1"
 
+array-union@^1.0.1:
+  version "1.0.2"
+  resolved "https://registry.yarnpkg.com/array-union/-/array-union-1.0.2.tgz#9a34410e4f4e3da23dea375be5be70f24778ec39"
+  dependencies:
+    array-uniq "^1.0.1"
+
+array-uniq@^1.0.1:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/array-uniq/-/array-uniq-1.0.3.tgz#af6ac877a25cc7f74e058894753858dfdb24fdb6"
+
 array-unique@^0.2.1:
   version "0.2.1"
   resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.2.1.tgz#a1d97ccafcbc2625cc70fadceb36a50c58b01a53"
 
-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"
 
@@ -852,6 +866,10 @@ bluebird@^3.1.1:
   version "3.5.0"
   resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.5.0.tgz#791420d7f551eea2897453a8a77653f96606d67c"
 
+bluebird@^3.5.1:
+  version "3.5.2"
+  resolved "https://registry.yarnpkg.com/bluebird/-/bluebird-3.5.2.tgz#1be0908e054a751754549c270489c1505d4ab15a"
+
 bn.js@^4.0.0, bn.js@^4.1.0, bn.js@^4.1.1, bn.js@^4.4.0:
   version "4.11.7"
   resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.11.7.tgz#ddb048e50d9482790094c13eb3fcfc833ce7ab46"
@@ -961,6 +979,10 @@ browserslist@^2.1.2:
     caniuse-lite "^1.0.30000684"
     electron-to-chromium "^1.3.14"
 
+buffer-from@^1.0.0:
+  version "1.1.1"
+  resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.1.tgz#32713bc028f75c02fdb710d7c7bcec1f2c6070ef"
+
 buffer-xor@^1.0.2:
   version "1.0.3"
   resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9"
@@ -989,6 +1011,24 @@ bytes@2.4.0:
   version "2.4.0"
   resolved "https://registry.yarnpkg.com/bytes/-/bytes-2.4.0.tgz#7d97196f9d5baf7f6935e25985549edd2a6c2339"
 
+cacache@^10.0.4:
+  version "10.0.4"
+  resolved "https://registry.yarnpkg.com/cacache/-/cacache-10.0.4.tgz#6452367999eff9d4188aefd9a14e9d7c6a263460"
+  dependencies:
+    bluebird "^3.5.1"
+    chownr "^1.0.1"
+    glob "^7.1.2"
+    graceful-fs "^4.1.11"
+    lru-cache "^4.1.1"
+    mississippi "^2.0.0"
+    mkdirp "^0.5.1"
+    move-concurrently "^1.0.1"
+    promise-inflight "^1.0.1"
+    rimraf "^2.6.2"
+    ssri "^5.2.4"
+    unique-filename "^1.1.0"
+    y18n "^4.0.0"
+
 camelcase-keys@^2.0.0:
   version "2.1.0"
   resolved "https://registry.yarnpkg.com/camelcase-keys/-/camelcase-keys-2.1.0.tgz#308beeaffdf28119051efa1d932213c91b8f92e7"
@@ -1091,6 +1131,10 @@ chokidar@^1.7.0:
   optionalDependencies:
     fsevents "^1.0.0"
 
+chownr@^1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.0.1.tgz#e2a75042a9551908bebd25b8523d5f9769d79181"
+
 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"
@@ -1214,6 +1258,15 @@ concat-map@0.0.1:
   version "0.0.1"
   resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b"
 
+concat-stream@^1.5.0:
+  version "1.6.2"
+  resolved "https://registry.yarnpkg.com/concat-stream/-/concat-stream-1.6.2.tgz#904bdf194cd3122fc675c77fc4ac3d4ff0fd1a34"
+  dependencies:
+    buffer-from "^1.0.0"
+    inherits "^2.0.3"
+    readable-stream "^2.2.2"
+    typedarray "^0.0.6"
+
 console-browserify@^1.1.0:
   version "1.1.0"
   resolved "https://registry.yarnpkg.com/console-browserify/-/console-browserify-1.1.0.tgz#f0241c45730a9fc6323b206dbf38edc741d0bb10"
@@ -1249,6 +1302,30 @@ convert-source-map@^1.5.0:
   version "1.5.0"
   resolved "https://registry.yarnpkg.com/convert-source-map/-/convert-source-map-1.5.0.tgz#9acd70851c6d5dfdd93d9282e5edf94a03ff46b5"
 
+copy-concurrently@^1.0.0:
+  version "1.0.5"
+  resolved "https://registry.yarnpkg.com/copy-concurrently/-/copy-concurrently-1.0.5.tgz#92297398cae34937fcafd6ec8139c18051f0b5e0"
+  dependencies:
+    aproba "^1.1.1"
+    fs-write-stream-atomic "^1.0.8"
+    iferr "^0.1.5"
+    mkdirp "^0.5.1"
+    rimraf "^2.5.4"
+    run-queue "^1.0.0"
+
+copy-webpack-plugin@^4.5.2:
+  version "4.5.2"
+  resolved "https://registry.yarnpkg.com/copy-webpack-plugin/-/copy-webpack-plugin-4.5.2.tgz#d53444a8fea2912d806e78937390ddd7e632ee5c"
+  dependencies:
+    cacache "^10.0.4"
+    find-cache-dir "^1.0.0"
+    globby "^7.1.1"
+    is-glob "^4.0.0"
+    loader-utils "^1.1.0"
+    minimatch "^3.0.4"
+    p-limit "^1.0.0"
+    serialize-javascript "^1.4.0"
+
 core-js@^2.4.0:
   version "2.4.1"
   resolved "https://registry.yarnpkg.com/core-js/-/core-js-2.4.1.tgz#4de911e667b0eae9124e34254b53aea6fc618d3e"
@@ -1421,6 +1498,10 @@ currently-unhandled@^0.4.1:
   dependencies:
     array-find-index "^1.0.1"
 
+cyclist@~0.2.2:
+  version "0.2.2"
+  resolved "https://registry.yarnpkg.com/cyclist/-/cyclist-0.2.2.tgz#1b33792e11e914a2fd6d6ed6447464444e5fa640"
+
 d@1:
   version "1.0.0"
   resolved "https://registry.yarnpkg.com/d/-/d-1.0.0.tgz#754bb5bfe55451da69a58b94d45f4c5b0462d58f"
@@ -1518,6 +1599,13 @@ 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"
+  dependencies:
+    arrify "^1.0.1"
+    path-type "^3.0.0"
+
 doctypes@^1.1.0:
   version "1.1.0"
   resolved "https://registry.yarnpkg.com/doctypes/-/doctypes-1.1.0.tgz#ea80b106a87538774e8a3a4a5afe293de489e0a9"
@@ -1526,6 +1614,15 @@ domain-browser@^1.1.1:
   version "1.1.7"
   resolved "https://registry.yarnpkg.com/domain-browser/-/domain-browser-1.1.7.tgz#867aa4b093faa05f1de08c06f4d7b21fdf8698bc"
 
+duplexify@^3.4.2, duplexify@^3.6.0:
+  version "3.6.0"
+  resolved "https://registry.yarnpkg.com/duplexify/-/duplexify-3.6.0.tgz#592903f5d80b38d037220541264d69a198fb3410"
+  dependencies:
+    end-of-stream "^1.0.0"
+    inherits "^2.0.1"
+    readable-stream "^2.0.0"
+    stream-shift "^1.0.0"
+
 ecc-jsbn@~0.1.1:
   version "0.1.1"
   resolved "https://registry.yarnpkg.com/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz#0fc73a9ed5f0d53c38193398523ef7e543777505"
@@ -1556,6 +1653,12 @@ emojis-list@^2.0.0:
   version "2.1.0"
   resolved "https://registry.yarnpkg.com/emojis-list/-/emojis-list-2.1.0.tgz#4daa4d9db00f9819880c79fa457ae5b09a1fd389"
 
+end-of-stream@^1.0.0, end-of-stream@^1.1.0:
+  version "1.4.1"
+  resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.1.tgz#ed29634d19baba463b6ce6b80a37213eab71ec43"
+  dependencies:
+    once "^1.4.0"
+
 enhanced-resolve@^3.4.0:
   version "3.4.1"
   resolved "https://registry.yarnpkg.com/enhanced-resolve/-/enhanced-resolve-3.4.1.tgz#0421e339fd71419b3da13d129b3979040230476e"
@@ -1793,6 +1896,13 @@ flatten@^1.0.2:
   version "1.0.2"
   resolved "https://registry.yarnpkg.com/flatten/-/flatten-1.0.2.tgz#dae46a9d78fbe25292258cc1e780a41d95c03782"
 
+flush-write-stream@^1.0.0:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/flush-write-stream/-/flush-write-stream-1.0.3.tgz#c5d586ef38af6097650b49bc41b55fabb19f35bd"
+  dependencies:
+    inherits "^2.0.1"
+    readable-stream "^2.0.4"
+
 follow-redirects@^1.2.5:
   version "1.4.1"
   resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.4.1.tgz#d8120f4518190f55aac65bb6fc7b85fcd666d6aa"
@@ -1831,6 +1941,22 @@ form-data@~2.1.1:
     combined-stream "^1.0.5"
     mime-types "^2.1.12"
 
+from2@^2.1.0:
+  version "2.3.0"
+  resolved "https://registry.yarnpkg.com/from2/-/from2-2.3.0.tgz#8bfb5502bde4a4d36cfdeea007fcca21d7e382af"
+  dependencies:
+    inherits "^2.0.1"
+    readable-stream "^2.0.0"
+
+fs-write-stream-atomic@^1.0.8:
+  version "1.0.10"
+  resolved "https://registry.yarnpkg.com/fs-write-stream-atomic/-/fs-write-stream-atomic-1.0.10.tgz#b47df53493ef911df75731e70a9ded0189db40c9"
+  dependencies:
+    graceful-fs "^4.1.2"
+    iferr "^0.1.5"
+    imurmurhash "^0.1.4"
+    readable-stream "1 || 2"
+
 fs.realpath@^1.0.0:
   version "1.0.0"
   resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f"
@@ -1948,10 +2074,32 @@ glob@^7.0.0, glob@^7.0.3, glob@^7.0.5, glob@~7.1.1:
     once "^1.3.0"
     path-is-absolute "^1.0.0"
 
+glob@^7.1.2:
+  version "7.1.3"
+  resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.3.tgz#3960832d3f1574108342dafd3a67b332c0969df1"
+  dependencies:
+    fs.realpath "^1.0.0"
+    inflight "^1.0.4"
+    inherits "2"
+    minimatch "^3.0.4"
+    once "^1.3.0"
+    path-is-absolute "^1.0.0"
+
 globals@^9.0.0, globals@^9.18.0:
   version "9.18.0"
   resolved "https://registry.yarnpkg.com/globals/-/globals-9.18.0.tgz#aa3896b3e69b487f17e31ed2143d69a8e30c2d8a"
 
+globby@^7.1.1:
+  version "7.1.1"
+  resolved "https://registry.yarnpkg.com/globby/-/globby-7.1.1.tgz#fb2ccff9401f8600945dfada97440cca972b8680"
+  dependencies:
+    array-union "^1.0.1"
+    dir-glob "^2.0.0"
+    glob "^7.1.2"
+    ignore "^3.3.5"
+    pify "^3.0.0"
+    slash "^1.0.0"
+
 globule@^1.0.0:
   version "1.2.0"
   resolved "https://registry.yarnpkg.com/globule/-/globule-1.2.0.tgz#1dc49c6822dd9e8a2fa00ba2a295006e8664bd09"
@@ -2123,6 +2271,14 @@ ieee754@^1.1.4:
   version "1.1.8"
   resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.1.8.tgz#be33d40ac10ef1926701f6f08a2d86fbfd1ad3e4"
 
+iferr@^0.1.5:
+  version "0.1.5"
+  resolved "https://registry.yarnpkg.com/iferr/-/iferr-0.1.5.tgz#c60eed69e6d8fdb6b3104a1fcbca1c192dc5b501"
+
+ignore@^3.3.5:
+  version "3.3.10"
+  resolved "https://registry.yarnpkg.com/ignore/-/ignore-3.3.10.tgz#0a97fb876986e8081c631160f8f9f389157f0043"
+
 imurmurhash@^0.1.4:
   version "0.1.4"
   resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea"
@@ -2238,6 +2394,10 @@ is-extglob@^1.0.0:
   version "1.0.0"
   resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-1.0.0.tgz#ac468177c4943405a092fc8f29760c6ffc6206c0"
 
+is-extglob@^2.1.1:
+  version "2.1.1"
+  resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2"
+
 is-finite@^1.0.0:
   version "1.0.2"
   resolved "https://registry.yarnpkg.com/is-finite/-/is-finite-1.0.2.tgz#cc6677695602be550ef11e8b4aa6305342b6d0aa"
@@ -2260,6 +2420,12 @@ is-glob@^2.0.0, is-glob@^2.0.1:
   dependencies:
     is-extglob "^1.0.0"
 
+is-glob@^4.0.0:
+  version "4.0.0"
+  resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.0.tgz#9521c76845cc2610a85203ddf080a958c2ffabc0"
+  dependencies:
+    is-extglob "^2.1.1"
+
 is-my-json-valid@^2.12.4:
   version "2.17.1"
   resolved "https://registry.yarnpkg.com/is-my-json-valid/-/is-my-json-valid-2.17.1.tgz#3da98914a70a22f0a8563ef1511a246c6fc55471"
@@ -2686,6 +2852,21 @@ minimist@^1.1.3, minimist@^1.2.0:
   version "1.2.0"
   resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.0.tgz#a35008b20f41383eec1fb914f4cd5df79a264284"
 
+mississippi@^2.0.0:
+  version "2.0.0"
+  resolved "https://registry.yarnpkg.com/mississippi/-/mississippi-2.0.0.tgz#3442a508fafc28500486feea99409676e4ee5a6f"
+  dependencies:
+    concat-stream "^1.5.0"
+    duplexify "^3.4.2"
+    end-of-stream "^1.1.0"
+    flush-write-stream "^1.0.0"
+    from2 "^2.1.0"
+    parallel-transform "^1.1.0"
+    pump "^2.0.1"
+    pumpify "^1.3.3"
+    stream-each "^1.1.0"
+    through2 "^2.0.0"
+
 mixin-object@^2.0.1:
   version "2.0.1"
   resolved "https://registry.yarnpkg.com/mixin-object/-/mixin-object-2.0.1.tgz#4fb949441dab182540f1fe035ba60e1947a5e57e"
@@ -2699,6 +2880,17 @@ mixin-object@^2.0.1:
   dependencies:
     minimist "0.0.8"
 
+move-concurrently@^1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/move-concurrently/-/move-concurrently-1.0.1.tgz#be2c005fda32e0b29af1f05d7c4b33214c701f92"
+  dependencies:
+    aproba "^1.1.1"
+    copy-concurrently "^1.0.0"
+    fs-write-stream-atomic "^1.0.8"
+    mkdirp "^0.5.1"
+    rimraf "^2.5.4"
+    run-queue "^1.0.3"
+
 ms@0.7.1:
   version "0.7.1"
   resolved "https://registry.yarnpkg.com/ms/-/ms-0.7.1.tgz#9cd13c03adbff25b65effde7ce864ee952017098"
@@ -2884,7 +3076,7 @@ on-finished@~2.3.0:
   dependencies:
     ee-first "1.1.1"
 
-once@^1.3.0, once@^1.3.3:
+once@^1.3.0, once@^1.3.1, once@^1.3.3, once@^1.4.0:
   version "1.4.0"
   resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1"
   dependencies:
@@ -2927,6 +3119,12 @@ p-finally@^1.0.0:
   version "1.0.0"
   resolved "https://registry.yarnpkg.com/p-finally/-/p-finally-1.0.0.tgz#3fbcfb15b899a44123b34b6dcc18b724336a2cae"
 
+p-limit@^1.0.0:
+  version "1.3.0"
+  resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.3.0.tgz#b86bd5f0c25690911c7590fcbfc2010d54b3ccb8"
+  dependencies:
+    p-try "^1.0.0"
+
 p-limit@^1.1.0:
   version "1.1.0"
   resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.1.0.tgz#b07ff2d9a5d88bec806035895a2bab66a27988bc"
@@ -2937,10 +3135,22 @@ p-locate@^2.0.0:
   dependencies:
     p-limit "^1.1.0"
 
+p-try@^1.0.0:
+  version "1.0.0"
+  resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3"
+
 pako@~0.2.0:
   version "0.2.9"
   resolved "https://registry.yarnpkg.com/pako/-/pako-0.2.9.tgz#f3f7522f4ef782348da8161bad9ecfd51bf83a75"
 
+parallel-transform@^1.1.0:
+  version "1.1.0"
+  resolved "https://registry.yarnpkg.com/parallel-transform/-/parallel-transform-1.1.0.tgz#d410f065b05da23081fcd10f28854c29bda33b06"
+  dependencies:
+    cyclist "~0.2.2"
+    inherits "^2.0.3"
+    readable-stream "^2.1.5"
+
 parse-asn1@^5.0.0:
   version "5.1.0"
   resolved "https://registry.yarnpkg.com/parse-asn1/-/parse-asn1-5.1.0.tgz#37c4f9b7ed3ab65c74817b5f2480937fbf97c712"
@@ -3010,6 +3220,12 @@ path-type@^2.0.0:
   dependencies:
     pify "^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"
+  dependencies:
+    pify "^3.0.0"
+
 pbkdf2@^3.0.3:
   version "3.0.12"
   resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.0.12.tgz#be36785c5067ea48d806ff923288c5f750b6b8a2"
@@ -3349,10 +3565,18 @@ process-nextick-args@~1.0.6:
   version "1.0.7"
   resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-1.0.7.tgz#150e20b756590ad3f91093f25a4f2ad8bff30ba3"
 
+process-nextick-args@~2.0.0:
+  version "2.0.0"
+  resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.0.tgz#a37d732f4271b4ab1ad070d35508e8290788ffaa"
+
 process@^0.11.0:
   version "0.11.10"
   resolved "https://registry.yarnpkg.com/process/-/process-0.11.10.tgz#7332300e840161bda3e69a1d1d91a7d4bc16f182"
 
+promise-inflight@^1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/promise-inflight/-/promise-inflight-1.0.1.tgz#98472870bf228132fcbdd868129bad12c3c029e3"
+
 promise@^7.0.1:
   version "7.3.1"
   resolved "https://registry.yarnpkg.com/promise/-/promise-7.3.1.tgz#064b72602b18f90f29192b8b1bc418ffd1ebd3bf"
@@ -3470,6 +3694,21 @@ pug@^2.0.0-rc.4:
     pug-runtime "^2.0.3"
     pug-strip-comments "^1.0.2"
 
+pump@^2.0.0, pump@^2.0.1:
+  version "2.0.1"
+  resolved "https://registry.yarnpkg.com/pump/-/pump-2.0.1.tgz#12399add6e4cf7526d973cbc8b5ce2e2908b3909"
+  dependencies:
+    end-of-stream "^1.1.0"
+    once "^1.3.1"
+
+pumpify@^1.3.3:
+  version "1.5.1"
+  resolved "https://registry.yarnpkg.com/pumpify/-/pumpify-1.5.1.tgz#36513be246ab27570b1a374a5ce278bfd74370ce"
+  dependencies:
+    duplexify "^3.6.0"
+    inherits "^2.0.3"
+    pump "^2.0.0"
+
 punycode@1.3.2:
   version "1.3.2"
   resolved "https://registry.yarnpkg.com/punycode/-/punycode-1.3.2.tgz#9653a036fb7c1ee42342f2325cceefea3926c48d"
@@ -3573,6 +3812,18 @@ read-pkg@^2.0.0:
     normalize-package-data "^2.3.2"
     path-type "^2.0.0"
 
+"readable-stream@1 || 2", readable-stream@^2.0.0, readable-stream@^2.0.4, readable-stream@^2.1.5, readable-stream@^2.2.2:
+  version "2.3.6"
+  resolved "http://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz#b11c27d88b8ff1fbe070643cf94b0c79ae1b0aaf"
+  dependencies:
+    core-util-is "~1.0.0"
+    inherits "~2.0.3"
+    isarray "~1.0.0"
+    process-nextick-args "~2.0.0"
+    safe-buffer "~5.1.1"
+    string_decoder "~1.1.1"
+    util-deprecate "~1.0.1"
+
 readable-stream@^2.0.1, readable-stream@^2.0.2, readable-stream@^2.0.5, readable-stream@^2.0.6, readable-stream@^2.1.4, readable-stream@^2.2.6:
   version "2.3.3"
   resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.3.tgz#368f2512d79f9d46fdfc71349ae7878bbc1eb95c"
@@ -3774,7 +4025,7 @@ rimraf@2, rimraf@^2.5.1, rimraf@^2.6.1:
   dependencies:
     glob "^7.0.5"
 
-rimraf@^2.6.2:
+rimraf@^2.5.4, rimraf@^2.6.2:
   version "2.6.2"
   resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.2.tgz#2ed8150d24a16ea8651e6d6ef0f47c4158ce7a36"
   dependencies:
@@ -3787,10 +4038,20 @@ ripemd160@^2.0.0, ripemd160@^2.0.1:
     hash-base "^2.0.0"
     inherits "^2.0.1"
 
+run-queue@^1.0.0, run-queue@^1.0.3:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/run-queue/-/run-queue-1.0.3.tgz#e848396f057d223f24386924618e25694161ec47"
+  dependencies:
+    aproba "^1.1.1"
+
 safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@~5.1.0, safe-buffer@~5.1.1:
   version "5.1.1"
   resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.1.tgz#893312af69b2123def71f57889001671eeb2c853"
 
+safe-buffer@^5.1.1:
+  version "5.1.2"
+  resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d"
+
 sass-graph@^2.2.4:
   version "2.2.4"
   resolved "https://registry.yarnpkg.com/sass-graph/-/sass-graph-2.2.4.tgz#13fbd63cd1caf0908b9fd93476ad43a51d1e0b49"
@@ -3838,6 +4099,10 @@ scss-tokenizer@^0.2.3:
   version "5.3.0"
   resolved "https://registry.yarnpkg.com/semver/-/semver-5.3.0.tgz#9b2ce5d3de02d17c6012ad326aa6b4d0cf54f94f"
 
+serialize-javascript@^1.4.0:
+  version "1.5.0"
+  resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-1.5.0.tgz#1aa336162c88a890ddad5384baebc93a655161fe"
+
 set-blocking@^2.0.0, set-blocking@~2.0.0:
   version "2.0.0"
   resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7"
@@ -3965,6 +4230,12 @@ sshpk@^1.7.0:
     jsbn "~0.1.0"
     tweetnacl "~0.14.0"
 
+ssri@^5.2.4:
+  version "5.3.0"
+  resolved "https://registry.yarnpkg.com/ssri/-/ssri-5.3.0.tgz#ba3872c9c6d33a0704a7d71ff045e5ec48999d06"
+  dependencies:
+    safe-buffer "^5.1.1"
+
 statuses@1:
   version "1.3.1"
   resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.3.1.tgz#faf51b9eb74aaef3b3acf4ad5f61abf24cb7b93e"
@@ -3982,6 +4253,13 @@ stream-browserify@^2.0.1:
     inherits "~2.0.1"
     readable-stream "^2.0.2"
 
+stream-each@^1.1.0:
+  version "1.2.3"
+  resolved "https://registry.yarnpkg.com/stream-each/-/stream-each-1.2.3.tgz#ebe27a0c389b04fbcc233642952e10731afa9bae"
+  dependencies:
+    end-of-stream "^1.1.0"
+    stream-shift "^1.0.0"
+
 stream-http@^2.3.1:
   version "2.7.2"
   resolved "https://registry.yarnpkg.com/stream-http/-/stream-http-2.7.2.tgz#40a050ec8dc3b53b33d9909415c02c0bf1abfbad"
@@ -3992,6 +4270,10 @@ stream-http@^2.3.1:
     to-arraybuffer "^1.0.0"
     xtend "^4.0.0"
 
+stream-shift@^1.0.0:
+  version "1.0.0"
+  resolved "https://registry.yarnpkg.com/stream-shift/-/stream-shift-1.0.0.tgz#d5c752825e5367e786f78e18e445ea223a155952"
+
 strict-uri-encode@^1.0.0:
   version "1.1.0"
   resolved "https://registry.yarnpkg.com/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz#279b225df1d582b1f54e65addd4352e18faa0713"
@@ -4021,6 +4303,12 @@ string_decoder@~1.0.3:
   dependencies:
     safe-buffer "~5.1.0"
 
+string_decoder@~1.1.1:
+  version "1.1.1"
+  resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8"
+  dependencies:
+    safe-buffer "~5.1.0"
+
 stringstream@~0.0.4:
   version "0.0.5"
   resolved "https://registry.yarnpkg.com/stringstream/-/stringstream-0.0.5.tgz#4e484cd4de5a0bbbee18e46307710a8a81621878"
@@ -4127,6 +4415,13 @@ tar@^2.0.0, tar@^2.2.1:
     fstream "^1.0.2"
     inherits "2"
 
+through2@^2.0.0:
+  version "2.0.3"
+  resolved "https://registry.yarnpkg.com/through2/-/through2-2.0.3.tgz#0004569b37c7c74ba39c43f3ced78d1ad94140be"
+  dependencies:
+    readable-stream "^2.1.5"
+    xtend "~4.0.1"
+
 timers-browserify@^2.0.2:
   version "2.0.2"
   resolved "https://registry.yarnpkg.com/timers-browserify/-/timers-browserify-2.0.2.tgz#ab4883cf597dcd50af211349a00fbca56ac86b86"
@@ -4201,6 +4496,10 @@ type-is@~1.6.10:
     media-typer "0.3.0"
     mime-types "~2.1.15"
 
+typedarray@^0.0.6:
+  version "0.0.6"
+  resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777"
+
 uglify-js@^2.6.1, uglify-js@^2.8.29:
   version "2.8.29"
   resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-2.8.29.tgz#29c5733148057bb4e1f75df35b7a9cb72e6a59dd"
@@ -4240,6 +4539,18 @@ uniqs@^2.0.0:
   version "2.0.0"
   resolved "https://registry.yarnpkg.com/uniqs/-/uniqs-2.0.0.tgz#ffede4b36b25290696e6e165d4a59edb998e6b02"
 
+unique-filename@^1.1.0:
+  version "1.1.0"
+  resolved "https://registry.yarnpkg.com/unique-filename/-/unique-filename-1.1.0.tgz#d05f2fe4032560871f30e93cbe735eea201514f3"
+  dependencies:
+    unique-slug "^2.0.0"
+
+unique-slug@^2.0.0:
+  version "2.0.0"
+  resolved "https://registry.yarnpkg.com/unique-slug/-/unique-slug-2.0.0.tgz#db6676e7c7cc0629878ff196097c78855ae9f4ab"
+  dependencies:
+    imurmurhash "^0.1.4"
+
 unpipe@1.0.0:
   version "1.0.0"
   resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec"
@@ -4503,7 +4814,7 @@ write-json-file@^2.3.0:
     sort-keys "^2.0.0"
     write-file-atomic "^2.0.0"
 
-xtend@^4.0.0:
+xtend@^4.0.0, xtend@~4.0.1:
   version "4.0.1"
   resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.1.tgz#a5c6d532be656e23db820efb943a1f04998d63af"
 
@@ -4511,6 +4822,10 @@ y18n@^3.2.1:
   version "3.2.1"
   resolved "https://registry.yarnpkg.com/y18n/-/y18n-3.2.1.tgz#6d15fba884c08679c0d77e88e7759e811e07fa41"
 
+y18n@^4.0.0:
+  version "4.0.0"
+  resolved "https://registry.yarnpkg.com/y18n/-/y18n-4.0.0.tgz#95ef94f85ecc81d007c264e190a120f0a3c8566b"
+
 yallist@^2.1.2:
   version "2.1.2"
   resolved "https://registry.yarnpkg.com/yallist/-/yallist-2.1.2.tgz#1c11f9218f076089a47dd512f93c6699a6a81d52"