diff --git a/client/package-lock.json b/client/package-lock.json index eed088c9..4308602a 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -1,6 +1,6 @@ { "name": "letra-extension", - "version": "1.0.8", + "version": "1.0.9", "lockfileVersion": 1, "requires": true, "dependencies": { @@ -2230,7 +2230,6 @@ "version": "3.1.1", "resolved": "https://registry.npmjs.org/archiver/-/archiver-3.1.1.tgz", "integrity": "sha512-5Hxxcig7gw5Jod/8Gq0OneVgLYET+oNHcxgWItq4TbhOzRLKNAFUb9edAftiMKXvXfCB0vbGrJdZDNq0dWMsxg==", - "dev": true, "requires": { "archiver-utils": "^2.1.0", "async": "^2.6.3", @@ -2245,7 +2244,6 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/archiver-utils/-/archiver-utils-2.1.0.tgz", "integrity": "sha512-bEL/yUb/fNNiNTuUz979Z0Yg5L+LzLxGJz8x79lYmR54fmTIb6ob/hNQgkQnIUDWIFjZVQwl9Xs356I6BAMHfw==", - "dev": true, "requires": { "glob": "^7.1.4", "graceful-fs": "^4.2.0", @@ -2263,7 +2261,6 @@ "version": "2.3.7", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", - "dev": true, "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", @@ -2467,7 +2464,6 @@ "version": "2.6.3", "resolved": "https://registry.npmjs.org/async/-/async-2.6.3.tgz", "integrity": "sha512-zflvls11DCy+dQWzTW2dzuilv8Z5X/pjfmZOWba6TNIVDm+2UDaJmXSOXlasHKfNBs8oo3M0aT50fDEWfKZjXg==", - "dev": true, "requires": { "lodash": "^4.17.14" } @@ -2880,8 +2876,7 @@ "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", - "dev": true + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, "base": { "version": "0.11.2", @@ -2947,8 +2942,7 @@ "base64-js": { "version": "1.3.1", "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.1.tgz", - "integrity": "sha512-mLQ4i2QO1ytvGWFWmcngKO//JXAQueZvwEKtjgQFM4jIK0kU+ytMfplL8j+n5mspOfjHwoAg+9yhb7BwAHm36g==", - "dev": true + "integrity": "sha512-mLQ4i2QO1ytvGWFWmcngKO//JXAQueZvwEKtjgQFM4jIK0kU+ytMfplL8j+n5mspOfjHwoAg+9yhb7BwAHm36g==" }, "bcrypt-pbkdf": { "version": "1.0.2", @@ -2986,7 +2980,6 @@ "version": "4.0.2", "resolved": "https://registry.npmjs.org/bl/-/bl-4.0.2.tgz", "integrity": "sha512-j4OH8f6Qg2bGuWfRiltT2HYGx0e1QcBTrK9KAHNMwMZdQnDZFk0ZSYIpADjYCB3U12nicC5tVJwSIhwOWjb4RQ==", - "dev": true, "requires": { "buffer": "^5.5.0", "inherits": "^2.0.4", @@ -3018,7 +3011,6 @@ "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "dev": true, "requires": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -3159,7 +3151,6 @@ "version": "5.6.0", "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.6.0.tgz", "integrity": "sha512-/gDYp/UtU0eA1ys8bOs9J6a+E/KWIY+DZ+Q2WESNUA0jFRsJOc0SNUO6xJ5SGA1xueg3NL65W6s+NY5l9cunuw==", - "dev": true, "requires": { "base64-js": "^1.0.2", "ieee754": "^1.1.4" @@ -3168,8 +3159,7 @@ "buffer-crc32": { "version": "0.2.13", "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", - "dev": true + "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=" }, "buffer-from": { "version": "1.1.1", @@ -3596,7 +3586,6 @@ "version": "2.1.1", "resolved": "https://registry.npmjs.org/compress-commons/-/compress-commons-2.1.1.tgz", "integrity": "sha512-eVw6n7CnEMFzc3duyFVrQEuY1BlHR3rYsSztyG32ibGMW722i3C6IizEGMFmfMU+A+fALvBIwxN3czffTcdA+Q==", - "dev": true, "requires": { "buffer-crc32": "^0.2.13", "crc32-stream": "^3.0.1", @@ -3608,7 +3597,6 @@ "version": "2.3.7", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", - "dev": true, "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", @@ -3624,8 +3612,7 @@ "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", - "dev": true + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" }, "concat-stream": { "version": "1.6.2", @@ -3849,14 +3836,12 @@ "core-util-is": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", - "dev": true + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, "crc": { "version": "3.8.0", "resolved": "https://registry.npmjs.org/crc/-/crc-3.8.0.tgz", "integrity": "sha512-iX3mfgcTMIq3ZKLIsVFAbv7+Mc10kxabAGQb8HvjA1o3T1PIYprbakQ65d3I+2HGHt6nSKkM9PYjgoJO2KcFBQ==", - "dev": true, "requires": { "buffer": "^5.1.0" } @@ -3865,7 +3850,6 @@ "version": "3.0.1", "resolved": "https://registry.npmjs.org/crc32-stream/-/crc32-stream-3.0.1.tgz", "integrity": "sha512-mctvpXlbzsvK+6z8kJwSJ5crm7yBwrQMTybJzMw1O4lLGJqjlDCXY2Zw7KheiA6XBEcBmfLx1D88mjRGVJtY9w==", - "dev": true, "requires": { "crc": "^3.4.4", "readable-stream": "^3.4.0" @@ -4419,7 +4403,6 @@ "version": "1.4.4", "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", - "dev": true, "requires": { "once": "^1.4.0" } @@ -5544,8 +5527,7 @@ "fs-constants": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", - "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", - "dev": true + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==" }, "fs-extra": { "version": "8.1.0", @@ -5590,8 +5572,7 @@ "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", - "dev": true + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" }, "fsevents": { "version": "2.1.3", @@ -5749,7 +5730,6 @@ "version": "7.1.6", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", - "dev": true, "requires": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", @@ -5889,8 +5869,7 @@ "graceful-fs": { "version": "4.2.4", "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.4.tgz", - "integrity": "sha512-WjKPNJF79dtJAVniUlGGWHYGz2jWxT6VhN/4m1NdkbZ2nOsEF+cI1Edgql5zCRhs/VsQYRvrXctxktVXZUkixw==", - "dev": true + "integrity": "sha512-WjKPNJF79dtJAVniUlGGWHYGz2jWxT6VhN/4m1NdkbZ2nOsEF+cI1Edgql5zCRhs/VsQYRvrXctxktVXZUkixw==" }, "growly": { "version": "1.3.0", @@ -6137,8 +6116,7 @@ "ieee754": { "version": "1.1.13", "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.13.tgz", - "integrity": "sha512-4vf7I2LYV/HaWerSo3XmlMkp5eZ83i+/CDluXi/IGTs/O1sejBNhTtnxzmRZfvOUqj7lZjqHkeTvpgSFDlWZTg==", - "dev": true + "integrity": "sha512-4vf7I2LYV/HaWerSo3XmlMkp5eZ83i+/CDluXi/IGTs/O1sejBNhTtnxzmRZfvOUqj7lZjqHkeTvpgSFDlWZTg==" }, "iferr": { "version": "0.1.5", @@ -6277,7 +6255,6 @@ "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "dev": true, "requires": { "once": "^1.3.0", "wrappy": "1" @@ -6286,8 +6263,7 @@ "inherits": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", - "dev": true + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" }, "ini": { "version": "1.3.5", @@ -6642,8 +6618,7 @@ "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" }, "isexe": { "version": "2.0.0", @@ -8294,7 +8269,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/lazystream/-/lazystream-1.0.0.tgz", "integrity": "sha1-9plf4PggOS9hOWvolGJAe7dxaOQ=", - "dev": true, "requires": { "readable-stream": "^2.0.5" }, @@ -8303,7 +8277,6 @@ "version": "2.3.7", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", - "dev": true, "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", @@ -8477,32 +8450,27 @@ "lodash": { "version": "4.17.15", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz", - "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==", - "dev": true + "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==" }, "lodash.defaults": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-4.2.0.tgz", - "integrity": "sha1-0JF4cW/+pN3p5ft7N/bwgCJ0WAw=", - "dev": true + "integrity": "sha1-0JF4cW/+pN3p5ft7N/bwgCJ0WAw=" }, "lodash.difference": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/lodash.difference/-/lodash.difference-4.5.0.tgz", - "integrity": "sha1-nMtOUF1Ia5FlE0V3KIWi3yf9AXw=", - "dev": true + "integrity": "sha1-nMtOUF1Ia5FlE0V3KIWi3yf9AXw=" }, "lodash.flatten": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/lodash.flatten/-/lodash.flatten-4.4.0.tgz", - "integrity": "sha1-8xwiIlqWMtK7+OSt2+8kCqdlph8=", - "dev": true + "integrity": "sha1-8xwiIlqWMtK7+OSt2+8kCqdlph8=" }, "lodash.isplainobject": { "version": "4.0.6", "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=", - "dev": true + "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=" }, "lodash.sortby": { "version": "4.7.0", @@ -8513,8 +8481,7 @@ "lodash.union": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/lodash.union/-/lodash.union-4.6.0.tgz", - "integrity": "sha1-SLtQiECfFvGCFmZkHETdGqrjzYg=", - "dev": true + "integrity": "sha1-SLtQiECfFvGCFmZkHETdGqrjzYg=" }, "longest": { "version": "1.0.1", @@ -8822,7 +8789,6 @@ "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "dev": true, "requires": { "brace-expansion": "^1.1.7" } @@ -9283,8 +9249,7 @@ "normalize-path": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", - "dev": true + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==" }, "npm-run-path": { "version": "2.0.2", @@ -9428,7 +9393,6 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "dev": true, "requires": { "wrappy": "1" } @@ -9648,8 +9612,7 @@ "path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", - "dev": true + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" }, "path-key": { "version": "2.0.1", @@ -9977,8 +9940,7 @@ "process-nextick-args": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", - "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", - "dev": true + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==" }, "progress": { "version": "2.0.3", @@ -10316,7 +10278,6 @@ "version": "3.6.0", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", - "dev": true, "requires": { "inherits": "^2.0.3", "string_decoder": "^1.1.1", @@ -10689,8 +10650,7 @@ "safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" }, "safe-regex": { "version": "1.1.0", @@ -11672,7 +11632,6 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "dev": true, "requires": { "safe-buffer": "~5.1.0" } @@ -11850,7 +11809,6 @@ "version": "2.1.2", "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.1.2.tgz", "integrity": "sha512-UaF6FoJ32WqALZGOIAApXx+OdxhekNMChu6axLJR85zMMjXKWFGjbIRe+J6P4UnRGg9rAwWvbTT0oI7hD/Un7Q==", - "dev": true, "requires": { "bl": "^4.0.1", "end-of-stream": "^1.4.1", @@ -12441,8 +12399,7 @@ "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", - "dev": true + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" }, "uuid": { "version": "3.4.0", @@ -13688,8 +13645,7 @@ "wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", - "dev": true + "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write": { "version": "1.0.3", @@ -13843,7 +13799,6 @@ "version": "2.1.3", "resolved": "https://registry.npmjs.org/zip-stream/-/zip-stream-2.1.3.tgz", "integrity": "sha512-EkXc2JGcKhO5N5aZ7TmuNo45budRaFGHOmz24wtJR7znbNqDPmdZtUauKX6et8KAVseAMBOyWJqEpXcHTBsh7Q==", - "dev": true, "requires": { "archiver-utils": "^2.1.0", "compress-commons": "^2.1.1", diff --git a/client/src/store/index.js b/client/src/store/index.js index 4ec11aa7..e3e8f993 100644 --- a/client/src/store/index.js +++ b/client/src/store/index.js @@ -6,9 +6,9 @@ import axios from 'axios'; Vue.use(Vuex); -const currentLanguagesCount = 11; +export const currentLanguagesCount = 11; -const state = { +export const state = { dailyData: { word: {}, language: {}, @@ -21,91 +21,97 @@ const state = { loading: false, }; -export default new Vuex.Store({ - state, - actions: { - getSelectedLanguages({ commit, dispatch }) { - commit('setLoading', true); - chrome.storage.sync.get('selectedLanguages', response => { - let { selectedLanguages } = response; - if (selectedLanguages === undefined || selectedLanguages.length === 0) { - selectedLanguages = ['german']; - } - dispatch('saveSelectedLanguages', selectedLanguages); - dispatch('getDailyData'); - }); - }, - saveSelectedLanguages({ commit }, selectedLanguages) { - chrome.storage.sync.set({ selectedLanguages }); - commit('setSelectedLanguages', selectedLanguages); - }, - resetSelectedLanguages({ dispatch }, selectedLanguages) { +export const actions = { + getSelectedLanguages({ commit, dispatch }) { + commit('setLoading', true); + chrome.storage.sync.get('selectedLanguages', response => { + let { selectedLanguages } = response; + if (selectedLanguages === undefined || selectedLanguages.length === 0) { + selectedLanguages = ['german']; + } dispatch('saveSelectedLanguages', selectedLanguages); - dispatch('retrieveDailyData'); - }, - getDailyData({ commit, dispatch }) { - chrome.storage.sync.get('dailyData', response => { - const data = response.dailyData; - if (!!data && data.created_at === new Date().toDateString()) { - dispatch('saveDailyData', data); - commit('setLoading', false); - } else dispatch('retrieveDailyData'); - }); - }, - retrieveDailyData({ commit, dispatch }) { - commit('setLoading', true); - const languages = state.selectedLanguages.join(','); - axios - .get(`${process.env.VUE_APP_API_URL}/daily?languages=${languages}`) - .then(response => { - const { data } = response; - data.created_at = new Date().toDateString(); - chrome.storage.sync.set({ dailyData: data }); - dispatch('saveDailyData', data); - commit('setLoading', false); - }) - .catch(() => commit('setHasError', true)); - }, - saveDailyData({ commit }, data) { - commit('setDailyData', data); - }, - getLanguageOptions({ dispatch }) { - chrome.storage.sync.get('languageOptions', response => { - const data = response.languageOptions; - if (!!data && data.length === currentLanguagesCount) - dispatch('saveLanguageOptions', data); - else dispatch('retrieveLanguageOptions'); + dispatch('getDailyData'); + }); + }, + saveSelectedLanguages({ commit }, selectedLanguages) { + chrome.storage.sync.set({ selectedLanguages }); + commit('setSelectedLanguages', selectedLanguages); + }, + resetSelectedLanguages({ dispatch }, selectedLanguages) { + dispatch('saveSelectedLanguages', selectedLanguages); + dispatch('retrieveDailyData'); + }, + getDailyData({ commit, dispatch }) { + chrome.storage.sync.get('dailyData', response => { + const data = response.dailyData; + if (!!data && data.created_at === new Date().toDateString()) { + dispatch('saveDailyData', data); + commit('setLoading', false); + } else dispatch('retrieveDailyData'); + }); + }, + retrieveDailyData({ commit, dispatch }) { + commit('setLoading', true); + const languages = state.selectedLanguages.join(','); + axios + .get(`${process.env.VUE_APP_API_URL}/daily?languages=${languages}`) + .then(response => { + const { data } = response; + data.created_at = new Date().toDateString(); + chrome.storage.sync.set({ dailyData: data }); + dispatch('saveDailyData', data); + commit('setLoading', false); + }) + .catch(() => { + commit('setHasError', true); }); - }, - retrieveLanguageOptions({ commit, dispatch }) { - axios - .get(`${process.env.VUE_APP_API_URL}/languages`) - .then(response => { - const options = Object.keys(response.data.languages); - chrome.storage.sync.set({ languageOptions: options }); - dispatch('saveLanguageOptions', options); - }) - .catch(() => commit('setHasError', true)); - }, - saveLanguageOptions({ commit }, options) { - commit('setLanguageOptions', options); - }, }, - mutations: { - setDailyData(state, data) { - state.dailyData = data; - }, - setLanguageOptions(state, languageOptions) { - state.languageOptions = languageOptions; - }, - setSelectedLanguages(state, selectedLanguages) { - state.selectedLanguages = selectedLanguages; - }, - setHasError(state, hasError) { - state.hasError = hasError; - }, - setLoading(state, loading) { - state.loading = loading; - }, + saveDailyData({ commit }, data) { + commit('setDailyData', data); + }, + getLanguageOptions({ dispatch }) { + chrome.storage.sync.get('languageOptions', response => { + const data = response.languageOptions; + if (!!data && data.length === currentLanguagesCount) + dispatch('saveLanguageOptions', data); + else dispatch('retrieveLanguageOptions'); + }); + }, + retrieveLanguageOptions({ commit, dispatch }) { + axios + .get(`${process.env.VUE_APP_API_URL}/languages`) + .then(response => { + const options = Object.keys(response.data.languages); + chrome.storage.sync.set({ languageOptions: options }); + dispatch('saveLanguageOptions', options); + }) + .catch(() => commit('setHasError', true)); + }, + saveLanguageOptions({ commit }, options) { + commit('setLanguageOptions', options); }, +}; + +export const mutations = { + setDailyData(state, data) { + state.dailyData = data; + }, + setLanguageOptions(state, languageOptions) { + state.languageOptions = languageOptions; + }, + setSelectedLanguages(state, selectedLanguages) { + state.selectedLanguages = selectedLanguages; + }, + setHasError(state, hasError) { + state.hasError = hasError; + }, + setLoading(state, loading) { + state.loading = loading; + }, +}; + +export default new Vuex.Store({ + state, + actions, + mutations, }); diff --git a/client/test/src/components/OptionsButton.test.js b/client/test/src/components/OptionsButton.test.js index 5fe4aed5..1ffbbd30 100644 --- a/client/test/src/components/OptionsButton.test.js +++ b/client/test/src/components/OptionsButton.test.js @@ -6,10 +6,6 @@ describe('OptionsButton', () => { const wrapper = mount(OptionsButton); expect(wrapper).toBeTruthy(); }); - it('gets the name of the component', () => { - const wrapper = mount(OptionsButton); - expect(wrapper.name()).toEqual('OptionsButton'); - }); it('has the icon class', () => { const wrapper = mount(OptionsButton); expect(wrapper.find('.icon').exists()).toBeTruthy(); diff --git a/client/test/src/components/RandomButton.test.js b/client/test/src/components/RandomButton.test.js new file mode 100644 index 00000000..a7ca49e4 --- /dev/null +++ b/client/test/src/components/RandomButton.test.js @@ -0,0 +1,19 @@ +import { mount } from '@vue/test-utils'; +import RandomButton from '../../../src/components/RandomButton'; + +describe('RandomButton', () => { + it('is a Vue instance', () => { + const wrapper = mount(RandomButton); + expect(wrapper).toBeTruthy(); + }); + it('has the icon class', () => { + const wrapper = mount(RandomButton); + expect(wrapper.find('.icon').exists()).toBeTruthy(); + }); + it('calls the emit event on button click', () => { + const wrapper = mount(RandomButton); + wrapper.find('#random-button').trigger('click'); + expect(wrapper.emitted().click).toBeTruthy(); + expect(wrapper.emitted().click.length).toBe(1); + }); +}); diff --git a/client/test/src/components/TranslateButton.test.js b/client/test/src/components/TranslateButton.test.js new file mode 100644 index 00000000..96473e88 --- /dev/null +++ b/client/test/src/components/TranslateButton.test.js @@ -0,0 +1,19 @@ +import { mount } from '@vue/test-utils'; +import TranslateButton from '../../../src/components/TranslateButton'; + +describe('RandomButton', () => { + it('is a Vue instance', () => { + const wrapper = mount(TranslateButton); + expect(wrapper).toBeTruthy(); + }); + it('has the icon class', () => { + const wrapper = mount(TranslateButton); + expect(wrapper.find('.icon').exists()).toBeTruthy(); + }); + it('calls the emit event on button click', () => { + const wrapper = mount(TranslateButton); + wrapper.find('.icon').trigger('click'); + expect(wrapper.emitted().click).toBeTruthy(); + expect(wrapper.emitted().click.length).toBe(1); + }); +}); diff --git a/client/test/src/router/index.test.js b/client/test/src/router/index.test.js new file mode 100644 index 00000000..fcd64573 --- /dev/null +++ b/client/test/src/router/index.test.js @@ -0,0 +1,16 @@ +import router from '../../../src/router/index'; + +describe('router', () => { + it('initialzes the router', () => { + expect(router).toBeTruthy(); + }); + it('has the main route for the app', () => { + expect(router.options.routes.length).toEqual(1); + }); + it('has the path for the route', () => { + expect(router.options.routes[0].path).toEqual('/'); + }); + it('has the name for the route', () => { + expect(router.options.routes[0].name).toEqual('Home'); + }); +}); diff --git a/client/test/src/store/index.test.js b/client/test/src/store/index.test.js new file mode 100644 index 00000000..53eded53 --- /dev/null +++ b/client/test/src/store/index.test.js @@ -0,0 +1,386 @@ +import axios from 'axios'; +import store, { + state, + actions, + mutations, + currentLanguagesCount, +} from '../../../src/store/index'; + +jest.mock('axios'); + +const get = jest.fn(); +const set = jest.fn(); +global.chrome = { + storage: { + sync: { + set, + get, + }, + }, +}; + +describe('store', () => { + it('initialzes the store', () => { + expect(store).toBeTruthy(); + }); + + describe('initial state', () => { + it('has the initial values for dailyData', () => { + expect(state.dailyData.word).toEqual({}); + expect(state.dailyData.language).toEqual({}); + expect(state.dailyData.quote).toEqual({}); + expect(state.dailyData.photo).toEqual({ user: {} }); + }); + it('has the initial value for hasError', () => { + expect(state.hasError).toBe(false); + }); + it('has the initial value for languageOptions', () => { + expect(state.languageOptions).toEqual([]); + }); + it('has the initial value for selectedLanguages', () => { + expect(state.selectedLanguages).toEqual([]); + }); + it('has the initial value for loading', () => { + expect(state.loading).toBe(false); + }); + }); + + describe('actions', () => { + let commit, dispatch; + beforeEach(() => { + jest.clearAllMocks(); + commit = jest.fn(); + dispatch = jest.fn(); + }); + describe('getSelectedLanguages', () => { + it('calls commit let loading', () => { + actions.getSelectedLanguages({ commit, dispatch }); + expect(commit).toHaveBeenCalledWith('setLoading', true); + }); + it('defaults to germen if selected language is undefined', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + selectedLanguages: undefined, + }); + }); + actions.getSelectedLanguages({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('saveSelectedLanguages', [ + 'german', + ]); + }); + it('defaults to germen if selected language is empty array', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + selectedLanguages: [], + }); + }); + actions.getSelectedLanguages({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('saveSelectedLanguages', [ + 'german', + ]); + }); + it('calls dispatch save selected languages', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + selectedLanguages: ['japanese'], + }); + }); + actions.getSelectedLanguages({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('saveSelectedLanguages', [ + 'japanese', + ]); + }); + it('calls dispatch get daily data', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + selectedLanguages: ['japanese'], + }); + }); + actions.getSelectedLanguages({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('getDailyData'); + }); + }); + + describe('saveSelectedLanguages', () => { + it('sets the selected langugage in chrome local storage', () => { + actions.saveSelectedLanguages({ commit }, ['japanese, korean']); + expect(set).toHaveBeenCalledWith({ + selectedLanguages: ['japanese, korean'], + }); + }); + it('calls commit set selected language', () => { + actions.saveSelectedLanguages({ commit }, ['japanese, korean']); + expect(commit).toHaveBeenCalledWith('setSelectedLanguages', [ + 'japanese, korean', + ]); + }); + }); + + describe('resetSelectedLanguages', () => { + it('calls dispatch save selected language', () => { + actions.resetSelectedLanguages({ dispatch }, ['japanese, korean']); + expect(dispatch).toHaveBeenCalledWith('saveSelectedLanguages', [ + 'japanese, korean', + ]); + }); + it('calls dispatch retrieve daily data', () => { + actions.resetSelectedLanguages({ dispatch }, ['japanese, korean']); + expect(dispatch).toHaveBeenCalledWith('retrieveDailyData'); + }); + }); + describe('getDailyData', () => { + let data; + const mockDate = new Date(1466424490000); + beforeEach(() => { + data = { + dailyData: { + created_at: mockDate.toDateString(), + }, + }; + }); + it('calls dispatch save daily data', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback(data); + }); + jest.spyOn(global, 'Date').mockImplementation(() => mockDate); + actions.getDailyData({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('saveDailyData', data.dailyData); + }); + it('calls commit set loading false', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback(data); + }); + jest.spyOn(global, 'Date').mockImplementation(() => mockDate); + actions.getDailyData({ commit, dispatch }); + expect(commit).toHaveBeenCalledWith('setLoading', false); + }); + it('calls dispatch retrieve daily data if created at date does not match new date to date string', () => { + data.created_at = new Date(); + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + dailyData: { + created_at: new Date(), + }, + }); + }); + actions.getDailyData({ commit, dispatch }); + expect(dispatch).toHaveBeenCalledWith('retrieveDailyData'); + }); + }); + describe('retrieveDailyData', () => { + let data; + beforeEach(() => { + process.env.VUE_APP_API_URL = 'app-api-url'; + state.selectedLanguages = ['japanese', 'korean']; + data = { + created_at: new Date(), + dailyData: [], + }; + }); + it('calls the get endpoint for the selected languages', () => { + axios.get.mockResolvedValue({ data }); + actions.retrieveDailyData({ commit, dispatch }); + expect(axios.get).toHaveBeenCalledWith( + 'app-api-url/daily?languages=japanese,korean', + ); + }); + it('calls chrome storage set', done => { + axios.get.mockResolvedValue({ data }); + actions.retrieveDailyData({ commit, dispatch }); + axios + .get('app-api-url/daily?languages=japanese,korean') + .then(response => { + expect(set).toHaveBeenCalledWith({ dailyData: data }); + done(); + }); + }); + it('calls dispatch save daily data', done => { + axios.get.mockResolvedValue({ data }); + actions.retrieveDailyData({ commit, dispatch }); + axios + .get('app-api-url/daily?languages=japanese,korean') + .then(response => { + expect(dispatch).toHaveBeenCalledWith('saveDailyData', data); + done(); + }); + }); + it('calls commit set loading', done => { + axios.get.mockResolvedValue({ data }); + actions.retrieveDailyData({ commit, dispatch }); + axios + .get('app-api-url/daily?languages=japanese,korean') + .then(response => { + expect(commit).toHaveBeenCalledWith('setLoading', false); + done(); + }); + }); + it('calls set has error if the call fails', done => { + axios.get.mockRejectedValue(new Error('Something bad happened!')); + actions.retrieveDailyData({ commit, dispatch }); + axios + .get('app-api-url/daily?languages=japanese,korean') + .then(response => { + // empty then with catch tagged on to test the code inside the catch block + }) + .catch(error => { + expect(commit).toHaveBeenCalledWith('setHasError', true); + done(); + }); + }); + }); + describe('saveDailyData', () => { + let data; + beforeEach(() => { + data = { + created_at: new Date(), + dailyData: [], + }; + }); + it('commits set daily data', () => { + actions.saveDailyData({ commit }, data); + expect(commit).toHaveBeenCalledWith('setDailyData', data); + }); + }); + describe('getLanguageOptions', () => { + let languageOptions; + beforeEach(() => { + languageOptions = ['japanese']; + }); + it('calls dispatch save language options', () => { + languageOptions.length = currentLanguagesCount; + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + languageOptions, + }); + }); + actions.getLanguageOptions({ dispatch }); + expect(dispatch).toHaveBeenCalledWith( + 'saveLanguageOptions', + languageOptions, + ); + }); + it('calls dispatch retrieve language options', () => { + jest + .spyOn(chrome.storage.sync, 'get') + .mockImplementation((language, callback) => { + return callback({ + languageOptions: [], + }); + }); + actions.getLanguageOptions({ dispatch }); + expect(dispatch).toHaveBeenCalledWith('retrieveLanguageOptions'); + }); + }); + describe('retrieveLanguageOptions', () => { + let data; + beforeEach(() => { + process.env.VUE_APP_API_URL = 'app-api-url'; + data = { + languages: [], + }; + }); + it('calls the get endpoint for the language options', () => { + axios.get.mockResolvedValue({ data }); + actions.retrieveLanguageOptions({ commit, dispatch }); + expect(axios.get).toHaveBeenCalledWith('app-api-url/languages'); + }); + it('calls chrome storage set', done => { + axios.get.mockResolvedValue({ data }); + actions.retrieveLanguageOptions({ commit, dispatch }); + axios.get('app-api-url/languages').then(response => { + expect(set).toHaveBeenCalledWith({ languageOptions: [] }); + done(); + }); + }); + it('calls dispatch save language options', done => { + axios.get.mockResolvedValue({ data }); + actions.retrieveLanguageOptions({ commit, dispatch }); + axios.get('app-api-url/languages').then(response => { + expect(dispatch).toHaveBeenCalledWith('saveLanguageOptions', []); + done(); + }); + }); + it('calls set has error if the call fails', done => { + axios.get.mockRejectedValue(new Error('Something bad happened!')); + actions.retrieveLanguageOptions({ commit, dispatch }); + axios + .get('app-api-url/languages') + .then(response => { + // empty then with catch tagged on to test the code inside the catch block + }) + .catch(error => { + expect(commit).toHaveBeenCalledWith('setHasError', true); + done(); + }); + }); + }); + describe('saveLanguageOptions', () => { + it('calls commit set language options', () => { + actions.saveLanguageOptions({ commit }, []); + expect(commit).toHaveBeenCalledWith('setLanguageOptions', []); + }); + }); + }); + describe('mutations', () => { + it('sets the daily data', () => { + const state = { + dailyData: {}, + }; + const data = { + items: [], + }; + mutations.setDailyData(state, data); + expect(state.dailyData).toEqual(data); + }); + it('sets the language options', () => { + const state = { + dailyData: {}, + }; + let languageOptions = ['korean']; + mutations.setLanguageOptions(state, languageOptions); + expect(state.languageOptions).toEqual(languageOptions); + }); + it('sets the selected languages', () => { + const state = { + dailyData: {}, + }; + let selectedLanguages = ['korean']; + mutations.setSelectedLanguages(state, selectedLanguages); + expect(state.selectedLanguages).toEqual(selectedLanguages); + }); + + it('sets has error', () => { + const state = { + dailyData: {}, + }; + let hasError = true; + mutations.setHasError(state, hasError); + expect(state.hasError).toEqual(hasError); + }); + + it('sets loading', () => { + const state = { + dailyData: {}, + }; + let loading = true; + mutations.setLoading(state, loading); + expect(state.loading).toEqual(loading); + }); + }); +});