From 16b743c277807b7a18ba98548a1db5240a08f6d6 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 14 Dec 2017 14:58:31 +0100 Subject: [PATCH 01/51] update svg code --- src/components/ToolchainEditor.jsx | 201 ++++++++++++++++++++++------- 1 file changed, 151 insertions(+), 50 deletions(-) diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index 405634c..b185083 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -100,13 +100,33 @@ const ThinInput = (props: any) => { const {x, y, height, width} = locMap.block; - const inputs = data && data.hasOwnProperty('inputs') ? data.inputs : []; - const outputs = data && data.hasOwnProperty('outputs') ? data.outputs : []; - - console.log(locMap); + const hasInputs = data && data.hasOwnProperty('inputs'); + const hasOutputs = data && data.hasOwnProperty('outputs'); + const inputs = hasInputs ? data.inputs : []; + const outputs = hasOutputs ? data.outputs : []; + let color = 'white'; + if(!hasInputs) + color = 'lightCyan'; + else if(!hasOutputs) + color = 'lightYellow'; + + //console.log(locMap); return ( + + + { name } + + { + /* { - { - inputs.map((inp, i) => - - ) - } - { - outputs.map((out, i) => - - ) + */ } + + { + inputs.map((inp, i) => { + const loc = locMap.inputs[inp]; + return ( + + + + { inp } + + + ); + }) + } + + + { + outputs.map((out, i) => { + const loc = locMap.outputs[out]; + return ( + + + + { out } + + + ); + }) + } + + + + + + + + + + ); }; @@ -211,15 +282,16 @@ export class ToolchainEditor extends React.Component { updateBlockLocation = (blockName: string, x: number, y: number) => { const rep = this.state.cache.contents.representation; + const block = rep.blocks[blockName]; this.setContents({ representation: { ...rep, blocks: { ...rep.blocks, [blockName]: { - ...rep.blocks[blockName], - col: x, - row: y, + ...block, + col: block.col + x, + row: block.row + y, } } } @@ -284,23 +356,52 @@ export class ToolchainEditor extends React.Component { setTimeout(() => { const updateBlockLocation = this.updateBlockLocation; let debouceTimeLast = 0; + let dx = 0; + let dy = 0; + let mx = 0; + let my = 0; function dragged(d) { /* if(Date.now() - debouceTimeLast < 10) return; */ - const x = Math.round(d3.event.x / 20.0); - const y = Math.round(d3.event.y / 20.0); - const bId = d3.select(this).attr('id'); - //console.log(`${ bId }: ${ x } | ${ y }`); - updateBlockLocation(bId, x, y); + dx += d3.event.dx; + dy += d3.event.dy; + if(Math.abs(dx) > 20){ + mx = Math.round(dx / 20.0); + dx = dx - mx * 20; + } + if(Math.abs(dy) > 20){ + my = Math.round(dy / 20.0); + dy = dy - my * 20; + } + if(mx != 0 || my != 0){ + const bId = d3.select(this).attr('id'); + //console.log(`${ bId }: ${ x } | ${ y }`); + updateBlockLocation(bId, mx, my); + } + mx = 0; + my = 0; //debouceTimeLast = Date.now(); } + function startDrag(d) { + dx = 0; + dy = 0; + mx = 0; + my = 0; + } + + function endDrag(d) { + + } + d3.selectAll('.fo').call( d3.drag() + .on('start', startDrag) + .on('end', endDrag) .on('drag', dragged) ); @@ -369,20 +470,6 @@ export class ToolchainEditor extends React.Component { height={svgHeight} viewBox={this.getSvgViewBox()} > - { - Object.entries(this.state.cache.contents.representation.blocks).map(([name, rep], i) => - b.name === name) || - this.state.cache.contents.datasets.find(b => b.name === name) || - this.state.cache.contents.analyzers.find(b => b.name === name) - } - key={i} - /> - ) - } { [...Array(Math.round(svgHeight / gridY))].map((u, i) => { @@ -415,13 +502,27 @@ export class ToolchainEditor extends React.Component { ); }) } + { + Object.entries(this.state.cache.contents.representation.blocks).map(([name, rep], i) => + b.name === name) || + this.state.cache.contents.datasets.find(b => b.name === name) || + this.state.cache.contents.analyzers.find(b => b.name === name) + } + key={i} + /> + ) + } { this.state.cache.contents.connections.map((conn, i) => { const connId = `#${ connectionToId(conn) }`; const fromInfo = conn.from.split('.'); const toInfo = conn.to.split('.'); - console.log(`Connecting "${ connId }" from ${ fromInfo } to ${ toInfo }`); + //console.log(`Connecting "${ connId }" from ${ fromInfo } to ${ toInfo }`); const connPath = document.querySelector(connId); const fromLoc = locMap[fromInfo[0]].outputs[fromInfo[1]]; const toLoc = locMap[toInfo[0]].inputs[toInfo[1]]; -- GitLab From 75e63442dd88bb8a8fa7fb60c597dde9c55e07dc Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 14 Dec 2017 14:59:58 +0100 Subject: [PATCH 02/51] update deps --- package-lock.json | 269 +++++++++++++++++++--------------------------- package.json | 25 ++--- 2 files changed, 123 insertions(+), 171 deletions(-) diff --git a/package-lock.json b/package-lock.json index 82dacf4..e46d579 100644 --- a/package-lock.json +++ b/package-lock.json @@ -98,7 +98,7 @@ "@babel/types": "7.0.0-beta.31", "babylon": "7.0.0-beta.31", "debug": "3.1.0", - "globals": "10.3.0", + "globals": "10.4.0", "invariant": "2.2.2", "lodash": "4.17.4" }, @@ -119,9 +119,9 @@ } }, "globals": { - "version": "10.3.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-10.3.0.tgz", - "integrity": "sha512-1g6qO5vMbiPHbRTDtR9JVjRkAhkgH4nSANYGyx1eOfqgxcMnYMMD+7MjmjfzXjwFpVUE/7/NzF+jQxYE7P4r7A==", + "version": "10.4.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-10.4.0.tgz", + "integrity": "sha512-uNUtxIZpGyuaq+5BqGGQHsL4wUlJAXRqOm6g3Y48/CWNGTLONgBibI0lh6lGxjR2HljFYUfszb+mk4WkgMntsA==", "dev": true } } @@ -214,9 +214,9 @@ "dev": true }, "ajv": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.0.tgz", - "integrity": "sha1-6yhAdG6dxIvV4GOjbj/UAMXqtak=", + "version": "5.5.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.1.tgz", + "integrity": "sha1-s4u4h22ehr7plJVqBOch6IskjrI=", "requires": { "co": "4.6.0", "fast-deep-equal": "1.0.0", @@ -525,9 +525,9 @@ } }, "babel-eslint": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.0.2.tgz", - "integrity": "sha512-yyl5U088oE+419+BNLJDKVWkUokuPLQeQt9ZTy9uM9kAzbtQgyYL3JkG425B8jxXA7MwTxnDAtRLMKJNH36qjA==", + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.0.3.tgz", + "integrity": "sha512-7D4iUpylEiKJPGbeSAlNddGcmA41PadgZ6UAb6JVyh003h3d0EbZusYFBR/+nBgqtaVJM2J2zUVa3N0hrpMH6g==", "dev": true, "requires": { "@babel/code-frame": "7.0.0-beta.31", @@ -775,9 +775,9 @@ } }, "babel-plugin-flow-react-proptypes": { - "version": "9.2.0", - "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-9.2.0.tgz", - "integrity": "sha512-gmClrDpTB1H27mh+6/8iliV5BzGic5F9DO7INAd/30sSkg4XZd7LTbv4z06usuUHS8SzXibwotk8ct51IZ5OaQ==", + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-11.0.0.tgz", + "integrity": "sha512-4ym+AUTETUmUmLA39BLHFBTdJRZtSPxQCCEEJPbg/E4UqNMUn+oOLnENZSa44eGbqhpL67LvUotxXT5TAdnNiw==", "dev": true, "requires": { "babel-core": "6.26.0", @@ -2159,12 +2159,6 @@ } } }, - "complex.js": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/complex.js/-/complex.js-2.0.4.tgz", - "integrity": "sha512-Syl95HpxUTS0QjwNxencZsKukgh1zdS9uXeXX2Us0pHaqBR6kiZZi0AkZ9VpZFwHJyVIUVzI4EumjWdXP3fy6w==", - "dev": true - }, "component-bind": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/component-bind/-/component-bind-1.0.0.tgz", @@ -2941,12 +2935,6 @@ "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", "dev": true }, - "decimal.js": { - "version": "7.2.3", - "resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-7.2.3.tgz", - "integrity": "sha512-AoFI37QS0S87Ft0r3Bdz4q9xSpm1Paa9lSeKLXgMPk/u/+QPIM5Gy4DHcZQS1seqPJH4gHLauPGn347z0HbsrA==", - "dev": true - }, "deep-eql": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", @@ -3647,12 +3635,12 @@ } }, "eslint": { - "version": "4.12.1", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.12.1.tgz", - "integrity": "sha512-28hOYej+NZ/R5H1yMvyKa1+bPlu+fnsIAQffK6hxXgvmXnImos2bA5XfCn5dYv2k2mrKj+/U/Z4L5ICWxC7TQw==", + "version": "4.13.1", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.13.1.tgz", + "integrity": "sha512-UCJVV50RtLHYzBp1DZ8CMPtRSg4iVZvjgO9IJHIKyWU/AnJVjtdRikoUPLB29n5pzMB7TnsLQWf0V6VUJfoPfw==", "dev": true, "requires": { - "ajv": "5.5.0", + "ajv": "5.5.1", "babel-code-frame": "6.26.0", "chalk": "2.3.0", "concat-stream": "1.6.0", @@ -3667,7 +3655,7 @@ "file-entry-cache": "2.0.0", "functional-red-black-tree": "1.0.1", "glob": "7.1.2", - "globals": "11.0.1", + "globals": "11.1.0", "ignore": "3.3.7", "imurmurhash": "0.1.4", "inquirer": "3.3.0", @@ -3742,9 +3730,9 @@ "dev": true }, "globals": { - "version": "11.0.1", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.0.1.tgz", - "integrity": "sha1-Eqh7sBDlFUOWrMU14eQ/x1Ow5eg=", + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.1.0.tgz", + "integrity": "sha512-uEuWt9mqTlPDwSqi+sHjD4nWU/1N+q0fiWI9T1mZpD2UENqX20CFD5T/ziLZvztPaBKl7ZylUi1q6Qfm7E2CiQ==", "dev": true }, "js-yaml": { @@ -3870,9 +3858,9 @@ } }, "eslint-plugin-flowtype": { - "version": "2.39.1", - "resolved": "https://registry.npmjs.org/eslint-plugin-flowtype/-/eslint-plugin-flowtype-2.39.1.tgz", - "integrity": "sha512-RiQv+7Z9QDJuzt+NO8sYgkLGT+h+WeCrxP7y8lI7wpU41x3x/2o3PGtHk9ck8QnA9/mlbNcy/hG0eKvmd7npaA==", + "version": "2.40.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-flowtype/-/eslint-plugin-flowtype-2.40.1.tgz", + "integrity": "sha512-0EBDPR3/iguDQin7nb5WMT1ZWYB95eNllY+oiFZjvLa1oqE0BGO6ZSFnMdNE9HEkajB6Cw850PRIBbp+O+EzYQ==", "dev": true, "requires": { "lodash": "4.17.4" @@ -3992,14 +3980,6 @@ "requires": { "acorn": "5.2.1", "acorn-jsx": "3.0.1" - }, - "dependencies": { - "acorn": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.2.1.tgz", - "integrity": "sha512-jG0u7c4Ly+3QkkW18V+NRDN+4bWHdln30NL1ZL2AvFZZmQe/BfopYCtghCKKVBUSetZ4QKcyA0pY6/4Gw8Pv8w==", - "dev": true - } } }, "esprima": { @@ -4418,9 +4398,9 @@ "dev": true }, "flow-bin": { - "version": "0.59.0", - "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.59.0.tgz", - "integrity": "sha512-yJDRffvby5mCTkbwOdXwiGDjeea8Z+BPVuP53/tHqHIZC+KtQD790zopVf7mHk65v+wRn+TZ7tkRSNA9oDmyLg==", + "version": "0.61.0", + "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.61.0.tgz", + "integrity": "sha512-w6SGi5CDfKLNGzYssRhW6N37qKclDXijsxDQ5M8c3WbivRYta0Horv22bwakegfKBVDnyeS0lRW3OqBC74eq2g==", "dev": true }, "for-in": { @@ -4459,12 +4439,6 @@ "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=", "dev": true }, - "fraction.js": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-4.0.2.tgz", - "integrity": "sha512-OswcigOSil3vYXgrPSx4NCaSyPikXqVNYN/4CyhS0ucVOJ4GVYr6KQQLLcAudvS/4bBOzxqJ3XIsFaaMjl98ZQ==", - "dev": true - }, "fresh": { "version": "0.5.2", "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", @@ -5518,9 +5492,9 @@ "dev": true }, "gonzales-pe": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/gonzales-pe/-/gonzales-pe-4.2.2.tgz", - "integrity": "sha512-jbQFnd6CD3iEuGtSKVhsh37tQIkkx+/eil3tufyYOHMouG89uqtkWGP03P4vxY+XGeJnCi3ewIY+BnBogyC61Q==", + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/gonzales-pe/-/gonzales-pe-4.2.3.tgz", + "integrity": "sha512-Kjhohco0esHQnOiqqdJeNz/5fyPkOMD/d6XVjwTAoPGUFh0mCollPUTUTa2OZy4dYNAqlPIQdTiNzJTWdd9Htw==", "dev": true, "requires": { "minimist": "1.1.3" @@ -6517,12 +6491,6 @@ "semver": "5.4.1" } }, - "javascript-natural-sort": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/javascript-natural-sort/-/javascript-natural-sort-0.7.1.tgz", - "integrity": "sha1-+eIwPUUH9tdDVac2ZNFED7Wg71k=", - "dev": true - }, "js-base64": { "version": "2.3.2", "resolved": "https://registry.npmjs.org/js-base64/-/js-base64-2.3.2.tgz", @@ -6729,9 +6697,9 @@ } }, "karma-firefox-launcher": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/karma-firefox-launcher/-/karma-firefox-launcher-1.0.1.tgz", - "integrity": "sha1-zlj0fCATqIFW1VpdYTN8CZz1u1E=", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/karma-firefox-launcher/-/karma-firefox-launcher-1.1.0.tgz", + "integrity": "sha512-LbZ5/XlIXLeQ3cqnCbYLn+rOVhuMIK9aZwlP6eOLGzWdo1UVp7t6CN3DP4SafiRLjexKwHeKHDm0c38Mtd3VxA==", "dev": true }, "karma-mocha": { @@ -6818,9 +6786,9 @@ } }, "karma-webpack": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/karma-webpack/-/karma-webpack-2.0.6.tgz", - "integrity": "sha512-dcKvtiW00caWrceCKwIvlKwHQu8zI+e3zWZYDLk7kr7nl1lYSp8uP+8fQoBvRCnZiPUGuwU5Psm20NbEIn7KlA==", + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/karma-webpack/-/karma-webpack-2.0.7.tgz", + "integrity": "sha512-cE7tZbuxjPXzRXyp/GsDla2p0SRNqih5Yj0ptXA7xYrUChYr1QsMUw7D3rTmZgeaXOUnBr4nOfqqwOdfnWWCfA==", "dev": true, "requires": { "async": "0.9.2", @@ -7111,9 +7079,9 @@ "dev": true }, "lolex": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/lolex/-/lolex-2.3.0.tgz", - "integrity": "sha512-rPO6R1t8PjYL6xbsFUg7aByKkWAql907na6powPBORVs4DCm8aMBUkL4+6CXO0gEIV8vtu3mWV0FB8ZaCYPBmA==", + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/lolex/-/lolex-2.3.1.tgz", + "integrity": "sha512-mQuW55GhduF3ppo+ZRUTz1PRjEh1hS5BbqU7d8D0ez2OKxHDod7StPPeAVKisZR5aLkHZjdGWSL42LSONUJsZw==", "dev": true }, "longest": { @@ -7201,21 +7169,6 @@ "integrity": "sha1-3oGf282E3M2PrlnGrreWFbnSZqw=", "dev": true }, - "mathjs": { - "version": "3.16.4", - "resolved": "https://registry.npmjs.org/mathjs/-/mathjs-3.16.4.tgz", - "integrity": "sha512-y/JI7xGE30KLVJwireFEj1w364D6KcGEMA7zja62nUbwHTP9hU6lHKHOFgvDsVRXLhnNwPp92dwZDeD5xnYyQw==", - "dev": true, - "requires": { - "complex.js": "2.0.4", - "decimal.js": "7.2.3", - "fraction.js": "4.0.2", - "javascript-natural-sort": "0.7.1", - "seed-random": "2.2.0", - "tiny-emitter": "2.0.0", - "typed-function": "0.10.5" - } - }, "mathml-tag-names": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/mathml-tag-names/-/mathml-tag-names-2.0.1.tgz", @@ -9963,43 +9916,13 @@ } }, "postcss-sass": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/postcss-sass/-/postcss-sass-0.1.0.tgz", - "integrity": "sha1-DSplW10kHsj0Gbs9o43lyhF0bds=", + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/postcss-sass/-/postcss-sass-0.2.0.tgz", + "integrity": "sha512-cUmYzkP747fPCQE6d+CH2l1L4VSyIlAzZsok3HPjb5Gzsq3jE+VjpAdGlPsnQ310WKWI42sw+ar0UNN59/f3hg==", "dev": true, "requires": { - "gonzales-pe": "4.2.2", - "mathjs": "3.16.4", - "postcss": "5.2.17" - }, - "dependencies": { - "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "dev": true - }, - "postcss": { - "version": "5.2.17", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-5.2.17.tgz", - "integrity": "sha1-z09Ze4ZNZcikkrLqvp1wbIecOIs=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "js-base64": "2.3.2", - "source-map": "0.5.7", - "supports-color": "3.2.3" - } - }, - "supports-color": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.2.3.tgz", - "integrity": "sha1-ZawFBLOVQXHYpklGsq48u4pfVPY=", - "dev": true, - "requires": { - "has-flag": "1.0.0" - } - } + "gonzales-pe": "4.2.3", + "postcss": "6.0.14" } }, "postcss-scss": { @@ -10059,22 +9982,42 @@ } }, "postcss-smart-import": { - "version": "0.7.5", - "resolved": "https://registry.npmjs.org/postcss-smart-import/-/postcss-smart-import-0.7.5.tgz", - "integrity": "sha512-Bs9wAFxH5irGpenBg9a65jTcydZLh7VBTX6NYwMXvVXO6y9CQ83kRmfpQDs5lHhl6IODeIeQfJep5HBMd9UVCQ==", + "version": "0.7.6", + "resolved": "https://registry.npmjs.org/postcss-smart-import/-/postcss-smart-import-0.7.6.tgz", + "integrity": "sha512-9OpXaQ1uMMHWafUh0RWIpAKa3xxUDC2yyxicUPpGffH33nzbZG4/z+nk5Ocw5gGZ+3qkXV91iDV23Cmxf2Jhew==", "dev": true, "requires": { "babel-runtime": "6.26.0", "lodash": "4.17.4", "object-assign": "4.1.1", "postcss": "6.0.14", - "postcss-sass": "0.1.0", + "postcss-sass": "0.2.0", "postcss-scss": "1.0.2", "postcss-value-parser": "3.3.0", "promise-each": "2.2.0", "read-cache": "1.0.0", - "resolve": "1.4.0", - "sugarss": "1.0.0" + "resolve": "1.5.0", + "sugarss": "1.0.1" + }, + "dependencies": { + "resolve": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz", + "integrity": "sha512-hgoSGrc3pjzAPHNBg+KnFcK2HwlHTs/YrAGUr6qgTVUZmXv1UEXXl0bZNBKMA9fud6lRYFdPGz0xXxycPzmmiw==", + "dev": true, + "requires": { + "path-parse": "1.0.5" + } + }, + "sugarss": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/sugarss/-/sugarss-1.0.1.tgz", + "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", + "dev": true, + "requires": { + "postcss": "6.0.14" + } + } } }, "postcss-svgo": { @@ -10528,6 +10471,15 @@ } } }, + "react-konva": { + "version": "1.6.4", + "resolved": "https://registry.npmjs.org/react-konva/-/react-konva-1.6.4.tgz", + "integrity": "sha512-4K5VE2TsGfUmIXbPbZu2uHJYIysZxmx76/pqcAaWT9PiWrJJj2mfDPBeQGX8jDAL1nr9yg6nOThs1Frt4MYXaA==", + "requires": { + "fbjs": "0.8.16", + "react-reconciler": "0.5.0" + } + }, "react-popper": { "version": "0.7.4", "resolved": "https://registry.npmjs.org/react-popper/-/react-popper-0.7.4.tgz", @@ -10546,6 +10498,17 @@ "lodash": "4.17.4" } }, + "react-reconciler": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/react-reconciler/-/react-reconciler-0.5.0.tgz", + "integrity": "sha512-AXRcMbbOYU+Wq7Zb3CooX76b9+TNg6b518XfT+muVs0lPIvN9bvm1nqT5DuDwLcdto2LlcUSB+SwmmAbWOQEmA==", + "requires": { + "fbjs": "0.8.16", + "loose-envify": "1.3.1", + "object-assign": "4.1.1", + "prop-types": "15.6.0" + } + }, "react-redux": { "version": "5.0.6", "resolved": "https://registry.npmjs.org/react-redux/-/react-redux-5.0.6.tgz", @@ -11267,15 +11230,9 @@ "integrity": "sha1-9YdyIs4+kx7a4DnxfrNxbnE3+M8=", "dev": true, "requires": { - "ajv": "5.5.0" + "ajv": "5.5.1" } }, - "seed-random": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/seed-random/-/seed-random-2.2.0.tgz", - "integrity": "sha1-KpsZ4lCoFwmSMaW5mk2vgLf77VQ=", - "dev": true - }, "select-hose": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/select-hose/-/select-hose-2.0.0.tgz", @@ -11435,18 +11392,18 @@ } }, "sinon": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/sinon/-/sinon-4.1.2.tgz", - "integrity": "sha512-5uLBZPdCWl59Lpbf45ygKj7Z0LVol+ftBe7RDIXOQV/sF58pcFmbK8raA7bt6eljNuGnvBP+/ZxlicVn0emDjA==", + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/sinon/-/sinon-4.1.3.tgz", + "integrity": "sha512-c7u0ZuvBRX1eXuB4jN3BRCAOGiUTlM8SE3TxbJHrNiHUKL7wonujMOB6Fi1gQc00U91IscFORQHDga/eccqpbw==", "dev": true, "requires": { "diff": "3.4.0", "formatio": "1.2.0", "lodash.get": "4.4.2", - "lolex": "2.3.0", + "lolex": "2.3.1", "nise": "1.2.0", "supports-color": "4.5.0", - "type-detect": "4.0.3" + "type-detect": "4.0.5" }, "dependencies": { "supports-color": { @@ -11457,6 +11414,12 @@ "requires": { "has-flag": "2.0.0" } + }, + "type-detect": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.5.tgz", + "integrity": "sha512-N9IvkQslUGYGC24RkJk1ba99foK6TkwC2FHAEBlQFBP0RxQZS8ZpJuAZcwiY/w9ZJHFQb1aOXBI60OdxhTrwEQ==", + "dev": true } } }, @@ -12197,7 +12160,7 @@ "integrity": "sha512-UUkEAPdSGxtRpiV9ozJ5cMTtYiqz7Ni1OGqLXRCynrvzdtR1p+cfOWe2RJLwvUG8hNanaSRjecIqwOjqeatDsA==", "dev": true, "requires": { - "ajv": "5.5.0", + "ajv": "5.5.1", "ajv-keywords": "2.1.0", "chalk": "2.3.0", "lodash": "4.17.4", @@ -12294,12 +12257,6 @@ "setimmediate": "1.0.5" } }, - "tiny-emitter": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/tiny-emitter/-/tiny-emitter-2.0.0.tgz", - "integrity": "sha1-utMnrbGAS0KiMa+nQVMr2ITNCa0=", - "dev": true - }, "tmp": { "version": "0.0.33", "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", @@ -12400,12 +12357,6 @@ "mime-types": "2.1.17" } }, - "typed-function": { - "version": "0.10.5", - "resolved": "https://registry.npmjs.org/typed-function/-/typed-function-0.10.5.tgz", - "integrity": "sha1-Lg8Yq9BlIZ+raUpEamXG0ZgYMsA=", - "dev": true - }, "typedarray": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", @@ -12802,14 +12753,14 @@ } }, "webpack": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/webpack/-/webpack-3.9.1.tgz", - "integrity": "sha512-jONJ0l8nqgiQVkqs15O9TFWLozbFkCgVodVrBXBK/PIBFeGkaOGo30Ov57iQqYRwAWNDM5vyLPZYmAIpPa5QSw==", + "version": "3.10.0", + "resolved": "https://registry.npmjs.org/webpack/-/webpack-3.10.0.tgz", + "integrity": "sha512-fxxKXoicjdXNUMY7LIdY89tkJJJ0m1Oo8PQutZ5rLgWbV5QVKI15Cn7+/IHnRTd3vfKfiwBx6SBqlorAuNA8LA==", "dev": true, "requires": { "acorn": "5.2.1", "acorn-dynamic-import": "2.0.2", - "ajv": "5.5.0", + "ajv": "5.5.1", "ajv-keywords": "2.1.0", "async": "2.6.0", "enhanced-resolve": "3.4.1", @@ -12973,9 +12924,9 @@ } }, "webpack-dev-server": { - "version": "2.9.5", - "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-2.9.5.tgz", - "integrity": "sha512-o0lS6enIxyOPiRJTh8vcgK5TsGNTn7lH1q/pNniAgs46mCE8sQYeqv7Y/oAIh/+u4kiBsFizLJo5EWC+ezz6FQ==", + "version": "2.9.7", + "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-2.9.7.tgz", + "integrity": "sha512-Pu7uoQFgQj5RE5wmlfkpYSzihMKxulwEuO2xCsaMnAnyRSApwoVi3B8WCm9XbigyWTHaIMzYGkB90Vr6leAeTQ==", "dev": true, "requires": { "ansi-html": "0.0.7", diff --git a/package.json b/package.json index da22a8b..c7d4008 100644 --- a/package.json +++ b/package.json @@ -23,10 +23,10 @@ "license": "MIT", "devDependencies": { "babel-core": "^6.26.0", - "babel-eslint": "^8.0.2", + "babel-eslint": "^8.0.3", "babel-loader": "^7.1.2", "babel-plugin-dynamic-import-webpack": "^1.0.2", - "babel-plugin-flow-react-proptypes": "^9.2.0", + "babel-plugin-flow-react-proptypes": "^11.0.0", "babel-plugin-istanbul": "^4.1.5", "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-syntax-object-rest-spread": "^6.13.0", @@ -40,51 +40,52 @@ "css-loader": "^0.28.7", "enzyme": "^3.2.0", "enzyme-adapter-react-16": "^1.1.0", - "eslint": "^4.12.1", + "eslint": "^4.13.1", "eslint-plugin-compat": "^2.1.0", - "eslint-plugin-flowtype": "^2.39.1", + "eslint-plugin-flowtype": "^2.40.1", "eslint-plugin-import": "^2.8.0", "eslint-plugin-react": "^7.5.1", - "flow-bin": "^0.59.0", + "flow-bin": "^0.61.0", "html-webpack-harddisk-plugin": "^0.1.0", "html-webpack-plugin": "^2.30.1", "husky": "^0.14.3", "karma": "^1.7.1", "karma-chrome-launcher": "^2.2.0", "karma-coverage": "^1.1.1", - "karma-firefox-launcher": "^1.0.1", + "karma-firefox-launcher": "^1.1.0", "karma-mocha": "^1.3.0", "karma-mocha-reporter": "^2.2.5", "karma-sourcemap-loader": "^0.3.7", - "karma-webpack": "^2.0.6", + "karma-webpack": "^2.0.7", "mocha": "^4.0.1", "postcss": "^6.0.14", "postcss-cli": "^4.1.1", "postcss-cssnext": "^3.0.2", "postcss-loader": "^2.0.9", - "postcss-smart-import": "^0.7.5", + "postcss-smart-import": "^0.7.6", "react-hot-loader": "^3.1.3", "react-test-renderer": "^16.2.0", "redux-devtools": "^3.4.1", "rimraf": "^2.6.2", - "sinon": "^4.1.2", + "sinon": "^4.1.3", "style-loader": "^0.19.0", "stylelint": "^8.3.1", "stylelint-config-standard": "^18.0.0", "svg-inline-loader": "^0.8.0", - "webpack": "^3.9.1", - "webpack-dev-server": "^2.9.5", + "webpack": "^3.10.0", + "webpack-dev-server": "^2.9.7", "webpack-visualizer-plugin": "^0.1.11", "worker-loader": "^1.1.0" }, "dependencies": { - "ajv": "^5.5.0", + "ajv": "^5.5.1", "bootstrap": "^4.0.0-beta.2", "classnames": "^2.2.5", "d3": "^4.12.0", "prop-types": "^15.6.0", "react": "^16.2.0", "react-dom": "^16.2.0", + "react-konva": "^1.6.4", "react-popper": "^0.7.4", "react-redux": "^5.0.6", "react-router-dom": "^4.2.2", -- GitLab From 62ad9445bc6e1eb5bc664d2db2ca0efdcbeedc06 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 19 Dec 2017 10:40:11 +0100 Subject: [PATCH 03/51] update deps --- package-lock.json | 298 ++++++++++++++++++++++++++++++++++++---------- package.json | 12 +- 2 files changed, 243 insertions(+), 67 deletions(-) diff --git a/package-lock.json b/package-lock.json index e46d579..64fc506 100644 --- a/package-lock.json +++ b/package-lock.json @@ -214,9 +214,9 @@ "dev": true }, "ajv": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.1.tgz", - "integrity": "sha1-s4u4h22ehr7plJVqBOch6IskjrI=", + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", "requires": { "co": "4.6.0", "fast-deep-equal": "1.0.0", @@ -775,9 +775,9 @@ } }, "babel-plugin-flow-react-proptypes": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-11.0.0.tgz", - "integrity": "sha512-4ym+AUTETUmUmLA39BLHFBTdJRZtSPxQCCEEJPbg/E4UqNMUn+oOLnENZSa44eGbqhpL67LvUotxXT5TAdnNiw==", + "version": "12.1.0", + "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-12.1.0.tgz", + "integrity": "sha512-6eoqK9NcSQvmEmtiOiAG0QhC5/R8rROvLE75/oHXHQ2S02GqKWBimbj0CzuRlODFSAq9r1hNS+DtjtXOEHulPQ==", "dev": true, "requires": { "babel-core": "6.26.0", @@ -2935,6 +2935,16 @@ "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", "dev": true }, + "decamelize-keys": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.0.tgz", + "integrity": "sha1-0XGoeTMlKAfrPLYdwcFEXQeN8tk=", + "dev": true, + "requires": { + "decamelize": "1.2.0", + "map-obj": "1.0.1" + } + }, "deep-eql": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", @@ -3434,23 +3444,38 @@ } }, "enzyme-adapter-react-16": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/enzyme-adapter-react-16/-/enzyme-adapter-react-16-1.1.0.tgz", - "integrity": "sha512-OlZJn5PJUJ91EOQQRuISZpXgPlqT9fYR2yBZQPu9UYok+wS19Rn4teXywF34LMcyw2AzE1s0ZRDtcI952/vQHg==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/enzyme-adapter-react-16/-/enzyme-adapter-react-16-1.1.1.tgz", + "integrity": "sha512-kC8pAtU2Jk3OJ0EG8Y2813dg9Ol0TXi7UNxHzHiWs30Jo/hj7alc//G1YpKUsPP1oKl9X+Lkx+WlGJpPYA+nvw==", "dev": true, "requires": { - "enzyme-adapter-utils": "1.1.1", + "enzyme-adapter-utils": "1.3.0", "lodash": "4.17.4", "object.assign": "4.0.4", "object.values": "1.0.4", "prop-types": "15.6.0", + "react-reconciler": "0.7.0", "react-test-renderer": "16.2.0" + }, + "dependencies": { + "react-reconciler": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/react-reconciler/-/react-reconciler-0.7.0.tgz", + "integrity": "sha512-50JwZ3yNyMS8fchN+jjWEJOH3Oze7UmhxeoJLn2j6f3NjpfCRbcmih83XTWmzqtar/ivd5f7tvQhvvhism2fgg==", + "dev": true, + "requires": { + "fbjs": "0.8.16", + "loose-envify": "1.3.1", + "object-assign": "4.1.1", + "prop-types": "15.6.0" + } + } } }, "enzyme-adapter-utils": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/enzyme-adapter-utils/-/enzyme-adapter-utils-1.1.1.tgz", - "integrity": "sha512-XU41nEiTl7O2JJvRA7JoCMhkDYRW9mQAgiy67Yz9BqTiRP/ldwuJYX8Gkom2LlihKIb9wy96IDuayR3RQspSNg==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/enzyme-adapter-utils/-/enzyme-adapter-utils-1.3.0.tgz", + "integrity": "sha512-vVXSt6uDv230DIv+ebCG66T1Pm36Kv+m74L1TrF4kaE7e1V7Q/LcxO0QRkajk5cA6R3uu9wJf5h13wOTezTbjA==", "dev": true, "requires": { "lodash": "4.17.4", @@ -3640,7 +3665,7 @@ "integrity": "sha512-UCJVV50RtLHYzBp1DZ8CMPtRSg4iVZvjgO9IJHIKyWU/AnJVjtdRikoUPLB29n5pzMB7TnsLQWf0V6VUJfoPfw==", "dev": true, "requires": { - "ajv": "5.5.1", + "ajv": "5.5.2", "babel-code-frame": "6.26.0", "chalk": "2.3.0", "concat-stream": "1.6.0", @@ -6524,6 +6549,12 @@ "integrity": "sha512-QLPs8Dj7lnf3e3QYS1zkCo+4ZwqOiF9d/nZnYozTISxXWCfNs9yuky5rJw4/W34s7POaNlbZmQGaB5NiXCbP4w==", "dev": true }, + "json-parse-better-errors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.1.tgz", + "integrity": "sha512-xyQpxeWWMKyJps9CuGJYeng6ssI5bpqS9ltQpdVQ90t4ql6NdnxFKh95JcRt2cun/DjMVNrdjniLPuMA69xmCw==", + "dev": true + }, "json-schema-traverse": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", @@ -6786,9 +6817,9 @@ } }, "karma-webpack": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/karma-webpack/-/karma-webpack-2.0.7.tgz", - "integrity": "sha512-cE7tZbuxjPXzRXyp/GsDla2p0SRNqih5Yj0ptXA7xYrUChYr1QsMUw7D3rTmZgeaXOUnBr4nOfqqwOdfnWWCfA==", + "version": "2.0.9", + "resolved": "https://registry.npmjs.org/karma-webpack/-/karma-webpack-2.0.9.tgz", + "integrity": "sha512-F1j3IG/XhiMzcunAXbWXH95uizjzr3WdTzmVWlta8xqxcCtAu9FByCb4sccIMxaVFAefpgnUW9KlCo0oLvIX6A==", "dev": true, "requires": { "async": "0.9.2", @@ -6840,9 +6871,9 @@ } }, "known-css-properties": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/known-css-properties/-/known-css-properties-0.4.1.tgz", - "integrity": "sha512-n+ThoCKhyMFKkMfksdLMP5ndp+VzwDRzQdH6JlmZ2GTpUenYB2EeEKjOue2SErAAG/MmBSUISpwvawDhydWQdQ==", + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/known-css-properties/-/known-css-properties-0.5.0.tgz", + "integrity": "sha512-LOS0CoS8zcZnB1EjLw4LLqDXw8nvt3AGH5dXLQP3D9O1nLLA+9GC5GnPl5mmF+JiQAtSX4VyZC7KvEtcA4kUtA==", "dev": true }, "lazy-cache": { @@ -7204,7 +7235,7 @@ "dev": true, "requires": { "unist-util-modify-children": "1.1.1", - "unist-util-visit": "1.2.0" + "unist-util-visit": "1.3.0" } }, "media-typer": { @@ -7364,6 +7395,16 @@ "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", "dev": true }, + "minimist-options": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/minimist-options/-/minimist-options-3.0.2.tgz", + "integrity": "sha512-FyBrT/d0d4+uiZRbqznPXqw3IpZZG3gl3wKWiX784FycUKVwBt0uLBFkQrtE4tZOrgo78nZp2jnKz3L65T5LdQ==", + "dev": true, + "requires": { + "arrify": "1.0.1", + "is-plain-obj": "1.1.0" + } + }, "mkdirp": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", @@ -9122,9 +9163,9 @@ } }, "postcss-html": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/postcss-html/-/postcss-html-0.11.0.tgz", - "integrity": "sha512-ruCTbRZWY+qOV4FNYNm6E0ucIbCkkuYHIqQ4W3iSVIc1aUVBTKMG0iUo2nPUAG2lhFaTmfBaZ17017osZ18ddA==", + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/postcss-html/-/postcss-html-0.12.0.tgz", + "integrity": "sha512-KxKUpj7AY7nlCbLcTOYxdfJnGE7QFAfU2n95ADj1Q90RM/pOLdz8k3n4avOyRFs7MDQHcRzJQWM1dehCwJxisQ==", "dev": true, "requires": { "htmlparser2": "3.9.2", @@ -10319,6 +10360,12 @@ "integrity": "sha1-DPf4T5Rj/wrlHExLFC2VvjdyTZw=", "dev": true }, + "quick-lru": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-1.1.0.tgz", + "integrity": "sha1-Q2CxfGETatOAeDl/8RQW4Ybc+7g=", + "dev": true + }, "raf": { "version": "3.4.0", "resolved": "https://registry.npmjs.org/raf/-/raf-3.4.0.tgz", @@ -11230,7 +11277,7 @@ "integrity": "sha1-9YdyIs4+kx7a4DnxfrNxbnE3+M8=", "dev": true, "requires": { - "ajv": "5.5.1" + "ajv": "5.5.2" } }, "select-hose": { @@ -11850,9 +11897,9 @@ "dev": true }, "style-loader": { - "version": "0.19.0", - "resolved": "https://registry.npmjs.org/style-loader/-/style-loader-0.19.0.tgz", - "integrity": "sha512-9mx9sC9nX1dgP96MZOODpGC6l1RzQBITI2D5WJhu+wnbrSYVKLGuy14XJSLVQih/0GFrPpjelt+s//VcZQ2Evw==", + "version": "0.19.1", + "resolved": "https://registry.npmjs.org/style-loader/-/style-loader-0.19.1.tgz", + "integrity": "sha512-IRE+ijgojrygQi3rsqT0U4dd+UcPCqcVvauZpCnQrGAlEe+FUIyrK93bUDScamesjP08JlQNsFJU+KmPedP5Og==", "dev": true, "requires": { "loader-utils": "1.1.0", @@ -11866,12 +11913,12 @@ "dev": true }, "stylelint": { - "version": "8.3.1", - "resolved": "https://registry.npmjs.org/stylelint/-/stylelint-8.3.1.tgz", - "integrity": "sha512-v5K6tv+Ky3SoJfNqGOvgzRDLqZV133CZ7Wtu3y5aAGjQHVi+6dixFLgI82VrJZJdC4HwZplafJcRP+4r7EUt5g==", + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/stylelint/-/stylelint-8.4.0.tgz", + "integrity": "sha512-56hPH5mTFnk8LzlEuTWq0epa34fHuS54UFYQidBOFt563RJBNi1nz1F2HK2MoT1X1waq47milvRsRahFCCJs/Q==", "dev": true, "requires": { - "autoprefixer": "7.1.6", + "autoprefixer": "7.2.3", "balanced-match": "1.0.0", "chalk": "2.3.0", "cosmiconfig": "3.1.0", @@ -11884,21 +11931,22 @@ "html-tags": "2.0.0", "ignore": "3.3.7", "imurmurhash": "0.1.4", - "known-css-properties": "0.4.1", + "known-css-properties": "0.5.0", "lodash": "4.17.4", "log-symbols": "2.1.0", "mathml-tag-names": "2.0.1", - "meow": "3.7.0", + "meow": "4.0.0", "micromatch": "2.3.11", "normalize-selector": "0.2.0", "pify": "3.0.0", "postcss": "6.0.14", - "postcss-html": "0.11.0", + "postcss-html": "0.12.0", "postcss-less": "1.1.3", "postcss-media-query-parser": "0.2.3", "postcss-reporter": "5.0.0", "postcss-resolve-nested-selector": "0.1.1", "postcss-safe-parser": "3.0.1", + "postcss-sass": "0.2.0", "postcss-scss": "1.0.2", "postcss-selector-parser": "3.1.1", "postcss-value-parser": "3.3.0", @@ -11906,7 +11954,7 @@ "specificity": "0.3.2", "string-width": "2.1.1", "style-search": "0.1.0", - "sugarss": "1.0.0", + "sugarss": "1.0.1", "svg-tags": "1.0.0", "table": "4.0.2" }, @@ -11921,13 +11969,13 @@ } }, "autoprefixer": { - "version": "7.1.6", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-7.1.6.tgz", - "integrity": "sha512-C9yv/UF3X+eJTi/zvfxuyfxmLibYrntpF3qoJYrMeQwgUJOZrZvpJiMG2FMQ3qnhWtF/be4pYONBBw95ZGe3vA==", + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-7.2.3.tgz", + "integrity": "sha512-dqzVGiz3v934+s3YZA6nk7tAs9xuTz5wMJbX1M+L4cY/MTNkOUqP61c1GWkEVlUL/PEy1pKRSCFuoRZrXYx9qA==", "dev": true, "requires": { - "browserslist": "2.9.1", - "caniuse-lite": "1.0.30000775", + "browserslist": "2.10.0", + "caniuse-lite": "1.0.30000783", "normalize-range": "0.1.2", "num2fraction": "1.2.2", "postcss": "6.0.14", @@ -11935,19 +11983,36 @@ } }, "browserslist": { - "version": "2.9.1", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-2.9.1.tgz", - "integrity": "sha512-3n3nPdbUqn3nWmsy4PeSQthz2ja1ndpoXta+dwFFNhveGjMg6FXpWYe12vsTpNoXJbzx3j7GZXdtoVIdvh3JbA==", + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-2.10.0.tgz", + "integrity": "sha512-WyvzSLsuAVPOjbljXnyeWl14Ae+ukAT8MUuagKVzIDvwBxl4UAwD1xqtyQs2eWYPGUKMeC3Ol62goqYuKqTTcw==", "dev": true, "requires": { - "caniuse-lite": "1.0.30000775", - "electron-to-chromium": "1.3.27" + "caniuse-lite": "1.0.30000783", + "electron-to-chromium": "1.3.29" + } + }, + "camelcase": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", + "dev": true + }, + "camelcase-keys": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/camelcase-keys/-/camelcase-keys-4.2.0.tgz", + "integrity": "sha1-oqpfsa9oh1glnDLBQUJteJI7m3c=", + "dev": true, + "requires": { + "camelcase": "4.1.0", + "map-obj": "2.0.0", + "quick-lru": "1.1.0" } }, "caniuse-lite": { - "version": "1.0.30000775", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30000775.tgz", - "integrity": "sha1-dNJ/7dxH88hM+8sTDDCSo168LeI=", + "version": "1.0.30000783", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30000783.tgz", + "integrity": "sha1-m1SZ+xtQPSNF0SqmuGEoUvQnb/0=", "dev": true }, "chalk": { @@ -11983,9 +12048,9 @@ } }, "electron-to-chromium": { - "version": "1.3.27", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.27.tgz", - "integrity": "sha1-eOy4o5kGYYe7N07t412ccFZagD0=", + "version": "1.3.29", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.29.tgz", + "integrity": "sha1-elgja5VGjD52YAkTSFItZddzazY=", "dev": true }, "esprima": { @@ -12014,6 +12079,12 @@ "slash": "1.0.0" } }, + "indent-string": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-3.2.0.tgz", + "integrity": "sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok=", + "dev": true + }, "js-yaml": { "version": "3.10.0", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.10.0.tgz", @@ -12024,6 +12095,59 @@ "esprima": "4.0.0" } }, + "load-json-file": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", + "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", + "dev": true, + "requires": { + "graceful-fs": "4.1.11", + "parse-json": "4.0.0", + "pify": "3.0.0", + "strip-bom": "3.0.0" + }, + "dependencies": { + "parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", + "dev": true, + "requires": { + "error-ex": "1.3.1", + "json-parse-better-errors": "1.0.1" + } + } + } + }, + "map-obj": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-2.0.0.tgz", + "integrity": "sha1-plzSkIepJZi4eRJXpSPgISIqwfk=", + "dev": true + }, + "meow": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/meow/-/meow-4.0.0.tgz", + "integrity": "sha512-Me/kel335m6vMKmEmA6c87Z6DUFW3JqkINRnxkbC+A/PUm0D5Fl2dEBQrPKnqCL9Te/CIa1MUt/0InMJhuC/sw==", + "dev": true, + "requires": { + "camelcase-keys": "4.2.0", + "decamelize-keys": "1.1.0", + "loud-rejection": "1.6.0", + "minimist": "1.2.0", + "minimist-options": "3.0.2", + "normalize-package-data": "2.4.0", + "read-pkg-up": "3.0.0", + "redent": "2.0.0", + "trim-newlines": "2.0.0" + } + }, + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true + }, "parse-json": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-3.0.0.tgz", @@ -12033,6 +12157,15 @@ "error-ex": "1.3.1" } }, + "path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "requires": { + "pify": "3.0.0" + } + }, "pify": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", @@ -12050,6 +12183,37 @@ "uniq": "1.0.1" } }, + "read-pkg": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", + "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", + "dev": true, + "requires": { + "load-json-file": "4.0.0", + "normalize-package-data": "2.4.0", + "path-type": "3.0.0" + } + }, + "read-pkg-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", + "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", + "dev": true, + "requires": { + "find-up": "2.1.0", + "read-pkg": "3.0.0" + } + }, + "redent": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/redent/-/redent-2.0.0.tgz", + "integrity": "sha1-wbIAe0LVfrE4kHmzyDM2OdXhzKo=", + "dev": true, + "requires": { + "indent-string": "3.2.0", + "strip-indent": "2.0.0" + } + }, "require-from-string": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.1.tgz", @@ -12062,6 +12226,12 @@ "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", "dev": true }, + "strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", + "dev": true + }, "supports-color": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", @@ -12070,6 +12240,12 @@ "requires": { "has-flag": "2.0.0" } + }, + "trim-newlines": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/trim-newlines/-/trim-newlines-2.0.0.tgz", + "integrity": "sha1-tAPQuRvlDDMd/EuC7s6yLD3hbSA=", + "dev": true } } }, @@ -12089,9 +12265,9 @@ } }, "sugarss": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/sugarss/-/sugarss-1.0.0.tgz", - "integrity": "sha1-ZeUbOVhDL7cNVFGmi7M+MtDPHvc=", + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/sugarss/-/sugarss-1.0.1.tgz", + "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", "dev": true, "requires": { "postcss": "6.0.14" @@ -12160,7 +12336,7 @@ "integrity": "sha512-UUkEAPdSGxtRpiV9ozJ5cMTtYiqz7Ni1OGqLXRCynrvzdtR1p+cfOWe2RJLwvUG8hNanaSRjecIqwOjqeatDsA==", "dev": true, "requires": { - "ajv": "5.5.1", + "ajv": "5.5.2", "ajv-keywords": "2.1.0", "chalk": "2.3.0", "lodash": "4.17.4", @@ -12497,7 +12673,7 @@ "integrity": "sha1-WoXBVV/BugwQG4ZwfRXlD6TIcbs=", "dev": true, "requires": { - "unist-util-visit": "1.2.0" + "unist-util-visit": "1.3.0" } }, "unist-util-stringify-position": { @@ -12507,9 +12683,9 @@ "dev": true }, "unist-util-visit": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-1.2.0.tgz", - "integrity": "sha512-lI+jyPlDztHZ2CJhUchcRMQ7MNc0yASgYFxwRTxs0EZ+9HbYFBLVGDJ2FchTBy+pra0O1LVEn0Wkgf19mDVDzw==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-1.3.0.tgz", + "integrity": "sha512-9ntYcxPFtl44gnwXrQKZ5bMqXMY0ZHzUpqMFiU4zcc8mmf/jzYm8GhYgezuUlX4cJIM1zIDYaO6fG/fI+L6iiQ==", "dev": true, "requires": { "unist-util-is": "2.1.1" @@ -12760,7 +12936,7 @@ "requires": { "acorn": "5.2.1", "acorn-dynamic-import": "2.0.2", - "ajv": "5.5.1", + "ajv": "5.5.2", "ajv-keywords": "2.1.0", "async": "2.6.0", "enhanced-resolve": "3.4.1", diff --git a/package.json b/package.json index c7d4008..422d8e6 100644 --- a/package.json +++ b/package.json @@ -26,7 +26,7 @@ "babel-eslint": "^8.0.3", "babel-loader": "^7.1.2", "babel-plugin-dynamic-import-webpack": "^1.0.2", - "babel-plugin-flow-react-proptypes": "^11.0.0", + "babel-plugin-flow-react-proptypes": "^12.1.0", "babel-plugin-istanbul": "^4.1.5", "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-syntax-object-rest-spread": "^6.13.0", @@ -39,7 +39,7 @@ "cross-env": "^5.1.1", "css-loader": "^0.28.7", "enzyme": "^3.2.0", - "enzyme-adapter-react-16": "^1.1.0", + "enzyme-adapter-react-16": "^1.1.1", "eslint": "^4.13.1", "eslint-plugin-compat": "^2.1.0", "eslint-plugin-flowtype": "^2.40.1", @@ -56,7 +56,7 @@ "karma-mocha": "^1.3.0", "karma-mocha-reporter": "^2.2.5", "karma-sourcemap-loader": "^0.3.7", - "karma-webpack": "^2.0.7", + "karma-webpack": "^2.0.9", "mocha": "^4.0.1", "postcss": "^6.0.14", "postcss-cli": "^4.1.1", @@ -68,8 +68,8 @@ "redux-devtools": "^3.4.1", "rimraf": "^2.6.2", "sinon": "^4.1.3", - "style-loader": "^0.19.0", - "stylelint": "^8.3.1", + "style-loader": "^0.19.1", + "stylelint": "^8.4.0", "stylelint-config-standard": "^18.0.0", "svg-inline-loader": "^0.8.0", "webpack": "^3.10.0", @@ -78,7 +78,7 @@ "worker-loader": "^1.1.0" }, "dependencies": { - "ajv": "^5.5.1", + "ajv": "^5.5.2", "bootstrap": "^4.0.0-beta.2", "classnames": "^2.2.5", "d3": "^4.12.0", -- GitLab From 49749d9b433b0103c81f226a5041c2d61d62d8c8 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 20 Dec 2017 09:55:03 +0100 Subject: [PATCH 04/51] refactor out blocks/connections, add create connection capability --- src/components/ToolchainBlock.jsx | 233 ++++++++++++++++++++ src/components/ToolchainBlockInput.jsx | 20 ++ src/components/ToolchainConnection.jsx | 54 +++++ src/components/ToolchainEditor.jsx | 293 ++++++++----------------- 4 files changed, 393 insertions(+), 207 deletions(-) create mode 100644 src/components/ToolchainBlock.jsx create mode 100644 src/components/ToolchainBlockInput.jsx create mode 100644 src/components/ToolchainConnection.jsx diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx new file mode 100644 index 0000000..45e3f9f --- /dev/null +++ b/src/components/ToolchainBlock.jsx @@ -0,0 +1,233 @@ +// @flow +import * as React from 'react'; +import { + Container, + Row, + Col, + Button, + ButtonGroup, + Form, + FormGroup, + Label, + Input, + InputGroup, + FormText, + Collapse, + Card, + CardHeader, + CardBody, + TabContent, TabPane, + Navbar, + Nav, NavItem, NavLink, CardTitle, CardText, + FormFeedback, + Alert, + InputGroupAddon, + Badge, +} from 'reactstrap'; +import ThinInput from './ToolchainBlockInput.jsx'; + +type Props = { + name: string, + locMap: { + block: { + x: number, + y: number, + height: number, + width: number, + }, + inputs?: any, + outputs?: any, + }, + data: any, +}; + +type State = { + editActive: boolean, +} + +class ToolchainBlock extends React.PureComponent { + constructor(props: Props){ + super(props); + } + + state = { + editActive: false, + } + + render = () => { + const name = this.props.name; + const {x, y, height, width} = this.props.locMap.block; + + const hasInputs = this.props.data && this.props.data.hasOwnProperty('inputs'); + const hasOutputs = this.props.data && this.props.data.hasOwnProperty('outputs'); + const inputs = hasInputs ? this.props.data.inputs : []; + const outputs = hasOutputs ? this.props.data.outputs : []; + let color = 'white'; + if(!hasInputs) + color = 'lightCyan'; + else if(!hasOutputs) + color = 'lightYellow'; + const nameClipId = `${ name }-name`; + const fullClipId = `${ name }-full`; + const inputClipId = `${ name }-input`; + const outputClipId = `${ name }-output`; + + //console.log(locMap); + + return ( + + { + this.state.editActive && + { + this.setState({ editActive: !this.state.editActive }); + }} + > + + { + e.stopPropagation(); + }} + /> + + { hasInputs && + + { + inputs.map((inp, i) => + { + e.stopPropagation(); + }} + /> + ) + } + + } + { hasOutputs && + + { + outputs.map((out, i) => + { + e.stopPropagation(); + }} + /> + ) + } + + } + + + + } + { + !this.state.editActive && + + { + this.setState({ editActive: !this.state.editActive }); + }} + /> + + { name } + + + { + inputs.map((inp, i) => { + const loc = this.props.locMap.inputs[inp]; + const varWidth = hasOutputs ? width / 2 : width; + const clipPath = hasOutputs ? inputClipId : fullClipId; + return ( + + + + { inp } + + + ); + }) + } + { + outputs.map((out, i) => { + const loc = this.props.locMap.outputs[out]; + const varWidth = hasInputs ? width / 2 : width; + const clipPath = hasInputs ? outputClipId : fullClipId; + return ( + + + + { out } + + + ); + }) + } + + + + + + + + + + + + + + } + + ); + } +} + +export default ToolchainBlock; diff --git a/src/components/ToolchainBlockInput.jsx b/src/components/ToolchainBlockInput.jsx new file mode 100644 index 0000000..39c089d --- /dev/null +++ b/src/components/ToolchainBlockInput.jsx @@ -0,0 +1,20 @@ +// @flow +import * as React from 'react'; +import { + Input, +} from 'reactstrap'; + +export const thinInputHeight = 20; + +const ToolchainBlockInput = (props: any) => ; + +export default ToolchainBlockInput; diff --git a/src/components/ToolchainConnection.jsx b/src/components/ToolchainConnection.jsx new file mode 100644 index 0000000..75eb2e2 --- /dev/null +++ b/src/components/ToolchainConnection.jsx @@ -0,0 +1,54 @@ +// @flow +import * as React from 'react'; + +type Props = { + locMap: any, + connection: { + from: string, + to: string, + channel: string, + }, + channelColors: any, +}; + +type State = { + selected: boolean, +}; + +const connectionToId = ({ from, to, channel }) => `${ from.replace('.', '-') }-${ to.replace('.', '-') }`; + +class ToolchainConnection extends React.PureComponent { + constructor(props: Props){ + super(props); + } + + state = { + selected: false, + } + + render = () => { + const connectionId = `#${ connectionToId(this.props.connection) }`; + const fromInfo = this.props.connection.from.split('.'); + const toInfo = this.props.connection.to.split('.'); + //console.log(`this.props.connectionecting "${ this.props.connectionId }" from ${ fromInfo } to ${ toInfo }`); + const fromLoc = this.props.locMap[fromInfo[0]].outputs[fromInfo[1]]; + const toLoc = this.props.locMap[toInfo[0]].inputs[toInfo[1]]; + + return ( + { + this.setState({ selected: !this.state.selected }); + }} + id={connectionId} + stroke={this.props.channelColors[this.props.connection.channel]} + strokeWidth={ this.state.selected ? 5 : 2 } + x1={fromLoc.x} + y1={fromLoc.y} + x2={toLoc.x} + y2={toLoc.y} + /> + ); + } +} + +export default ToolchainConnection; diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index b185083..0e55672 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -41,6 +41,9 @@ import ValidSchemaBadge from './ValidSchemaBadge.jsx'; import CacheInput from './CacheInput.jsx'; import DeleteInputBtn from './DeleteInputBtn.jsx'; import TypedField from './TypedField.jsx'; +import { thinInputHeight } from './ToolchainBlockInput.jsx'; +import Block from './ToolchainBlock.jsx'; +import Connection from './ToolchainConnection.jsx'; //console.log(d3); @@ -84,158 +87,7 @@ const getValidObj = (data = {}) => { const blockWidth = 200; const distanceFactor = 20; -const thinInputHeight = 20; - -const ThinInput = (props: any) => ; - -const Block = ({name, locMap, data}) => { - const {x, y, height, width} = locMap.block; - - const hasInputs = data && data.hasOwnProperty('inputs'); - const hasOutputs = data && data.hasOwnProperty('outputs'); - const inputs = hasInputs ? data.inputs : []; - const outputs = hasOutputs ? data.outputs : []; - let color = 'white'; - if(!hasInputs) - color = 'lightCyan'; - else if(!hasOutputs) - color = 'lightYellow'; - - //console.log(locMap); - - return ( - - - - { name } - - { - /* - - - - - - { - inputs.map((inp, i) => - - ) - } - - - { - outputs.map((out, i) => - - ) - } - - - - - */ - } - - { - inputs.map((inp, i) => { - const loc = locMap.inputs[inp]; - return ( - - - - { inp } - - - ); - }) - } - - - { - outputs.map((out, i) => { - const loc = locMap.outputs[out]; - return ( - - - - { out } - - - ); - }) - } - - - - - - - - - - - - ); -}; -const connectionToId = ({ from, to, channel }) => `${ from.replace('.', '-') }-${ to.replace('.', '-') }`; export class ToolchainEditor extends React.Component { constructor(props: Props) { @@ -278,6 +130,19 @@ export class ToolchainEditor extends React.Component { setZoomLevel = (zoomLevel: number) => this.setState({...this.state, zoomLevel: zoomLevel}); + createConnection = (from: string, to: string, channel: string) => { + this.setContents({ + connections: [ + ...this.state.cache.contents.connections, + { + from, + to, + channel, + } + ] + }); + } + getSvgViewBox = () => `0 0 ${ this.state.zoomLevel } ${ this.state.zoomLevel }`; updateBlockLocation = (blockName: string, x: number, y: number) => { @@ -353,6 +218,7 @@ export class ToolchainEditor extends React.Component { } initD3 = () => { + // dragging blocks around setTimeout(() => { const updateBlockLocation = this.updateBlockLocation; let debouceTimeLast = 0; @@ -368,13 +234,13 @@ export class ToolchainEditor extends React.Component { dx += d3.event.dx; dy += d3.event.dy; - if(Math.abs(dx) > 20){ - mx = Math.round(dx / 20.0); - dx = dx - mx * 20; + if(Math.abs(dx) > distanceFactor){ + mx = Math.round(dx / distanceFactor); + dx = dx - mx * distanceFactor; } - if(Math.abs(dy) > 20){ - my = Math.round(dy / 20.0); - dy = dy - my * 20; + if(Math.abs(dy) > distanceFactor){ + my = Math.round(dy / distanceFactor); + dy = dy - my * distanceFactor; } if(mx != 0 || my != 0){ const bId = d3.select(this).attr('id'); @@ -404,29 +270,56 @@ export class ToolchainEditor extends React.Component { .on('end', endDrag) .on('drag', dragged) ); + }, 50); + + // creating connections + setTimeout(() => { + //const updateBlockLocation = this.updateBlockLocation; + let startId; + const createConnection = this.createConnection; + const channelColors = this.state.cache.contents.representation.channel_colors; + function startDrag(d) { + startId = d3.select(this).attr('id').replace('-output-', '.'); + d3.select('svg') + .append('line') + .classed('tmp', true) + .attr('stroke', 'black') + .attr('x1', d3.event.x) + .attr('y1', d3.event.y) + .attr('x2', d3.event.x) + .attr('y2', d3.event.y); + } + + function endDrag() { + const {x, y} = d3.event; + d3.select('.tmp') + .remove(); + const endInput = Array.from(document.querySelectorAll('.iBlock')) + .find(n => { + const nx = n.x.baseVal.value; + const ny = n.y.baseVal.value; + const width = n.width.baseVal.value; + const height = n.height.baseVal.value; + return nx <= x && x <= nx + width && ny <= y && y <= ny + height; + }); + if(endInput === undefined) + return; + const endId = endInput.id.replace('-input-', '.'); + createConnection(startId, endId, Object.keys(channelColors)[0]); + } - /* - this.state.cache.contents.connections.forEach((conn) => { - const connId = `#${ connectionToId(conn) }`; - const fromId = `#${ conn.from.replace('.', '-output-') }`; - const toId = `#${ conn.to.replace('.', '-input-') }`; - console.log(`Connecting "${ connId }" from ${ fromId } to ${ toId }`); - const connPath = document.querySelector(connId); - const fromBlock = d3.select(fromId); - const toBlock = d3.select(toId); - - d3.select('svg').append('line') - .style('stroke', this.state.cache.contents.representation.channel_colors[conn.channel]) - .style('stroke-width', '2') - .attr('x1', fromBlock.attr('x')) - .attr('y1', fromBlock.attr('y')) - .attr('x2', toBlock.attr('x')) - .attr('y2', toBlock.attr('y')) - ; - - //console.log(p); - }); - */ + function dragged() { + d3.select('.tmp') + .attr('x2', d3.event.x) + .attr('y2', d3.event.y); + } + + d3.selectAll('.oBlock').call( + d3.drag() + .on('start', startDrag) + .on('end', endDrag) + .on('drag', dragged) + ); }, 50); }; @@ -437,8 +330,8 @@ export class ToolchainEditor extends React.Component { renderGraphicalEditor = () => { const svgWidth = 3000; const svgHeight = 3000; - const gridX = 20; - const gridY = 20; + const gridX = distanceFactor; + const gridY = distanceFactor; const locMap = this.getLocationMap(); return ( @@ -502,6 +395,18 @@ export class ToolchainEditor extends React.Component { ); }) } + + { + this.state.cache.contents.connections.map((conn, i) => + + ) + } + { Object.entries(this.state.cache.contents.representation.blocks).map(([name, rep], i) => { /> ) } - - { - this.state.cache.contents.connections.map((conn, i) => { - const connId = `#${ connectionToId(conn) }`; - const fromInfo = conn.from.split('.'); - const toInfo = conn.to.split('.'); - //console.log(`Connecting "${ connId }" from ${ fromInfo } to ${ toInfo }`); - const connPath = document.querySelector(connId); - const fromLoc = locMap[fromInfo[0]].outputs[fromInfo[1]]; - const toLoc = locMap[toInfo[0]].inputs[toInfo[1]]; - - return ( - - ); - - }) - } -- GitLab From 58b904e9ef8d9a92e5148beef42b11d0d03f062e Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 21 Dec 2017 11:06:28 +0100 Subject: [PATCH 05/51] refactor out generating new keys for objs, add IO creation support to tc modal --- src/components/AlgorithmEditor.jsx | 99 +++++----- src/components/DataformatEditor.jsx | 14 +- src/components/ToolchainBlock.jsx | 241 ++++++++++-------------- src/components/ToolchainConnection.jsx | 2 + src/components/ToolchainEditor.jsx | 248 +++++++++++++++++++++++-- src/helpers/index.js | 16 ++ 6 files changed, 408 insertions(+), 212 deletions(-) diff --git a/src/components/AlgorithmEditor.jsx b/src/components/AlgorithmEditor.jsx index a4914be..37c58e8 100644 --- a/src/components/AlgorithmEditor.jsx +++ b/src/components/AlgorithmEditor.jsx @@ -18,7 +18,7 @@ import type { MapStateToProps, MapDispatchToProps } from 'react-redux'; import cn from 'classnames'; -import { changeObjFieldName } from '@helpers'; +import { changeObjFieldName, generateNewKey } from '@helpers'; import { algorithmValidator, nameValidator, BUILTIN_TYPES, ANALYZER_RESULT_TYPES } from '@helpers/beat'; import type { AlgorithmValidatorObject, BeatObject } from '@helpers/beat'; @@ -275,17 +275,19 @@ export class AlgorithmEditor extends React.Component { } @@ -314,17 +316,19 @@ export class AlgorithmEditor extends React.Component { } @@ -667,15 +671,19 @@ export class AlgorithmEditor extends React.Component { } @@ -724,11 +732,15 @@ export class AlgorithmEditor extends React.Component { @@ -795,15 +807,18 @@ export class AlgorithmEditor extends React.Component { } diff --git a/src/components/DataformatEditor.jsx b/src/components/DataformatEditor.jsx index 06ea373..720f2f7 100644 --- a/src/components/DataformatEditor.jsx +++ b/src/components/DataformatEditor.jsx @@ -37,7 +37,7 @@ import type { BeatObject, } from '@helpers/beat.js'; -import { changeObjFieldName } from '@helpers'; +import { changeObjFieldName, generateNewKey } from '@helpers'; type Props = { data: BeatObject, @@ -225,17 +225,7 @@ const RecursiveObj = ({ obj, dfs, updateFunc }: {obj: any, dfs: string[], update + + } + { + hasOutputs && + + Outputs + { + data.outputs.map((output, i, outputs) => + + { + this.props.updateBlockIOName('output', output, e.target.value); + }} + validateFunc={(str) => { + return str === output || !outputs.includes(str) || + This output name is already in use in this block + ; + + }} + > + { + this.props.deleteBlockIO('output', output); + }} + /> + + + ) + } + + + } + + + + + ); + } +} + +export default ToolchainModal; -- GitLab From ab0adc330067483404dd588d70661db3f6ce6f63 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 21 Dec 2017 12:00:04 +0100 Subject: [PATCH 07/51] add block deletion --- src/components/ToolchainEditor.jsx | 29 +++++++++++++++++++++++++++++ src/components/ToolchainModal.jsx | 10 +++++++++- 2 files changed, 38 insertions(+), 1 deletion(-) diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index de8f530..ae602e8 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -326,6 +326,31 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } + deleteBlock = (blockName: string, set: BlockSet) => { + const rep = {...this.state.cache.contents.representation}; + + delete rep.blocks[blockName]; + rep.connections = Object.entries(rep.connections).filter(([name, rep]) => { + const [from, to] = name.split('/'); + if(to.startsWith(`${ blockName }.`) || from.startsWith(`${ blockName }.`)) + return false; + return true; + }) + .reduce((cs, c) => ({...cs, c}), {}) + ; + const newContents = { + ...this.state.cache.contents, + [set]: this.state.cache.contents[set].filter(s => s.name !== blockName), + connections: this.state.cache.contents.connections.filter(c => { + if(c.to.startsWith(`${ blockName }.`) || c.from.startsWith(`${ blockName }.`)) + return false; + return true; + }), + }; + + this.setContents(newContents); + } + deleteBlockIO = (blockName: string, set: BlockSet, ioType: 'input' | 'output', ioName: string) => { const rep = {...this.state.cache.contents.representation}; @@ -738,6 +763,10 @@ export class ToolchainEditor extends React.Component { ioType, ioName )} + deleteBlock={() => this.deleteBlock( + this.state.modalBlockInfo.name, + this.state.modalBlockInfo.set, + )} /> diff --git a/src/components/ToolchainModal.jsx b/src/components/ToolchainModal.jsx index fbeae01..5d2a997 100644 --- a/src/components/ToolchainModal.jsx +++ b/src/components/ToolchainModal.jsx @@ -39,6 +39,7 @@ type Props = { updateBlockIOName: (ioType: 'input' | 'output', oldName: string, newName: string) => any, addBlockIO: (ioType: 'input' | 'output', newName: string) => any, deleteBlockIO: (ioType: 'input' | 'output', ioName: string) => any, + deleteBlock: () => any, }; type State = { @@ -72,7 +73,7 @@ class ToolchainModal extends React.Component { }} > - Editing
{data.name}
+ Editing
{data.name}
{' '}
@@ -176,6 +177,13 @@ class ToolchainModal extends React.Component {
+ + + ); } -- GitLab From f7a7acc9acd57957ff71c44504fcf68515ce10b1 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 21 Dec 2017 12:06:17 +0100 Subject: [PATCH 08/51] much better block dragging experience --- src/components/ToolchainBlock.jsx | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index c6ff342..2d44ba9 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -80,7 +80,7 @@ class ToolchainBlock extends React.PureComponent { return ( - { @@ -95,11 +95,6 @@ class ToolchainBlock extends React.PureComponent { > { name } - { inputs.map((inp, i) => { const loc = this.props.locMap.inputs[inp]; -- GitLab From 4c5e5e088401bdfef40d2987963649631c92ca24 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 21 Dec 2017 15:34:04 +0100 Subject: [PATCH 09/51] add react-contextmenu, add context menus for blocks & connections, add .stylelintrc --- .stylelintrc | 6 ++ main.jsx | 1 + package-lock.json | 9 +++ package.json | 1 + react-contextmenu.css | 82 ++++++++++++++++++++++++++ src/components/ToolchainBlock.jsx | 23 +++++--- src/components/ToolchainConnection.jsx | 32 ++++++---- src/components/ToolchainEditor.jsx | 58 +++++++++++++++++- 8 files changed, 192 insertions(+), 20 deletions(-) create mode 100644 .stylelintrc create mode 100644 react-contextmenu.css diff --git a/.stylelintrc b/.stylelintrc new file mode 100644 index 0000000..7fd1f96 --- /dev/null +++ b/.stylelintrc @@ -0,0 +1,6 @@ +{ + "extends": "stylelint-config-standard", + "rules": { + "indentation": "tab" + } +} diff --git a/main.jsx b/main.jsx index bdea091..9bd011e 100644 --- a/main.jsx +++ b/main.jsx @@ -1,5 +1,6 @@ // bootstrap first import 'bootstrap/dist/css/bootstrap.min.css'; +import './react-contextmenu.css'; // rest of app import React from 'react'; diff --git a/package-lock.json b/package-lock.json index 64fc506..3ea2429 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10480,6 +10480,15 @@ "prop-types": "15.6.0" } }, + "react-contextmenu": { + "version": "2.9.2", + "resolved": "https://registry.npmjs.org/react-contextmenu/-/react-contextmenu-2.9.2.tgz", + "integrity": "sha512-DdcO6iLBIJuDVsRpJLG/9N6ine0OVZhuQvnSPCEihfcyJFz+SHU9pQo+w9LWi2PdUxFbFV52BwAuutQkAYJxaA==", + "requires": { + "classnames": "2.2.5", + "object-assign": "4.1.1" + } + }, "react-deep-force-update": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/react-deep-force-update/-/react-deep-force-update-2.1.1.tgz", diff --git a/package.json b/package.json index 422d8e6..ead67e0 100644 --- a/package.json +++ b/package.json @@ -84,6 +84,7 @@ "d3": "^4.12.0", "prop-types": "^15.6.0", "react": "^16.2.0", + "react-contextmenu": "^2.9.2", "react-dom": "^16.2.0", "react-konva": "^1.6.4", "react-popper": "^0.7.4", diff --git a/react-contextmenu.css b/react-contextmenu.css new file mode 100644 index 0000000..ab66641 --- /dev/null +++ b/react-contextmenu.css @@ -0,0 +1,82 @@ +/* taken from react-contextmenu's example CSS https://github.com/vkbansal/react-contextmenu/blob/65df2dec9737eed4e5e1b0b8fbc1018629082f89/examples/react-contextmenu.css + * adapted to more closely conform to this repo's stylelint's settings (see .stylelintrc) + */ +.react-contextmenu { + min-width: 160px; + padding: 5px 0; + margin: 2px 0 0; + font-size: 16px; + color: #373a3c; + text-align: left; + background-color: #fff; + background-clip: padding-box; + border: 1px solid rgba(0, 0, 0, 0.15); + border-radius: 0.25rem; + outline: none; + opacity: 0; + pointer-events: none; + transition: opacity 250ms ease; +} + +.react-contextmenu.react-contextmenu--visible { + opacity: 1; + pointer-events: auto; +} + +.react-contextmenu-item { + padding: 3px 20px; + font-weight: 400; + line-height: 1.5; + color: #373a3c; + text-align: inherit; + white-space: nowrap; + background: 0 0; + border: 0; + cursor: pointer; +} + +.react-contextmenu-item.react-contextmenu-item--active, +.react-contextmenu-item.react-contextmenu-item--selected { + color: #fff; + background-color: #20a0ff; + border-color: #20a0ff; + text-decoration: none; +} + +.react-contextmenu-item.react-contextmenu-item--disabled, +.react-contextmenu-item.react-contextmenu-item--disabled:hover { + color: #878a8c; + background-color: transparent; + border-color: rgba(0, 0, 0, 0.15); +} + +.react-contextmenu-item--divider { + margin-bottom: 3px; + padding: 2px 0; + border-bottom: 1px solid rgba(0, 0, 0, 0.15); + cursor: inherit; +} + +.react-contextmenu-item--divider:hover { + background-color: transparent; + border-color: rgba(0, 0, 0, 0.15); +} + +.react-contextmenu-item.react-contextmenu-submenu { + padding: 0; +} + +.react-contextmenu-item.react-contextmenu-submenu > .react-contextmenu-item { +} + +.react-contextmenu-item.react-contextmenu-submenu > .react-contextmenu-item::after { + content: "â–¶"; + display: inline-block; + position: absolute; + right: 7px; +} + +.example-multiple-targets::after { + content: attr(data-count); + display: block; +} diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index 2d44ba9..c0d93a4 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -25,6 +25,7 @@ import { Badge, } from 'reactstrap'; import ThinInput from './ToolchainBlockInput.jsx'; +import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; export type BlockSet = 'analyzers' | 'blocks' | 'datasets'; @@ -80,13 +81,21 @@ class ToolchainBlock extends React.PureComponent { return ( - { - this.props.openEditor(); - }} - /> + ({ name: props.name, set: props.set })} + renderTag='g' + > + { + this.props.openEditor(); + }} + /> + { return null; return ( - { - this.setState({ selected: !this.state.selected }); - }} - id={connectionId} - stroke={this.props.channelColors[this.props.connection.channel]} - strokeWidth={ this.state.selected ? 5 : 2 } - x1={fromLoc.x} - y1={fromLoc.y} - x2={toLoc.x} - y2={toLoc.y} - /> + ({ connection: props.connection })} + renderTag='g' + > + { + this.setState({ selected: !this.state.selected }); + }} + id={connectionId} + stroke={this.props.channelColors[this.props.connection.channel]} + strokeWidth={ this.state.selected ? 5 : 2 } + x1={fromLoc.x} + y1={fromLoc.y} + x2={toLoc.x} + y2={toLoc.y} + /> + ); } } diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index ae602e8..bb895f4 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -30,6 +30,7 @@ import type { MapStateToProps, MapDispatchToProps } from 'react-redux'; import cn from 'classnames'; import * as d3 from 'd3'; +import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; import { nameValidator } from '@helpers/beat'; import type { BeatObject } from '@helpers/beat'; @@ -339,7 +340,6 @@ export class ToolchainEditor extends React.Component { .reduce((cs, c) => ({...cs, c}), {}) ; const newContents = { - ...this.state.cache.contents, [set]: this.state.cache.contents[set].filter(s => s.name !== blockName), connections: this.state.cache.contents.connections.filter(c => { if(c.to.startsWith(`${ blockName }.`) || c.from.startsWith(`${ blockName }.`)) @@ -351,6 +351,28 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } + deleteConnection = (cn: {from: string, to: string, channel: string}) => { + const rep = {...this.state.cache.contents.representation}; + + rep.connections = Object.entries(rep.connections).filter(([name, rep]) => { + const [from, to] = name.split('/'); + if(from === cn.from && to === cn.to) + return false; + return true; + }) + .reduce((cs, c) => ({...cs, c}), {}) + ; + const newContents = { + connections: this.state.cache.contents.connections.filter(c => { + if(c.from === cn.from && c.to === cn.to) + return false; + return true; + }), + }; + + this.setContents(newContents); + } + deleteBlockIO = (blockName: string, set: BlockSet, ioType: 'input' | 'output', ioName: string) => { const rep = {...this.state.cache.contents.representation}; @@ -686,6 +708,40 @@ export class ToolchainEditor extends React.Component { + + { + const {name, set, clicked} = data; + switch(clicked){ + case 'delete': + this.deleteBlock(name, set); + break; + default: + break; + } + }} + > + Delete Block + + + + { + const {connection, clicked} = data; + switch(clicked){ + case 'delete': + this.deleteConnection(connection); + break; + default: + break; + } + }} + > + Delete Connection + + ); } -- GitLab From beddafe545e2878829f299a8a7eb23b6b4385c89 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Fri, 22 Dec 2017 11:09:43 +0100 Subject: [PATCH 10/51] update deps --- package-lock.json | 2328 +++++++++++++++++++++++++++++++++++++++------ package.json | 6 +- 2 files changed, 2020 insertions(+), 314 deletions(-) diff --git a/package-lock.json b/package-lock.json index 3ea2429..9548fdf 100644 --- a/package-lock.json +++ b/package-lock.json @@ -151,6 +151,16 @@ "integrity": "sha512-wOU/VRodnI/4Chxuu6R6bcyN9aE3rztO0i8R76PZO7+DxTXWy60nseGN4ujspucmxrfj5mzgCYPXiXqrD6KC3Q==", "dev": true }, + "JSONStream": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.2.tgz", + "integrity": "sha1-wQI3G27Dp887hHygDCC7D85Mbeo=", + "dev": true, + "requires": { + "jsonparse": "1.3.1", + "through": "2.3.8" + } + }, "abbrev": { "version": "1.0.9", "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", @@ -207,12 +217,37 @@ } } }, + "addressparser": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/addressparser/-/addressparser-1.0.1.tgz", + "integrity": "sha1-R6++GiqSYhkdtoOOT9HTm0CCF0Y=", + "dev": true, + "optional": true + }, "after": { "version": "0.8.2", "resolved": "https://registry.npmjs.org/after/-/after-0.8.2.tgz", "integrity": "sha1-/ts5T58OAqqXaOcCvaI7UF+ufh8=", "dev": true }, + "agent-base": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-2.1.1.tgz", + "integrity": "sha1-1t4Q1a9hMtW9aSQn1G/FOFOQlMc=", + "dev": true, + "requires": { + "extend": "3.0.1", + "semver": "5.0.3" + }, + "dependencies": { + "semver": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.0.3.tgz", + "integrity": "sha1-d0Zt5YnNXTyV8TiqeLxWmjy10no=", + "dev": true + } + } + }, "ajv": { "version": "5.5.2", "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", @@ -317,6 +352,12 @@ "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", "dev": true }, + "array-filter": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/array-filter/-/array-filter-0.0.1.tgz", + "integrity": "sha1-fajPLiZijtcygDWB/SH2fKzS7uw=", + "dev": true + }, "array-find-index": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/array-find-index/-/array-find-index-1.0.2.tgz", @@ -345,6 +386,18 @@ "integrity": "sha1-hlv3+K851rCYLGCQKRSsdrwBCPY=", "dev": true }, + "array-map": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/array-map/-/array-map-0.0.0.tgz", + "integrity": "sha1-iKK6tz0c97zVwbEYoAP2b2ZfpmI=", + "dev": true + }, + "array-reduce": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/array-reduce/-/array-reduce-0.0.0.tgz", + "integrity": "sha1-FziZ0//Rx9k4PkR5Ul2+J4yrXys=", + "dev": true + }, "array-slice": { "version": "0.2.3", "resolved": "https://registry.npmjs.org/array-slice/-/array-slice-0.2.3.tgz", @@ -389,6 +442,13 @@ "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", "integrity": "sha1-5QNHYR1+aQlDIIu9r+vLwvuGbUY=" }, + "asn1": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", + "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=", + "dev": true, + "optional": true + }, "asn1.js": { "version": "4.9.2", "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.9.2.tgz", @@ -409,6 +469,12 @@ "util": "0.10.3" } }, + "assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true + }, "assertion-error": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.0.2.tgz", @@ -421,6 +487,23 @@ "integrity": "sha1-ECyenpAF0+fjgpvwxPok7oYu6bk=", "dev": true }, + "astw": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/astw/-/astw-2.2.0.tgz", + "integrity": "sha1-e9QXhNMkk5h66yOba04cV6hzuRc=", + "dev": true, + "requires": { + "acorn": "4.0.13" + }, + "dependencies": { + "acorn": { + "version": "4.0.13", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-4.0.13.tgz", + "integrity": "sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c=", + "dev": true + } + } + }, "async": { "version": "1.5.2", "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", @@ -433,6 +516,19 @@ "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", "dev": true }, + "async-limiter": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", + "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==", + "dev": true + }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true, + "optional": true + }, "autoprefixer": { "version": "6.7.7", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-6.7.7.tgz", @@ -486,6 +582,30 @@ } } }, + "aws-sign2": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", + "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", + "dev": true, + "optional": true + }, + "aws4": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", + "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=", + "dev": true, + "optional": true + }, + "axios": { + "version": "0.15.3", + "resolved": "https://registry.npmjs.org/axios/-/axios-0.15.3.tgz", + "integrity": "sha1-LJ1jiy4ZGgjqHWzJiOrda6W9wFM=", + "dev": true, + "optional": true, + "requires": { + "follow-redirects": "1.0.0" + } + }, "babel-code-frame": { "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", @@ -775,9 +895,9 @@ } }, "babel-plugin-flow-react-proptypes": { - "version": "12.1.0", - "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-12.1.0.tgz", - "integrity": "sha512-6eoqK9NcSQvmEmtiOiAG0QhC5/R8rROvLE75/oHXHQ2S02GqKWBimbj0CzuRlODFSAq9r1hNS+DtjtXOEHulPQ==", + "version": "13.0.0", + "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-13.0.0.tgz", + "integrity": "sha512-km7Jrt2mkavHIUOneZoSXYrozTT5NZTplReZ6lUprqv9zGkFkmrY6mem5+MaPNk+NwU2ff7vR5ComleYkrk0pA==", "dev": true, "requires": { "babel-core": "6.26.0", @@ -1477,6 +1597,16 @@ "integrity": "sha1-3DQxT05nkxgJP8dgJyUl+UvyXBY=", "dev": true }, + "bcrypt-pbkdf": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", + "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", + "dev": true, + "optional": true, + "requires": { + "tweetnacl": "0.14.5" + } + }, "better-assert": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/better-assert/-/better-assert-1.0.2.tgz", @@ -1498,6 +1628,47 @@ "integrity": "sha1-muuabF6IY4qtFx4Wf1kAq+JINdA=", "dev": true }, + "bl": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/bl/-/bl-1.1.2.tgz", + "integrity": "sha1-/cqHGplxOqANGeO7ukHER4emU5g=", + "dev": true, + "optional": true, + "requires": { + "readable-stream": "2.0.6" + }, + "dependencies": { + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true, + "optional": true + }, + "readable-stream": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.0.6.tgz", + "integrity": "sha1-j5A0HmilPMySh4jaz80Rs265t44=", + "dev": true, + "optional": true, + "requires": { + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "1.0.7", + "string_decoder": "0.10.31", + "util-deprecate": "1.0.2" + } + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true, + "optional": true + } + } + }, "blob": { "version": "0.0.4", "resolved": "https://registry.npmjs.org/blob/-/blob-0.0.4.tgz", @@ -1554,6 +1725,16 @@ "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", "dev": true }, + "boom": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", + "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", + "dev": true, + "optional": true, + "requires": { + "hoek": "4.2.0" + } + }, "bootstrap": { "version": "4.0.0-beta.2", "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.0.0-beta.2.tgz", @@ -1586,12 +1767,163 @@ "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=", "dev": true }, + "browser-pack": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/browser-pack/-/browser-pack-6.0.2.tgz", + "integrity": "sha1-+GzWzvT1MAyOY+B6TVEvZfv/RTE=", + "dev": true, + "requires": { + "JSONStream": "1.3.2", + "combine-source-map": "0.7.2", + "defined": "1.0.0", + "through2": "2.0.3", + "umd": "3.0.1" + } + }, + "browser-resolve": { + "version": "1.11.2", + "resolved": "https://registry.npmjs.org/browser-resolve/-/browser-resolve-1.11.2.tgz", + "integrity": "sha1-j/CbCixCFxihBRwmCzLkj0QpOM4=", + "dev": true, + "requires": { + "resolve": "1.1.7" + }, + "dependencies": { + "resolve": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", + "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "dev": true + } + } + }, "browser-stdout": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=", "dev": true }, + "browserify": { + "version": "14.5.0", + "resolved": "https://registry.npmjs.org/browserify/-/browserify-14.5.0.tgz", + "integrity": "sha512-gKfOsNQv/toWz+60nSPfYzuwSEdzvV2WdxrVPUbPD/qui44rAkB3t3muNtmmGYHqrG56FGwX9SUEQmzNLAeS7g==", + "dev": true, + "requires": { + "JSONStream": "1.3.2", + "assert": "1.4.1", + "browser-pack": "6.0.2", + "browser-resolve": "1.11.2", + "browserify-zlib": "0.2.0", + "buffer": "5.0.8", + "cached-path-relative": "1.0.1", + "concat-stream": "1.5.2", + "console-browserify": "1.1.0", + "constants-browserify": "1.0.0", + "crypto-browserify": "3.12.0", + "defined": "1.0.0", + "deps-sort": "2.0.0", + "domain-browser": "1.1.7", + "duplexer2": "0.1.4", + "events": "1.1.1", + "glob": "7.1.2", + "has": "1.0.1", + "htmlescape": "1.1.1", + "https-browserify": "1.0.0", + "inherits": "2.0.3", + "insert-module-globals": "7.0.1", + "labeled-stream-splicer": "2.0.0", + "module-deps": "4.1.1", + "os-browserify": "0.3.0", + "parents": "1.0.1", + "path-browserify": "0.0.0", + "process": "0.11.10", + "punycode": "1.4.1", + "querystring-es3": "0.2.1", + "read-only-stream": "2.0.0", + "readable-stream": "2.3.3", + "resolve": "1.4.0", + "shasum": "1.0.2", + "shell-quote": "1.6.1", + "stream-browserify": "2.0.1", + "stream-http": "2.7.2", + "string_decoder": "1.0.3", + "subarg": "1.0.0", + "syntax-error": "1.3.0", + "through2": "2.0.3", + "timers-browserify": "1.4.2", + "tty-browserify": "0.0.0", + "url": "0.11.0", + "util": "0.10.3", + "vm-browserify": "0.0.4", + "xtend": "4.0.1" + }, + "dependencies": { + "buffer": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.0.8.tgz", + "integrity": "sha512-xXvjQhVNz50v2nPeoOsNqWCLGfiv4ji/gXZM28jnVwdLJxH4mFyqgqCKfaK9zf1KUbG6zTkjLOy7ou+jSMarGA==", + "dev": true, + "requires": { + "base64-js": "1.2.1", + "ieee754": "1.1.8" + } + }, + "concat-stream": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.5.2.tgz", + "integrity": "sha1-cIl4Yk2FavQaWnQd790mHadSwmY=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.0.6", + "typedarray": "0.0.6" + }, + "dependencies": { + "readable-stream": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.0.6.tgz", + "integrity": "sha1-j5A0HmilPMySh4jaz80Rs265t44=", + "dev": true, + "requires": { + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "1.0.7", + "string_decoder": "0.10.31", + "util-deprecate": "1.0.2" + } + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true + } + } + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "process": { + "version": "0.11.10", + "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", + "integrity": "sha1-czIwDoQBYb2j5podHZGn1LwW8YI=", + "dev": true + }, + "timers-browserify": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/timers-browserify/-/timers-browserify-1.4.2.tgz", + "integrity": "sha1-ycWLV1voQHN1y14kYtrO50NZ9B0=", + "dev": true, + "requires": { + "process": "0.11.10" + } + } + } + }, "browserify-aes": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.1.1.tgz", @@ -1703,6 +2035,22 @@ "integrity": "sha1-JuYe0UIvtw3ULm42cp7VHYVf6Nk=", "dev": true }, + "buildmail": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/buildmail/-/buildmail-4.0.1.tgz", + "integrity": "sha1-h393OLeHKYccmhBeO4N9K+EaenI=", + "dev": true, + "optional": true, + "requires": { + "addressparser": "1.0.1", + "libbase64": "0.1.0", + "libmime": "3.0.0", + "libqp": "1.1.0", + "nodemailer-fetch": "1.6.0", + "nodemailer-shared": "1.1.0", + "punycode": "1.4.1" + } + }, "builtin-modules": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", @@ -1721,6 +2069,12 @@ "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=", "dev": true }, + "cached-path-relative": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.1.tgz", + "integrity": "sha1-0JxLUoAKpMB44t2BqGmqyQ0uVOc=", + "dev": true + }, "caller-path": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/caller-path/-/caller-path-0.1.0.tgz", @@ -1804,6 +2158,13 @@ "integrity": "sha1-vFJrwgRua8OHN8/XfTAm7wS49GQ=", "dev": true }, + "caseless": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", + "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", + "dev": true, + "optional": true + }, "ccount": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/ccount/-/ccount-1.0.2.tgz", @@ -2116,6 +2477,41 @@ "lodash": "4.17.4" } }, + "combine-source-map": { + "version": "0.7.2", + "resolved": "https://registry.npmjs.org/combine-source-map/-/combine-source-map-0.7.2.tgz", + "integrity": "sha1-CHAxKFazB6h8xKxIbzqaYq7MwJ4=", + "dev": true, + "requires": { + "convert-source-map": "1.1.3", + "inline-source-map": "0.6.2", + "lodash.memoize": "3.0.4", + "source-map": "0.5.7" + }, + "dependencies": { + "convert-source-map": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.1.3.tgz", + "integrity": "sha1-SCnId+n+SbMWHzvzZziI4gRpmGA=", + "dev": true + }, + "lodash.memoize": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-3.0.4.tgz", + "integrity": "sha1-LcvSwofLwKVcxCMovQxzYVDVPj8=", + "dev": true + } + } + }, + "combined-stream": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.5.tgz", + "integrity": "sha1-k4NwpXtKUd6ix3wV1cX9+JUWQAk=", + "dev": true, + "requires": { + "delayed-stream": "1.0.0" + } + }, "commander": { "version": "2.11.0", "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", @@ -2166,9 +2562,9 @@ "dev": true }, "component-emitter": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.1.2.tgz", - "integrity": "sha1-KWWU8nU9qmOZbSrwjRWpURbJrsM=", + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", + "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", "dev": true }, "component-inherit": { @@ -2370,9 +2766,9 @@ } }, "cross-env": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/cross-env/-/cross-env-5.1.1.tgz", - "integrity": "sha512-Wtvr+z0Z06KO1JxjfRRsPC+df7biIOiuV4iZ73cThjFGkH+ULBZq1MkBdywEcJC4cTDbO6c8IjgRjfswx3YTBA==", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/cross-env/-/cross-env-5.1.3.tgz", + "integrity": "sha512-UOokgwvDzCT0mqRSLEkJzUhYXB1vK3E5UgDrD41QiXsm9UetcW2rCGHYz/O3p873lMJ1VZbFCF9Izkwh7nYR5A==", "dev": true, "requires": { "cross-spawn": "5.1.0", @@ -2390,6 +2786,28 @@ "which": "1.3.0" } }, + "cryptiles": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", + "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", + "dev": true, + "optional": true, + "requires": { + "boom": "5.2.0" + }, + "dependencies": { + "boom": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", + "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", + "dev": true, + "optional": true, + "requires": { + "hoek": "4.2.0" + } + } + } + }, "crypto-browserify": { "version": "3.12.0", "resolved": "https://registry.npmjs.org/crypto-browserify/-/crypto-browserify-3.12.0.tgz", @@ -2904,6 +3322,29 @@ "d3-transition": "1.1.1" } }, + "dashdash": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", + "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "1.0.0" + } + }, + "data-uri-to-buffer": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/data-uri-to-buffer/-/data-uri-to-buffer-1.2.0.tgz", + "integrity": "sha512-vKQ9DTQPN1FLYiiEEOQ6IBGFqvjCa5rSK3cWMy/Nespm5d/x3dGFT9UBZnkLxCwua/IXBi2TYnwTEpsOvhC4UQ==", + "dev": true, + "optional": true + }, + "date-format": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/date-format/-/date-format-1.2.0.tgz", + "integrity": "sha1-YV6CjiM90aubua4JUODOzPpuytg=", + "dev": true + }, "date-now": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/date-now/-/date-now-0.1.4.tgz", @@ -2982,6 +3423,27 @@ "integrity": "sha1-yY2bzvdWdBiOEQlpFRGZ45sfppM=", "dev": true }, + "degenerator": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/degenerator/-/degenerator-1.0.4.tgz", + "integrity": "sha1-/PSQo37OJmRk2cxDGrmMWBnO0JU=", + "dev": true, + "optional": true, + "requires": { + "ast-types": "0.9.6", + "escodegen": "1.8.1", + "esprima": "3.1.3" + }, + "dependencies": { + "esprima": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-3.1.3.tgz", + "integrity": "sha1-/cpRzuYTOJXjyI1TXOSdv/YqRjM=", + "dev": true, + "optional": true + } + } + }, "del": { "version": "2.2.2", "resolved": "https://registry.npmjs.org/del/-/del-2.2.2.tgz", @@ -2997,6 +3459,12 @@ "rimraf": "2.6.2" } }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", + "dev": true + }, "depd": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", @@ -3009,6 +3477,18 @@ "integrity": "sha1-ce33lF27qGwbGayYK2r7ZHa1bdU=", "dev": true }, + "deps-sort": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/deps-sort/-/deps-sort-2.0.0.tgz", + "integrity": "sha1-CRckkC6EZYJg65EHSMzNGvbiH7U=", + "dev": true, + "requires": { + "JSONStream": "1.3.2", + "shasum": "1.0.2", + "subarg": "1.0.0", + "through2": "2.0.3" + } + }, "des.js": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/des.js/-/des.js-1.0.0.tgz", @@ -3255,6 +3735,32 @@ "is-obj": "1.0.1" } }, + "double-ended-queue": { + "version": "2.1.0-0", + "resolved": "https://registry.npmjs.org/double-ended-queue/-/double-ended-queue-2.1.0-0.tgz", + "integrity": "sha1-ED01J/0xUo9AGIEwyEHv3XgmTlw=", + "dev": true, + "optional": true + }, + "duplexer2": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer2/-/duplexer2-0.1.4.tgz", + "integrity": "sha1-ixLauHjA1p4+eJEFFmKjL8a93ME=", + "dev": true, + "requires": { + "readable-stream": "2.3.3" + } + }, + "ecc-jsbn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", + "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", + "dev": true, + "optional": true, + "requires": { + "jsbn": "0.1.1" + } + }, "ee-first": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", @@ -3303,91 +3809,50 @@ } }, "engine.io": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-1.8.3.tgz", - "integrity": "sha1-jef5eJXSDTm4X4ju7nd7K9QrE9Q=", + "version": "3.1.4", + "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-3.1.4.tgz", + "integrity": "sha1-PQIRtwpVLOhB/8fahiezAamkFi4=", "dev": true, "requires": { "accepts": "1.3.3", "base64id": "1.0.0", "cookie": "0.3.1", - "debug": "2.3.3", - "engine.io-parser": "1.3.2", - "ws": "1.1.2" - }, - "dependencies": { - "debug": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.3.3.tgz", - "integrity": "sha1-QMRT5n5uE8kB3ewxeviYbNqe/4w=", - "dev": true, - "requires": { - "ms": "0.7.2" - } - }, - "ms": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.2.tgz", - "integrity": "sha1-riXPJRKziFodldfwN4aNhDESR2U=", - "dev": true - } + "debug": "2.6.9", + "engine.io-parser": "2.1.1", + "uws": "0.14.5", + "ws": "3.3.3" } }, "engine.io-client": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-1.8.3.tgz", - "integrity": "sha1-F5jtk0USRkU9TG9jXXogH+lA1as=", + "version": "3.1.4", + "resolved": "https://registry.npmjs.org/engine.io-client/-/engine.io-client-3.1.4.tgz", + "integrity": "sha1-T88TcLRxY70s6b4nM5ckMDUNTqE=", "dev": true, "requires": { "component-emitter": "1.2.1", "component-inherit": "0.0.3", - "debug": "2.3.3", - "engine.io-parser": "1.3.2", + "debug": "2.6.9", + "engine.io-parser": "2.1.1", "has-cors": "1.1.0", "indexof": "0.0.1", - "parsejson": "0.0.3", "parseqs": "0.0.5", "parseuri": "0.0.5", - "ws": "1.1.2", - "xmlhttprequest-ssl": "1.5.3", + "ws": "3.3.3", + "xmlhttprequest-ssl": "1.5.4", "yeast": "0.1.2" - }, - "dependencies": { - "component-emitter": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", - "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", - "dev": true - }, - "debug": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.3.3.tgz", - "integrity": "sha1-QMRT5n5uE8kB3ewxeviYbNqe/4w=", - "dev": true, - "requires": { - "ms": "0.7.2" - } - }, - "ms": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.2.tgz", - "integrity": "sha1-riXPJRKziFodldfwN4aNhDESR2U=", - "dev": true - } } }, "engine.io-parser": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-1.3.2.tgz", - "integrity": "sha1-k3sHnwAH0Ik+xW1GyyILjLQ1Igo=", + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/engine.io-parser/-/engine.io-parser-2.1.1.tgz", + "integrity": "sha1-4Ps/DgRi9/WLt3waUun1p+JuRmg=", "dev": true, "requires": { "after": "0.8.2", "arraybuffer.slice": "0.0.6", "base64-arraybuffer": "0.1.5", "blob": "0.0.4", - "has-binary": "0.1.7", - "wtf-8": "1.0.0" + "has-binary2": "1.0.2" } }, "enhanced-resolve": { @@ -4286,6 +4751,12 @@ "is-extglob": "1.0.0" } }, + "extsprintf": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", + "dev": true + }, "fast-deep-equal": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.0.0.tgz", @@ -4350,6 +4821,13 @@ "object-assign": "4.1.1" } }, + "file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==", + "dev": true, + "optional": true + }, "filename-regex": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", @@ -4428,6 +4906,16 @@ "integrity": "sha512-w6SGi5CDfKLNGzYssRhW6N37qKclDXijsxDQ5M8c3WbivRYta0Horv22bwakegfKBVDnyeS0lRW3OqBC74eq2g==", "dev": true }, + "follow-redirects": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.0.0.tgz", + "integrity": "sha1-jjQpjL0uF28lTv/sdaHHjMhJ/Tc=", + "dev": true, + "optional": true, + "requires": { + "debug": "2.6.9" + } + }, "for-in": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", @@ -4449,6 +4937,25 @@ "integrity": "sha1-C+4AUBiusmDQo6865ljdATbsG5k=", "dev": true }, + "forever-agent": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", + "dev": true, + "optional": true + }, + "form-data": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.1.tgz", + "integrity": "sha1-b7lPvXGIUwbXPRXMSX/kzE7NRL8=", + "dev": true, + "optional": true, + "requires": { + "asynckit": "0.4.0", + "combined-stream": "1.0.5", + "mime-types": "2.1.17" + } + }, "formatio": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/formatio/-/formatio-1.2.0.tgz", @@ -5400,6 +5907,39 @@ } } }, + "ftp": { + "version": "0.3.10", + "resolved": "https://registry.npmjs.org/ftp/-/ftp-0.3.10.tgz", + "integrity": "sha1-kZfYYa2BQvPmPVqDv+TFn3MwiF0=", + "dev": true, + "optional": true, + "requires": { + "readable-stream": "1.1.14", + "xregexp": "2.0.0" + }, + "dependencies": { + "readable-stream": { + "version": "1.1.14", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", + "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", + "dev": true, + "optional": true, + "requires": { + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "0.0.1", + "string_decoder": "0.10.31" + } + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true, + "optional": true + } + } + }, "function-bind": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", @@ -5423,6 +5963,23 @@ "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", "dev": true }, + "generate-function": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/generate-function/-/generate-function-2.0.0.tgz", + "integrity": "sha1-aFj+fAlpt9TpCTM3ZHrHn2DfvnQ=", + "dev": true, + "optional": true + }, + "generate-object-property": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/generate-object-property/-/generate-object-property-1.2.0.tgz", + "integrity": "sha1-nA4cQDCM6AT0eDYYuTf6iPmdUNA=", + "dev": true, + "optional": true, + "requires": { + "is-property": "1.0.2" + } + }, "get-caller-file": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.2.tgz", @@ -5447,6 +6004,31 @@ "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", "dev": true }, + "get-uri": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/get-uri/-/get-uri-2.0.1.tgz", + "integrity": "sha512-7aelVrYqCLuVjq2kEKRTH8fXPTC0xKTkM+G7UlFkEwCXY3sFbSxvY375JoFowOAYbkaU47SrBvOefUlLZZ+6QA==", + "dev": true, + "optional": true, + "requires": { + "data-uri-to-buffer": "1.2.0", + "debug": "2.6.9", + "extend": "3.0.1", + "file-uri-to-path": "1.0.0", + "ftp": "0.3.10", + "readable-stream": "2.3.3" + } + }, + "getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "1.0.0" + } + }, "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", @@ -5595,6 +6177,24 @@ } } }, + "har-schema": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", + "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", + "dev": true, + "optional": true + }, + "har-validator": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", + "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", + "dev": true, + "optional": true, + "requires": { + "ajv": "5.5.2", + "har-schema": "2.0.0" + } + }, "has": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/has/-/has-1.0.1.tgz", @@ -5613,13 +6213,21 @@ "ansi-regex": "2.1.1" } }, - "has-binary": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/has-binary/-/has-binary-0.1.7.tgz", - "integrity": "sha1-aOYesWIQyVRaClzOBqhzkS/h5ow=", + "has-binary2": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-binary2/-/has-binary2-1.0.2.tgz", + "integrity": "sha1-6D26SfC5vk0CbSc2U1DZ8D9Uvpg=", "dev": true, "requires": { - "isarray": "0.0.1" + "isarray": "2.0.1" + }, + "dependencies": { + "isarray": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.1.tgz", + "integrity": "sha1-o32U7ZzaLVmGXJ92/llu4fM4dB4=", + "dev": true + } } }, "has-cors": { @@ -5653,12 +6261,36 @@ "minimalistic-assert": "1.0.0" } }, + "hawk": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", + "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", + "dev": true, + "optional": true, + "requires": { + "boom": "4.3.1", + "cryptiles": "3.1.2", + "hoek": "4.2.0", + "sntp": "2.1.0" + } + }, "he": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", "dev": true }, + "hipchat-notifier": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/hipchat-notifier/-/hipchat-notifier-1.1.0.tgz", + "integrity": "sha1-ttJJdVQ3wZEII2d5nTupoPI7Ix4=", + "dev": true, + "optional": true, + "requires": { + "lodash": "4.17.4", + "request": "2.83.0" + } + }, "history": { "version": "4.7.2", "resolved": "https://registry.npmjs.org/history/-/history-4.7.2.tgz", @@ -5682,6 +6314,12 @@ "minimalistic-crypto-utils": "1.0.1" } }, + "hoek": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz", + "integrity": "sha512-v0XCLxICi9nPfYrS9RL8HbYnXi9obYAeLbSP00BmnZwCK9+Ih9WOjoZ8YoHCoav2csqn4FOz4Orldsy2dmDwmQ==", + "dev": true + }, "hoist-non-react-statics": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/hoist-non-react-statics/-/hoist-non-react-statics-2.3.1.tgz", @@ -5795,6 +6433,12 @@ } } }, + "htmlescape": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/htmlescape/-/htmlescape-1.1.1.tgz", + "integrity": "sha1-OgPtwiFLyjtmQko+eVk0lQnLA1E=", + "dev": true + }, "htmlparser2": { "version": "3.9.2", "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-3.9.2.tgz", @@ -5843,6 +6487,17 @@ "requires-port": "1.0.0" } }, + "http-proxy-agent": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-1.0.0.tgz", + "integrity": "sha1-zBzjjkU7+YSg93AtLdWcc9CBKEo=", + "dev": true, + "requires": { + "agent-base": "2.1.1", + "debug": "2.6.9", + "extend": "3.0.1" + } + }, "http-proxy-middleware": { "version": "0.17.4", "resolved": "https://registry.npmjs.org/http-proxy-middleware/-/http-proxy-middleware-0.17.4.tgz", @@ -5872,12 +6527,59 @@ } } }, + "http-signature": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", + "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "1.0.0", + "jsprim": "1.4.1", + "sshpk": "1.13.1" + } + }, + "httpntlm": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/httpntlm/-/httpntlm-1.6.1.tgz", + "integrity": "sha1-rQFScUOi6Hc8+uapb1hla7UqNLI=", + "dev": true, + "requires": { + "httpreq": "0.4.24", + "underscore": "1.7.0" + }, + "dependencies": { + "underscore": { + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.7.0.tgz", + "integrity": "sha1-a7rwh3UA02vjTsqlhODbn+8DUgk=", + "dev": true + } + } + }, + "httpreq": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/httpreq/-/httpreq-0.4.24.tgz", + "integrity": "sha1-QzX/2CzZaWaKOUZckprGHWOTYn8=", + "dev": true + }, "https-browserify": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/https-browserify/-/https-browserify-1.0.0.tgz", "integrity": "sha1-7AbBDgo0wPL68Zn3/X/Hj//QPHM=", "dev": true }, + "https-proxy-agent": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-1.0.0.tgz", + "integrity": "sha1-NffabEjOTdv6JkiRrFk+5f+GceY=", + "dev": true, + "requires": { + "agent-base": "2.1.1", + "debug": "2.6.9", + "extend": "3.0.1" + } + }, "husky": { "version": "0.14.3", "resolved": "https://registry.npmjs.org/husky/-/husky-0.14.3.tgz", @@ -5966,6 +6668,13 @@ "integrity": "sha1-gtwzbSMrkGIXnQWrMpOmYFn9Q10=", "dev": true }, + "inflection": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/inflection/-/inflection-1.10.0.tgz", + "integrity": "sha1-W//LEZetPoEFD44X4hZoCH7p6y8=", + "dev": true, + "optional": true + }, "inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", @@ -5982,6 +6691,15 @@ "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=", "dev": true }, + "inline-source-map": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/inline-source-map/-/inline-source-map-0.6.2.tgz", + "integrity": "sha1-+Tk0ccGKedFyT4Y/o4tYY3Ct4qU=", + "dev": true, + "requires": { + "source-map": "0.5.7" + } + }, "inquirer": { "version": "3.3.0", "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", @@ -6050,49 +6768,110 @@ } } }, - "internal-ip": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/internal-ip/-/internal-ip-1.2.0.tgz", - "integrity": "sha1-rp+/k7mEh4eF1QqN4bNWlWBYz1w=", + "insert-module-globals": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/insert-module-globals/-/insert-module-globals-7.0.1.tgz", + "integrity": "sha1-wDv04BywhtW15azorQr+eInWOMM=", "dev": true, "requires": { - "meow": "3.7.0" - } - }, - "interpret": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz", - "integrity": "sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=", - "dev": true - }, - "invariant": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.2.tgz", - "integrity": "sha1-nh9WrArNtr8wMwbzOL47IErmA2A=", - "requires": { - "loose-envify": "1.3.1" - } - }, - "invert-kv": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", - "dev": true - }, - "ip": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.5.tgz", - "integrity": "sha1-vd7XARQpCCjAoDnnLvJfWq7ENUo=", - "dev": true - }, - "ipaddr.js": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.5.2.tgz", - "integrity": "sha1-1LUFvemUaYfM8PxY2QEP+WB+P6A=", - "dev": true - }, - "is-absolute-url": { - "version": "2.1.0", + "JSONStream": "1.3.2", + "combine-source-map": "0.7.2", + "concat-stream": "1.5.2", + "is-buffer": "1.1.5", + "lexical-scope": "1.2.0", + "process": "0.11.10", + "through2": "2.0.3", + "xtend": "4.0.1" + }, + "dependencies": { + "concat-stream": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.5.2.tgz", + "integrity": "sha1-cIl4Yk2FavQaWnQd790mHadSwmY=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.0.6", + "typedarray": "0.0.6" + } + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "process": { + "version": "0.11.10", + "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", + "integrity": "sha1-czIwDoQBYb2j5podHZGn1LwW8YI=", + "dev": true + }, + "readable-stream": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.0.6.tgz", + "integrity": "sha1-j5A0HmilPMySh4jaz80Rs265t44=", + "dev": true, + "requires": { + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "1.0.7", + "string_decoder": "0.10.31", + "util-deprecate": "1.0.2" + } + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true + } + } + }, + "internal-ip": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/internal-ip/-/internal-ip-1.2.0.tgz", + "integrity": "sha1-rp+/k7mEh4eF1QqN4bNWlWBYz1w=", + "dev": true, + "requires": { + "meow": "3.7.0" + } + }, + "interpret": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz", + "integrity": "sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=", + "dev": true + }, + "invariant": { + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.2.tgz", + "integrity": "sha1-nh9WrArNtr8wMwbzOL47IErmA2A=", + "requires": { + "loose-envify": "1.3.1" + } + }, + "invert-kv": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", + "dev": true + }, + "ip": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.5.tgz", + "integrity": "sha1-vd7XARQpCCjAoDnnLvJfWq7ENUo=", + "dev": true + }, + "ipaddr.js": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.5.2.tgz", + "integrity": "sha1-1LUFvemUaYfM8PxY2QEP+WB+P6A=", + "dev": true + }, + "is-absolute-url": { + "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-absolute-url/-/is-absolute-url-2.1.0.tgz", "integrity": "sha1-UFMN+4T8yap9vnhS6Do3uTufKqY=", "dev": true @@ -6239,6 +7018,19 @@ "integrity": "sha1-bghLvJIGH7sJcexYts5tQE4k2mk=", "dev": true }, + "is-my-json-valid": { + "version": "2.17.1", + "resolved": "https://registry.npmjs.org/is-my-json-valid/-/is-my-json-valid-2.17.1.tgz", + "integrity": "sha512-Q2khNw+oBlWuaYvEEHtKSw/pCxD2L5Rc1C+UQme9X6JdRDh7m5D7HkozA0qa3DUkQ6VzCnEm8mVIQPyIRkI5sQ==", + "dev": true, + "optional": true, + "requires": { + "generate-function": "2.0.0", + "generate-object-property": "1.2.0", + "jsonpointer": "4.0.1", + "xtend": "4.0.1" + } + }, "is-number": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", @@ -6302,6 +7094,13 @@ "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", "dev": true }, + "is-property": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-property/-/is-property-1.0.2.tgz", + "integrity": "sha1-V/4cTkhHTt1lsJkR8msc1Ald2oQ=", + "dev": true, + "optional": true + }, "is-regex": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", @@ -6358,6 +7157,13 @@ "integrity": "sha1-PMWfAAJRlLarLjjbrmaJJWtmBXI=", "dev": true }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true, + "optional": true + }, "is-utf8": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", @@ -6437,6 +7243,13 @@ "whatwg-fetch": "2.0.3" } }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true, + "optional": true + }, "istanbul": { "version": "0.4.5", "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.4.5.tgz", @@ -6537,6 +7350,13 @@ "esprima": "2.7.3" } }, + "jsbn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", + "dev": true, + "optional": true + }, "jsesc": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", @@ -6555,17 +7375,39 @@ "integrity": "sha512-xyQpxeWWMKyJps9CuGJYeng6ssI5bpqS9ltQpdVQ90t4ql6NdnxFKh95JcRt2cun/DjMVNrdjniLPuMA69xmCw==", "dev": true }, + "json-schema": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", + "dev": true, + "optional": true + }, "json-schema-traverse": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" }, + "json-stable-stringify": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-0.0.1.tgz", + "integrity": "sha1-YRwj6BTbN1Un34URk9tZ3Sryf0U=", + "dev": true, + "requires": { + "jsonify": "0.0.0" + } + }, "json-stable-stringify-without-jsonify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", "dev": true }, + "json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", + "dev": true + }, "json3": { "version": "3.3.2", "resolved": "https://registry.npmjs.org/json3/-/json3-3.3.2.tgz", @@ -6587,6 +7429,38 @@ "graceful-fs": "4.1.11" } }, + "jsonify": { + "version": "0.0.0", + "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", + "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", + "dev": true + }, + "jsonparse": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/jsonparse/-/jsonparse-1.3.1.tgz", + "integrity": "sha1-P02uSpH6wxX3EGL4UhzCOfE2YoA=", + "dev": true + }, + "jsonpointer": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-4.0.1.tgz", + "integrity": "sha1-T9kss04OnbPInIYi7PUfm5eMbLk=", + "dev": true, + "optional": true + }, + "jsprim": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", + "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "1.0.0", + "extsprintf": "1.3.0", + "json-schema": "0.2.3", + "verror": "1.10.0" + } + }, "jstransform": { "version": "11.0.3", "resolved": "https://registry.npmjs.org/jstransform/-/jstransform-11.0.3.tgz", @@ -6639,18 +7513,19 @@ "dev": true }, "karma": { - "version": "1.7.1", - "resolved": "https://registry.npmjs.org/karma/-/karma-1.7.1.tgz", - "integrity": "sha512-k5pBjHDhmkdaUccnC7gE3mBzZjcxyxYsYVaqiL2G5AqlfLyBO5nw2VdNK+O16cveEPd/gIOWULH7gkiYYwVNHg==", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/karma/-/karma-2.0.0.tgz", + "integrity": "sha512-K9Kjp8CldLyL9ANSUctDyxC7zH3hpqXj/K09qVf06K3T/kXaHtFZ5tQciK7OzQu68FLvI89Na510kqQ2LCbpIw==", "dev": true, "requires": { "bluebird": "3.5.0", "body-parser": "1.18.2", + "browserify": "14.5.0", "chokidar": "1.7.0", "colors": "1.1.2", "combine-lists": "1.0.1", "connect": "3.6.5", - "core-js": "2.5.1", + "core-js": "2.5.3", "di": "0.0.1", "dom-serialize": "2.2.1", "expand-braces": "0.1.2", @@ -6658,8 +7533,8 @@ "graceful-fs": "4.1.11", "http-proxy": "1.16.2", "isbinaryfile": "3.0.2", - "lodash": "3.10.1", - "log4js": "0.6.38", + "lodash": "4.17.4", + "log4js": "2.4.1", "mime": "1.4.1", "minimatch": "3.0.4", "optimist": "0.6.1", @@ -6667,32 +7542,23 @@ "range-parser": "1.2.0", "rimraf": "2.6.2", "safe-buffer": "5.1.1", - "socket.io": "1.7.3", - "source-map": "0.5.7", - "tmp": "0.0.31", + "socket.io": "2.0.4", + "source-map": "0.6.1", + "tmp": "0.0.33", "useragent": "2.2.1" }, "dependencies": { "core-js": { - "version": "2.5.1", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.1.tgz", - "integrity": "sha1-rmh03GaTd4m4B1T/VCjfZoGcpQs=", + "version": "2.5.3", + "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.3.tgz", + "integrity": "sha1-isw4NFgk8W2DZbfJtCWRaOjtYD4=", "dev": true }, - "lodash": { - "version": "3.10.1", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-3.10.1.tgz", - "integrity": "sha1-W/Rejkm6QYnhfUgnid/RW9FAt7Y=", + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", "dev": true - }, - "tmp": { - "version": "0.0.31", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.31.tgz", - "integrity": "sha1-jzirlDjhcxXl29izZX6L+yd65Kc=", - "dev": true, - "requires": { - "os-tmpdir": "1.0.2" - } } } }, @@ -6876,6 +7742,17 @@ "integrity": "sha512-LOS0CoS8zcZnB1EjLw4LLqDXw8nvt3AGH5dXLQP3D9O1nLLA+9GC5GnPl5mmF+JiQAtSX4VyZC7KvEtcA4kUtA==", "dev": true }, + "labeled-stream-splicer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/labeled-stream-splicer/-/labeled-stream-splicer-2.0.0.tgz", + "integrity": "sha1-pS4dE4AkwAuGscDJH2d5GLiuClk=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "isarray": "0.0.1", + "stream-splicer": "2.0.0" + } + }, "lazy-cache": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", @@ -6901,6 +7778,46 @@ "type-check": "0.3.2" } }, + "lexical-scope": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/lexical-scope/-/lexical-scope-1.2.0.tgz", + "integrity": "sha1-/Ope3HBKSzqHls3KQZw6CvryLfQ=", + "dev": true, + "requires": { + "astw": "2.2.0" + } + }, + "libbase64": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/libbase64/-/libbase64-0.1.0.tgz", + "integrity": "sha1-YjUag5VjrF/1vSbxL2Dpgwu3UeY=", + "dev": true + }, + "libmime": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/libmime/-/libmime-3.0.0.tgz", + "integrity": "sha1-UaGp50SOy9Ms2lRCFnW7IbwJPaY=", + "dev": true, + "requires": { + "iconv-lite": "0.4.15", + "libbase64": "0.1.0", + "libqp": "1.1.0" + }, + "dependencies": { + "iconv-lite": { + "version": "0.4.15", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.15.tgz", + "integrity": "sha1-/iZaIYrGpXz+hUkn6dBMGYJe3es=", + "dev": true + } + } + }, + "libqp": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/libqp/-/libqp-1.1.0.tgz", + "integrity": "sha1-9ebgatdLeU+1tbZpiL9yjvHe2+g=", + "dev": true + }, "load-json-file": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", @@ -7068,38 +7985,203 @@ } }, "log4js": { - "version": "0.6.38", - "resolved": "https://registry.npmjs.org/log4js/-/log4js-0.6.38.tgz", - "integrity": "sha1-LElBFmldb7JUgJQ9P8hy5mKlIv0=", + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/log4js/-/log4js-2.4.1.tgz", + "integrity": "sha512-GohFT8UU/Mq++o2NAp87r6cZi4bCNT4inPimRBWa+ewd6PVeA5xJTNmgdEcSYDOXzxk7hCyLh0gmpJNEPgLS+g==", "dev": true, "requires": { - "readable-stream": "1.0.34", - "semver": "4.3.6" + "axios": "0.15.3", + "circular-json": "0.4.0", + "date-format": "1.2.0", + "debug": "3.1.0", + "hipchat-notifier": "1.1.0", + "loggly": "1.1.1", + "mailgun-js": "0.7.15", + "nodemailer": "2.7.2", + "redis": "2.8.0", + "semver": "5.4.1", + "slack-node": "0.2.0", + "streamroller": "0.7.0" }, "dependencies": { - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", + "circular-json": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/circular-json/-/circular-json-0.4.0.tgz", + "integrity": "sha512-tKV502ADgm9Z37s6B1QOohegjJJrCl2iyMMb1+8ITHrh1fquW8Jdbkb4s5r4Iwutr1UfL1qvkqvc1wZZlLvwow==", + "dev": true + }, + "debug": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "dev": true, "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" + "ms": "2.0.0" } + } + } + }, + "loggly": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/loggly/-/loggly-1.1.1.tgz", + "integrity": "sha1-Cg/B0/o6XsRP3HuJe+uipGlc6+4=", + "dev": true, + "optional": true, + "requires": { + "json-stringify-safe": "5.0.1", + "request": "2.75.0", + "timespan": "2.3.0" + }, + "dependencies": { + "assert-plus": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", + "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=", + "dev": true, + "optional": true }, - "semver": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/semver/-/semver-4.3.6.tgz", - "integrity": "sha1-MAvG4OhjdPe6YQaLWx7NV/xlMto=", - "dev": true + "aws-sign2": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", + "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=", + "dev": true, + "optional": true }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "boom": { + "version": "2.10.1", + "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", + "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", + "dev": true, + "requires": { + "hoek": "2.16.3" + } + }, + "caseless": { + "version": "0.11.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.11.0.tgz", + "integrity": "sha1-cVuW6phBWTzDMGeSP17GDr2k99c=", + "dev": true, + "optional": true + }, + "cryptiles": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", + "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", + "dev": true, + "optional": true, + "requires": { + "boom": "2.10.1" + } + }, + "form-data": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.0.0.tgz", + "integrity": "sha1-bwrrrcxdoWwT4ezBETfYX5uIOyU=", + "dev": true, + "optional": true, + "requires": { + "asynckit": "0.4.0", + "combined-stream": "1.0.5", + "mime-types": "2.1.17" + } + }, + "har-validator": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-2.0.6.tgz", + "integrity": "sha1-zcvAgYgmWtEZtqWnyKtw7s+10n0=", + "dev": true, + "optional": true, + "requires": { + "chalk": "1.1.3", + "commander": "2.11.0", + "is-my-json-valid": "2.17.1", + "pinkie-promise": "2.0.1" + } + }, + "hawk": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", + "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", + "dev": true, + "optional": true, + "requires": { + "boom": "2.10.1", + "cryptiles": "2.0.5", + "hoek": "2.16.3", + "sntp": "1.0.9" + } + }, + "hoek": { + "version": "2.16.3", + "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", + "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=", "dev": true + }, + "http-signature": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", + "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "0.2.0", + "jsprim": "1.4.1", + "sshpk": "1.13.1" + } + }, + "qs": { + "version": "6.2.3", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.2.3.tgz", + "integrity": "sha1-HPyyXBCpsrSDBT/zn138kjOQjP4=", + "dev": true, + "optional": true + }, + "request": { + "version": "2.75.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.75.0.tgz", + "integrity": "sha1-0rgmiihtoT6qXQGt9dGMyQ9lfZM=", + "dev": true, + "optional": true, + "requires": { + "aws-sign2": "0.6.0", + "aws4": "1.6.0", + "bl": "1.1.2", + "caseless": "0.11.0", + "combined-stream": "1.0.5", + "extend": "3.0.1", + "forever-agent": "0.6.1", + "form-data": "2.0.0", + "har-validator": "2.0.6", + "hawk": "3.1.3", + "http-signature": "1.1.1", + "is-typedarray": "1.0.0", + "isstream": "0.1.2", + "json-stringify-safe": "5.0.1", + "mime-types": "2.1.17", + "node-uuid": "1.4.8", + "oauth-sign": "0.8.2", + "qs": "6.2.3", + "stringstream": "0.0.5", + "tough-cookie": "2.3.3", + "tunnel-agent": "0.4.3" + } + }, + "sntp": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", + "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", + "dev": true, + "optional": true, + "requires": { + "hoek": "2.16.3" + } + }, + "tunnel-agent": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.4.3.tgz", + "integrity": "sha1-Y3PbdpCf5XDgjXNYM2Xtgop07us=", + "dev": true, + "optional": true } } }, @@ -7167,6 +8249,83 @@ "integrity": "sha1-WQTcU3w57G2+/q6QIycTX6hRHxI=", "dev": true }, + "mailcomposer": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/mailcomposer/-/mailcomposer-4.0.1.tgz", + "integrity": "sha1-DhxEsqB890DuF9wUm6AJ8Zyt/rQ=", + "dev": true, + "optional": true, + "requires": { + "buildmail": "4.0.1", + "libmime": "3.0.0" + } + }, + "mailgun-js": { + "version": "0.7.15", + "resolved": "https://registry.npmjs.org/mailgun-js/-/mailgun-js-0.7.15.tgz", + "integrity": "sha1-7jZqINrGTDwVwD1sGz4O15UlKrs=", + "dev": true, + "optional": true, + "requires": { + "async": "2.1.5", + "debug": "2.2.0", + "form-data": "2.1.4", + "inflection": "1.10.0", + "is-stream": "1.1.0", + "path-proxy": "1.0.0", + "proxy-agent": "2.0.0", + "q": "1.4.1", + "tsscmp": "1.0.5" + }, + "dependencies": { + "async": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/async/-/async-2.1.5.tgz", + "integrity": "sha1-5YfGhYCZSsZ/xW/4bTrFa9voELw=", + "dev": true, + "optional": true, + "requires": { + "lodash": "4.17.4" + } + }, + "debug": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", + "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", + "dev": true, + "optional": true, + "requires": { + "ms": "0.7.1" + } + }, + "form-data": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", + "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", + "dev": true, + "optional": true, + "requires": { + "asynckit": "0.4.0", + "combined-stream": "1.0.5", + "mime-types": "2.1.17" + } + }, + "ms": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", + "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", + "dev": true, + "optional": true + }, + "q": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/q/-/q-1.4.1.tgz", + "integrity": "sha1-VXBbzZPF82c1MMLCy8DCs63cKG4=", + "dev": true, + "optional": true + } + } + }, "make-dir": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.0.0.tgz", @@ -7458,6 +8617,70 @@ } } }, + "module-deps": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/module-deps/-/module-deps-4.1.1.tgz", + "integrity": "sha1-IyFYM/HaE/1gbMuAh7RIUty4If0=", + "dev": true, + "requires": { + "JSONStream": "1.3.2", + "browser-resolve": "1.11.2", + "cached-path-relative": "1.0.1", + "concat-stream": "1.5.2", + "defined": "1.0.0", + "detective": "4.5.0", + "duplexer2": "0.1.4", + "inherits": "2.0.3", + "parents": "1.0.1", + "readable-stream": "2.3.3", + "resolve": "1.4.0", + "stream-combiner2": "1.1.1", + "subarg": "1.0.0", + "through2": "2.0.3", + "xtend": "4.0.1" + }, + "dependencies": { + "concat-stream": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.5.2.tgz", + "integrity": "sha1-cIl4Yk2FavQaWnQd790mHadSwmY=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.0.6", + "typedarray": "0.0.6" + }, + "dependencies": { + "readable-stream": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.0.6.tgz", + "integrity": "sha1-j5A0HmilPMySh4jaz80Rs265t44=", + "dev": true, + "requires": { + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "1.0.7", + "string_decoder": "0.10.31", + "util-deprecate": "1.0.2" + } + } + } + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "string_decoder": { + "version": "0.10.31", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", + "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", + "dev": true + } + } + }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", @@ -7525,6 +8748,13 @@ "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=", "dev": true }, + "netmask": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/netmask/-/netmask-1.0.6.tgz", + "integrity": "sha1-ICl+idhvb2QA8lDZ9Pa0wZRfzTU=", + "dev": true, + "optional": true + }, "nise": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/nise/-/nise-1.2.0.tgz", @@ -7609,6 +8839,98 @@ } } }, + "node-uuid": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/node-uuid/-/node-uuid-1.4.8.tgz", + "integrity": "sha1-sEDrCSOWivq/jTL7HxfxFn/auQc=", + "dev": true, + "optional": true + }, + "nodemailer": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/nodemailer/-/nodemailer-2.7.2.tgz", + "integrity": "sha1-8kLmSa7q45tsftdA73sGHEBNMPk=", + "dev": true, + "optional": true, + "requires": { + "libmime": "3.0.0", + "mailcomposer": "4.0.1", + "nodemailer-direct-transport": "3.3.2", + "nodemailer-shared": "1.1.0", + "nodemailer-smtp-pool": "2.8.2", + "nodemailer-smtp-transport": "2.7.2", + "socks": "1.1.9" + }, + "dependencies": { + "socks": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/socks/-/socks-1.1.9.tgz", + "integrity": "sha1-Yo1+TQSRJDVEWsC25Fk3bLPm1pE=", + "dev": true, + "optional": true, + "requires": { + "ip": "1.1.5", + "smart-buffer": "1.1.15" + } + } + } + }, + "nodemailer-direct-transport": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/nodemailer-direct-transport/-/nodemailer-direct-transport-3.3.2.tgz", + "integrity": "sha1-6W+vuQNYVglH5WkBfZfmBzilCoY=", + "dev": true, + "optional": true, + "requires": { + "nodemailer-shared": "1.1.0", + "smtp-connection": "2.12.0" + } + }, + "nodemailer-fetch": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/nodemailer-fetch/-/nodemailer-fetch-1.6.0.tgz", + "integrity": "sha1-ecSQihwPXzdbc/6IjamCj23JY6Q=", + "dev": true + }, + "nodemailer-shared": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/nodemailer-shared/-/nodemailer-shared-1.1.0.tgz", + "integrity": "sha1-z1mU4v0mjQD1zw+nZ6CBae2wfsA=", + "dev": true, + "requires": { + "nodemailer-fetch": "1.6.0" + } + }, + "nodemailer-smtp-pool": { + "version": "2.8.2", + "resolved": "https://registry.npmjs.org/nodemailer-smtp-pool/-/nodemailer-smtp-pool-2.8.2.tgz", + "integrity": "sha1-LrlNbPhXgLG0clzoU7nL1ejajHI=", + "dev": true, + "optional": true, + "requires": { + "nodemailer-shared": "1.1.0", + "nodemailer-wellknown": "0.1.10", + "smtp-connection": "2.12.0" + } + }, + "nodemailer-smtp-transport": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/nodemailer-smtp-transport/-/nodemailer-smtp-transport-2.7.2.tgz", + "integrity": "sha1-A9ccdjFPFKx9vHvwM6am0W1n+3c=", + "dev": true, + "optional": true, + "requires": { + "nodemailer-shared": "1.1.0", + "nodemailer-wellknown": "0.1.10", + "smtp-connection": "2.12.0" + } + }, + "nodemailer-wellknown": { + "version": "0.1.10", + "resolved": "https://registry.npmjs.org/nodemailer-wellknown/-/nodemailer-wellknown-0.1.10.tgz", + "integrity": "sha1-WG24EB2zDLRDjrVGc3pBqtDPE9U=", + "dev": true + }, "nomnom": { "version": "1.6.2", "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.6.2.tgz", @@ -7717,6 +9039,13 @@ "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", "dev": true }, + "oauth-sign": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", + "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=", + "dev": true, + "optional": true + }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", @@ -7871,12 +9200,6 @@ "wordwrap": "1.0.0" } }, - "options": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/options/-/options-0.0.6.tgz", - "integrity": "sha1-7CLTEoBrtT5zF3Pnza788cZDEo8=", - "dev": true - }, "ora": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/ora/-/ora-1.3.0.tgz", @@ -7977,6 +9300,54 @@ "integrity": "sha512-r6zKACMNhjPJMTl8KcFH4li//gkrXWfbD6feV8l6doRHlzljFWGJ2AP6iKaCJXyZmAUMOPtvbW7EXkbWO/pLEA==", "dev": true }, + "pac-proxy-agent": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/pac-proxy-agent/-/pac-proxy-agent-1.1.0.tgz", + "integrity": "sha512-QBELCWyLYPgE2Gj+4wUEiMscHrQ8nRPBzYItQNOHWavwBt25ohZHQC4qnd5IszdVVrFbLsQ+dPkm6eqdjJAmwQ==", + "dev": true, + "optional": true, + "requires": { + "agent-base": "2.1.1", + "debug": "2.6.9", + "extend": "3.0.1", + "get-uri": "2.0.1", + "http-proxy-agent": "1.0.0", + "https-proxy-agent": "1.0.0", + "pac-resolver": "2.0.0", + "raw-body": "2.3.2", + "socks-proxy-agent": "2.1.1" + } + }, + "pac-resolver": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pac-resolver/-/pac-resolver-2.0.0.tgz", + "integrity": "sha1-mbiNLxk/ve78HJpSnB8yYKtSd80=", + "dev": true, + "optional": true, + "requires": { + "co": "3.0.6", + "degenerator": "1.0.4", + "ip": "1.0.1", + "netmask": "1.0.6", + "thunkify": "2.1.2" + }, + "dependencies": { + "co": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/co/-/co-3.0.6.tgz", + "integrity": "sha1-FEXyJsXrlWE45oyawwFn6n0ua9o=", + "dev": true, + "optional": true + }, + "ip": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/ip/-/ip-1.0.1.tgz", + "integrity": "sha1-x+NWzeoiWucbNtcPLnGpK6TkJZA=", + "dev": true, + "optional": true + } + } + }, "pako": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/pako/-/pako-1.0.6.tgz", @@ -7992,6 +9363,15 @@ "no-case": "2.3.2" } }, + "parents": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parents/-/parents-1.0.1.tgz", + "integrity": "sha1-/t1NK/GTp3dF/nHjcdc8MwfZx1E=", + "dev": true, + "requires": { + "path-platform": "0.11.15" + } + }, "parse-asn1": { "version": "5.1.0", "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.0.tgz", @@ -8049,15 +9429,6 @@ "@types/node": "8.0.52" } }, - "parsejson": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/parsejson/-/parsejson-0.0.3.tgz", - "integrity": "sha1-q343WfIJ7OmUN5c/fQ8fZK4OZKs=", - "dev": true, - "requires": { - "better-assert": "1.0.2" - } - }, "parseqs": { "version": "0.0.5", "resolved": "https://registry.npmjs.org/parseqs/-/parseqs-0.0.5.tgz", @@ -8118,6 +9489,31 @@ "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=", "dev": true }, + "path-platform": { + "version": "0.11.15", + "resolved": "https://registry.npmjs.org/path-platform/-/path-platform-0.11.15.tgz", + "integrity": "sha1-6GQhf3TDaFDwhSt43Hv31KVyG/I=", + "dev": true + }, + "path-proxy": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/path-proxy/-/path-proxy-1.0.0.tgz", + "integrity": "sha1-GOijaFn8nS8aU7SN7hOFQ8Ag3l4=", + "dev": true, + "optional": true, + "requires": { + "inflection": "1.3.8" + }, + "dependencies": { + "inflection": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/inflection/-/inflection-1.3.8.tgz", + "integrity": "sha1-y9Fg2p91sUw8xjV41POWeEvzAU4=", + "dev": true, + "optional": true + } + } + }, "path-to-regexp": { "version": "1.7.0", "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-1.7.0.tgz", @@ -10283,6 +11679,32 @@ "ipaddr.js": "1.5.2" } }, + "proxy-agent": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/proxy-agent/-/proxy-agent-2.0.0.tgz", + "integrity": "sha1-V+tTR6qAXXTsaByyVknbo5yTNJk=", + "dev": true, + "optional": true, + "requires": { + "agent-base": "2.1.1", + "debug": "2.6.9", + "extend": "3.0.1", + "http-proxy-agent": "1.0.0", + "https-proxy-agent": "1.0.0", + "lru-cache": "2.6.5", + "pac-proxy-agent": "1.1.0", + "socks-proxy-agent": "2.1.1" + }, + "dependencies": { + "lru-cache": { + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.6.5.tgz", + "integrity": "sha1-5W1jVBSO3o13B7WNFDIg/QjfD9U=", + "dev": true, + "optional": true + } + } + }, "prr": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/prr/-/prr-0.0.0.tgz", @@ -10652,6 +12074,15 @@ "pify": "2.3.0" } }, + "read-only-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/read-only-stream/-/read-only-stream-2.0.0.tgz", + "integrity": "sha1-JyT9aoET1zdkrCiNQ4YnDB2/F/A=", + "dev": true, + "requires": { + "readable-stream": "2.3.3" + } + }, "read-pkg": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", @@ -10782,6 +12213,32 @@ } } }, + "redis": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/redis/-/redis-2.8.0.tgz", + "integrity": "sha512-M1OkonEQwtRmZv4tEWF2VgpG0JWJ8Fv1PhlgT5+B+uNq2cA3Rt1Yt/ryoR+vQNOQcIEgdCdfH0jr3bDpihAw1A==", + "dev": true, + "optional": true, + "requires": { + "double-ended-queue": "2.1.0-0", + "redis-commands": "1.3.1", + "redis-parser": "2.6.0" + } + }, + "redis-commands": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/redis-commands/-/redis-commands-1.3.1.tgz", + "integrity": "sha1-gdgm9F+pyLIBH0zXoP5ZfSQdRCs=", + "dev": true, + "optional": true + }, + "redis-parser": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/redis-parser/-/redis-parser-2.6.0.tgz", + "integrity": "sha1-Uu0J2srBCPGmMcB+m2mUHnoZUEs=", + "dev": true, + "optional": true + }, "reduce-css-calc": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/reduce-css-calc/-/reduce-css-calc-1.3.0.tgz", @@ -11070,21 +12527,74 @@ "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", "dev": true }, - "repeating": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", - "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", + "repeating": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", + "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", + "dev": true, + "requires": { + "is-finite": "1.0.2" + } + }, + "replace-ext": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", + "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", + "dev": true + }, + "request": { + "version": "2.83.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.83.0.tgz", + "integrity": "sha512-lR3gD69osqm6EYLk9wB/G1W/laGWjzH90t1vEa2xuxHD5KUrSzp9pUSfTm+YC5Nxt2T8nMPEvKlhbQayU7bgFw==", + "dev": true, + "optional": true, + "requires": { + "aws-sign2": "0.7.0", + "aws4": "1.6.0", + "caseless": "0.12.0", + "combined-stream": "1.0.5", + "extend": "3.0.1", + "forever-agent": "0.6.1", + "form-data": "2.3.1", + "har-validator": "5.0.3", + "hawk": "6.0.2", + "http-signature": "1.2.0", + "is-typedarray": "1.0.0", + "isstream": "0.1.2", + "json-stringify-safe": "5.0.1", + "mime-types": "2.1.17", + "oauth-sign": "0.8.2", + "performance-now": "2.1.0", + "qs": "6.5.1", + "safe-buffer": "5.1.1", + "stringstream": "0.0.5", + "tough-cookie": "2.3.3", + "tunnel-agent": "0.6.0", + "uuid": "3.1.0" + }, + "dependencies": { + "uuid": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz", + "integrity": "sha512-DIWtzUkw04M4k3bf1IcpS2tngXEL26YUD2M0tMDUpnUrz2hgzUBlD55a4FjdLGPvfHxS6uluGWvaVEqgBcVa+g==", + "dev": true, + "optional": true + } + } + }, + "requestretry": { + "version": "1.12.2", + "resolved": "https://registry.npmjs.org/requestretry/-/requestretry-1.12.2.tgz", + "integrity": "sha512-wDYnH4imurLs5upu31WoPaOFfEu31qhFlF7KgpYbBsmBagFmreZZo8E/XpoQ3erCP5za+72t8k8QI4wlrtwVXw==", "dev": true, + "optional": true, "requires": { - "is-finite": "1.0.2" + "extend": "3.0.1", + "lodash": "4.17.4", + "request": "2.83.0", + "when": "3.7.8" } }, - "replace-ext": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", - "dev": true - }, "require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", @@ -11403,6 +12913,16 @@ "safe-buffer": "5.1.1" } }, + "shasum": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/shasum/-/shasum-1.0.2.tgz", + "integrity": "sha1-5wEjENj0F/TetXEhUOVni4euVl8=", + "dev": true, + "requires": { + "json-stable-stringify": "0.0.1", + "sha.js": "2.4.9" + } + }, "shebang-command": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", @@ -11418,6 +12938,18 @@ "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", "dev": true }, + "shell-quote": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.6.1.tgz", + "integrity": "sha1-9HgZSczkAmlxJ0MOo7PFR29IF2c=", + "dev": true, + "requires": { + "array-filter": "0.0.1", + "array-map": "0.0.0", + "array-reduce": "0.0.0", + "jsonify": "0.0.0" + } + }, "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", @@ -11479,6 +13011,16 @@ } } }, + "slack-node": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/slack-node/-/slack-node-0.2.0.tgz", + "integrity": "sha1-3kuN3aqLeT9h29KTgQT9q/N9+jA=", + "dev": true, + "optional": true, + "requires": { + "requestretry": "1.12.2" + } + }, "slash": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", @@ -11494,138 +13036,88 @@ "is-fullwidth-code-point": "2.0.0" } }, - "socket.io": { - "version": "1.7.3", - "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-1.7.3.tgz", - "integrity": "sha1-uK+cq6AJSeVo42nxMn6pvp6iRhs=", + "smart-buffer": { + "version": "1.1.15", + "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-1.1.15.tgz", + "integrity": "sha1-fxFLW2X6s+KjWqd1uxLw0cZJvxY=", + "dev": true + }, + "smtp-connection": { + "version": "2.12.0", + "resolved": "https://registry.npmjs.org/smtp-connection/-/smtp-connection-2.12.0.tgz", + "integrity": "sha1-1275EnyyPCJZ7bHoNJwujV4tdME=", "dev": true, "requires": { - "debug": "2.3.3", - "engine.io": "1.8.3", - "has-binary": "0.1.7", - "object-assign": "4.1.0", - "socket.io-adapter": "0.5.0", - "socket.io-client": "1.7.3", - "socket.io-parser": "2.3.1" - }, - "dependencies": { - "debug": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.3.3.tgz", - "integrity": "sha1-QMRT5n5uE8kB3ewxeviYbNqe/4w=", - "dev": true, - "requires": { - "ms": "0.7.2" - } - }, - "ms": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.2.tgz", - "integrity": "sha1-riXPJRKziFodldfwN4aNhDESR2U=", - "dev": true - }, - "object-assign": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.0.tgz", - "integrity": "sha1-ejs9DpgGPUP0wD8uiubNUahog6A=", - "dev": true - } + "httpntlm": "1.6.1", + "nodemailer-shared": "1.1.0" } }, - "socket.io-adapter": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-0.5.0.tgz", - "integrity": "sha1-y21LuL7IHhB4uZZ3+c7QBGBmu4s=", + "sntp": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", + "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", "dev": true, + "optional": true, "requires": { - "debug": "2.3.3", - "socket.io-parser": "2.3.1" - }, - "dependencies": { - "debug": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.3.3.tgz", - "integrity": "sha1-QMRT5n5uE8kB3ewxeviYbNqe/4w=", - "dev": true, - "requires": { - "ms": "0.7.2" - } - }, - "ms": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.2.tgz", - "integrity": "sha1-riXPJRKziFodldfwN4aNhDESR2U=", - "dev": true - } + "hoek": "4.2.0" } }, + "socket.io": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/socket.io/-/socket.io-2.0.4.tgz", + "integrity": "sha1-waRZDO/4fs8TxyZS8Eb3FrKeYBQ=", + "dev": true, + "requires": { + "debug": "2.6.9", + "engine.io": "3.1.4", + "socket.io-adapter": "1.1.1", + "socket.io-client": "2.0.4", + "socket.io-parser": "3.1.2" + } + }, + "socket.io-adapter": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/socket.io-adapter/-/socket.io-adapter-1.1.1.tgz", + "integrity": "sha1-KoBeihTWNyEk3ZFZrUUC+MsH8Gs=", + "dev": true + }, "socket.io-client": { - "version": "1.7.3", - "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-1.7.3.tgz", - "integrity": "sha1-sw6GqhDV7zVGYBwJzeR2Xjgdo3c=", + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/socket.io-client/-/socket.io-client-2.0.4.tgz", + "integrity": "sha1-CRilUkBtxeVAs4Dc2Xr8SmQzL44=", "dev": true, "requires": { "backo2": "1.0.2", + "base64-arraybuffer": "0.1.5", "component-bind": "1.0.0", "component-emitter": "1.2.1", - "debug": "2.3.3", - "engine.io-client": "1.8.3", - "has-binary": "0.1.7", + "debug": "2.6.9", + "engine.io-client": "3.1.4", + "has-cors": "1.1.0", "indexof": "0.0.1", "object-component": "0.0.3", + "parseqs": "0.0.5", "parseuri": "0.0.5", - "socket.io-parser": "2.3.1", + "socket.io-parser": "3.1.2", "to-array": "0.1.4" - }, - "dependencies": { - "component-emitter": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", - "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", - "dev": true - }, - "debug": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.3.3.tgz", - "integrity": "sha1-QMRT5n5uE8kB3ewxeviYbNqe/4w=", - "dev": true, - "requires": { - "ms": "0.7.2" - } - }, - "ms": { - "version": "0.7.2", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.2.tgz", - "integrity": "sha1-riXPJRKziFodldfwN4aNhDESR2U=", - "dev": true - } } }, "socket.io-parser": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-2.3.1.tgz", - "integrity": "sha1-3VMgJRA85Clpcya+/WQAX8/ltKA=", + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/socket.io-parser/-/socket.io-parser-3.1.2.tgz", + "integrity": "sha1-28IoIVH8T6675Aru3Ady66YZ9/I=", "dev": true, "requires": { - "component-emitter": "1.1.2", - "debug": "2.2.0", - "isarray": "0.0.1", - "json3": "3.3.2" + "component-emitter": "1.2.1", + "debug": "2.6.9", + "has-binary2": "1.0.2", + "isarray": "2.0.1" }, "dependencies": { - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", + "isarray": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.1.tgz", + "integrity": "sha1-o32U7ZzaLVmGXJ92/llu4fM4dB4=", "dev": true } } @@ -11665,6 +13157,27 @@ } } }, + "socks": { + "version": "1.1.10", + "resolved": "https://registry.npmjs.org/socks/-/socks-1.1.10.tgz", + "integrity": "sha1-W4t/x8jzQcU+0FbpKbe/Tei6e1o=", + "dev": true, + "requires": { + "ip": "1.1.5", + "smart-buffer": "1.1.15" + } + }, + "socks-proxy-agent": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/socks-proxy-agent/-/socks-proxy-agent-2.1.1.tgz", + "integrity": "sha512-sFtmYqdUK5dAMh85H0LEVFUCO7OhJJe1/z2x/Z6mxp3s7/QPf1RkZmpZy+BpuU0bEjcV9npqKjq9Y3kwFUjnxw==", + "dev": true, + "requires": { + "agent-base": "2.1.1", + "extend": "3.0.1", + "socks": "1.1.10" + } + }, "sort-keys": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-1.1.2.tgz", @@ -11774,6 +13287,23 @@ "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, + "sshpk": { + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.13.1.tgz", + "integrity": "sha1-US322mKHFEMW3EwY/hzx2UBzm+M=", + "dev": true, + "optional": true, + "requires": { + "asn1": "0.2.3", + "assert-plus": "1.0.0", + "bcrypt-pbkdf": "1.0.1", + "dashdash": "1.14.1", + "ecc-jsbn": "0.1.1", + "getpass": "0.1.7", + "jsbn": "0.1.1", + "tweetnacl": "0.14.5" + } + }, "stackframe": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/stackframe/-/stackframe-0.3.1.tgz", @@ -11802,6 +13332,16 @@ "readable-stream": "2.3.3" } }, + "stream-combiner2": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/stream-combiner2/-/stream-combiner2-1.1.1.tgz", + "integrity": "sha1-+02KFCDqNidk4hrUeAOXvry0HL4=", + "dev": true, + "requires": { + "duplexer2": "0.1.4", + "readable-stream": "2.3.3" + } + }, "stream-http": { "version": "2.7.2", "resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.7.2.tgz", @@ -11815,6 +13355,39 @@ "xtend": "4.0.1" } }, + "stream-splicer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/stream-splicer/-/stream-splicer-2.0.0.tgz", + "integrity": "sha1-G2O+Q4oTPktnHMGTUZdgAXWRDYM=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, + "streamroller": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/streamroller/-/streamroller-0.7.0.tgz", + "integrity": "sha512-WREzfy0r0zUqp3lGO096wRuUp7ho1X6uo/7DJfTlEi0Iv/4gT7YHqXDjKC2ioVGBZtE8QzsQD9nx1nIuoZ57jQ==", + "dev": true, + "requires": { + "date-format": "1.2.0", + "debug": "3.1.0", + "mkdirp": "0.5.1", + "readable-stream": "2.3.3" + }, + "dependencies": { + "debug": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + } + } + }, "strict-uri-encode": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", @@ -11869,6 +13442,13 @@ "is-hexadecimal": "1.0.1" } }, + "stringstream": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", + "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=", + "dev": true, + "optional": true + }, "strip-ansi": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", @@ -12273,6 +13853,23 @@ "stylelint-config-recommended": "2.0.0" } }, + "subarg": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/subarg/-/subarg-1.0.0.tgz", + "integrity": "sha1-9izxdYHplrSPyWVpn1TAauJouNI=", + "dev": true, + "requires": { + "minimist": "1.2.0" + }, + "dependencies": { + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true + } + } + }, "sugarss": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/sugarss/-/sugarss-1.0.1.tgz", @@ -12339,6 +13936,23 @@ "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.4.tgz", "integrity": "sha1-Kb9hXUqnEhvdiYsi1LP5vE4qoD0=" }, + "syntax-error": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/syntax-error/-/syntax-error-1.3.0.tgz", + "integrity": "sha1-HtkmbE1AvnXcVb+bsct3Biu5bKE=", + "dev": true, + "requires": { + "acorn": "4.0.13" + }, + "dependencies": { + "acorn": { + "version": "4.0.13", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-4.0.13.tgz", + "integrity": "sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c=", + "dev": true + } + } + }, "table": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/table/-/table-4.0.2.tgz", @@ -12421,6 +14035,23 @@ "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", "dev": true }, + "through2": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", + "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", + "dev": true, + "requires": { + "readable-stream": "2.3.3", + "xtend": "4.0.1" + } + }, + "thunkify": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/thunkify/-/thunkify-2.1.2.tgz", + "integrity": "sha1-+qDp0jDFGsyVyhOjYawFyn4EVT0=", + "dev": true, + "optional": true + }, "thunky": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/thunky/-/thunky-0.1.0.tgz", @@ -12442,6 +14073,13 @@ "setimmediate": "1.0.5" } }, + "timespan": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/timespan/-/timespan-2.3.0.tgz", + "integrity": "sha1-SQLOBAvRPYRcj1myfp1ZutbzmSk=", + "dev": true, + "optional": true + }, "tmp": { "version": "0.0.33", "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", @@ -12475,6 +14113,16 @@ "integrity": "sha1-wxdI5V0hDv/AD9zcfW5o19e7nOw=", "dev": true }, + "tough-cookie": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.3.tgz", + "integrity": "sha1-C2GKVWW23qkL80JdBNVe3EdadWE=", + "dev": true, + "optional": true, + "requires": { + "punycode": "1.4.1" + } + }, "trim": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", @@ -12511,12 +14159,36 @@ "integrity": "sha1-OTvnMKlEb9Hq1tpZoBQwjzbCics=", "dev": true }, + "tsscmp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.5.tgz", + "integrity": "sha1-fcSjOvcVgatDN9qR2FylQn69mpc=", + "dev": true, + "optional": true + }, "tty-browserify": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/tty-browserify/-/tty-browserify-0.0.0.tgz", "integrity": "sha1-oVe6QC2iTpv5V/mqadUk7tQpAaY=", "dev": true }, + "tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, + "optional": true, + "requires": { + "safe-buffer": "5.1.1" + } + }, + "tweetnacl": { + "version": "0.14.5", + "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", + "dev": true, + "optional": true + }, "type-check": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", @@ -12595,9 +14267,15 @@ } }, "ultron": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.0.2.tgz", - "integrity": "sha1-rOEWq1V80Zc4ak6I9GhTeMiy5Po=", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", + "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==", + "dev": true + }, + "umd": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/umd/-/umd-3.0.1.tgz", + "integrity": "sha1-iuVW4RAR9jwllnCKiDclnwGz1g4=", "dev": true }, "underscore": { @@ -12823,6 +14501,13 @@ "integrity": "sha1-Z+LoY3lyFVMN/zGOW/nc6/1Hsho=", "dev": true }, + "uws": { + "version": "0.14.5", + "resolved": "https://registry.npmjs.org/uws/-/uws-0.14.5.tgz", + "integrity": "sha1-Z6rzPEaypYel9mZtAPdpEyjxSdw=", + "dev": true, + "optional": true + }, "validate-npm-package-license": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", @@ -12850,6 +14535,18 @@ "integrity": "sha1-N61zyO5Bf7PVgOeFMSMH0nSEfyI=", "dev": true }, + "verror": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", + "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "dev": true, + "optional": true, + "requires": { + "assert-plus": "1.0.0", + "core-util-is": "1.0.2", + "extsprintf": "1.3.0" + } + }, "vfile": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/vfile/-/vfile-2.3.0.tgz", @@ -13380,6 +15077,13 @@ "resolved": "https://registry.npmjs.org/whatwg-fetch/-/whatwg-fetch-2.0.3.tgz", "integrity": "sha1-nITsLc9oGH/wC8ZOEnS0QhduHIQ=" }, + "when": { + "version": "3.7.8", + "resolved": "https://registry.npmjs.org/when/-/when-3.7.8.tgz", + "integrity": "sha1-xxMLan6gRpPoQs3J56Hyqjmjn4I=", + "dev": true, + "optional": true + }, "whet.extend": { "version": "0.9.9", "resolved": "https://registry.npmjs.org/whet.extend/-/whet.extend-0.9.9.tgz", @@ -13471,21 +15175,16 @@ } }, "ws": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/ws/-/ws-1.1.2.tgz", - "integrity": "sha1-iiRPoFJAHgjJiGz0SoUYnh/UBn8=", + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", + "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", "dev": true, "requires": { - "options": "0.0.6", - "ultron": "1.0.2" + "async-limiter": "1.0.0", + "safe-buffer": "5.1.1", + "ultron": "1.1.1" } }, - "wtf-8": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/wtf-8/-/wtf-8-1.0.0.tgz", - "integrity": "sha1-OS2LotDxw00e4tYw8V0O+2jhBIo=", - "dev": true - }, "x-is-function": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/x-is-function/-/x-is-function-1.0.4.tgz", @@ -13510,11 +15209,18 @@ "integrity": "sha1-Z/4HXFwk/vOfnWX197f+dRcZaPw=" }, "xmlhttprequest-ssl": { - "version": "1.5.3", - "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-1.5.3.tgz", - "integrity": "sha1-GFqIjATspGw+QHDZn3tJ3jUomS0=", + "version": "1.5.4", + "resolved": "https://registry.npmjs.org/xmlhttprequest-ssl/-/xmlhttprequest-ssl-1.5.4.tgz", + "integrity": "sha1-BPVgkVcks4kIhxXMDteBPpZ3v1c=", "dev": true }, + "xregexp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/xregexp/-/xregexp-2.0.0.tgz", + "integrity": "sha1-UqY+VsoLhKfzpfPWGHLxJq16WUM=", + "dev": true, + "optional": true + }, "xtend": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", diff --git a/package.json b/package.json index ead67e0..f8721a1 100644 --- a/package.json +++ b/package.json @@ -26,7 +26,7 @@ "babel-eslint": "^8.0.3", "babel-loader": "^7.1.2", "babel-plugin-dynamic-import-webpack": "^1.0.2", - "babel-plugin-flow-react-proptypes": "^12.1.0", + "babel-plugin-flow-react-proptypes": "^13.0.0", "babel-plugin-istanbul": "^4.1.5", "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-syntax-object-rest-spread": "^6.13.0", @@ -36,7 +36,7 @@ "babel-preset-react": "^6.24.1", "chai": "^4.1.2", "chai-enzyme": "^1.0.0-beta.0", - "cross-env": "^5.1.1", + "cross-env": "^5.1.3", "css-loader": "^0.28.7", "enzyme": "^3.2.0", "enzyme-adapter-react-16": "^1.1.1", @@ -49,7 +49,7 @@ "html-webpack-harddisk-plugin": "^0.1.0", "html-webpack-plugin": "^2.30.1", "husky": "^0.14.3", - "karma": "^1.7.1", + "karma": "^2.0.0", "karma-chrome-launcher": "^2.2.0", "karma-coverage": "^1.1.1", "karma-firefox-launcher": "^1.1.0", -- GitLab From d64d1ae48dd0353d5585e1d87354d68df41361aa Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Fri, 22 Dec 2017 11:11:00 +0100 Subject: [PATCH 11/51] add block creation func via svg context menu & mouse puck, d3 handler regen --- src/components/ToolchainBlock.jsx | 2 + src/components/ToolchainConnection.jsx | 1 + src/components/ToolchainEditor.jsx | 242 ++++++++++++++++++++----- 3 files changed, 203 insertions(+), 42 deletions(-) diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index c0d93a4..c96392e 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -93,6 +93,8 @@ class ToolchainBlock extends React.PureComponent { fill={color} onClick={e => { this.props.openEditor(); + e.stopPropagation(); + e.preventDefault(); }} /> diff --git a/src/components/ToolchainConnection.jsx b/src/components/ToolchainConnection.jsx index 142e4d5..0931806 100644 --- a/src/components/ToolchainConnection.jsx +++ b/src/components/ToolchainConnection.jsx @@ -43,6 +43,7 @@ class ToolchainConnection extends React.PureComponent { connection={this.props.connection} collect={(props) => ({ connection: props.connection })} renderTag='g' + attributes={{className: 'tcConnection'}} > { diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index bb895f4..6598b9c 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -34,7 +34,7 @@ import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; import { nameValidator } from '@helpers/beat'; import type { BeatObject } from '@helpers/beat'; -import { changeObjFieldName } from '@helpers'; +import { changeObjFieldName, generateNewKey } from '@helpers'; import * as Selectors from '@store/selectors.js'; @@ -64,6 +64,10 @@ type State = { name: string, active: boolean, }, + svgActionLocation: { + x: number, + y: number, + } }; const getValidObj = (data = {}) => { @@ -103,10 +107,14 @@ export class ToolchainEditor extends React.Component { state = { cache: getValidObj(this.props.data), - zoomLevel: 2000, + zoomLevel: 3000, modalBlockInfo: { active: false, }, + svgActionLocation: { + x: -1, + y: -1, + } } componentWillReceiveProps (nextProps: Props) { @@ -308,6 +316,37 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } + addBlock = (blockName: string, set: BlockSet, x: number, y: number) => { + console.log(blockName); + const newBlock = { + name: blockName, + synchronized_channel: Object.keys(this.state.cache.contents.representation.channel_colors)[0] + }; + if(set === 'blocks' || set === 'analyzers'){ + newBlock.inputs = []; + } + if(set === 'blocks' || set === 'datasets'){ + newBlock.outputs = []; + } + + const rep = {...this.state.cache.contents.representation}; + + rep.blocks[blockName] = { + col: x, + row: y, + height: 3, + width: 6, + }; + + const newContents = { + [set]: [...this.state.cache.contents[set], newBlock], + representation: rep, + }; + + this.setContents(newContents); + this.initD3Drag(); + } + addBlockIO = (blockName: string, set: BlockSet, ioType: 'input' | 'output', newName: string) => { const newContents = { [set]: this.state.cache.contents[set].map(s => { @@ -325,6 +364,8 @@ export class ToolchainEditor extends React.Component { }; this.setContents(newContents); + if(ioType === 'output') + this.initD3Connections(); } deleteBlock = (blockName: string, set: BlockSet) => { @@ -415,6 +456,19 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } + triggerSvgAction = (x: number, y: number, clickEvent: any) => { + this.setState({ + ...this.state, + svgActionLocation: { + x, + y, + } + }); + + if(this.svgContextMenu) + this.svgContextMenu.handleContextClick(clickEvent); + } + // generates a map of the location (and sizes) of all blocks, inputs, & outputs on the graphical editor. // necessary to draw lines between connected outputs & inputs. getLocationMap = (): {} => { @@ -471,8 +525,7 @@ export class ToolchainEditor extends React.Component { ; } - // initializes d3 behaviours (most SVG interactions) - initD3 = () => { + initD3Drag = () => { // dragging blocks around setTimeout(() => { const updateBlockLocation = this.updateBlockLocation; @@ -527,6 +580,9 @@ export class ToolchainEditor extends React.Component { ); }, 50); + }; + + initD3Connections = () => { // creating connections setTimeout(() => { //const updateBlockLocation = this.updateBlockLocation; @@ -576,10 +632,69 @@ export class ToolchainEditor extends React.Component { .on('drag', dragged) ); }, 50); - }; + } + + initD3MouseMovement = () => { + // mouse movement + setTimeout(() => { + + let cx = 0; + let cy = 0; + + d3.select('svg') + .insert('circle', '.tcConnection') + .attr('id', 'puck') + .attr('class', 'background') + .attr('cx', 0) + .attr('cy', 0) + .attr('r', 5); + + d3.select('svg') + .on('mousemove', () => { + cx = Math.round((d3.event.layerX * (this.state.zoomLevel / 3000)) / distanceFactor) * 20; + cy = Math.round((d3.event.layerY * (this.state.zoomLevel / 3000)) / distanceFactor) * 20; + d3.select('#puck') + .attr('cx', cx) + .attr('cy', cy) + ; + }) + .on('click', () => { + if(!Array.from(d3.event.target.classList).includes('background')) + return; + this.triggerSvgAction(cx / distanceFactor, cy / distanceFactor, d3.event); + }) + ; + }, 50); + } + // initializes d3 behaviours (most SVG interactions) componentDidMount = () => { - this.initD3(); + this.initD3Drag(); + this.initD3Connections(); + this.initD3MouseMovement(); + } + + svgContextMenu = null; + + handleSvgContextMenu = (e: any, data: { clicked: string }) => { + const { clicked } = data; + let newBlockName = ''; + switch(clicked){ + case 'addBlock': + newBlockName = generateNewKey('block', this.state.cache.contents.blocks.map(b => b.name)); + this.addBlock(newBlockName, 'blocks', this.state.svgActionLocation.x, this.state.svgActionLocation.y); + break; + case 'addDataset': + newBlockName = generateNewKey('dataset', this.state.cache.contents.datasets.map(b => b.name)); + this.addBlock(newBlockName, 'datasets', this.state.svgActionLocation.x, this.state.svgActionLocation.y); + break; + case 'addAnalyzer': + newBlockName = generateNewKey('analyzer', this.state.cache.contents.analyzers.map(b => b.name)); + this.addBlock(newBlockName, 'analyzers', this.state.svgActionLocation.x, this.state.svgActionLocation.y); + break; + default: + break; + } } renderGraphicalEditor = () => { @@ -617,12 +732,34 @@ export class ToolchainEditor extends React.Component { width={svgWidth} height={svgHeight} viewBox={this.getSvgViewBox()} + style={{cursor: 'pointer'}} > - + this.svgContextMenu = e} + attributes={{ + onContextMenu: (e) => { + e.stopPropagation(); + e.preventDefault(); + } + }} + > + + + { [...Array(Math.round(svgHeight / gridY))].map((u, i) => { return ( { [...Array(Math.round(svgWidth / gridX))].map((u, i) => { return ( { name, active: true, }; - console.log(newMBI); + //console.log(newMBI); this.setState({ ...this.state, modalBlockInfo: newMBI, @@ -706,42 +844,62 @@ export class ToolchainEditor extends React.Component { + + { + const {name, set, clicked} = data; + switch(clicked){ + case 'delete': + this.deleteBlock(name, set); + break; + default: + break; + } + }} + > + Delete Block + + + + { + const {connection, clicked} = data; + switch(clicked){ + case 'delete': + this.deleteConnection(connection); + break; + default: + break; + } + }} + > + Delete Connection + + + + + Add Block + + + Add Dataset + + + Add Analyzer + + - - { - const {name, set, clicked} = data; - switch(clicked){ - case 'delete': - this.deleteBlock(name, set); - break; - default: - break; - } - }} - > - Delete Block - - - - { - const {connection, clicked} = data; - switch(clicked){ - case 'delete': - this.deleteConnection(connection); - break; - default: - break; - } - }} - > - Delete Connection - - ); } -- GitLab From aae3a82b912b687a6dfc56eaf71b90323bc9d491 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 2 Jan 2018 17:36:39 +0100 Subject: [PATCH 12/51] update deps --- package-lock.json | 269 ++++++++++++++++++++++++++++------------------ package.json | 18 ++-- 2 files changed, 173 insertions(+), 114 deletions(-) diff --git a/package-lock.json b/package-lock.json index 9548fdf..b630c3a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -146,9 +146,9 @@ } }, "@types/node": { - "version": "8.0.52", - "resolved": "https://registry.npmjs.org/@types/node/-/node-8.0.52.tgz", - "integrity": "sha512-wOU/VRodnI/4Chxuu6R6bcyN9aE3rztO0i8R76PZO7+DxTXWy60nseGN4ujspucmxrfj5mzgCYPXiXqrD6KC3Q==", + "version": "8.5.2", + "resolved": "https://registry.npmjs.org/@types/node/-/node-8.5.2.tgz", + "integrity": "sha512-KA4GKOpgXnrqEH2eCVhiv2CsxgXGQJgV1X0vsGlh+WCnxbeAE1GT44ZsTU1IN5dEeV/gDupKa7gWo08V5IxWVQ==", "dev": true }, "JSONStream": { @@ -645,15 +645,17 @@ } }, "babel-eslint": { - "version": "8.0.3", - "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.0.3.tgz", - "integrity": "sha512-7D4iUpylEiKJPGbeSAlNddGcmA41PadgZ6UAb6JVyh003h3d0EbZusYFBR/+nBgqtaVJM2J2zUVa3N0hrpMH6g==", + "version": "8.1.2", + "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.1.2.tgz", + "integrity": "sha512-IE+glF8t0lLoldylN7JyR8gT7e3jwyuNH2ds8g3UVUwGob/U4iT7Xpsiq2kQ8QGLb0eX4RcQXNqeW6mgPysu9A==", "dev": true, "requires": { "@babel/code-frame": "7.0.0-beta.31", "@babel/traverse": "7.0.0-beta.31", "@babel/types": "7.0.0-beta.31", - "babylon": "7.0.0-beta.31" + "babylon": "7.0.0-beta.31", + "eslint-scope": "3.7.1", + "eslint-visitor-keys": "1.0.0" }, "dependencies": { "babylon": { @@ -895,9 +897,9 @@ } }, "babel-plugin-flow-react-proptypes": { - "version": "13.0.0", - "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-13.0.0.tgz", - "integrity": "sha512-km7Jrt2mkavHIUOneZoSXYrozTT5NZTplReZ6lUprqv9zGkFkmrY6mem5+MaPNk+NwU2ff7vR5ComleYkrk0pA==", + "version": "13.0.1", + "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-13.0.1.tgz", + "integrity": "sha512-notPlr8BYsWuavjRuqIxUYs8G8Spwc0wYG+WrdXIPlJMnu6/UktgBQKxppMn6kczKIGAtYJvSoZkcp5Fm5BqYQ==", "dev": true, "requires": { "babel-core": "6.26.0", @@ -1736,9 +1738,9 @@ } }, "bootstrap": { - "version": "4.0.0-beta.2", - "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.0.0-beta.2.tgz", - "integrity": "sha512-DzGtdTlKbrMoGMpz0LigKSqJ+MgtFKxA791PU/q062OlRG0HybNZcTLH7rpDAmLS66Y3esN9yzKHLLbqa5UR3w==" + "version": "4.0.0-beta.3", + "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.0.0-beta.3.tgz", + "integrity": "sha512-/Qe1Q2d1muLEZRX2iCteMQHZBBAm6ZIjJ9FcBYK/xLr05+HvDtBOVBN+Cz7mCNZuy0zr+y5artZHM05W7mIz6g==" }, "brace-expansion": { "version": "1.1.8", @@ -3068,9 +3070,9 @@ } }, "d3": { - "version": "4.12.0", - "resolved": "https://registry.npmjs.org/d3/-/d3-4.12.0.tgz", - "integrity": "sha512-ibAzFJrj1uuX+wIy29baTx9JebA5i670UKlp+H3c9pg0w8PKl8jpj4zf64MmLPVBXm2vA1i29obnWuM/rmyfWA==", + "version": "4.12.2", + "resolved": "https://registry.npmjs.org/d3/-/d3-4.12.2.tgz", + "integrity": "sha512-aKAlpgTmpuGeEpezB+GvPpX1x+gCMs/PHpuse6sCpkgw4Un3ZeqUobIc87eIy9adcl+wxPAnEyKyO5oulH3MOw==", "requires": { "d3-array": "1.2.1", "d3-axis": "1.0.8", @@ -3084,7 +3086,7 @@ "d3-ease": "1.0.3", "d3-force": "1.1.0", "d3-format": "1.2.1", - "d3-geo": "1.9.0", + "d3-geo": "1.9.1", "d3-hierarchy": "1.1.5", "d3-interpolate": "1.1.6", "d3-path": "1.0.5", @@ -3191,9 +3193,9 @@ "integrity": "sha512-U4zRVLDXW61bmqoo+OJ/V687e1T5nVd3TAKAJKgtpZ/P1JsMgyod0y9br+mlQOryTAACdiXI3wCjuERHFNp91w==" }, "d3-geo": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/d3-geo/-/d3-geo-1.9.0.tgz", - "integrity": "sha512-94YbAT+q5E/p+XEd4VKiNkQNicrrON3l6eoW70sC8aHjUGoBDJ/Ht8Z/hvhGJJTi2zhYBvUd34Mfqv4TG7we9A==", + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/d3-geo/-/d3-geo-1.9.1.tgz", + "integrity": "sha512-l9wL/cEQkyZQYXw3xbmLsH3eQ5ij+icNfo4r0GrLa5rOCZR/e/3am45IQ0FvQ5uMsv+77zBRunLc9ufTWSQYFA==", "requires": { "d3-array": "1.2.1" } @@ -3890,22 +3892,41 @@ } }, "enzyme": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/enzyme/-/enzyme-3.2.0.tgz", - "integrity": "sha512-l0HcjycivXjB4IXkwuRc1K5z8hzWIVZB2b/Y/H2bao9eFTpBz4ACOwAQf44SgG5Nu3d1jF41LasxDgFWZeeysA==", + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/enzyme/-/enzyme-3.3.0.tgz", + "integrity": "sha512-l8csyPyLmtxskTz6pX9W8eDOyH1ckEtDttXk/vlFWCjv00SkjTjtoUrogqp4yEvMyneU9dUJoOLnqFoiHb8IHA==", "dev": true, "requires": { "cheerio": "1.0.0-rc.2", - "function.prototype.name": "1.0.3", + "function.prototype.name": "1.1.0", "has": "1.0.1", + "is-boolean-object": "1.0.0", + "is-callable": "1.1.3", + "is-number-object": "1.0.3", + "is-string": "1.0.4", "is-subset": "0.1.1", "lodash": "4.17.4", + "object-inspect": "1.5.0", "object-is": "1.0.1", - "object.assign": "4.0.4", + "object.assign": "4.1.0", "object.entries": "1.0.4", "object.values": "1.0.4", "raf": "3.4.0", "rst-selector-parser": "2.2.3" + }, + "dependencies": { + "object.assign": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.0.tgz", + "integrity": "sha512-exHJeq6kBKj58mqGyTQ9DFvrZC/eR6OwxzoM9YRoGBqrXYonaFyGiFMuc9VZrXf7DarreEwMpurG3dd+CNyW5w==", + "dev": true, + "requires": { + "define-properties": "1.1.2", + "function-bind": "1.1.1", + "has-symbols": "1.0.0", + "object-keys": "1.0.11" + } + } } }, "enzyme-adapter-react-16": { @@ -4125,9 +4146,9 @@ } }, "eslint": { - "version": "4.13.1", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.13.1.tgz", - "integrity": "sha512-UCJVV50RtLHYzBp1DZ8CMPtRSg4iVZvjgO9IJHIKyWU/AnJVjtdRikoUPLB29n5pzMB7TnsLQWf0V6VUJfoPfw==", + "version": "4.14.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.14.0.tgz", + "integrity": "sha512-Ul6CSGRjKscEyg0X/EeNs7o2XdnbTEOD1OM8cTjmx85RPcBJQrEhZLevhuJZNAE/vS2iVl5Uhgiqf3h5uLMCJQ==", "dev": true, "requires": { "ajv": "5.5.2", @@ -4138,9 +4159,9 @@ "debug": "3.1.0", "doctrine": "2.0.2", "eslint-scope": "3.7.1", + "eslint-visitor-keys": "1.0.0", "espree": "3.5.2", "esquery": "1.0.0", - "estraverse": "4.2.0", "esutils": "2.0.2", "file-entry-cache": "2.0.0", "functional-red-black-tree": "1.0.1", @@ -4149,7 +4170,7 @@ "ignore": "3.3.7", "imurmurhash": "0.1.4", "inquirer": "3.3.0", - "is-resolvable": "1.0.0", + "is-resolvable": "1.0.1", "js-yaml": "3.10.0", "json-stable-stringify-without-jsonify": "1.0.1", "levn": "0.3.0", @@ -4462,6 +4483,12 @@ "estraverse": "4.2.0" } }, + "eslint-visitor-keys": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.0.0.tgz", + "integrity": "sha512-qzm/XxIbxm/FHyH341ZrbnMUpe+5Bocte9xkmFMzPMjRaZMcXww+MpBptFvtU+79L362nqiLhekCxCxDPaUMBQ==", + "dev": true + }, "espree": { "version": "3.5.2", "resolved": "https://registry.npmjs.org/espree/-/espree-3.5.2.tgz", @@ -4901,9 +4928,9 @@ "dev": true }, "flow-bin": { - "version": "0.61.0", - "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.61.0.tgz", - "integrity": "sha512-w6SGi5CDfKLNGzYssRhW6N37qKclDXijsxDQ5M8c3WbivRYta0Horv22bwakegfKBVDnyeS0lRW3OqBC74eq2g==", + "version": "0.62.0", + "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.62.0.tgz", + "integrity": "sha1-FLymaabj+VwLwMLR61XsTpjLHYM=", "dev": true }, "follow-redirects": { @@ -5947,9 +5974,9 @@ "dev": true }, "function.prototype.name": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.0.3.tgz", - "integrity": "sha512-5EblxZUdioXi2JiMZ9FUbwYj40eQ9MFHyzFLBSPdlRl3SO8l7SLWuAnQ/at/1Wi4hjJwME/C5WpF2ZfAc8nGNw==", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.0.tgz", + "integrity": "sha512-Bs0VRrTz4ghD8pTmbJQD1mZ8A/mN0ur/jGz+A6FBxPDUPkm1tNfF6bhTYPA7i7aF4lZJVr+OXTNNrnnIl58Wfg==", "dev": true, "requires": { "define-properties": "1.1.2", @@ -6242,6 +6269,12 @@ "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", "dev": true }, + "has-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz", + "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=", + "dev": true + }, "hash-base": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", @@ -6616,7 +6649,7 @@ "integrity": "sha1-g/Cg7DeL8yRheLbCrZE28TWxyWI=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "ieee754": { @@ -6913,6 +6946,12 @@ "binary-extensions": "1.10.0" } }, + "is-boolean-object": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.0.0.tgz", + "integrity": "sha1-mPiygDBoQhmpXzdc+9iM40Bd/5M=", + "dev": true + }, "is-buffer": { "version": "1.1.5", "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.5.tgz", @@ -7040,6 +7079,12 @@ "kind-of": "3.2.2" } }, + "is-number-object": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.3.tgz", + "integrity": "sha1-8mWrian0RQNO9q/xWo8AsA9VF5k=", + "dev": true + }, "is-obj": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", @@ -7117,19 +7162,22 @@ "dev": true }, "is-resolvable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-resolvable/-/is-resolvable-1.0.0.tgz", - "integrity": "sha1-jfV8YeouPFAUCNEA+wE8+NbgzGI=", - "dev": true, - "requires": { - "tryit": "1.0.3" - } + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-resolvable/-/is-resolvable-1.0.1.tgz", + "integrity": "sha512-y5CXYbzvB3jTnWAZH1Nl7ykUWb6T3BcTs56HUruwBf8MhF56n1HWqhDWnVFo8GHrUPDgvUUNVhrc2U8W7iqz5g==", + "dev": true }, "is-stream": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, + "is-string": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.4.tgz", + "integrity": "sha1-zDqbaYV9Yh6WNyWiTK7shzuCbmQ=", + "dev": true + }, "is-subset": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/is-subset/-/is-subset-0.1.1.tgz", @@ -8574,9 +8622,9 @@ } }, "mocha": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.0.1.tgz", - "integrity": "sha512-evDmhkoA+cBNiQQQdSKZa2b9+W2mpLoj50367lhy+Klnx9OV8XlCIhigUnn1gaTFLQCa0kdNhEGDr0hCXOQFDw==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", + "integrity": "sha512-0RVnjg1HJsXY2YFDoTNzcc1NKhYuXKRrBAG2gDygmJJA136Cs2QlRliZG1mA0ap7cuaT30mw16luAeln+4RiNA==", "dev": true, "requires": { "browser-stdout": "1.3.0", @@ -9057,6 +9105,12 @@ "integrity": "sha1-8MaapQ78lbhmwYb0AKM3acsvEpE=", "dev": true }, + "object-inspect": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.5.0.tgz", + "integrity": "sha512-UmOFbHbwvv+XHj7BerrhVq+knjceBdkvU5AriwLMvhv2qi+e7DJzxfBeFpILEjVzCp+xA+W/pIf06RGPWlZNfw==", + "dev": true + }, "object-is": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/object-is/-/object-is-1.0.1.tgz", @@ -9426,7 +9480,7 @@ "integrity": "sha512-rgO9Zg5LLLkfJF9E6CCmXlSE4UVceloys8JrFqCcHloC3usd/kJCyPDwH2SOlzix2j3xaP9sUX3e8+kvkuleAA==", "dev": true, "requires": { - "@types/node": "8.0.52" + "@types/node": "8.5.2" } }, "parseqs": { @@ -9586,7 +9640,7 @@ "dev": true, "requires": { "browserslist": "2.4.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "reduce-css-calc": "1.3.0" } }, @@ -9606,7 +9660,7 @@ "dev": true, "requires": { "onecolor": "3.0.4", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "pluralize": { @@ -9632,14 +9686,14 @@ } }, "postcss": { - "version": "6.0.14", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-6.0.14.tgz", - "integrity": "sha512-NJ1z0f+1offCgadPhz+DvGm5Mkci+mmV5BqD13S992o0Xk9eElxUfPPF+t2ksH5R/17gz4xVK8KWocUQ5o3Rog==", + "version": "6.0.15", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-6.0.15.tgz", + "integrity": "sha512-v/SpyMzLbtkmh45zUdaqLAaqXqzPdSrw8p4cQVO0/w6YiYfpj4k+Wkzhn68qk9br+H+0qfddhdPEVnbmBPfXVQ==", "dev": true, "requires": { "chalk": "2.3.0", "source-map": "0.6.1", - "supports-color": "4.5.0" + "supports-color": "5.1.0" }, "dependencies": { "ansi-styles": { @@ -9660,6 +9714,17 @@ "ansi-styles": "3.2.0", "escape-string-regexp": "1.0.5", "supports-color": "4.5.0" + }, + "dependencies": { + "supports-color": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", + "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "dev": true, + "requires": { + "has-flag": "2.0.0" + } + } } }, "source-map": { @@ -9669,9 +9734,9 @@ "dev": true }, "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.1.0.tgz", + "integrity": "sha512-Ry0AwkoKjDpVKK4sV4h6o3UJmNRbjYm2uXhwfj3J56lMVdvnUNqzQVRztOOMGQ++w1K/TjNDFvpJk0F/LoeBCQ==", "dev": true, "requires": { "has-flag": "2.0.0" @@ -9687,7 +9752,7 @@ "requires": { "babel-runtime": "6.26.0", "balanced-match": "0.4.2", - "postcss": "6.0.14" + "postcss": "6.0.15" }, "dependencies": { "balanced-match": { @@ -9704,7 +9769,7 @@ "integrity": "sha1-lNxCLI+QmX8WvTOjZUu77AhJY7Q=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-selector-parser": "2.2.3" } }, @@ -9761,7 +9826,7 @@ "get-stdin": "5.0.1", "globby": "6.1.0", "ora": "1.3.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-load-config": "1.2.0", "postcss-reporter": "5.0.0", "pretty-hrtime": "1.0.3", @@ -9934,7 +9999,7 @@ "dev": true, "requires": { "css-color-function": "1.3.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-message-helpers": "2.0.0", "postcss-value-parser": "3.3.0" } @@ -9946,7 +10011,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-message-helpers": "2.0.0", "reduce-function-call": "1.0.2" }, @@ -9980,7 +10045,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-message-helpers": "2.0.0" }, "dependencies": { @@ -10012,7 +10077,7 @@ "integrity": "sha1-EnA2ZvoxBDDj8wpFTawThjF9WEQ=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0", "units-css": "0.4.0" } @@ -10024,7 +10089,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-message-helpers": "2.0.0", "reduce-function-call": "1.0.2" }, @@ -10057,7 +10122,7 @@ "integrity": "sha1-7rrwPTY7QwC5Z5K9MIHBntZlE9M=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0" } }, @@ -10067,7 +10132,7 @@ "integrity": "sha1-FFOcinExSUtILg3RzCZf9lFLUmM=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0" } }, @@ -10077,7 +10142,7 @@ "integrity": "sha1-N9XJNToHoJJwkSqCYGu0Kg1wLAQ=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0", "rgb-hex": "2.1.0" } @@ -10172,7 +10237,7 @@ "chalk": "2.1.0", "pixrem": "4.0.1", "pleeease-filters": "4.0.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-apply": "0.8.0", "postcss-attribute-case-insensitive": "2.0.0", "postcss-calc": "6.0.0", @@ -10219,7 +10284,7 @@ "caniuse-lite": "1.0.30000741", "normalize-range": "0.1.2", "num2fraction": "1.2.2", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0" } }, @@ -10253,7 +10318,7 @@ "dev": true, "requires": { "css-unit-converter": "1.1.1", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-selector-parser": "2.2.3", "reduce-css-calc": "2.0.5" } @@ -10285,7 +10350,7 @@ "integrity": "sha1-vlMnhBEOyylQRPtTlaGABushpzc=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-custom-properties": { @@ -10295,7 +10360,7 @@ "dev": true, "requires": { "balanced-match": "1.0.0", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-custom-selectors": { @@ -10304,7 +10369,7 @@ "integrity": "sha1-eBOC+UxS5yfvXKR3bqKt9JphE4I=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-selector-matches": "3.0.1" } }, @@ -10545,7 +10610,7 @@ "dev": true, "requires": { "lodash": "4.17.4", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0" } }, @@ -10555,7 +10620,7 @@ "integrity": "sha1-CMzIj2BQuoLtjvLMdsDGprQfGD4=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-html": { @@ -10575,7 +10640,7 @@ "integrity": "sha1-Dxk0E3AM8fgr05Bm7wFtZaShgYE=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-media-query-parser": "0.2.3" } }, @@ -10586,7 +10651,7 @@ "dev": true, "requires": { "lodash.template": "4.4.0", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-less": { @@ -10666,7 +10731,7 @@ "dev": true, "requires": { "loader-utils": "1.1.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-load-config": "1.2.0", "schema-utils": "0.3.0" } @@ -10677,7 +10742,7 @@ "integrity": "sha1-Z1JWA3pD70C8Twdgv9BtTcadSNI=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-media-query-parser": { @@ -10989,7 +11054,7 @@ "integrity": "sha1-thTJcgvmgW6u41+zpfqh26agXds=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-modules-local-by-default": { @@ -10999,7 +11064,7 @@ "dev": true, "requires": { "css-selector-tokenizer": "0.7.0", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-modules-scope": { @@ -11009,7 +11074,7 @@ "dev": true, "requires": { "css-selector-tokenizer": "0.7.0", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-modules-values": { @@ -11019,7 +11084,7 @@ "dev": true, "requires": { "icss-replace-symbols": "1.1.0", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-nesting": { @@ -11028,7 +11093,7 @@ "integrity": "sha512-IkyWXICwagCnlaviRexi7qOdwPw3+xVVjgFfGsxmztvRVaNxAlrypOIKqDE5mxY+BVxnId1rnUKBRQoNE2VDaA==", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-normalize-charset": { @@ -11155,7 +11220,7 @@ "integrity": "sha1-kVKgYT00UHIFE+iJKFS65C0O5o4=", "dev": true, "requires": { - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-selector-parser": "2.2.3" } }, @@ -11165,7 +11230,7 @@ "integrity": "sha1-7vGU6NUkZFylIKlJ6V5RjoEkAss=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-reduce-idents": { @@ -11291,7 +11356,7 @@ "integrity": "sha1-eU22+qVPjbEAhUOSqTr0V2i04ls=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-reporter": { @@ -11303,7 +11368,7 @@ "chalk": "2.1.0", "lodash": "4.17.4", "log-symbols": "2.1.0", - "postcss": "6.0.14" + "postcss": "6.0.15" }, "dependencies": { "ansi-styles": { @@ -11349,7 +11414,7 @@ "integrity": "sha1-t1Pv9sfArqXoN1++TN6L+QY/8UI=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-sass": { @@ -11359,7 +11424,7 @@ "dev": true, "requires": { "gonzales-pe": "4.2.3", - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-scss": { @@ -11368,7 +11433,7 @@ "integrity": "sha1-/0XPM1S4ee6JpOtoaA9GrJuxT5Q=", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "postcss-selector-matches": { @@ -11378,7 +11443,7 @@ "dev": true, "requires": { "balanced-match": "0.4.2", - "postcss": "6.0.14" + "postcss": "6.0.15" }, "dependencies": { "balanced-match": { @@ -11396,7 +11461,7 @@ "dev": true, "requires": { "balanced-match": "0.4.2", - "postcss": "6.0.14" + "postcss": "6.0.15" }, "dependencies": { "balanced-match": { @@ -11427,7 +11492,7 @@ "babel-runtime": "6.26.0", "lodash": "4.17.4", "object-assign": "4.1.1", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-sass": "0.2.0", "postcss-scss": "1.0.2", "postcss-value-parser": "3.3.0", @@ -11452,7 +11517,7 @@ "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } } } @@ -13528,7 +13593,7 @@ "micromatch": "2.3.11", "normalize-selector": "0.2.0", "pify": "3.0.0", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-html": "0.12.0", "postcss-less": "1.1.3", "postcss-media-query-parser": "0.2.3", @@ -13567,7 +13632,7 @@ "caniuse-lite": "1.0.30000783", "normalize-range": "0.1.2", "num2fraction": "1.2.2", - "postcss": "6.0.14", + "postcss": "6.0.15", "postcss-value-parser": "3.3.0" } }, @@ -13876,7 +13941,7 @@ "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", "dev": true, "requires": { - "postcss": "6.0.14" + "postcss": "6.0.15" } }, "supports-color": { @@ -14153,12 +14218,6 @@ "integrity": "sha1-qf2LA5Swro//guBjOgo2zK1bX4Y=", "dev": true }, - "tryit": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/tryit/-/tryit-1.0.3.tgz", - "integrity": "sha1-OTvnMKlEb9Hq1tpZoBQwjzbCics=", - "dev": true - }, "tsscmp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.5.tgz", diff --git a/package.json b/package.json index f8721a1..74ce798 100644 --- a/package.json +++ b/package.json @@ -23,10 +23,10 @@ "license": "MIT", "devDependencies": { "babel-core": "^6.26.0", - "babel-eslint": "^8.0.3", + "babel-eslint": "^8.1.2", "babel-loader": "^7.1.2", "babel-plugin-dynamic-import-webpack": "^1.0.2", - "babel-plugin-flow-react-proptypes": "^13.0.0", + "babel-plugin-flow-react-proptypes": "^13.0.1", "babel-plugin-istanbul": "^4.1.5", "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-syntax-object-rest-spread": "^6.13.0", @@ -38,14 +38,14 @@ "chai-enzyme": "^1.0.0-beta.0", "cross-env": "^5.1.3", "css-loader": "^0.28.7", - "enzyme": "^3.2.0", + "enzyme": "^3.3.0", "enzyme-adapter-react-16": "^1.1.1", - "eslint": "^4.13.1", + "eslint": "^4.14.0", "eslint-plugin-compat": "^2.1.0", "eslint-plugin-flowtype": "^2.40.1", "eslint-plugin-import": "^2.8.0", "eslint-plugin-react": "^7.5.1", - "flow-bin": "^0.61.0", + "flow-bin": "^0.62.0", "html-webpack-harddisk-plugin": "^0.1.0", "html-webpack-plugin": "^2.30.1", "husky": "^0.14.3", @@ -57,8 +57,8 @@ "karma-mocha-reporter": "^2.2.5", "karma-sourcemap-loader": "^0.3.7", "karma-webpack": "^2.0.9", - "mocha": "^4.0.1", - "postcss": "^6.0.14", + "mocha": "^4.1.0", + "postcss": "^6.0.15", "postcss-cli": "^4.1.1", "postcss-cssnext": "^3.0.2", "postcss-loader": "^2.0.9", @@ -79,9 +79,9 @@ }, "dependencies": { "ajv": "^5.5.2", - "bootstrap": "^4.0.0-beta.2", + "bootstrap": "^4.0.0-beta.3", "classnames": "^2.2.5", - "d3": "^4.12.0", + "d3": "^4.12.2", "prop-types": "^15.6.0", "react": "^16.2.0", "react-contextmenu": "^2.9.2", -- GitLab From 0f6cf40f64ea117aead7c1745f05c7c3109e914e Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 2 Jan 2018 17:38:54 +0100 Subject: [PATCH 13/51] add tc editor css, add basic tc sync channel management, make connections easier to work with --- main.jsx | 2 +- src/components/ToolchainBlock.jsx | 24 ++-- src/components/ToolchainConnection.jsx | 26 +++- src/components/ToolchainEditor.css | 31 +++++ src/components/ToolchainEditor.jsx | 171 +++++++++++++++++-------- src/components/ToolchainModal.jsx | 59 ++++++++- src/helpers/index.js | 15 ++- 7 files changed, 248 insertions(+), 80 deletions(-) create mode 100644 src/components/ToolchainEditor.css diff --git a/main.jsx b/main.jsx index 9bd011e..fc895a0 100644 --- a/main.jsx +++ b/main.jsx @@ -1,6 +1,6 @@ // bootstrap first -import 'bootstrap/dist/css/bootstrap.min.css'; import './react-contextmenu.css'; +import 'bootstrap/dist/css/bootstrap.min.css'; // rest of app import React from 'react'; diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index c96392e..e7df3b6 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -46,6 +46,7 @@ type Props = { updateBlockName: (newName: string) => any, updateBlockIOName: (ioType: 'input' | 'output', oldName: string, newName: string) => any, openEditor: () => any, + channelColors: any, }; type State = { @@ -106,6 +107,15 @@ class ToolchainBlock extends React.PureComponent { > { name } + + Synchronized to the {this.props.data.synchronized_channel || name} channel + { inputs.map((inp, i) => { const loc = this.props.locMap.inputs[inp]; @@ -122,17 +132,16 @@ class ToolchainBlock extends React.PureComponent { id={`${ name }-input-${ inp }`} key={i} {...loc} - stroke='black' - fill='transparent' - strokeWidth='5' + fill='black' /> { inp } + { inp } ); @@ -152,17 +161,16 @@ class ToolchainBlock extends React.PureComponent { id={`${ name }-output-${ out }`} key={i} {...loc} - stroke='black' - fill='transparent' - strokeWidth='5' + fill='black' /> { out } + { out } ); diff --git a/src/components/ToolchainConnection.jsx b/src/components/ToolchainConnection.jsx index 0931806..19bd74a 100644 --- a/src/components/ToolchainConnection.jsx +++ b/src/components/ToolchainConnection.jsx @@ -28,10 +28,11 @@ class ToolchainConnection extends React.PureComponent { } render = () => { - const connectionId = `#${ connectionToId(this.props.connection) }`; - const fromInfo = this.props.connection.from.split('.'); - const toInfo = this.props.connection.to.split('.'); - //console.log(`this.props.connectionecting "${ this.props.connectionId }" from ${ fromInfo } to ${ toInfo }`); + const conn = this.props.connection; + const connectionId = `#${ connectionToId(conn) }`; + const fromInfo = conn.from.split('.'); + const toInfo = conn.to.split('.'); + //console.log(`connecting "${ connId }" from ${ fromInfo } to ${ toInfo }`); const fromLoc = this.props.locMap[fromInfo[0]].outputs[fromInfo[1]]; const toLoc = this.props.locMap[toInfo[0]].inputs[toInfo[1]]; if(!fromLoc || !toLoc) @@ -40,7 +41,7 @@ class ToolchainConnection extends React.PureComponent { return ( ({ connection: props.connection })} renderTag='g' attributes={{className: 'tcConnection'}} @@ -50,12 +51,23 @@ class ToolchainConnection extends React.PureComponent { this.setState({ selected: !this.state.selected }); }} id={connectionId} - stroke={this.props.channelColors[this.props.connection.channel]} - strokeWidth={ this.state.selected ? 5 : 2 } + stroke={this.props.channelColors[conn.channel]} + strokeOpacity={0.005} + strokeWidth={10} x1={fromLoc.x} y1={fromLoc.y} x2={toLoc.x} y2={toLoc.y} + > + Connection from {conn.from} to {conn.to} synchronized to the {conn.channel} channel +
+ ); diff --git a/src/components/ToolchainEditor.css b/src/components/ToolchainEditor.css new file mode 100644 index 0000000..bb7bea3 --- /dev/null +++ b/src/components/ToolchainEditor.css @@ -0,0 +1,31 @@ +.tcConnection > line:hover + line, +.tcConnection > line + line:hover { + stroke-width: 5; +} + +.preInline { + display: inline; +} + +.editorWrapper { + display: relative; + height: 500px; + width: 100%; + background-color: grey; +} + +.editorWrapper > div { + display: absolute; + height: 100%; + width: 100%; + background-color: white; + overflow: scroll; +} + +svg { + cursor: pointer; +} + +text:hover { + clip-path: none; +} diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index 6598b9c..b9576f9 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -1,4 +1,5 @@ // @flow +import './ToolchainEditor.css'; import * as React from 'react'; import { Container, @@ -34,7 +35,7 @@ import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; import { nameValidator } from '@helpers/beat'; import type { BeatObject } from '@helpers/beat'; -import { changeObjFieldName, generateNewKey } from '@helpers'; +import { changeObjFieldName, generateNewKey, getRandomBrightColor } from '@helpers'; import * as Selectors from '@store/selectors.js'; @@ -60,8 +61,8 @@ type State = { cache: any, zoomLevel: number, modalBlockInfo: { - set: BlockSet, - name: string, + set?: BlockSet, + name?: string, active: boolean, }, svgActionLocation: { @@ -233,6 +234,11 @@ export class ToolchainEditor extends React.Component { }) .reduce((cs, c) => ({...cs, c}), {}) ; + if(set === 'datasets'){ + rep.channel_colors[newName] = rep.channel_colors[oldName]; + delete rep.channel_colors[oldName]; + } + const newContents = { ...this.state.cache.contents, [set]: this.state.cache.contents[set].map(s => s.name === oldName ? {...s, name: newName} : s), @@ -320,10 +326,10 @@ export class ToolchainEditor extends React.Component { console.log(blockName); const newBlock = { name: blockName, - synchronized_channel: Object.keys(this.state.cache.contents.representation.channel_colors)[0] }; if(set === 'blocks' || set === 'analyzers'){ newBlock.inputs = []; + newBlock.synchronized_channel = Object.keys(this.state.cache.contents.representation.channel_colors)[0]; } if(set === 'blocks' || set === 'datasets'){ newBlock.outputs = []; @@ -338,6 +344,10 @@ export class ToolchainEditor extends React.Component { width: 6, }; + if(set === 'datasets'){ + rep.channel_colors[blockName] = getRandomBrightColor(); + } + const newContents = { [set]: [...this.state.cache.contents[set], newBlock], representation: rep, @@ -456,6 +466,31 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } + updateBlockChannel = (blockName: string, set: BlockSet, channel: string) => { + const newContents = { + ...this.state.cache.contents, + [set]: this.state.cache.contents[set].map(s => { + if(s.name !== blockName) + return s; + const newBlock = { + ...s, + synchronized_channel: channel + }; + return newBlock; + }), + connections: this.state.cache.contents.connections.map(c => { + if(c.from.split('.')[0] !== blockName) + return c; + return { + ...c, + channel, + }; + }), + }; + + this.setContents(newContents); + } + triggerSvgAction = (x: number, y: number, clickEvent: any) => { this.setState({ ...this.state, @@ -494,10 +529,10 @@ export class ToolchainEditor extends React.Component { const locInputs = inputs.map((inp, i) => ({ [inp]: { - x: x - 4, + x: x - 8, y: (y + thinInputHeight) + (i * thinInputHeight) + (thinInputHeight * 0.3), - width: 3, - height: thinInputHeight * 0.5, + width: 8, + height: thinInputHeight * 0.75, } }) ) @@ -506,10 +541,10 @@ export class ToolchainEditor extends React.Component { const locOutputs = outputs.map((out, i) => ({ [out]: { - x: x + blockWidth + 2, + x: x + blockWidth, y: (y + thinInputHeight) + (i * thinInputHeight) + (thinInputHeight * 0.3), - width: 3, - height: thinInputHeight * 0.5, + width: 8, + height: thinInputHeight * 0.75, } }) ) @@ -589,8 +624,15 @@ export class ToolchainEditor extends React.Component { let startId; const createConnection = this.createConnection; const channelColors = this.state.cache.contents.representation.channel_colors; + const contents = this.state.cache.contents; + let startBlock; function startDrag(d) { - startId = d3.select(this).attr('id').replace('-output-', '.'); + const rawId = d3.select(this).attr('id'); + const bName = rawId.split('-output-')[0]; + startId = rawId.replace('-output-', '.'); + startBlock = contents.datasets.find(d => d.name === bName); + if(!startBlock) + startBlock = contents.blocks.find(d => d.name === bName); d3.select('svg') .append('line') .classed('tmp', true) @@ -616,7 +658,7 @@ export class ToolchainEditor extends React.Component { if(endInput === undefined) return; const endId = endInput.id.replace('-input-', '.'); - createConnection(startId, endId, Object.keys(channelColors)[0]); + createConnection(startId, endId, startBlock.synchronized_channel || startBlock.name); } function dragged() { @@ -697,6 +739,14 @@ export class ToolchainEditor extends React.Component { } } + getPossibleChannels = (blockName: string) => { + const relConns = this.state.cache.contents.connections.filter(c => c.to.split('.')[0] === blockName) || []; + const possibleChannels = Array.from(new Set(relConns.map(c => c.channel))) + .reduce((o, channel) => ({...o, [channel]: this.state.cache.contents.representation.channel_colors[channel]}), {}); + + return possibleChannels; + } + renderGraphicalEditor = () => { const svgWidth = 3000; const svgHeight = 3000; @@ -726,13 +776,12 @@ export class ToolchainEditor extends React.Component { -
-
+
+
{ modalBlockInfo: newMBI, }); }} + channelColors={this.state.cache.contents.representation.channel_colors} /> ); }) @@ -904,6 +954,55 @@ export class ToolchainEditor extends React.Component { ); } + renderModal = () => { + const {active, name, set} = this.state.modalBlockInfo; + const possibleChannels = active ? this.getPossibleChannels(name) : {}; + return ( + d.name === name) : {}} + active={active} + toggle={() => { + this.setState({ + ...this.state, + modalBlockInfo: { + ...this.state.modalBlockInfo, + active: false, + } + }); + }} + blockNames={Object.keys(this.state.cache.contents.representation.blocks) || []} + updateBlockName={(newName: string) => { + this.updateBlockName(set, name, newName); + }} + updateBlockIOName={(ioType: 'input' | 'output', oldName: string, newName: string) => this.updateBlockIOName( + name, + set, + ioType, + oldName, + newName + )} + addBlockIO={(ioType: 'input' | 'output', newName: string) => this.addBlockIO( + name, + set, + ioType, + newName + )} + deleteBlockIO={(ioType: 'input' | 'output', ioName: string) => this.deleteBlockIO( + name, + set, + ioType, + ioName + )} + deleteBlock={() => this.deleteBlock( + name, + set, + )} + possibleChannels={possibleChannels} + updateBlockChannel={(channel: string) => this.updateBlockChannel(name, set, channel)} + /> + ); + } + render = () => (
@@ -941,48 +1040,8 @@ export class ToolchainEditor extends React.Component { { this.renderGraphicalEditor() } + { this.renderModal() } - d.name === this.state.modalBlockInfo.name) : {}} - active={this.state.modalBlockInfo.active} - toggle={() => { - this.setState({ - ...this.state, - modalBlockInfo: { - ...this.state.modalBlockInfo, - active: false, - } - }); - }} - blockNames={Object.keys(this.state.cache.contents.representation.blocks) || []} - updateBlockName={(newName: string) => { - this.updateBlockName(this.state.modalBlockInfo.set, this.state.modalBlockInfo.name, newName); - }} - updateBlockIOName={(ioType: 'input' | 'output', oldName: string, newName: string) => this.updateBlockIOName( - this.state.modalBlockInfo.name, - this.state.modalBlockInfo.set, - ioType, - oldName, - newName - )} - addBlockIO={(ioType: 'input' | 'output', newName: string) => this.addBlockIO( - this.state.modalBlockInfo.name, - this.state.modalBlockInfo.set, - ioType, - newName - )} - deleteBlockIO={(ioType: 'input' | 'output', ioName: string) => this.deleteBlockIO( - this.state.modalBlockInfo.name, - this.state.modalBlockInfo.set, - ioType, - ioName - )} - deleteBlock={() => this.deleteBlock( - this.state.modalBlockInfo.name, - this.state.modalBlockInfo.set, - )} - - />
); } diff --git a/src/components/ToolchainModal.jsx b/src/components/ToolchainModal.jsx index 5d2a997..b040438 100644 --- a/src/components/ToolchainModal.jsx +++ b/src/components/ToolchainModal.jsx @@ -24,6 +24,7 @@ import { InputGroupAddon, Badge, Modal, ModalBody, ModalHeader, ModalFooter, + UncontrolledButtonDropdown, DropdownToggle, DropdownMenu, DropdownItem, } from 'reactstrap'; import CacheInput from './CacheInput.jsx'; @@ -31,15 +32,28 @@ import DeleteInputBtn from './DeleteInputBtn.jsx'; import { generateNewKey } from '@helpers'; type Props = { + // block data data: any, + // func to close modal toggle: () => any, + // is the modal active? active: boolean, + // name of all blocks blockNames: string[], + // change the block name updateBlockName: (newName: string) => any, + // change the name of an input or output updateBlockIOName: (ioType: 'input' | 'output', oldName: string, newName: string) => any, + // create an input or output addBlockIO: (ioType: 'input' | 'output', newName: string) => any, + // delete an input or output deleteBlockIO: (ioType: 'input' | 'output', ioName: string) => any, + // delete the block deleteBlock: () => any, + // possible channels the block can be sync'd to (an obj w keys as channel names & vals as colours) + possibleChannels: any, + // update sync'd channel + updateBlockChannel: (channel: string) => any, }; type State = { @@ -73,7 +87,8 @@ class ToolchainModal extends React.Component { }} > - Editing
{data.name}
{' '} + Editing
{data.name}
+ {' '}
@@ -86,12 +101,38 @@ class ToolchainModal extends React.Component { this.props.updateBlockName(e.target.value); }} validateFunc={(str) => { - return str === data.name || !this.props.blockNames.includes(str) || + return ( + str === data.name || + !this.props.blockNames.includes(str) || This name is already taken by an existing block - ; + ); }} /> + { data.hasOwnProperty('synchronized_channel') + && + + + this.props.updateBlockChannel(e.target.value)} + > + { + Object.entries(this.props.possibleChannels) + .map(([channel, color], i) => + + ) + } + + + } { hasInputs && @@ -109,9 +150,11 @@ class ToolchainModal extends React.Component { this.props.updateBlockIOName('input', input, e.target.value); }} validateFunc={(str) => { - return str === input || !inputs.includes(str) || + return ( + str === input || + !inputs.includes(str) || This input name is already in use in this block - ; + ); }} > { this.props.updateBlockIOName('output', output, e.target.value); }} validateFunc={(str) => { - return str === output || !outputs.includes(str) || + return ( + str === output || + !outputs.includes(str) || This output name is already in use in this block - ; + ); }} > diff --git a/src/helpers/index.js b/src/helpers/index.js index 9511ca4..2f9230f 100644 --- a/src/helpers/index.js +++ b/src/helpers/index.js @@ -31,4 +31,17 @@ export const generateNewKey = (keyPrefix: string = '', existingKeys: string[]) = } return newKey; -} +}; + +/* + * Generates a random "bright" colour, ignoring extreme values (very close to white/black). + * Adapted from https://stackoverflow.com/a/1484514 + */ +export const getRandomBrightColor = () => { + var letters = '789ABCD'; + var color = '#'; + for (var i = 0; i < 6; i++) { + color += letters[Math.floor(Math.random() * letters.length)]; + } + return color; +}; -- GitLab From 9b1a1659518da1d1bc547e354e704b1f6ecf6cd3 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 2 Jan 2018 17:57:41 +0100 Subject: [PATCH 14/51] fix drag perf by dragging placeholder shape instead of block --- src/components/ToolchainEditor.jsx | 40 ++++++++++++++++++++++++------ 1 file changed, 33 insertions(+), 7 deletions(-) diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index b9576f9..7f2cb5d 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -181,8 +181,8 @@ export class ToolchainEditor extends React.Component { ...rep.blocks, [blockName]: { ...block, - col: block.col + x, - row: block.row + y, + col: x, + row: y, } } } @@ -586,9 +586,10 @@ export class ToolchainEditor extends React.Component { dy = dy - my * distanceFactor; } if(mx != 0 || my != 0){ - const bId = d3.select(this).attr('id'); - //console.log(`${ bId }: ${ x } | ${ y }`); - updateBlockLocation(bId, mx, my); + const dRect = d3.select('#dragRect'); + dRect + .attr('x', Number.parseInt(dRect.attr('x')) + mx * distanceFactor) + .attr('y', Number.parseInt(dRect.attr('y')) + my * distanceFactor); } mx = 0; my = 0; @@ -597,6 +598,26 @@ export class ToolchainEditor extends React.Component { } function startDrag(d) { + const b = d3.select(this); + const x = b.attr('x'); + const y = b.attr('y'); + const height = b.attr('height'); + const width = b.attr('width'); + + d3.select('svg') + .append('rect') + .attr('id', 'dragRect') + .attr('fill', 'grey') + .attr('stroke', 'black') + .attr('stroke-width', '2') + .attr('stroke-dasharray', '10, 10') + .attr('opacity', '0.4') + .attr('x', x) + .attr('y', y) + .attr('height', height) + .attr('width', width) + ; + dx = 0; dy = 0; mx = 0; @@ -604,7 +625,13 @@ export class ToolchainEditor extends React.Component { } function endDrag(d) { - + const dRect = d3.select('#dragRect'); + const x = Number.parseInt(dRect.attr('x')) / 20; + const y = Number.parseInt(dRect.attr('y')) / 20; + const bId = d3.select(this).attr('id'); + //console.log(`${ bId }: ${ x } | ${ y }`); + updateBlockLocation(bId, x, y); + dRect.remove(); } d3.selectAll('.fo').call( @@ -620,7 +647,6 @@ export class ToolchainEditor extends React.Component { initD3Connections = () => { // creating connections setTimeout(() => { - //const updateBlockLocation = this.updateBlockLocation; let startId; const createConnection = this.createConnection; const channelColors = this.state.cache.contents.representation.channel_colors; -- GitLab From e62657c5c646c6f9eb490824cea6283bf56ef373 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 2 Jan 2018 18:04:06 +0100 Subject: [PATCH 15/51] fix background grid not matching zoomed svg --- src/components/ToolchainEditor.jsx | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index 7f2cb5d..12c134a 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -779,6 +779,8 @@ export class ToolchainEditor extends React.Component { const gridX = distanceFactor; const gridY = distanceFactor; const locMap = this.getLocationMap(); + const scaledSvgWidth = svgWidth * (this.state.zoomLevel / 3000); + const scaledSvgHeight = svgHeight * (this.state.zoomLevel / 3000); return ( @@ -831,14 +833,14 @@ export class ToolchainEditor extends React.Component { height={svgHeight} /> { - [...Array(Math.round(svgHeight / gridY))].map((u, i) => { + [...Array(Math.round(scaledSvgHeight / gridY))].map((u, i) => { return ( { } { - [...Array(Math.round(svgWidth / gridX))].map((u, i) => { + [...Array(Math.round(scaledSvgWidth / gridX))].map((u, i) => { return ( { x1={i * gridX} y1={0} x2={i * gridX} - y2={svgHeight} + y2={scaledSvgHeight} stroke='gray' strokeWidth={1} /> -- GitLab From 39c6eed9d712de5b293823ad961213cb5e6ac589 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 3 Jan 2018 14:10:32 +0100 Subject: [PATCH 16/51] commit server file & enable settings --- .gitignore | 3 + server.py | 297 ++++++++++++++++++++++++++++++++++++ src/components/MainNav.jsx | 24 +-- src/components/Settings.jsx | 74 +++++++-- src/helpers/api.js | 6 +- src/helpers/beat.js | 4 + src/store/actionTypes.js | 4 +- src/store/actions.js | 17 +-- src/store/reducers.js | 25 ++- src/store/selectors.js | 1 + 10 files changed, 418 insertions(+), 37 deletions(-) create mode 100644 server.py diff --git a/.gitignore b/.gitignore index 6a91bcc..c16fb4d 100644 --- a/.gitignore +++ b/.gitignore @@ -72,3 +72,6 @@ styleguide/ flow-typed/ coverage/ + +# user conf file for app +user_conf.json diff --git a/server.py b/server.py new file mode 100644 index 0000000..ac48f03 --- /dev/null +++ b/server.py @@ -0,0 +1,297 @@ +"""A simple Flask server providing an API for the local BEAT prefix and user configuration.""" +import os +import json +import re +from pprint import pprint +from enum import Enum +import simplejson +from flask import Flask, request, abort +from flask_restful import Resource, Api +from flask_cors import CORS, cross_origin + +app = Flask(__name__) +api = Api(app) +CORS(app) + +def get_user_conf(): + """Reads & returns the user configuration in a dict""" + user_conf = {} + if os.path.isfile('./user_conf.json'): + with open('./user_conf.json') as f: + try: + user_conf = json.load(f) + except json.JSONDecodeError: + print('user_conf.json is invalid!') + raise SystemExit + else: + with open('./user_conf.json', 'w') as f: + user_conf = { + 'prefix': '~' + } + json.dump(user_conf, f) + + + if 'prefix' not in user_conf: + raise Exception('Invalid user_conf: Needs "prefix" key!') + return user_conf + +def get_prefix(): + """Returns an absolute path to the user-defined BEAT prefix location""" + return os.path.expanduser(get_user_conf()['prefix']) + +class BeatEntity(Enum): + """List of BEAT entities to serve to the webapp""" + DATAFORMAT = 'dataformats' + DATABASE = 'databases' + LIBRARY = 'libraries' + ALGORITHM = 'algorithms' + TOOLCHAIN = 'toolchains' + EXPERIMENT = 'experiments' + + +def read_json(path): + """Reads a JSON file and returns the parse JSON obj""" + with open(path, 'r') as f: + data = json.load(f) + return data + + +def path_to_dict(path): + """Generates a dict of the given file/folder in the BEAT prefix""" + d = { + 'name': os.path.basename(path) + } + if os.path.isdir(path): + d['type'] = "directory" + d['children'] = [path_to_dict(os.path.join(path, x)) + for x in os.listdir(path)] + elif os.path.isfile(path): + d['type'] = "file" + fname, fext = os.path.splitext(path) + if fext == '.json': + d['json'] = read_json(path) + return d + + +def generate_file_tree(be): + """Generates a file tree (of dicts) given a specific BEAT entity""" + resource_path = os.path.join(get_prefix(), be.value) + if not os.path.isdir(resource_path): + raise NotADirectoryError('Invalid resource path %s' % resource_path) + + #print('generating entity tree for path %s' % resource_path) + return path_to_dict(resource_path) + + +def generate_json_entity(fto, parent_names): + """Generates info for a file in the BEAT path""" + if fto['type'] != 'file': + raise Exception('bad file tree obj') + + fname, fext = os.path.splitext(fto['name']) + + name_str = '' + for name in parent_names: + name_str += name + '/' + + name_str += fname + + return { + 'name': name_str, + 'contents': fto['json'] + } + + +def generate_entity_tree(be): + """Generates the entire tree for an entity type from the prefix""" + file_tree = generate_file_tree(be) + entity_tree = {} + user_and_name = [ + BeatEntity.DATAFORMAT, + BeatEntity.LIBRARY, + BeatEntity.ALGORITHM, + BeatEntity.TOOLCHAIN + ] + + if be in user_and_name: + for user in file_tree['children']: + entity_tree[user['name']] = {} + for obj in user['children']: + entity_tree[user['name']][obj['name']] = list() + for f in obj['children']: + fname, fext = os.path.splitext(f['name']) + if fext != '.json': + continue + parent_names = [user['name'], obj['name']] + json_obj = generate_json_entity(f, parent_names) + entity_tree[user['name']][obj['name']].append(json_obj) + + elif be == BeatEntity.DATABASE: + for obj in file_tree['children']: + entity_tree[obj['name']] = list() + for f in obj['children']: + fname, fext = os.path.splitext(f['name']) + if fext != '.json': + continue + parent_names = [obj['name']] + json_obj = generate_json_entity(f, parent_names) + entity_tree[obj['name']].append(json_obj) + + elif be == BeatEntity.EXPERIMENT: + for user in file_tree['children']: + uname = user['name'] + entity_tree[uname] = {} + for tc_user in user['children']: + tcuname = tc_user['name'] + entity_tree[uname][tcuname] = {} + for tc_name in tc_user['children']: + tcname = tc_name['name'] + entity_tree[uname][tcuname][tcname] = {} + for tc_version in tc_name['children']: + tcv = tc_version['name'] + entity_tree[uname][tcuname][tcname][tcv] = list() + for exp_name in tc_version['children']: + fname, fext = os.path.splitext(exp_name['name']) + if fext != '.json': + continue + parent_names = [uname, tcuname, tcname, tcv] + json_obj = generate_json_entity( + exp_name, parent_names) + entity_tree[uname][tcuname][tcname][tcv].append( + json_obj) + + return entity_tree + + +class WriteMode(Enum): + """Write modes for requests from the web app""" + CREATE = 0 + UPDATE = 1 + DELETE = 2 + + +def write_json(be, obj, mode): + """writes JSON from a webapp request to the prefix using the specified mode""" + resource_path = os.path.join(get_prefix(), be.value) + file_tree = generate_file_tree(be) + name = obj['name'] + name_segs = name.split('/') + contents = obj['contents'] + stringified = simplejson.dumps(contents, indent=4, sort_keys=True) + + folder_path = os.path.join(resource_path, '/'.join(name_segs[:-1])) + file_path = os.path.join(resource_path, name + '.json') + + if mode == WriteMode.CREATE or mode == WriteMode.UPDATE: + os.makedirs(folder_path, exist_ok=True) + with open(file_path, 'w') as f: + f.write(stringified) + elif mode == WriteMode.DELETE: + if not os.path.isfile(file_path): + raise FileNotFoundError(file_path) + else: + os.remove(file_path) + # taken from https://stackoverflow.com/a/23488980 + + def remove_empty_dirs(path): + """Remove directories now made empty by deleting an object from the prefix""" + for root, dirnames, filenames in os.walk(path, topdown=False): + for dirname in dirnames: + remove_empty_dirs( + os.path.realpath( + os.path.join(root, dirname) + ) + ) + + remove_empty_dirs(folder_path) + else: + raise TypeError('Invalid WriteMode %s' % mode) + + +class Home(Resource): + """The base resource path with subroutes""" + def get(self): + """Returns the available sub-routes""" + return { + 'routes': [ + 'databases', + 'dataformats', + 'libraries', + 'algorithms', + 'toolchains', + 'experiments', + 'settings', + ] + } + + +class Settings(Resource): + """Exposes user settings""" + + def get(self): + """Returns the settings""" + return get_user_conf() + + def post(self): + """Overwrites the settings""" + new_conf = request.get_json() + with open('./user_conf.json', 'w') as f: + try: + json.dump(new_conf, f) + except json.JSONDecodeError: + print('Invalid new_conf %s' % new_conf) + raise SystemExit + return get_user_conf() + + +def gen_beat_endpoint(entity): + """Generates an endpoint for the given BEAT entity, exposing actions to perform on the prefix""" + class BeatEndpoint(Resource): + """A class representing the template for an endpoint for a BEAT entity""" + be = entity + + def refresh(self): + """Regenerates the entity tree""" + try: + return generate_entity_tree(self.be) + except NotADirectoryError: + return {} + + def get(self): + """Returns the entity tree""" + return self.refresh() + + def post(self): + """Creates a new object""" + obj_list = request.get_json() + if not isinstance(obj_list, list): + obj_list = [obj_list] + for obj in obj_list: + write_json(self.be, obj, WriteMode.CREATE) + return self.refresh() + + def put(self): + """Updates an already-existing object""" + obj = request.get_json() + write_json(self.be, obj, WriteMode.UPDATE) + return self.refresh() + + def delete(self): + """Deletes an object""" + obj = request.get_json() + write_json(self.be, obj, WriteMode.DELETE) + return self.refresh() + + BeatEndpoint.__name__ = entity.value + + return BeatEndpoint + + +api.add_resource(Home, '/') +api.add_resource(Settings, '/settings') +for entity in BeatEntity: + val = entity.value + api.add_resource(gen_beat_endpoint(entity), '/' + val) + +if __name__ == '__main__': + app.run(debug=True) diff --git a/src/components/MainNav.jsx b/src/components/MainNav.jsx index 438e8d4..4f87b47 100644 --- a/src/components/MainNav.jsx +++ b/src/components/MainNav.jsx @@ -22,16 +22,18 @@ import * as Selectors from '@store/selectors'; import { BEAT_ENTITIES } from '@helpers/beat'; import { genModuleApiFuncs } from '@helpers/api'; +import type { BeatEntity, BeatSettings } from '@helpers/beat'; import Settings from './Settings.jsx'; type Props = { - database: any[], - library: any[], - dataformat: any[], - algorithm: any[], - toolchain: any[], - experiment: any[], + database: BeatEntity[], + library: BeatEntity[], + dataformat: BeatEntity[], + algorithm: BeatEntity[], + toolchain: BeatEntity[], + experiment: BeatEntity[], + settings: BeatSettings, }; type State = { @@ -41,8 +43,8 @@ type State = { const saveAll = (allLists: Props) => { return Promise.all( - BEAT_ENTITIES - .filter(e => Array.isArray(allLists[e])) + [...BEAT_ENTITIES, 'settings'] + //.filter(e => Array.isArray(allLists[e])) .map(e => { const post = genModuleApiFuncs(e).post; return post(allLists[e]); @@ -99,7 +101,10 @@ export class MainNav extends React.Component {
); @@ -1016,7 +1102,9 @@ const mapStateToProps: MapStateToProps<*,*,*> = (state, ownProps) => { }; const obj = { experiments: Selectors.experimentGet(state), + // algorithms for normal blocks normalBlocks: Selectors.normalBlocks(state), + // algorithms for analyzer blocks analyzerBlocks: Selectors.analyzerBlocks(state), datasets: Selectors.flattenedDatabases(state), toolchain: tc, diff --git a/src/components/ExperimentModal.jsx b/src/components/ExperimentModal.jsx new file mode 100644 index 0000000..ef0d76a --- /dev/null +++ b/src/components/ExperimentModal.jsx @@ -0,0 +1,136 @@ +// @flow +import * as React from 'react'; +import { + Container, + Row, + Col, + Button, + ButtonGroup, + Form, + FormGroup, + Label, + Input, + InputGroup, + FormText, + Collapse, + Card, + CardHeader, + CardBody, + TabContent, TabPane, + Navbar, + Nav, NavItem, NavLink, CardTitle, CardText, + FormFeedback, + Alert, + InputGroupAddon, + Badge, + Modal, ModalBody, ModalHeader, ModalFooter, + UncontrolledButtonDropdown, DropdownToggle, DropdownMenu, DropdownItem, +} from 'reactstrap'; + +import type { BeatObject } from '@helpers/beat'; + +type Props = { + // experiment block data + expData: any, + // toolchain block data + tcData: any, + // algorithms + algorithms: BeatObject[], + // func to close modal + toggle: () => any, + // is the modal active? + active: boolean, +}; + +type State = { +}; + +class ExperimentModal extends React.Component { + constructor(props: Props){ + super(props); + } + + state = { + } + + render = () => { + const {expData, tcData} = this.props; + if(!expData || !tcData) + return null; + + const hasInputs = Array.isArray(tcData.inputs); + const hasOutputs = Array.isArray(tcData.outputs); + + return ( + { + const f = document.querySelector('#expModalInitFocus'); + if(f && f.focus) + f.focus(); + }} + > + + Editing
{tcData.name}
+ {' '} +
+ +
+ + {/* choose algorithm/dataset */} + + {/* parameters */} + + { + hasInputs && + + Inputs + { + tcData.inputs.map((input, i, inputs) => + + + { input } + + + + + ) + } + + } + { + hasOutputs && + + Outputs + { + tcData.outputs.map((output, i, outputs) => + + + + + { output } + + + ) + } + + } + +
+
+ + +
+ ); + } +} + +export default ExperimentModal; diff --git a/src/components/GraphicalEditor.jsx b/src/components/GraphicalEditor.jsx index 4d0dc77..f39a780 100644 --- a/src/components/GraphicalEditor.jsx +++ b/src/components/GraphicalEditor.jsx @@ -32,6 +32,7 @@ type Props = { svgChildren?: React.Node, // extra children (e.g. context menus) that arent svg divChildren?: React.Node, + // should the d3 behaviours be enabled? interactable?: boolean, }; diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index 8628856..6335fb4 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -44,12 +44,8 @@ import CacheInput from './CacheInput.jsx'; import type { BlockSet } from './ToolchainBlock.jsx'; import EditModal from './ToolchainModal.jsx'; import GraphicalEditor, { - blockTextHeight, - svgWidth, - svgHeight, blockWidth, gridDistance, - zoomAdjustmentAmount, } from './GraphicalEditor.jsx'; type Props = { -- GitLab From 54abe11b8841b5f27cdeeaee34f77bf04c073e30 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Fri, 5 Jan 2018 17:46:30 +0100 Subject: [PATCH 29/51] add foundation for click&drag area select --- src/components/GraphicalEditor.jsx | 77 +++++++++++++++++++++++++++--- src/components/ToolchainBlock.jsx | 4 +- 2 files changed, 74 insertions(+), 7 deletions(-) diff --git a/src/components/GraphicalEditor.jsx b/src/components/GraphicalEditor.jsx index f39a780..73907bb 100644 --- a/src/components/GraphicalEditor.jsx +++ b/src/components/GraphicalEditor.jsx @@ -75,6 +75,7 @@ export default class GraphicalEditor extends React.Component { this.initD3Drag(); this.initD3Connections(); this.initD3MouseMovement(); + this.initD3AreaSelect(); } } @@ -84,6 +85,7 @@ export default class GraphicalEditor extends React.Component { this.initD3Drag(); this.initD3Connections(); this.initD3MouseMovement(); + this.initD3AreaSelect(); } } @@ -174,6 +176,19 @@ export default class GraphicalEditor extends React.Component { this.svgContextMenu.handleContextClick(clickEvent); } + scaleD3EventLocation = (d3X: number, d3Y: number): [number, number] => { + const x = d3X * (this.state.zoomLevel / svgWidth); + const y = d3Y * (this.state.zoomLevel / svgHeight); + return [x, y]; + }; + + clampD3EventLocationToGrid = (d3X: number, d3Y: number): [number, number] => { + const [sx, sy] = this.scaleD3EventLocation(d3X, d3Y); + const x = Math.round(sx / gridDistance) * gridDistance; + const y = Math.round(sy / gridDistance) * gridDistance; + return [x, y]; + }; + // d3 hooks for dragging blocks around // to get around perf problems with updating the entire react state every drag event, // a placeholder (that's outside the react framework!) is drawn via d3. @@ -253,9 +268,9 @@ export default class GraphicalEditor extends React.Component { // when the user lets go, move the block to the location of the placeholder function endDrag(d) { const dRect = d3.select('.dragRect'); - const x = Number.parseInt(dRect.attr('x')) / 20; - const y = Number.parseInt(dRect.attr('y')) / 20; - const bId = d3.select(this).attr('id'); + const x = Number.parseInt(dRect.attr('x')) / gridDistance; + const y = Number.parseInt(dRect.attr('y')) / gridDistance; + const bId = d3.select(this).attr('id').slice(6); //console.log(`${ bId }: ${ x } | ${ y }`); if(updateBlockLocation) updateBlockLocation(bId, x, y); @@ -270,7 +285,6 @@ export default class GraphicalEditor extends React.Component { .on('drag', dragged) ); }, 50); - }; // d3 behaviour for dragging lines from an output to an input and creating a connection @@ -350,6 +364,7 @@ export default class GraphicalEditor extends React.Component { initD3MouseMovement = () => { // mouse movement setTimeout(() => { + const clampD3EventLocationToGrid = this.clampD3EventLocationToGrid; let cx = 0; let cy = 0; @@ -369,8 +384,9 @@ export default class GraphicalEditor extends React.Component { // needs to scale to the zoomlevel d3.select('svg') .on('mousemove', () => { - cx = Math.round((d3.event.layerX * (this.state.zoomLevel / 3000)) / gridDistance) * 20; - cy = Math.round((d3.event.layerY * (this.state.zoomLevel / 3000)) / gridDistance) * 20; + const [x, y] = clampD3EventLocationToGrid(d3.event.layerX, d3.event.layerY); + cx = x; + cy = y; d3.select('.puck') .attr('cx', cx) .attr('cy', cy) @@ -387,6 +403,55 @@ export default class GraphicalEditor extends React.Component { }, 50); } + // d3 behaviour for selecting all blocks inside a rect (via click-and-drag) + initD3AreaSelect = () => { + setTimeout(() => { + const clampD3EventLocationToGrid = this.clampD3EventLocationToGrid; + let startX, startY; + let currX, currY; + const getPolygonPoints = () => { + return `${ startX },${ startY } ${ startX },${ currY } ${ currX },${ currY } ${ currX },${ startY }`; + }; + function startDrag(d) { + const [x, y] = clampD3EventLocationToGrid(d3.event.x, d3.event.y); + startX = x; + startY = y; + currX = x; + currY = y; + d3.select('svg') + .insert('polygon', '.tcConnection') + .attr('class', 'tmp') + .attr('fill', 'grey') + .attr('stroke', 'black') + .attr('opacity', '0.3') + .attr('points', getPolygonPoints()) + ; + } + + function endDrag(d) { + const p = d3.select('polygon.tmp'); + p.remove(); + } + + // update the temp rect + function dragged(d) { + const [x, y] = clampD3EventLocationToGrid(d3.event.x, d3.event.y); + currX = x; + currY = y; + d3.select('polygon.tmp') + .attr('points', getPolygonPoints()) + ; + } + + d3.selectAll('.background').call( + d3.drag() + .on('start', startDrag) + .on('end', endDrag) + .on('drag', dragged) + ); + }, 50); + } + render = () => { const gridX = gridDistance; diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index ea0ff82..ca093fd 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -75,6 +75,8 @@ export type Props = { type State = { } +export const blockNameToId = (name: string) => `block_${ name }`; + class ToolchainBlock extends React.PureComponent { constructor(props: Props){ super(props); @@ -117,7 +119,7 @@ class ToolchainBlock extends React.PureComponent { renderTag='g' > {/* the background rectangle with the click handler */} - { -- GitLab From 5725b4aa0a4ac8154aa9dc94e6d4597fb2155bf9 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 9 Jan 2018 11:58:12 +0100 Subject: [PATCH 30/51] update deps except webpack-dev-server (bug) --- package-lock.json | 327 +++++++++++++++++++++++++++------------------- package.json | 18 +-- 2 files changed, 205 insertions(+), 140 deletions(-) diff --git a/package-lock.json b/package-lock.json index 73b06d3..108c284 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5,9 +5,9 @@ "requires": true, "dependencies": { "@babel/code-frame": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.0.0-beta.31.tgz", - "integrity": "sha512-yd7CkUughvHQoEahQqcMdrZw6o/6PwUxiRkfZuVDVHCDe77mysD/suoNyk5mK6phTnRW1kyIbPHyCJgxw++LXg==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.0.0-beta.36.tgz", + "integrity": "sha512-sW77BFwJ48YvQp3Gzz5xtAUiXuYOL2aMJKDwiaY3OcvdqBFurtYfOpSa4QrNyDxmOGRFSYzUpabU2m9QrlWE7w==", "dev": true, "requires": { "chalk": "2.3.0", @@ -47,66 +47,65 @@ } }, "@babel/helper-function-name": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.0.0-beta.31.tgz", - "integrity": "sha512-c+DAyp8LMm2nzSs2uXEuxp4LYGSUYEyHtU3fU57avFChjsnTmmpWmXj2dv0yUxHTEydgVAv5fIzA+4KJwoqWDA==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.0.0-beta.36.tgz", + "integrity": "sha512-/SGPOyifPf20iTrMN+WdlY2MbKa7/o4j7B/4IAsdOusASp2icT+Wcdjf4tjJHaXNX8Pe9bpgVxLNxhRvcf8E5w==", "dev": true, "requires": { - "@babel/helper-get-function-arity": "7.0.0-beta.31", - "@babel/template": "7.0.0-beta.31", - "@babel/traverse": "7.0.0-beta.31", - "@babel/types": "7.0.0-beta.31" + "@babel/helper-get-function-arity": "7.0.0-beta.36", + "@babel/template": "7.0.0-beta.36", + "@babel/types": "7.0.0-beta.36" } }, "@babel/helper-get-function-arity": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/helper-get-function-arity/-/helper-get-function-arity-7.0.0-beta.31.tgz", - "integrity": "sha512-m7rVVX/dMLbbB9NCzKYRrrFb0qZxgpmQ4Wv6y7zEsB6skoJHRuXVeb/hAFze79vXBbuD63ci7AVHXzAdZSk9KQ==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/helper-get-function-arity/-/helper-get-function-arity-7.0.0-beta.36.tgz", + "integrity": "sha512-vPPcx2vsSoDbcyWr9S3nd0FM3B4hEXnt0p1oKpwa08GwK0fSRxa98MyaRGf8suk8frdQlG1P3mDrz5p/Rr3pbA==", "dev": true, "requires": { - "@babel/types": "7.0.0-beta.31" + "@babel/types": "7.0.0-beta.36" } }, "@babel/template": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.0.0-beta.31.tgz", - "integrity": "sha512-97IRmLvoDhIDSQkqklVt3UCxJsv0LUEVb/0DzXWtc8Lgiyxj567qZkmTG9aR21CmcJVVIvq2Y/moZj4oEpl5AA==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.0.0-beta.36.tgz", + "integrity": "sha512-mUBi90WRyZ9iVvlWLEdeo8gn/tROyJdjKNC4W5xJTSZL+9MS89rTJSqiaJKXIkxk/YRDL/g/8snrG/O0xl33uA==", "dev": true, "requires": { - "@babel/code-frame": "7.0.0-beta.31", - "@babel/types": "7.0.0-beta.31", - "babylon": "7.0.0-beta.31", + "@babel/code-frame": "7.0.0-beta.36", + "@babel/types": "7.0.0-beta.36", + "babylon": "7.0.0-beta.36", "lodash": "4.17.4" }, "dependencies": { "babylon": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.31.tgz", - "integrity": "sha512-6lm2mV3S51yEnKmQQNnswoABL1U1H1KHoCCVwdwI3hvIv+W7ya4ki7Aw4o4KxtUHjNKkK5WpZb22rrMMOcJXJQ==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.36.tgz", + "integrity": "sha512-rw4YdadGwajAMMRl6a5swhQ0JCOOFyaYCfJ0AsmNBD8uBD/r4J8mux7wBaqavvFKqUKQYWOzA1Speams4YDzsQ==", "dev": true } } }, "@babel/traverse": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.0.0-beta.31.tgz", - "integrity": "sha512-3N+VJW+KlezEjFBG7WSYeMyC5kIqVLPb/PGSzCDPFcJrnArluD1GIl7Y3xC7cjKiTq2/JohaLWHVPjJWHlo9Gg==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.0.0-beta.36.tgz", + "integrity": "sha512-OTUb6iSKVR/98dGThRJ1BiyfwbuX10BVnkz89IpaerjTPRhDfMBfLsqmzxz5MiywUOW4M0Clta0o7rSxkfcuzw==", "dev": true, "requires": { - "@babel/code-frame": "7.0.0-beta.31", - "@babel/helper-function-name": "7.0.0-beta.31", - "@babel/types": "7.0.0-beta.31", - "babylon": "7.0.0-beta.31", + "@babel/code-frame": "7.0.0-beta.36", + "@babel/helper-function-name": "7.0.0-beta.36", + "@babel/types": "7.0.0-beta.36", + "babylon": "7.0.0-beta.36", "debug": "3.1.0", - "globals": "10.4.0", + "globals": "11.1.0", "invariant": "2.2.2", "lodash": "4.17.4" }, "dependencies": { "babylon": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.31.tgz", - "integrity": "sha512-6lm2mV3S51yEnKmQQNnswoABL1U1H1KHoCCVwdwI3hvIv+W7ya4ki7Aw4o4KxtUHjNKkK5WpZb22rrMMOcJXJQ==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.36.tgz", + "integrity": "sha512-rw4YdadGwajAMMRl6a5swhQ0JCOOFyaYCfJ0AsmNBD8uBD/r4J8mux7wBaqavvFKqUKQYWOzA1Speams4YDzsQ==", "dev": true }, "debug": { @@ -119,17 +118,17 @@ } }, "globals": { - "version": "10.4.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-10.4.0.tgz", - "integrity": "sha512-uNUtxIZpGyuaq+5BqGGQHsL4wUlJAXRqOm6g3Y48/CWNGTLONgBibI0lh6lGxjR2HljFYUfszb+mk4WkgMntsA==", + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.1.0.tgz", + "integrity": "sha512-uEuWt9mqTlPDwSqi+sHjD4nWU/1N+q0fiWI9T1mZpD2UENqX20CFD5T/ziLZvztPaBKl7ZylUi1q6Qfm7E2CiQ==", "dev": true } } }, "@babel/types": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.0.0-beta.31.tgz", - "integrity": "sha512-exAHB+NeFGxkfQ5dSUD03xl3zYGneeSk2Mw2ldTt/nTvYxuDiuSp3DlxgUBgzbdTFG4fbwPk0WtKWOoTXCmNGg==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.0.0-beta.36.tgz", + "integrity": "sha512-PyAORDO9um9tfnrddXgmWN9e6Sq9qxraQIt5ynqBOSXKA5qvK1kUr+Q3nSzKFdzorsiK+oqcUnAFvEoKxv9D+Q==", "dev": true, "requires": { "esutils": "2.0.2", @@ -249,11 +248,10 @@ } }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.0.0.tgz", + "integrity": "sha1-CTvsTZusjkUF5UGuEOthUCaGhMI=", "requires": { - "co": "4.6.0", "fast-deep-equal": "1.0.0", "fast-json-stable-stringify": "2.0.0", "json-schema-traverse": "0.3.1" @@ -645,23 +643,23 @@ } }, "babel-eslint": { - "version": "8.1.2", - "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.1.2.tgz", - "integrity": "sha512-IE+glF8t0lLoldylN7JyR8gT7e3jwyuNH2ds8g3UVUwGob/U4iT7Xpsiq2kQ8QGLb0eX4RcQXNqeW6mgPysu9A==", + "version": "8.2.1", + "resolved": "https://registry.npmjs.org/babel-eslint/-/babel-eslint-8.2.1.tgz", + "integrity": "sha512-RzdVOyWKQRUnLXhwLk+eKb4oyW+BykZSkpYwFhM4tnfzAG5OWfvG0w/uyzMp5XKEU0jN82+JefHr39bG2+KhRQ==", "dev": true, "requires": { - "@babel/code-frame": "7.0.0-beta.31", - "@babel/traverse": "7.0.0-beta.31", - "@babel/types": "7.0.0-beta.31", - "babylon": "7.0.0-beta.31", + "@babel/code-frame": "7.0.0-beta.36", + "@babel/traverse": "7.0.0-beta.36", + "@babel/types": "7.0.0-beta.36", + "babylon": "7.0.0-beta.36", "eslint-scope": "3.7.1", "eslint-visitor-keys": "1.0.0" }, "dependencies": { "babylon": { - "version": "7.0.0-beta.31", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.31.tgz", - "integrity": "sha512-6lm2mV3S51yEnKmQQNnswoABL1U1H1KHoCCVwdwI3hvIv+W7ya4ki7Aw4o4KxtUHjNKkK5WpZb22rrMMOcJXJQ==", + "version": "7.0.0-beta.36", + "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.36.tgz", + "integrity": "sha512-rw4YdadGwajAMMRl6a5swhQ0JCOOFyaYCfJ0AsmNBD8uBD/r4J8mux7wBaqavvFKqUKQYWOzA1Speams4YDzsQ==", "dev": true } } @@ -897,9 +895,9 @@ } }, "babel-plugin-flow-react-proptypes": { - "version": "13.0.1", - "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-13.0.1.tgz", - "integrity": "sha512-notPlr8BYsWuavjRuqIxUYs8G8Spwc0wYG+WrdXIPlJMnu6/UktgBQKxppMn6kczKIGAtYJvSoZkcp5Fm5BqYQ==", + "version": "13.0.2", + "resolved": "https://registry.npmjs.org/babel-plugin-flow-react-proptypes/-/babel-plugin-flow-react-proptypes-13.0.2.tgz", + "integrity": "sha512-kv9fakJMkh5HGL2YZRSlaPeudvZ3aqAjWub1/hUe1l67E9DDC4fEyxYUa2YMJyIaUfCLQcYqjKJWX/VzDrLiDA==", "dev": true, "requires": { "babel-core": "6.26.0", @@ -2395,7 +2393,8 @@ "co": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" + "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", + "dev": true }, "coa": { "version": "1.0.4", @@ -4146,9 +4145,9 @@ } }, "eslint": { - "version": "4.14.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.14.0.tgz", - "integrity": "sha512-Ul6CSGRjKscEyg0X/EeNs7o2XdnbTEOD1OM8cTjmx85RPcBJQrEhZLevhuJZNAE/vS2iVl5Uhgiqf3h5uLMCJQ==", + "version": "4.15.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.15.0.tgz", + "integrity": "sha512-zEO/Z1ZUxIQ+MhDVKkVTUYpIPDTEJLXGMrkID+5v1NeQHtCz6FZikWuFRgxE1Q/RV2V4zVl1u3xmpPADHhMZ6A==", "dev": true, "requires": { "ajv": "5.5.2", @@ -4157,7 +4156,7 @@ "concat-stream": "1.6.0", "cross-spawn": "5.1.0", "debug": "3.1.0", - "doctrine": "2.0.2", + "doctrine": "2.1.0", "eslint-scope": "3.7.1", "eslint-visitor-keys": "1.0.0", "espree": "3.5.2", @@ -4190,6 +4189,18 @@ "text-table": "0.2.0" }, "dependencies": { + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "dev": true, + "requires": { + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + }, "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", @@ -4226,9 +4237,9 @@ } }, "doctrine": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.0.2.tgz", - "integrity": "sha512-y0tm5Pq6ywp3qSTZ1vPgVdAnbDEoeoc5wlOHXoY1c4Wug/a7JvqHIl7BTvwodaHmejWkK/9dSb3sCYfyo/om8A==", + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", "dev": true, "requires": { "esutils": "2.0.2" @@ -4369,9 +4380,9 @@ } }, "eslint-plugin-flowtype": { - "version": "2.40.1", - "resolved": "https://registry.npmjs.org/eslint-plugin-flowtype/-/eslint-plugin-flowtype-2.40.1.tgz", - "integrity": "sha512-0EBDPR3/iguDQin7nb5WMT1ZWYB95eNllY+oiFZjvLa1oqE0BGO6ZSFnMdNE9HEkajB6Cw850PRIBbp+O+EzYQ==", + "version": "2.41.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-flowtype/-/eslint-plugin-flowtype-2.41.0.tgz", + "integrity": "sha512-M5X6qu/zvvXQ7flXp9plyBRlNRMQGNl3c+kQmox+m/jpnCZt0txgauxcrBKAVa9LKE/hBnsItJ9BojdmkefAkA==", "dev": true, "requires": { "lodash": "4.17.4" @@ -4928,9 +4939,9 @@ "dev": true }, "flow-bin": { - "version": "0.62.0", - "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.62.0.tgz", - "integrity": "sha1-FLymaabj+VwLwMLR61XsTpjLHYM=", + "version": "0.63.1", + "resolved": "https://registry.npmjs.org/flow-bin/-/flow-bin-0.63.1.tgz", + "integrity": "sha512-aWKHYs3UECgpwrIDVUiABjSC8dgaKmonymQDWO+6FhGcp9lnnxdDBE6Sfm3F7YaRPfLYsWAY4lndBrfrfyn+9g==", "dev": true }, "follow-redirects": { @@ -5470,7 +5481,8 @@ "jsbn": { "version": "0.1.1", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "json-schema": { "version": "0.2.3", @@ -6219,6 +6231,21 @@ "requires": { "ajv": "5.5.2", "har-schema": "2.0.0" + }, + "dependencies": { + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "dev": true, + "optional": true, + "requires": { + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + } } }, "has": { @@ -6648,7 +6675,7 @@ "integrity": "sha1-g/Cg7DeL8yRheLbCrZE28TWxyWI=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "ieee754": { @@ -9639,7 +9666,7 @@ "dev": true, "requires": { "browserslist": "2.4.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "reduce-css-calc": "1.3.0" } }, @@ -9659,7 +9686,7 @@ "dev": true, "requires": { "onecolor": "3.0.4", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "pluralize": { @@ -9669,9 +9696,9 @@ "dev": true }, "popper.js": { - "version": "1.12.6", - "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.12.6.tgz", - "integrity": "sha512-wZlMkIJM1hFcM9F7nSrRCbKKfkH0kk/GrCoj3EUoKU8kx9xPtvnOZNHKsQOM12+xqbYv2HeBWI8Y8pxb6vmnRQ==" + "version": "1.12.9", + "resolved": "https://registry.npmjs.org/popper.js/-/popper.js-1.12.9.tgz", + "integrity": "sha1-DfvC3/lsRRuzMu3Pz6r1ZtMx1bM=" }, "portfinder": { "version": "1.0.13", @@ -9685,9 +9712,9 @@ } }, "postcss": { - "version": "6.0.15", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-6.0.15.tgz", - "integrity": "sha512-v/SpyMzLbtkmh45zUdaqLAaqXqzPdSrw8p4cQVO0/w6YiYfpj4k+Wkzhn68qk9br+H+0qfddhdPEVnbmBPfXVQ==", + "version": "6.0.16", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-6.0.16.tgz", + "integrity": "sha512-m758RWPmSjFH/2MyyG3UOW1fgYbR9rtdzz5UNJnlm7OLtu4B2h9C6gi+bE4qFKghsBRFfZT8NzoQBs6JhLotoA==", "dev": true, "requires": { "chalk": "2.3.0", @@ -9751,7 +9778,7 @@ "requires": { "babel-runtime": "6.26.0", "balanced-match": "0.4.2", - "postcss": "6.0.15" + "postcss": "6.0.16" }, "dependencies": { "balanced-match": { @@ -9768,7 +9795,7 @@ "integrity": "sha1-lNxCLI+QmX8WvTOjZUu77AhJY7Q=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-selector-parser": "2.2.3" } }, @@ -9825,7 +9852,7 @@ "get-stdin": "5.0.1", "globby": "6.1.0", "ora": "1.3.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-load-config": "1.2.0", "postcss-reporter": "5.0.0", "pretty-hrtime": "1.0.3", @@ -9998,7 +10025,7 @@ "dev": true, "requires": { "css-color-function": "1.3.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-message-helpers": "2.0.0", "postcss-value-parser": "3.3.0" } @@ -10010,7 +10037,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-message-helpers": "2.0.0", "reduce-function-call": "1.0.2" }, @@ -10044,7 +10071,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-message-helpers": "2.0.0" }, "dependencies": { @@ -10076,7 +10103,7 @@ "integrity": "sha1-EnA2ZvoxBDDj8wpFTawThjF9WEQ=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0", "units-css": "0.4.0" } @@ -10088,7 +10115,7 @@ "dev": true, "requires": { "color": "1.0.3", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-message-helpers": "2.0.0", "reduce-function-call": "1.0.2" }, @@ -10121,7 +10148,7 @@ "integrity": "sha1-7rrwPTY7QwC5Z5K9MIHBntZlE9M=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0" } }, @@ -10131,7 +10158,7 @@ "integrity": "sha1-FFOcinExSUtILg3RzCZf9lFLUmM=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0" } }, @@ -10141,7 +10168,7 @@ "integrity": "sha1-N9XJNToHoJJwkSqCYGu0Kg1wLAQ=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0", "rgb-hex": "2.1.0" } @@ -10236,7 +10263,7 @@ "chalk": "2.1.0", "pixrem": "4.0.1", "pleeease-filters": "4.0.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-apply": "0.8.0", "postcss-attribute-case-insensitive": "2.0.0", "postcss-calc": "6.0.0", @@ -10283,7 +10310,7 @@ "caniuse-lite": "1.0.30000741", "normalize-range": "0.1.2", "num2fraction": "1.2.2", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0" } }, @@ -10317,7 +10344,7 @@ "dev": true, "requires": { "css-unit-converter": "1.1.1", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-selector-parser": "2.2.3", "reduce-css-calc": "2.0.5" } @@ -10349,7 +10376,7 @@ "integrity": "sha1-vlMnhBEOyylQRPtTlaGABushpzc=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-custom-properties": { @@ -10359,7 +10386,7 @@ "dev": true, "requires": { "balanced-match": "1.0.0", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-custom-selectors": { @@ -10368,7 +10395,7 @@ "integrity": "sha1-eBOC+UxS5yfvXKR3bqKt9JphE4I=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-selector-matches": "3.0.1" } }, @@ -10609,7 +10636,7 @@ "dev": true, "requires": { "lodash": "4.17.4", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0" } }, @@ -10619,7 +10646,7 @@ "integrity": "sha1-CMzIj2BQuoLtjvLMdsDGprQfGD4=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-html": { @@ -10639,7 +10666,7 @@ "integrity": "sha1-Dxk0E3AM8fgr05Bm7wFtZaShgYE=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-media-query-parser": "0.2.3" } }, @@ -10650,7 +10677,7 @@ "dev": true, "requires": { "lodash.template": "4.4.0", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-less": { @@ -10730,7 +10757,7 @@ "dev": true, "requires": { "loader-utils": "1.1.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-load-config": "1.2.0", "schema-utils": "0.3.0" } @@ -10741,7 +10768,7 @@ "integrity": "sha1-Z1JWA3pD70C8Twdgv9BtTcadSNI=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-media-query-parser": { @@ -11053,7 +11080,7 @@ "integrity": "sha1-thTJcgvmgW6u41+zpfqh26agXds=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-modules-local-by-default": { @@ -11063,7 +11090,7 @@ "dev": true, "requires": { "css-selector-tokenizer": "0.7.0", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-modules-scope": { @@ -11073,7 +11100,7 @@ "dev": true, "requires": { "css-selector-tokenizer": "0.7.0", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-modules-values": { @@ -11083,7 +11110,7 @@ "dev": true, "requires": { "icss-replace-symbols": "1.1.0", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-nesting": { @@ -11092,7 +11119,7 @@ "integrity": "sha512-IkyWXICwagCnlaviRexi7qOdwPw3+xVVjgFfGsxmztvRVaNxAlrypOIKqDE5mxY+BVxnId1rnUKBRQoNE2VDaA==", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-normalize-charset": { @@ -11219,7 +11246,7 @@ "integrity": "sha1-kVKgYT00UHIFE+iJKFS65C0O5o4=", "dev": true, "requires": { - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-selector-parser": "2.2.3" } }, @@ -11229,7 +11256,7 @@ "integrity": "sha1-7vGU6NUkZFylIKlJ6V5RjoEkAss=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-reduce-idents": { @@ -11355,7 +11382,7 @@ "integrity": "sha1-eU22+qVPjbEAhUOSqTr0V2i04ls=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-reporter": { @@ -11367,7 +11394,7 @@ "chalk": "2.1.0", "lodash": "4.17.4", "log-symbols": "2.1.0", - "postcss": "6.0.15" + "postcss": "6.0.16" }, "dependencies": { "ansi-styles": { @@ -11413,7 +11440,7 @@ "integrity": "sha1-t1Pv9sfArqXoN1++TN6L+QY/8UI=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-sass": { @@ -11423,7 +11450,7 @@ "dev": true, "requires": { "gonzales-pe": "4.2.3", - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-scss": { @@ -11432,7 +11459,7 @@ "integrity": "sha1-/0XPM1S4ee6JpOtoaA9GrJuxT5Q=", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "postcss-selector-matches": { @@ -11442,7 +11469,7 @@ "dev": true, "requires": { "balanced-match": "0.4.2", - "postcss": "6.0.15" + "postcss": "6.0.16" }, "dependencies": { "balanced-match": { @@ -11460,7 +11487,7 @@ "dev": true, "requires": { "balanced-match": "0.4.2", - "postcss": "6.0.15" + "postcss": "6.0.16" }, "dependencies": { "balanced-match": { @@ -11491,7 +11518,7 @@ "babel-runtime": "6.26.0", "lodash": "4.17.4", "object-assign": "4.1.1", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-sass": "0.2.0", "postcss-scss": "1.0.2", "postcss-value-parser": "3.3.0", @@ -11516,7 +11543,7 @@ "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } } } @@ -12023,11 +12050,11 @@ } }, "react-popper": { - "version": "0.7.4", - "resolved": "https://registry.npmjs.org/react-popper/-/react-popper-0.7.4.tgz", - "integrity": "sha512-dx1fcKYYkidq7f71I1g+YX7g3QBLZ9taqiSRdJ7wbP7v/o7F6JsrUaNWGbVNul+TqdDDIZ5/k0xPUol9baqQJQ==", + "version": "0.7.5", + "resolved": "https://registry.npmjs.org/react-popper/-/react-popper-0.7.5.tgz", + "integrity": "sha512-ya9dhhGCf74JTOB2uyksEHhIGw7w9tNZRUJF73lEq2h4H5JT6MBa4PdT4G+sx6fZwq+xKZAL/sVNAIuojPn7Dg==", "requires": { - "popper.js": "1.12.6", + "popper.js": "1.12.9", "prop-types": "15.6.0" } }, @@ -12125,7 +12152,7 @@ "lodash.isobject": "3.0.2", "lodash.tonumber": "4.0.3", "prop-types": "15.6.0", - "react-popper": "0.7.4", + "react-popper": "0.7.5", "react-transition-group": "2.2.1" } }, @@ -12861,6 +12888,20 @@ "dev": true, "requires": { "ajv": "5.5.2" + }, + "dependencies": { + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "dev": true, + "requires": { + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + } } }, "select-hose": { @@ -13044,9 +13085,9 @@ } }, "sinon": { - "version": "4.1.3", - "resolved": "https://registry.npmjs.org/sinon/-/sinon-4.1.3.tgz", - "integrity": "sha512-c7u0ZuvBRX1eXuB4jN3BRCAOGiUTlM8SE3TxbJHrNiHUKL7wonujMOB6Fi1gQc00U91IscFORQHDga/eccqpbw==", + "version": "4.1.4", + "resolved": "https://registry.npmjs.org/sinon/-/sinon-4.1.4.tgz", + "integrity": "sha512-ISJZDPf8RS2z4/LAgy1gIimAvF9zg9C9ClQhLTWYWm4HBZjo1WELXlVfkudjdYeN+GtQ2uVBe52m0npIV0gDow==", "dev": true, "requires": { "diff": "3.4.0", @@ -13592,7 +13633,7 @@ "micromatch": "2.3.11", "normalize-selector": "0.2.0", "pify": "3.0.0", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-html": "0.12.0", "postcss-less": "1.1.3", "postcss-media-query-parser": "0.2.3", @@ -13631,7 +13672,7 @@ "caniuse-lite": "1.0.30000783", "normalize-range": "0.1.2", "num2fraction": "1.2.2", - "postcss": "6.0.15", + "postcss": "6.0.16", "postcss-value-parser": "3.3.0" } }, @@ -13940,7 +13981,7 @@ "integrity": "sha512-3qgLZytikQQEVn1/FrhY7B68gPUUGY3R1Q1vTiD5xT+Ti1DP/8iZuwFet9ONs5+bmL8pZoDQ6JrQHVgrNlK6mA==", "dev": true, "requires": { - "postcss": "6.0.15" + "postcss": "6.0.16" } }, "supports-color": { @@ -14031,6 +14072,18 @@ "string-width": "2.1.1" }, "dependencies": { + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "dev": true, + "requires": { + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + }, "ansi-styles": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", @@ -14722,6 +14775,18 @@ "yargs": "8.0.2" }, "dependencies": { + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "dev": true, + "requires": { + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + }, "async": { "version": "2.6.0", "resolved": "https://registry.npmjs.org/async/-/async-2.6.0.tgz", diff --git a/package.json b/package.json index be95a98..951b921 100644 --- a/package.json +++ b/package.json @@ -23,10 +23,10 @@ "license": "MIT", "devDependencies": { "babel-core": "^6.26.0", - "babel-eslint": "^8.1.2", + "babel-eslint": "^8.2.1", "babel-loader": "^7.1.2", "babel-plugin-dynamic-import-webpack": "^1.0.2", - "babel-plugin-flow-react-proptypes": "^13.0.1", + "babel-plugin-flow-react-proptypes": "^13.0.2", "babel-plugin-istanbul": "^4.1.5", "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-syntax-object-rest-spread": "^6.13.0", @@ -40,12 +40,12 @@ "css-loader": "^0.28.8", "enzyme": "^3.3.0", "enzyme-adapter-react-16": "^1.1.1", - "eslint": "^4.14.0", + "eslint": "^4.15.0", "eslint-plugin-compat": "^2.1.0", - "eslint-plugin-flowtype": "^2.40.1", + "eslint-plugin-flowtype": "^2.41.0", "eslint-plugin-import": "^2.8.0", "eslint-plugin-react": "^7.5.1", - "flow-bin": "^0.62.0", + "flow-bin": "^0.63.1", "html-webpack-harddisk-plugin": "^0.1.0", "html-webpack-plugin": "^2.30.1", "husky": "^0.14.3", @@ -58,7 +58,7 @@ "karma-sourcemap-loader": "^0.3.7", "karma-webpack": "^2.0.9", "mocha": "^4.1.0", - "postcss": "^6.0.15", + "postcss": "^6.0.16", "postcss-cli": "^4.1.1", "postcss-cssnext": "^3.0.2", "postcss-loader": "^2.0.10", @@ -67,7 +67,7 @@ "react-test-renderer": "^16.2.0", "redux-devtools": "^3.4.1", "rimraf": "^2.6.2", - "sinon": "^4.1.3", + "sinon": "^4.1.4", "style-loader": "^0.19.1", "stylelint": "^8.4.0", "stylelint-config-standard": "^18.0.0", @@ -78,7 +78,7 @@ "worker-loader": "^1.1.0" }, "dependencies": { - "ajv": "^5.5.2", + "ajv": "^6.0.0", "bootstrap": "^4.0.0-beta.3", "classnames": "^2.2.5", "d3": "^4.12.2", @@ -87,7 +87,7 @@ "react-contextmenu": "^2.9.2", "react-dom": "^16.2.0", "react-konva": "^1.6.4", - "react-popper": "^0.7.4", + "react-popper": "^0.7.5", "react-redux": "^5.0.6", "react-router-dom": "^4.2.2", "react-transition-group": "^2.2.1", -- GitLab From f26e7c56a79085058796b5c4db5c5cdfa872a2e9 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 9 Jan 2018 12:00:46 +0100 Subject: [PATCH 31/51] update ajv config for schema v4 --- src/helpers/schema/index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/helpers/schema/index.js b/src/helpers/schema/index.js index adf0aab..5dec9dc 100644 --- a/src/helpers/schema/index.js +++ b/src/helpers/schema/index.js @@ -10,7 +10,7 @@ import experiment from './experiment.json'; import execution from './execution.json'; import draft04 from 'ajv/lib/refs/json-schema-draft-04.json'; -const ajv = new Ajv({ allErrors: true }); +const ajv = new Ajv({ allErrors: true, schemaId: 'id' }); ajv.addMetaSchema(draft04); ajv.addSchema([common, dataformat, database, library, algorithm, toolchain, experiment, execution]); -- GitLab From f3b7588b2e2f5c9554eb8ed0c7d4c4a3b57ecf8f Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Tue, 9 Jan 2018 15:49:20 +0100 Subject: [PATCH 32/51] fix leftclick background to rightclick, add multiselect dnd! --- src/components/GraphicalEditor.jsx | 146 +++++++++++++++++++++++++---- src/components/ToolchainBlock.jsx | 7 +- src/components/ToolchainEditor.jsx | 1 - 3 files changed, 132 insertions(+), 22 deletions(-) diff --git a/src/components/GraphicalEditor.jsx b/src/components/GraphicalEditor.jsx index 73907bb..5625428 100644 --- a/src/components/GraphicalEditor.jsx +++ b/src/components/GraphicalEditor.jsx @@ -44,6 +44,7 @@ type State = { x: number, y: number, }, + selectedBlocks: BlockType[], }; // note: all measurements are in px by default for svg @@ -67,6 +68,7 @@ export default class GraphicalEditor extends React.Component { x: -1, y: -1, }, + selectedBlocks: [], }; // initializes d3 behaviours (most SVG interactions) @@ -74,8 +76,8 @@ export default class GraphicalEditor extends React.Component { if(this.props.interactable){ this.initD3Drag(); this.initD3Connections(); - this.initD3MouseMovement(); this.initD3AreaSelect(); + this.initD3MouseMovement(); } } @@ -84,8 +86,8 @@ export default class GraphicalEditor extends React.Component { if(nextProps.interactable){ this.initD3Drag(); this.initD3Connections(); - this.initD3MouseMovement(); this.initD3AreaSelect(); + this.initD3MouseMovement(); } } @@ -102,6 +104,18 @@ export default class GraphicalEditor extends React.Component { // generates the string representing the viewbox of the svg. The first two numbers represent the offset, the last two the scaling. getSvgViewBox = () => `0 0 ${ this.state.zoomLevel } ${ this.state.zoomLevel }`; + findBlock = (name: string): BlockType => { + const b = this.props.blocks.find(b => b.name === name) || + this.props.datasets.find(b => b.name === name) || + this.props.analyzers.find(b => b.name === name) + ; + if(!b) + throw new Error(`invalid block name: ${ name }`); + + return b; + + } + // generates a map of the location (and sizes) of all blocks, inputs, & outputs on the graphical editor. // necessary to draw lines between connected outputs & inputs. getLocationMap = (): {} => { @@ -111,14 +125,7 @@ export default class GraphicalEditor extends React.Component { */ return Object.entries(this.props.repData.blocks) .map(([name, rep], i) => { - const data: ?BlockType = - this.props.blocks.find(b => b.name === name) || - this.props.datasets.find(b => b.name === name) || - this.props.analyzers.find(b => b.name === name) - ; - - if(!data) - throw new Error(`invalid name: ${ name }`); + const data: BlockType = this.findBlock(name); const x = Math.max(rep.col * gridDistance, 0); const y = Math.max(rep.row * gridDistance, 0); @@ -189,6 +196,14 @@ export default class GraphicalEditor extends React.Component { return [x, y]; }; + selectBlocks = (blocks: BlockType[]) => { + this.setState({ + ...this.state, + selectedBlocks: blocks, + }); + this.initD3Drag(); + } + // d3 hooks for dragging blocks around // to get around perf problems with updating the entire react state every drag event, // a placeholder (that's outside the react framework!) is drawn via d3. @@ -196,8 +211,11 @@ export default class GraphicalEditor extends React.Component { initD3Drag = () => { setTimeout(() => { const updateBlockLocation = this.props.updateBlockLocation; + const that = this; // currently debouncing isnt necessary perf-wise //let debouceTimeLast = 0; + let startX = 0; + let startY = 0; let dx = 0; let dy = 0; let mx = 0; @@ -239,10 +257,12 @@ export default class GraphicalEditor extends React.Component { // when the user starts dragging, create the placeholder block function startDrag(d) { const b = d3.select(this); - const x = b.attr('x'); - const y = b.attr('y'); + const x = Number.parseFloat(b.attr('x')); + const y = Number.parseFloat(b.attr('y')); const height = b.attr('height'); const width = b.attr('width'); + startX = x / gridDistance; + startY = y / gridDistance; d3.select('svg') .insert('rect', '.tcBlock') @@ -268,17 +288,34 @@ export default class GraphicalEditor extends React.Component { // when the user lets go, move the block to the location of the placeholder function endDrag(d) { const dRect = d3.select('.dragRect'); + const d3this = d3.select(this); const x = Number.parseInt(dRect.attr('x')) / gridDistance; const y = Number.parseInt(dRect.attr('y')) / gridDistance; - const bId = d3.select(this).attr('id').slice(6); - //console.log(`${ bId }: ${ x } | ${ y }`); - if(updateBlockLocation) - updateBlockLocation(bId, x, y); + if(d3this.classed('areaSelect')){ + // multiselect move + const xShift = x - startX; + const yShift = y - startY; + that.state.selectedBlocks.forEach(b => { + const el = d3.select(`#block_${ b.name }`); + const bx = Number.parseFloat(el.attr('x')) / gridDistance + xShift; + const by = Number.parseFloat(el.attr('y')) / gridDistance + yShift; + + if(updateBlockLocation) + updateBlockLocation(b.name, bx, by); + }); + + } else { + // single block + const bId = d3.select(this).attr('id').slice(6); + //console.log(`${ bId }: ${ x } | ${ y }`); + if(updateBlockLocation) + updateBlockLocation(bId, x, y); + } dRect.remove(); } // all block elements should be draggable - d3.selectAll('.fo').call( + d3.selectAll('.fo,.areaSelect').call( d3.drag() .on('start', startDrag) .on('end', endDrag) @@ -394,7 +431,8 @@ export default class GraphicalEditor extends React.Component { }) // if the click event's target is the svg background, // trigger the svg action at the puck's current point - .on('click', () => { + .on('contextmenu', () => { + console.log(d3.event); if(!Array.from(d3.event.target.classList).includes('background')) return; this.triggerSvgAction(cx / gridDistance, cy / gridDistance, d3.event); @@ -406,7 +444,7 @@ export default class GraphicalEditor extends React.Component { // d3 behaviour for selecting all blocks inside a rect (via click-and-drag) initD3AreaSelect = () => { setTimeout(() => { - const clampD3EventLocationToGrid = this.clampD3EventLocationToGrid; + const {clampD3EventLocationToGrid, findBlock, selectBlocks} = this; let startX, startY; let currX, currY; const getPolygonPoints = () => { @@ -414,6 +452,8 @@ export default class GraphicalEditor extends React.Component { }; function startDrag(d) { const [x, y] = clampD3EventLocationToGrid(d3.event.x, d3.event.y); + console.log(x); + console.log(y); startX = x; startY = y; currX = x; @@ -430,7 +470,35 @@ export default class GraphicalEditor extends React.Component { function endDrag(d) { const p = d3.select('polygon.tmp'); + const lesserX = Math.min(startX, currX); + const lesserY = Math.min(startY, currY); + const greaterX = Math.max(startX, currX); + const greaterY = Math.max(startY, currY); + const isInArea = (svgEl) => { + const ex = svgEl.x.baseVal.value; + const ey = svgEl.y.baseVal.value; + const ew = svgEl.width.baseVal.value; + const eh = svgEl.height.baseVal.value; + if(ex >= greaterX || ex + ew <= lesserX) + return false; + if(ey >= greaterY || ey + eh <= lesserY) + return false; + return true; + }; + const blocksInArea = Array.from(document.querySelectorAll('.fo')) + .filter(el => isInArea(el)) + .map(el => el.id.slice(6)) + .map(name => findBlock(name)) + ; + + console.log(blocksInArea); + selectBlocks(blocksInArea); + p.remove(); + startX = 0; + startY = 0; + currX = 0; + currY = 0; } // update the temp rect @@ -460,6 +528,19 @@ export default class GraphicalEditor extends React.Component { // scales width/height to the zoomlevel so the background grid lines cover the entire svg const scaledSvgWidth = svgWidth * (this.state.zoomLevel / 3000); const scaledSvgHeight = svgHeight * (this.state.zoomLevel / 3000); + const selBlockLocs = this.state.selectedBlocks.map(b => locMap[b.name].block); + + const selX = Math.min(...selBlockLocs.map(l => l.x)); + const selY = Math.min(...selBlockLocs.map(l => l.y)); + const selWidth = Math.max(...selBlockLocs.map(l => l.x + l.width - selX)); + const selHeight = Math.max(...selBlockLocs.map(l => l.y + l.height - selY)); + + const selectBoxCoords = { + x: selX - gridDistance, + y: selY - gridDistance, + width: selWidth + gridDistance * 2, + height: selHeight + gridDistance * 2, + }; return (
@@ -517,6 +598,19 @@ export default class GraphicalEditor extends React.Component { }) } + { + Number.isFinite(selectBoxCoords.x) && + + } + { /* connections between blocks */ this.props.connections.map((conn, i) => @@ -533,7 +627,7 @@ export default class GraphicalEditor extends React.Component { /* blocks */ Object.entries(this.props.repData.blocks).map(([name, rep], i) => { // assume the block is in "blocks" - let data = this.props.blocks.find(b => b.name === name); + let data: ?BlockType = this.props.blocks.find(b => b.name === name); // find the set the block belongs to manually let set: BlockSet = 'blocks'; if(data === undefined){ @@ -549,6 +643,8 @@ export default class GraphicalEditor extends React.Component { if(data === undefined) return null; + const isSelected = this.state.selectedBlocks.find(b => b.name === name); + /* * the block handleClick must be bound here, not in a different file! * it needs to be bound afterish the d3 drag setup code runs @@ -561,7 +657,17 @@ export default class GraphicalEditor extends React.Component { data={data} set={set} handleClick={() => this.props.handleBlockClick ? this.props.handleBlockClick(name, set) : undefined} + handleShiftClick={() => { + const sels = this.state.selectedBlocks; + if(!this.props.interactable) + return; + if(sels.find(b => b.name === name)) + this.selectBlocks(sels.filter(b => b.name !== name)); + else + this.selectBlocks([...sels, data]); + }} channelColor={this.props.repData.channel_colors[data.synchronized_channel || data.name]} + opacity={isSelected ? 0.5 : 1} /> ); }) diff --git a/src/components/ToolchainBlock.jsx b/src/components/ToolchainBlock.jsx index ca093fd..961158a 100644 --- a/src/components/ToolchainBlock.jsx +++ b/src/components/ToolchainBlock.jsx @@ -68,6 +68,8 @@ export type Props = { set: BlockSet, // handler for the user clicking the block handleClick: (name: string, set: BlockSet) => any, + // handler for the user clicking the block + handleShiftClick: (name: string, set: BlockSet) => any, // the color of the channel the block is sync'd to channelColor: string, }; @@ -123,7 +125,10 @@ class ToolchainBlock extends React.PureComponent { stroke='black' fill={color} onClick={e => { - this.props.handleClick(name, this.props.set); + if(e.shiftKey) + this.props.handleShiftClick(name, this.props.set); + else + this.props.handleClick(name, this.props.set); e.stopPropagation(); e.preventDefault(); }} diff --git a/src/components/ToolchainEditor.jsx b/src/components/ToolchainEditor.jsx index 6335fb4..50ca09d 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/ToolchainEditor.jsx @@ -502,7 +502,6 @@ export class ToolchainEditor extends React.Component { // handles the left click on the svg's background // shows a menu to add/paste blocks at the click location handleSvgContextMenu = (e: any, data: { x: number, y: number, clicked: string }) => { - console.log('hi'); const {blocks, datasets, analyzers, representation} = this.state.cache.contents; const { x, y, clicked } = data; let newBlockName = ''; -- GitLab From ba9940c2503d1311bfe1eec77b67a8cbc2a5a815 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 10:04:00 +0100 Subject: [PATCH 33/51] update webpack-dev-server to fixed version --- package-lock.json | 1626 ++++++++++++++++++++++++++++++++++++++++++--- package.json | 2 +- 2 files changed, 1542 insertions(+), 86 deletions(-) diff --git a/package-lock.json b/package-lock.json index 108c284..d2ca524 100644 --- a/package-lock.json +++ b/package-lock.json @@ -350,6 +350,12 @@ "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", "dev": true }, + "arr-union": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz", + "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", + "dev": true + }, "array-filter": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/array-filter/-/array-filter-0.0.1.tgz", @@ -479,6 +485,12 @@ "integrity": "sha1-E8pRXYYgbaC6xm6DTdOX2HWBCUw=", "dev": true }, + "assign-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz", + "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", + "dev": true + }, "ast-types": { "version": "0.9.6", "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.9.6.tgz", @@ -527,6 +539,12 @@ "dev": true, "optional": true }, + "atob": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.0.3.tgz", + "integrity": "sha1-GcenYEc3dEaPILLS0DNyrX1Mv10=", + "dev": true + }, "autoprefixer": { "version": "6.7.7", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-6.7.7.tgz", @@ -1567,6 +1585,29 @@ "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", "dev": true }, + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "dev": true, + "requires": { + "cache-base": "1.0.1", + "class-utils": "0.3.5", + "component-emitter": "1.2.1", + "define-property": "1.0.0", + "isobject": "3.0.1", + "mixin-deep": "1.3.0", + "pascalcase": "0.1.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "base62": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/base62/-/base62-1.2.0.tgz", @@ -2069,6 +2110,31 @@ "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=", "dev": true }, + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "dev": true, + "requires": { + "collection-visit": "1.0.0", + "component-emitter": "1.2.1", + "get-value": "2.0.6", + "has-value": "1.0.0", + "isobject": "3.0.1", + "set-value": "2.0.0", + "to-object-path": "0.3.0", + "union-value": "1.0.0", + "unset-value": "1.0.0" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "cached-path-relative": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.1.tgz", @@ -2320,6 +2386,102 @@ "chalk": "1.1.3" } }, + "class-utils": { + "version": "0.3.5", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.5.tgz", + "integrity": "sha1-F+eTEDdQ+WJ7IXbqNM/RtWWQPIA=", + "dev": true, + "requires": { + "arr-union": "3.1.0", + "define-property": "0.2.5", + "isobject": "3.0.1", + "lazy-cache": "2.0.2", + "static-extend": "0.1.2" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + } + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + }, + "lazy-cache": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-2.0.2.tgz", + "integrity": "sha1-uRkKT5EzVGlIQIWfio9whNiCImQ=", + "dev": true, + "requires": { + "set-getter": "0.1.0" + } + } + } + }, "classnames": { "version": "2.2.5", "resolved": "https://registry.npmjs.org/classnames/-/classnames-2.2.5.tgz", @@ -2417,6 +2579,16 @@ "integrity": "sha1-S5BvZw5aljqHt2sOFolkM0G2Ajw=", "dev": true }, + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "dev": true, + "requires": { + "map-visit": "1.0.0", + "object-visit": "1.0.1" + } + }, "color": { "version": "0.11.4", "resolved": "https://registry.npmjs.org/color/-/color-0.11.4.tgz", @@ -2696,6 +2868,12 @@ "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=", "dev": true }, + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", + "dev": true + }, "core-js": { "version": "1.2.7", "resolved": "https://registry.npmjs.org/core-js/-/core-js-1.2.7.tgz", @@ -3387,6 +3565,12 @@ "map-obj": "1.0.1" } }, + "decode-uri-component": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", + "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=", + "dev": true + }, "deep-eql": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", @@ -3418,6 +3602,15 @@ "object-keys": "1.0.11" } }, + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "1.0.2" + } + }, "defined": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/defined/-/defined-1.0.0.tgz", @@ -4769,6 +4962,15 @@ "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=", "dev": true }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "0.1.1" + } + }, "external-editor": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.1.0.tgz", @@ -5009,6 +5211,15 @@ "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=", "dev": true }, + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "dev": true, + "requires": { + "map-cache": "0.2.2" + } + }, "fresh": { "version": "0.5.2", "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", @@ -6057,6 +6268,12 @@ "readable-stream": "2.3.3" } }, + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", + "dev": true + }, "getpass": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", @@ -6301,6 +6518,66 @@ "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=", "dev": true }, + "has-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", + "dev": true, + "requires": { + "get-value": "2.0.6", + "has-values": "1.0.0", + "isobject": "3.0.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, + "has-values": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", + "dev": true, + "requires": { + "is-number": "3.0.0", + "kind-of": "4.0.0" + }, + "dependencies": { + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, "hash-base": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", @@ -6691,9 +6968,9 @@ "dev": true }, "import-local": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/import-local/-/import-local-0.1.1.tgz", - "integrity": "sha1-sReVcqrNwRxqkQCftDDbyrX2aKg=", + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/import-local/-/import-local-1.0.0.tgz", + "integrity": "sha512-vAaZHieK9qjGo58agRBg+bhHX3hoTZU/Oa3GESWLz7t1U62fk63aHuDJJEteXoDeTCcPmUT+z38gkHPZkkmpmQ==", "dev": true, "requires": { "pkg-dir": "2.0.0", @@ -6935,6 +7212,23 @@ "integrity": "sha1-UFMN+4T8yap9vnhS6Do3uTufKqY=", "dev": true }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "6.0.2" + }, + "dependencies": { + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + } + } + }, "is-alphabetical": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.1.tgz", @@ -7008,6 +7302,23 @@ "ci-info": "1.1.1" } }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "6.0.2" + }, + "dependencies": { + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + } + } + }, "is-date-object": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", @@ -7020,6 +7331,25 @@ "integrity": "sha1-9ftqlJlq2ejjdh+/vQkfH8qMToI=", "dev": true }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "1.0.0", + "is-data-descriptor": "1.0.0", + "kind-of": "6.0.2" + }, + "dependencies": { + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + } + } + }, "is-directory": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/is-directory/-/is-directory-0.3.1.tgz", @@ -7117,6 +7447,26 @@ "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", "dev": true }, + "is-odd": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-odd/-/is-odd-1.0.0.tgz", + "integrity": "sha1-O4qTLrAos3dcObsJ6RdnrM22kIg=", + "dev": true, + "requires": { + "is-number": "3.0.0" + }, + "dependencies": { + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + } + } + }, "is-path-cwd": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", @@ -7147,6 +7497,23 @@ "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=", "dev": true }, + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "requires": { + "isobject": "3.0.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "is-posix-bracket": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", @@ -8409,12 +8776,27 @@ "pify": "2.3.0" } }, + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", + "dev": true + }, "map-obj": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz", "integrity": "sha1-2TPOuSBdgr3PSIb2dCvcK03qFG0=", "dev": true }, + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", + "dev": true, + "requires": { + "object-visit": "1.0.1" + } + }, "markdown-escapes": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/markdown-escapes/-/markdown-escapes-1.0.1.tgz", @@ -8638,6 +9020,27 @@ "is-plain-obj": "1.1.0" } }, + "mixin-deep": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.0.tgz", + "integrity": "sha512-dgaCvoh6i1nosAUBKb0l0pfJ78K8+S9fluyIR2YvAeUD/QuMahnFnF3xYty5eYXMjhGSsB0DsW6A0uAZyetoAg==", + "dev": true, + "requires": { + "for-in": "1.0.2", + "is-extendable": "1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "2.0.4" + } + } + } + }, "mkdirp": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", @@ -8790,18 +9193,57 @@ "dev": true, "optional": true }, - "natural-compare": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", - "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", - "dev": true - }, - "ncname": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/ncname/-/ncname-1.0.0.tgz", - "integrity": "sha1-W1etGLHKCShk72Kwse2BlPODtxw=", - "dev": true, - "requires": { + "nanomatch": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.7.tgz", + "integrity": "sha512-/5ldsnyurvEw7wNpxLFgjVvBLMta43niEYOy0CJ4ntcYSbx6bugRUTQeFb4BR/WanEL1o3aQgHuVLHQaB6tOqg==", + "dev": true, + "requires": { + "arr-diff": "4.0.0", + "array-unique": "0.3.2", + "define-property": "1.0.0", + "extend-shallow": "2.0.1", + "fragment-cache": "0.2.1", + "is-odd": "1.0.0", + "kind-of": "5.1.0", + "object.pick": "1.3.0", + "regex-not": "1.0.0", + "snapdragon": "0.8.1", + "to-regex": "3.0.1" + }, + "dependencies": { + "arr-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz", + "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=", + "dev": true + }, + "array-unique": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", + "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=", + "dev": true + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", + "dev": true + }, + "ncname": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/ncname/-/ncname-1.0.0.tgz", + "integrity": "sha1-W1etGLHKCShk72Kwse2BlPODtxw=", + "dev": true, + "requires": { "xml-char-classes": "1.0.0" } }, @@ -9131,6 +9573,65 @@ "integrity": "sha1-8MaapQ78lbhmwYb0AKM3acsvEpE=", "dev": true }, + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "dev": true, + "requires": { + "copy-descriptor": "0.1.1", + "define-property": "0.2.5", + "kind-of": "3.2.2" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + } + } + }, "object-inspect": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.5.0.tgz", @@ -9149,6 +9650,23 @@ "integrity": "sha1-xUYBd4rVYPEULODgG8yotW0TQm0=", "dev": true }, + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "dev": true, + "requires": { + "isobject": "3.0.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "object.assign": { "version": "4.0.4", "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.0.4.tgz", @@ -9182,6 +9700,23 @@ "is-extendable": "0.1.1" } }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "dev": true, + "requires": { + "isobject": "3.0.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "object.values": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.0.4.tgz", @@ -9533,12 +10068,24 @@ "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=", "dev": true }, + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "dev": true + }, "path-browserify": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/path-browserify/-/path-browserify-0.0.0.tgz", "integrity": "sha1-oLhwcpquIUAFt9UDLsLLuw+0RRo=", "dev": true }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "dev": true + }, "path-exists": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", @@ -9711,6 +10258,12 @@ "mkdirp": "0.5.1" } }, + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", + "dev": true + }, "postcss": { "version": "6.0.16", "resolved": "https://registry.npmjs.org/postcss/-/postcss-6.0.16.tgz", @@ -12435,6 +12988,15 @@ "is-equal-shallow": "0.1.3" } }, + "regex-not": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.0.tgz", + "integrity": "sha1-Qvg+OXcWIt+CawKvF2Ul1qXxV/k=", + "dev": true, + "requires": { + "extend-shallow": "2.0.1" + } + }, "regexpu-core": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", @@ -12768,6 +13330,12 @@ "resolved": "https://registry.npmjs.org/resolve-pathname/-/resolve-pathname-2.2.0.tgz", "integrity": "sha512-bAFz9ld18RzJfddgrO2e/0S2O81710++chRMUxHjXOYKF6jTAMrUNZrEZ1PvV0zlhfjidm08iRPdTLPno1FuRg==" }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", + "dev": true + }, "restore-cursor": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", @@ -12991,12 +13559,33 @@ "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", "dev": true }, + "set-getter": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/set-getter/-/set-getter-0.1.0.tgz", + "integrity": "sha1-12nBgsnVpR9AkUXy+6guXoboA3Y=", + "dev": true, + "requires": { + "to-object-path": "0.3.0" + } + }, "set-immediate-shim": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz", "integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=", "dev": true }, + "set-value": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", + "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", + "dev": true, + "requires": { + "extend-shallow": "2.0.1", + "is-extendable": "0.1.1", + "is-plain-object": "2.0.4", + "split-string": "3.1.0" + } + }, "setimmediate": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", @@ -13157,6 +13746,118 @@ "nodemailer-shared": "1.1.0" } }, + "snapdragon": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.1.tgz", + "integrity": "sha1-4StUh/re0+PeoKyR6UAL91tAE3A=", + "dev": true, + "requires": { + "base": "0.11.2", + "debug": "2.6.9", + "define-property": "0.2.5", + "extend-shallow": "2.0.1", + "map-cache": "0.2.2", + "source-map": "0.5.7", + "source-map-resolve": "0.5.1", + "use": "2.0.2" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + } + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", + "dev": true, + "requires": { + "define-property": "1.0.0", + "isobject": "3.0.1", + "snapdragon-util": "3.0.1" + }, + "dependencies": { + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + }, "sntp": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", @@ -13228,13 +13929,21 @@ } }, "sockjs": { - "version": "0.3.18", - "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.18.tgz", - "integrity": "sha1-2bKJMWyn33dZXvKZ4HXw+TfrQgc=", + "version": "0.3.19", + "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.19.tgz", + "integrity": "sha512-V48klKZl8T6MzatbLlzzRNhMepEys9Y4oGFpypBFFn1gLI/QQ9HtLLyWJNbPlwGLelOVOEijUbTTJeLLI59jLw==", "dev": true, "requires": { "faye-websocket": "0.10.0", - "uuid": "2.0.3" + "uuid": "3.1.0" + }, + "dependencies": { + "uuid": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz", + "integrity": "sha512-DIWtzUkw04M4k3bf1IcpS2tngXEL26YUD2M0tMDUpnUrz2hgzUBlD55a4FjdLGPvfHxS6uluGWvaVEqgBcVa+g==", + "dev": true + } } }, "sockjs-client": { @@ -13304,6 +14013,19 @@ "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", "dev": true }, + "source-map-resolve": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.1.tgz", + "integrity": "sha512-0KW2wvzfxm8NCTb30z0LMNyPqWCdDGE2viwzUaucqJdkTRXtZiSY3I+2A6nVAjmdOy0I4gU8DwnVVGsk9jvP2A==", + "dev": true, + "requires": { + "atob": "2.0.3", + "decode-uri-component": "0.2.0", + "resolve-url": "0.2.1", + "source-map-url": "0.4.0", + "urix": "0.1.0" + } + }, "source-map-support": { "version": "0.4.18", "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", @@ -13313,6 +14035,12 @@ "source-map": "0.5.7" } }, + "source-map-url": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", + "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", + "dev": true + }, "sourcemapped-stacktrace": { "version": "1.1.7", "resolved": "https://registry.npmjs.org/sourcemapped-stacktrace/-/sourcemapped-stacktrace-1.1.7.tgz", @@ -13386,6 +14114,36 @@ "integrity": "sha512-Nc/QN/A425Qog7j9aHmwOrlwX2e7pNI47ciwxwy4jOlvbbMHkNNJchit+FX+UjF3IAdiaaV5BKeWuDUnws6G1A==", "dev": true }, + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "dev": true, + "requires": { + "extend-shallow": "3.0.2" + }, + "dependencies": { + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "dev": true, + "requires": { + "assign-symbols": "1.0.0", + "is-extendable": "1.0.1" + } + }, + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "2.0.4" + } + } + } + }, "sprintf-js": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", @@ -13421,56 +14179,134 @@ "integrity": "sha1-0g+aYWu08MO5i5GSLSW2QKorxCU=", "dev": true }, - "statuses": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.3.1.tgz", - "integrity": "sha1-+vUbnrdKrvOzrPStX2Gr8ky3uT4=", - "dev": true - }, - "stream-browserify": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.1.tgz", - "integrity": "sha1-ZiZu5fm9uZQKTkUUyvtDu3Hlyds=", - "dev": true, - "requires": { - "inherits": "2.0.3", - "readable-stream": "2.3.3" - } - }, - "stream-combiner2": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/stream-combiner2/-/stream-combiner2-1.1.1.tgz", - "integrity": "sha1-+02KFCDqNidk4hrUeAOXvry0HL4=", - "dev": true, - "requires": { - "duplexer2": "0.1.4", - "readable-stream": "2.3.3" - } - }, - "stream-http": { - "version": "2.7.2", - "resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.7.2.tgz", - "integrity": "sha512-c0yTD2rbQzXtSsFSVhtpvY/vS6u066PcXOX9kBB3mSO76RiUQzL340uJkGBWnlBg4/HZzqiUXtaVA7wcRcJgEw==", - "dev": true, - "requires": { - "builtin-status-codes": "3.0.0", - "inherits": "2.0.3", - "readable-stream": "2.3.3", - "to-arraybuffer": "1.0.1", - "xtend": "4.0.1" - } - }, - "stream-splicer": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/stream-splicer/-/stream-splicer-2.0.0.tgz", - "integrity": "sha1-G2O+Q4oTPktnHMGTUZdgAXWRDYM=", + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", "dev": true, "requires": { - "inherits": "2.0.3", - "readable-stream": "2.3.3" - } - }, - "streamroller": { + "define-property": "0.2.5", + "object-copy": "0.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + } + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "statuses": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.3.1.tgz", + "integrity": "sha1-+vUbnrdKrvOzrPStX2Gr8ky3uT4=", + "dev": true + }, + "stream-browserify": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/stream-browserify/-/stream-browserify-2.0.1.tgz", + "integrity": "sha1-ZiZu5fm9uZQKTkUUyvtDu3Hlyds=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, + "stream-combiner2": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/stream-combiner2/-/stream-combiner2-1.1.1.tgz", + "integrity": "sha1-+02KFCDqNidk4hrUeAOXvry0HL4=", + "dev": true, + "requires": { + "duplexer2": "0.1.4", + "readable-stream": "2.3.3" + } + }, + "stream-http": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.7.2.tgz", + "integrity": "sha512-c0yTD2rbQzXtSsFSVhtpvY/vS6u066PcXOX9kBB3mSO76RiUQzL340uJkGBWnlBg4/HZzqiUXtaVA7wcRcJgEw==", + "dev": true, + "requires": { + "builtin-status-codes": "3.0.0", + "inherits": "2.0.3", + "readable-stream": "2.3.3", + "to-arraybuffer": "1.0.1", + "xtend": "4.0.1" + } + }, + "stream-splicer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/stream-splicer/-/stream-splicer-2.0.0.tgz", + "integrity": "sha1-G2O+Q4oTPktnHMGTUZdgAXWRDYM=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, + "streamroller": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/streamroller/-/streamroller-0.7.0.tgz", "integrity": "sha512-WREzfy0r0zUqp3lGO096wRuUp7ho1X6uo/7DJfTlEi0Iv/4gT7YHqXDjKC2ioVGBZtE8QzsQD9nx1nIuoZ57jQ==", @@ -14224,6 +15060,115 @@ "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=", "dev": true }, + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + }, + "to-regex": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.1.tgz", + "integrity": "sha1-FTWL7kosg712N3uh3ASdDxiDeq4=", + "dev": true, + "requires": { + "define-property": "0.2.5", + "extend-shallow": "2.0.1", + "regex-not": "1.0.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + } + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "dev": true, + "requires": { + "is-number": "3.0.0", + "repeat-string": "1.6.1" + }, + "dependencies": { + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + } + } + } + }, "toposort": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/toposort/-/toposort-1.0.6.tgz", @@ -14420,6 +15365,32 @@ "x-is-string": "0.1.0" } }, + "union-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", + "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "dev": true, + "requires": { + "arr-union": "3.1.0", + "get-value": "2.0.6", + "is-extendable": "0.1.1", + "set-value": "0.4.3" + }, + "dependencies": { + "set-value": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", + "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", + "dev": true, + "requires": { + "extend-shallow": "2.0.1", + "is-extendable": "0.1.1", + "is-plain-object": "2.0.4", + "to-object-path": "0.3.0" + } + } + } + }, "uniq": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/uniq/-/uniq-1.0.1.tgz", @@ -14511,12 +15482,70 @@ "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=", "dev": true }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "dev": true, + "requires": { + "has-value": "0.3.1", + "isobject": "3.0.1" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "dev": true, + "requires": { + "get-value": "2.0.6", + "has-values": "0.1.4", + "isobject": "2.1.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "dev": true, + "requires": { + "isarray": "1.0.0" + } + } + } + }, + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + } + } + }, "upper-case": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/upper-case/-/upper-case-1.1.3.tgz", "integrity": "sha1-9rRQHC7EzdJrp4vnIilh3ndiFZg=", "dev": true }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", + "dev": true + }, "url": { "version": "0.11.0", "resolved": "https://registry.npmjs.org/url/-/url-0.11.0.tgz", @@ -14553,6 +15582,100 @@ } } }, + "use": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/use/-/use-2.0.2.tgz", + "integrity": "sha1-riig1y+TvyJCKhii43mZMRLeyOg=", + "dev": true, + "requires": { + "define-property": "0.2.5", + "isobject": "3.0.1", + "lazy-cache": "2.0.2" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + } + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + }, + "lazy-cache": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-2.0.2.tgz", + "integrity": "sha1-uRkKT5EzVGlIQIWfio9whNiCImQ=", + "dev": true, + "requires": { + "set-getter": "0.1.0" + } + } + } + }, "useragent": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/useragent/-/useragent-2.2.1.tgz", @@ -14606,12 +15729,6 @@ "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=", "dev": true }, - "uuid": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-2.0.3.tgz", - "integrity": "sha1-Z+LoY3lyFVMN/zGOW/nc6/1Hsho=", - "dev": true - }, "uws": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/uws/-/uws-0.14.5.tgz", @@ -14929,15 +16046,15 @@ } }, "webpack-dev-server": { - "version": "2.9.7", - "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-2.9.7.tgz", - "integrity": "sha512-Pu7uoQFgQj5RE5wmlfkpYSzihMKxulwEuO2xCsaMnAnyRSApwoVi3B8WCm9XbigyWTHaIMzYGkB90Vr6leAeTQ==", + "version": "2.10.1", + "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-2.10.1.tgz", + "integrity": "sha512-R9iZOrbIIsP2mw2j172HVjf479Zb9kcG0chjzHRrE/4M333NZ+3jOWRWJMGEQXwJzUtRNvVKzX2o27qM59TIhQ==", "dev": true, "requires": { "ansi-html": "0.0.7", "array-includes": "3.0.3", "bonjour": "3.5.0", - "chokidar": "1.7.0", + "chokidar": "2.0.0", "compression": "1.7.1", "connect-history-api-fallback": "1.5.0", "debug": "3.1.0", @@ -14945,7 +16062,7 @@ "express": "4.16.2", "html-entities": "1.2.1", "http-proxy-middleware": "0.17.4", - "import-local": "0.1.1", + "import-local": "1.0.0", "internal-ip": "1.2.0", "ip": "1.1.5", "killable": "1.0.0", @@ -14954,21 +16071,87 @@ "portfinder": "1.0.13", "selfsigned": "1.10.1", "serve-index": "1.9.1", - "sockjs": "0.3.18", + "sockjs": "0.3.19", "sockjs-client": "1.1.4", "spdy": "3.4.7", - "strip-ansi": "3.0.1", - "supports-color": "4.5.0", - "webpack-dev-middleware": "1.12.0", + "strip-ansi": "4.0.0", + "supports-color": "5.1.0", + "webpack-dev-middleware": "1.12.2", "yargs": "6.6.0" }, "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "anymatch": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz", + "integrity": "sha512-5teOsQWABXHHBFP9y3skS5P3d/WfWXpv3FUpy+LorMrNYaT9pI4oLMQX7jzQ2KklNpGpWHzdCXTDT2Y3XGlZBw==", + "dev": true, + "requires": { + "micromatch": "3.1.5", + "normalize-path": "2.1.1" + } + }, + "arr-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz", + "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=", + "dev": true + }, + "array-unique": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", + "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=", + "dev": true + }, + "braces": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.0.tgz", + "integrity": "sha512-P4O8UQRdGiMLWSizsApmXVQDBS6KCt7dSexgLKBmH5Hr1CZq7vsnscFh8oR1sP1ab1Zj0uCHCEzZeV6SfUf3rA==", + "dev": true, + "requires": { + "arr-flatten": "1.1.0", + "array-unique": "0.3.2", + "define-property": "1.0.0", + "extend-shallow": "2.0.1", + "fill-range": "4.0.0", + "isobject": "3.0.1", + "repeat-element": "1.1.2", + "snapdragon": "0.8.1", + "snapdragon-node": "2.1.1", + "split-string": "3.1.0", + "to-regex": "3.0.1" + } + }, "camelcase": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=", "dev": true }, + "chokidar": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.0.0.tgz", + "integrity": "sha512-OgXCNv2U6TnG04D3tth0gsvdbV4zdbxFG3sYUqcoQMoEFVd1j1pZR6TZ8iknC45o9IJ6PeQI/J6wT/+cHcniAw==", + "dev": true, + "requires": { + "anymatch": "2.0.0", + "async-each": "1.0.1", + "braces": "2.3.0", + "fsevents": "1.1.3", + "glob-parent": "3.1.0", + "inherits": "2.0.3", + "is-binary-path": "1.0.1", + "is-glob": "4.0.0", + "normalize-path": "2.1.1", + "path-is-absolute": "1.0.1", + "readdirp": "2.1.0" + } + }, "cliui": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", @@ -14978,6 +16161,23 @@ "string-width": "1.0.2", "strip-ansi": "3.0.1", "wrap-ansi": "2.1.0" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", + "dev": true + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "dev": true, + "requires": { + "ansi-regex": "2.1.1" + } + } } }, "debug": { @@ -15003,6 +16203,90 @@ "rimraf": "2.6.2" } }, + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", + "dev": true, + "requires": { + "debug": "2.6.9", + "define-property": "0.2.5", + "extend-shallow": "2.0.1", + "posix-character-classes": "0.1.1", + "regex-not": "1.0.0", + "snapdragon": "0.8.1", + "to-regex": "3.0.1" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "0.1.6" + } + } + } + }, + "extglob": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.3.tgz", + "integrity": "sha512-AyptZexgu7qppEPq59DtN/XJGZDrLcVxSHai+4hdgMMS9EpF4GBvygcWWApno8lL9qSjVpYt7Raao28qzJX1ww==", + "dev": true, + "requires": { + "array-unique": "0.3.2", + "define-property": "1.0.0", + "expand-brackets": "2.1.4", + "extend-shallow": "2.0.1", + "fragment-cache": "0.2.1", + "regex-not": "1.0.0", + "snapdragon": "0.8.1", + "to-regex": "3.0.1" + } + }, + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "dev": true, + "requires": { + "extend-shallow": "2.0.1", + "is-number": "3.0.0", + "repeat-string": "1.6.1", + "to-regex-range": "2.1.1" + } + }, + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", + "dev": true, + "requires": { + "is-glob": "3.1.0", + "path-dirname": "1.0.2" + }, + "dependencies": { + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", + "dev": true, + "requires": { + "is-extglob": "2.1.1" + } + } + } + }, "globby": { "version": "6.1.0", "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", @@ -15024,6 +16308,71 @@ } } }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } + } + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", + "dev": true + }, "is-fullwidth-code-point": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", @@ -15033,6 +16382,74 @@ "number-is-nan": "1.0.1" } }, + "is-glob": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", + "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", + "dev": true, + "requires": { + "is-extglob": "2.1.1" + } + }, + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, + "requires": { + "kind-of": "3.2.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "1.1.5" + } + } + } + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + }, + "micromatch": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.5.tgz", + "integrity": "sha512-ykttrLPQrz1PUJcXjwsTUjGoPJ64StIGNE2lGVD1c9CuguJ+L7/navsE8IcDNndOoCMvYV0qc/exfVbMHkUhvA==", + "dev": true, + "requires": { + "arr-diff": "4.0.0", + "array-unique": "0.3.2", + "braces": "2.3.0", + "define-property": "1.0.0", + "extend-shallow": "2.0.1", + "extglob": "2.0.3", + "fragment-cache": "0.2.1", + "kind-of": "6.0.2", + "nanomatch": "1.2.7", + "object.pick": "1.3.0", + "regex-not": "1.0.0", + "snapdragon": "0.8.1", + "to-regex": "3.0.1" + } + }, + "mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "dev": true + }, "os-locale": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", @@ -15057,17 +16474,56 @@ "code-point-at": "1.1.0", "is-fullwidth-code-point": "1.0.0", "strip-ansi": "3.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", + "dev": true + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "dev": true, + "requires": { + "ansi-regex": "2.1.1" + } + } + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "3.0.0" } }, "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.1.0.tgz", + "integrity": "sha512-Ry0AwkoKjDpVKK4sV4h6o3UJmNRbjYm2uXhwfj3J56lMVdvnUNqzQVRztOOMGQ++w1K/TjNDFvpJk0F/LoeBCQ==", "dev": true, "requires": { "has-flag": "2.0.0" } }, + "webpack-dev-middleware": { + "version": "1.12.2", + "resolved": "https://registry.npmjs.org/webpack-dev-middleware/-/webpack-dev-middleware-1.12.2.tgz", + "integrity": "sha512-FCrqPy1yy/sN6U/SaEZcHKRXGlqU0DUaEBL45jkUYoB8foVb6wCnbIJ1HKIx+qUFTW+3JpVcCJCxZ8VATL4e+A==", + "dev": true, + "requires": { + "memory-fs": "0.4.1", + "mime": "1.6.0", + "path-is-absolute": "1.0.1", + "range-parser": "1.2.0", + "time-stamp": "2.0.0" + } + }, "which-module": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/which-module/-/which-module-1.0.0.tgz", diff --git a/package.json b/package.json index 951b921..1ca3a2e 100644 --- a/package.json +++ b/package.json @@ -73,7 +73,7 @@ "stylelint-config-standard": "^18.0.0", "svg-inline-loader": "^0.8.0", "webpack": "^3.10.0", - "webpack-dev-server": "^2.9.7", + "webpack-dev-server": "^2.10.1", "webpack-visualizer-plugin": "^0.1.11", "worker-loader": "^1.1.0" }, -- GitLab From 7915a90493e4d748291fb5b863380cff70025b45 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 10:34:36 +0100 Subject: [PATCH 34/51] reorganize component files into subfolders --- src/components/EntityDetail.jsx | 12 ++++++------ src/components/{ => algorithm}/AlgorithmEditor.jsx | 10 +++++----- .../{ => algorithm}/AlgorithmEditor.spec.jsx | 2 +- src/components/algorithm/index.js | 8 ++++++++ src/components/{ => database}/DatabaseEditor.jsx | 8 ++++---- .../{ => database}/DatabaseEditor.spec.jsx | 2 +- src/components/database/index.js | 8 ++++++++ src/components/{ => dataformat}/DataformatEditor.jsx | 8 ++++---- .../{ => dataformat}/DataformatEditor.spec.jsx | 2 +- src/components/dataformat/index.js | 8 ++++++++ src/components/{ => experiment}/ExperimentEditor.jsx | 12 ++++++------ .../{ => experiment}/ExperimentEditor.spec.jsx | 2 +- src/components/{ => experiment}/ExperimentModal.jsx | 0 src/components/experiment/index.js | 8 ++++++++ src/components/{ => library}/LibraryEditor.jsx | 8 ++++---- src/components/{ => library}/LibraryEditor.spec.jsx | 2 +- src/components/library/index.js | 8 ++++++++ src/components/{ => toolchain}/GraphicalEditor.css | 0 src/components/{ => toolchain}/GraphicalEditor.jsx | 0 src/components/{ => toolchain}/ToolchainBlock.jsx | 0 .../{ => toolchain}/ToolchainConnection.jsx | 0 src/components/{ => toolchain}/ToolchainEditor.css | 0 src/components/{ => toolchain}/ToolchainEditor.jsx | 4 ++-- src/components/{ => toolchain}/ToolchainModal.jsx | 4 ++-- src/components/toolchain/index.js | 11 +++++++++++ 25 files changed, 89 insertions(+), 38 deletions(-) rename src/components/{ => algorithm}/AlgorithmEditor.jsx (99%) rename src/components/{ => algorithm}/AlgorithmEditor.spec.jsx (99%) create mode 100644 src/components/algorithm/index.js rename src/components/{ => database}/DatabaseEditor.jsx (98%) rename src/components/{ => database}/DatabaseEditor.spec.jsx (99%) create mode 100644 src/components/database/index.js rename src/components/{ => dataformat}/DataformatEditor.jsx (97%) rename src/components/{ => dataformat}/DataformatEditor.spec.jsx (99%) create mode 100644 src/components/dataformat/index.js rename src/components/{ => experiment}/ExperimentEditor.jsx (99%) rename src/components/{ => experiment}/ExperimentEditor.spec.jsx (98%) rename src/components/{ => experiment}/ExperimentModal.jsx (100%) create mode 100644 src/components/experiment/index.js rename src/components/{ => library}/LibraryEditor.jsx (96%) rename src/components/{ => library}/LibraryEditor.spec.jsx (97%) create mode 100644 src/components/library/index.js rename src/components/{ => toolchain}/GraphicalEditor.css (100%) rename src/components/{ => toolchain}/GraphicalEditor.jsx (100%) rename src/components/{ => toolchain}/ToolchainBlock.jsx (100%) rename src/components/{ => toolchain}/ToolchainConnection.jsx (100%) rename src/components/{ => toolchain}/ToolchainEditor.css (100%) rename src/components/{ => toolchain}/ToolchainEditor.jsx (99%) rename src/components/{ => toolchain}/ToolchainModal.jsx (98%) create mode 100644 src/components/toolchain/index.js diff --git a/src/components/EntityDetail.jsx b/src/components/EntityDetail.jsx index d31da0a..eacea88 100644 --- a/src/components/EntityDetail.jsx +++ b/src/components/EntityDetail.jsx @@ -27,12 +27,12 @@ import { import type { BeatObject } from '@helpers/beat'; import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import DataformatEditorContainer from './DataformatEditor.jsx'; -import AlgorithmEditorContainer from './AlgorithmEditor.jsx'; -import LibraryEditorContainer from './LibraryEditor.jsx'; -import DatabaseEditorContainer from './DatabaseEditor.jsx'; -import ExperimentEditorContainer from './ExperimentEditor.jsx'; -import ToolchainEditorContainer from './ToolchainEditor.jsx'; +import DataformatEditorContainer from './dataformat'; +import AlgorithmEditorContainer from './algorithm'; +import LibraryEditorContainer from './library'; +import DatabaseEditorContainer from './database'; +import ExperimentEditorContainer from './experiment'; +import ToolchainEditorContainer from './toolchain'; type Props = { match: any, diff --git a/src/components/AlgorithmEditor.jsx b/src/components/algorithm/AlgorithmEditor.jsx similarity index 99% rename from src/components/AlgorithmEditor.jsx rename to src/components/algorithm/AlgorithmEditor.jsx index 37c58e8..d9bf819 100644 --- a/src/components/AlgorithmEditor.jsx +++ b/src/components/algorithm/AlgorithmEditor.jsx @@ -24,11 +24,11 @@ import type { AlgorithmValidatorObject, BeatObject } from '@helpers/beat'; import * as Selectors from '@store/selectors.js'; -import CacheInput from './CacheInput.jsx'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; -import TypedField from './TypedField.jsx'; -import { getDefaultEntityObject } from './EntityDetail.jsx'; +import CacheInput from '../CacheInput.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; +import TypedField from '../TypedField.jsx'; +import { getDefaultEntityObject } from '../EntityDetail.jsx'; type Props = { data: BeatObject, diff --git a/src/components/AlgorithmEditor.spec.jsx b/src/components/algorithm/AlgorithmEditor.spec.jsx similarity index 99% rename from src/components/AlgorithmEditor.spec.jsx rename to src/components/algorithm/AlgorithmEditor.spec.jsx index 27d1aee..ea9e87c 100644 --- a/src/components/AlgorithmEditor.spec.jsx +++ b/src/components/algorithm/AlgorithmEditor.spec.jsx @@ -5,7 +5,7 @@ import { mount } from 'enzyme'; import sinon from 'sinon'; import { spies } from '@test'; -import { AlgorithmEditor as C } from './AlgorithmEditor.jsx'; +import { AlgorithmEditor as C } from '.'; import testAlgs from '@test/test_algs.json'; import testDfs from '@test/test_dfs.json'; diff --git a/src/components/algorithm/index.js b/src/components/algorithm/index.js new file mode 100644 index 0000000..ee4f492 --- /dev/null +++ b/src/components/algorithm/index.js @@ -0,0 +1,8 @@ +// @flow +import ConnectedAlgorithmEditor, {AlgorithmEditor} from './AlgorithmEditor.jsx'; + +export { + AlgorithmEditor, +}; + +export default ConnectedAlgorithmEditor; diff --git a/src/components/DatabaseEditor.jsx b/src/components/database/DatabaseEditor.jsx similarity index 98% rename from src/components/DatabaseEditor.jsx rename to src/components/database/DatabaseEditor.jsx index 77456c8..96be24f 100644 --- a/src/components/DatabaseEditor.jsx +++ b/src/components/database/DatabaseEditor.jsx @@ -33,10 +33,10 @@ import type { BeatObject } from '@helpers/beat'; import * as Selectors from '@store/selectors.js'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import CacheInput from './CacheInput.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; -import TypedField from './TypedField.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import CacheInput from '../CacheInput.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; +import TypedField from '../TypedField.jsx'; type Props = { diff --git a/src/components/DatabaseEditor.spec.jsx b/src/components/database/DatabaseEditor.spec.jsx similarity index 99% rename from src/components/DatabaseEditor.spec.jsx rename to src/components/database/DatabaseEditor.spec.jsx index 7cc2790..a4c5677 100644 --- a/src/components/DatabaseEditor.spec.jsx +++ b/src/components/database/DatabaseEditor.spec.jsx @@ -5,7 +5,7 @@ import { mount } from 'enzyme'; import sinon from 'sinon'; import { spies } from '@test'; -import { DatabaseEditor as C } from './DatabaseEditor.jsx'; +import { DatabaseEditor as C } from '.'; import testDbs from '@test/test_dbs.json'; import testDfs from '@test/test_dfs.json'; diff --git a/src/components/database/index.js b/src/components/database/index.js new file mode 100644 index 0000000..6436068 --- /dev/null +++ b/src/components/database/index.js @@ -0,0 +1,8 @@ +// @flow +import ConnectedDatabaseEditor, {DatabaseEditor} from './DatabaseEditor.jsx'; + +export { + DatabaseEditor, +}; + +export default ConnectedDatabaseEditor; diff --git a/src/components/DataformatEditor.jsx b/src/components/dataformat/DataformatEditor.jsx similarity index 97% rename from src/components/DataformatEditor.jsx rename to src/components/dataformat/DataformatEditor.jsx index 720f2f7..7cd891c 100644 --- a/src/components/DataformatEditor.jsx +++ b/src/components/dataformat/DataformatEditor.jsx @@ -27,10 +27,10 @@ import type { MapStateToProps, MapDispatchToProps } from 'react-redux'; import * as Selectors from '@store/selectors.js'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import CacheInput from './CacheInput.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; -import TypedField from './TypedField.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import CacheInput from '../CacheInput.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; +import TypedField from '../TypedField.jsx'; import { nameValidator, BUILTIN_TYPES } from '@helpers/beat'; import type { diff --git a/src/components/DataformatEditor.spec.jsx b/src/components/dataformat/DataformatEditor.spec.jsx similarity index 99% rename from src/components/DataformatEditor.spec.jsx rename to src/components/dataformat/DataformatEditor.spec.jsx index 5f68aa9..ca2be8d 100644 --- a/src/components/DataformatEditor.spec.jsx +++ b/src/components/dataformat/DataformatEditor.spec.jsx @@ -5,7 +5,7 @@ import { mount } from 'enzyme'; import sinon from 'sinon'; import { spies } from '@test'; -import { DataformatEditor as C } from './DataformatEditor.jsx'; +import { DataformatEditor as C } from '.'; import testDfs from '@test/test_dfs.json'; diff --git a/src/components/dataformat/index.js b/src/components/dataformat/index.js new file mode 100644 index 0000000..9a1ab79 --- /dev/null +++ b/src/components/dataformat/index.js @@ -0,0 +1,8 @@ +// @flow +import ConnectedDataformatEditor, {DataformatEditor} from './DataformatEditor.jsx'; + +export { + DataformatEditor, +}; + +export default ConnectedDataformatEditor; diff --git a/src/components/ExperimentEditor.jsx b/src/components/experiment/ExperimentEditor.jsx similarity index 99% rename from src/components/ExperimentEditor.jsx rename to src/components/experiment/ExperimentEditor.jsx index 7c98040..cb4c026 100644 --- a/src/components/ExperimentEditor.jsx +++ b/src/components/experiment/ExperimentEditor.jsx @@ -33,13 +33,13 @@ import { changeObjFieldName } from '@helpers'; import * as Selectors from '@store/selectors.js'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import CacheInput from './CacheInput.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; -import TypedField from './TypedField.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import CacheInput from '../CacheInput.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; +import TypedField from '../TypedField.jsx'; -import GraphicalEditor from './GraphicalEditor.jsx'; -import type { BlockSet } from './ToolchainBlock.jsx'; +import { GraphicalEditor } from '../toolchain'; +import type { BlockSet } from '../toolchain'; import ExperimentModal from './ExperimentModal.jsx'; diff --git a/src/components/ExperimentEditor.spec.jsx b/src/components/experiment/ExperimentEditor.spec.jsx similarity index 98% rename from src/components/ExperimentEditor.spec.jsx rename to src/components/experiment/ExperimentEditor.spec.jsx index 7b0096d..3a2b42b 100644 --- a/src/components/ExperimentEditor.spec.jsx +++ b/src/components/experiment/ExperimentEditor.spec.jsx @@ -6,7 +6,7 @@ import sinon from 'sinon'; import { spies } from '@test'; import * as Selectors from '@store/selectors.js'; -import { ExperimentEditor as C } from './ExperimentEditor.jsx'; +import { ExperimentEditor as C } from '.'; import testAlgs from '@test/test_algs.json'; import testDbs from '@test/test_dbs.json'; diff --git a/src/components/ExperimentModal.jsx b/src/components/experiment/ExperimentModal.jsx similarity index 100% rename from src/components/ExperimentModal.jsx rename to src/components/experiment/ExperimentModal.jsx diff --git a/src/components/experiment/index.js b/src/components/experiment/index.js new file mode 100644 index 0000000..f530318 --- /dev/null +++ b/src/components/experiment/index.js @@ -0,0 +1,8 @@ +// @flow +import ConnectedExperimentEditor, {ExperimentEditor} from './ExperimentEditor.jsx'; + +export { + ExperimentEditor, +}; + +export default ConnectedExperimentEditor; diff --git a/src/components/LibraryEditor.jsx b/src/components/library/LibraryEditor.jsx similarity index 96% rename from src/components/LibraryEditor.jsx rename to src/components/library/LibraryEditor.jsx index 553d7b5..5789d74 100644 --- a/src/components/LibraryEditor.jsx +++ b/src/components/library/LibraryEditor.jsx @@ -30,10 +30,10 @@ import { changeObjFieldName } from '@helpers'; import * as Selectors from '@store/selectors.js'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import CacheInput from './CacheInput.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; -import TypedField from './TypedField.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import CacheInput from '../CacheInput.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; +import TypedField from '../TypedField.jsx'; type Props = { data: BeatObject, diff --git a/src/components/LibraryEditor.spec.jsx b/src/components/library/LibraryEditor.spec.jsx similarity index 97% rename from src/components/LibraryEditor.spec.jsx rename to src/components/library/LibraryEditor.spec.jsx index c5c6cfe..b25ff98 100644 --- a/src/components/LibraryEditor.spec.jsx +++ b/src/components/library/LibraryEditor.spec.jsx @@ -5,7 +5,7 @@ import { mount } from 'enzyme'; import sinon from 'sinon'; import { spies } from '@test'; -import { LibraryEditor as C } from './LibraryEditor.jsx'; +import { LibraryEditor as C } from '.'; import testLibs from '@test/test_libs.json'; diff --git a/src/components/library/index.js b/src/components/library/index.js new file mode 100644 index 0000000..e331ab4 --- /dev/null +++ b/src/components/library/index.js @@ -0,0 +1,8 @@ +// @flow +import ConnectedLibraryEditor, {LibraryEditor} from './LibraryEditor.jsx'; + +export { + LibraryEditor, +}; + +export default ConnectedLibraryEditor; diff --git a/src/components/GraphicalEditor.css b/src/components/toolchain/GraphicalEditor.css similarity index 100% rename from src/components/GraphicalEditor.css rename to src/components/toolchain/GraphicalEditor.css diff --git a/src/components/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx similarity index 100% rename from src/components/GraphicalEditor.jsx rename to src/components/toolchain/GraphicalEditor.jsx diff --git a/src/components/ToolchainBlock.jsx b/src/components/toolchain/ToolchainBlock.jsx similarity index 100% rename from src/components/ToolchainBlock.jsx rename to src/components/toolchain/ToolchainBlock.jsx diff --git a/src/components/ToolchainConnection.jsx b/src/components/toolchain/ToolchainConnection.jsx similarity index 100% rename from src/components/ToolchainConnection.jsx rename to src/components/toolchain/ToolchainConnection.jsx diff --git a/src/components/ToolchainEditor.css b/src/components/toolchain/ToolchainEditor.css similarity index 100% rename from src/components/ToolchainEditor.css rename to src/components/toolchain/ToolchainEditor.css diff --git a/src/components/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx similarity index 99% rename from src/components/ToolchainEditor.jsx rename to src/components/toolchain/ToolchainEditor.jsx index 50ca09d..8488766 100644 --- a/src/components/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -39,8 +39,8 @@ import * as Selectors from '@store/selectors.js'; import Block from './ToolchainBlock.jsx'; import type { BlockType, Props as BlockProps } from './ToolchainBlock.jsx'; import type { ConnectionType } from './ToolchainConnection.jsx'; -import ValidSchemaBadge from './ValidSchemaBadge.jsx'; -import CacheInput from './CacheInput.jsx'; +import ValidSchemaBadge from '../ValidSchemaBadge.jsx'; +import CacheInput from '../CacheInput.jsx'; import type { BlockSet } from './ToolchainBlock.jsx'; import EditModal from './ToolchainModal.jsx'; import GraphicalEditor, { diff --git a/src/components/ToolchainModal.jsx b/src/components/toolchain/ToolchainModal.jsx similarity index 98% rename from src/components/ToolchainModal.jsx rename to src/components/toolchain/ToolchainModal.jsx index b040438..48269c0 100644 --- a/src/components/ToolchainModal.jsx +++ b/src/components/toolchain/ToolchainModal.jsx @@ -27,8 +27,8 @@ import { UncontrolledButtonDropdown, DropdownToggle, DropdownMenu, DropdownItem, } from 'reactstrap'; -import CacheInput from './CacheInput.jsx'; -import DeleteInputBtn from './DeleteInputBtn.jsx'; +import CacheInput from '../CacheInput.jsx'; +import DeleteInputBtn from '../DeleteInputBtn.jsx'; import { generateNewKey } from '@helpers'; type Props = { diff --git a/src/components/toolchain/index.js b/src/components/toolchain/index.js new file mode 100644 index 0000000..40b14ad --- /dev/null +++ b/src/components/toolchain/index.js @@ -0,0 +1,11 @@ +// @flow +import ConnectedToolchainEditor, {ToolchainEditor} from './ToolchainEditor.jsx'; +import GraphicalEditor from './GraphicalEditor.jsx'; +export type { BlockSet } from './ToolchainBlock.jsx'; + +export { + ToolchainEditor, + GraphicalEditor, +}; + +export default ConnectedToolchainEditor; -- GitLab From d9d62a9d7a9cdde5f15483c3095329d65d146d03 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 11:06:50 +0100 Subject: [PATCH 35/51] add tc tests --- .../experiment/ExperimentEditor.spec.jsx | 2 +- .../toolchain/ToolchainEditor.spec.jsx | 47 +++++++++++++++++++ 2 files changed, 48 insertions(+), 1 deletion(-) create mode 100644 src/components/toolchain/ToolchainEditor.spec.jsx diff --git a/src/components/experiment/ExperimentEditor.spec.jsx b/src/components/experiment/ExperimentEditor.spec.jsx index 3a2b42b..cd97c31 100644 --- a/src/components/experiment/ExperimentEditor.spec.jsx +++ b/src/components/experiment/ExperimentEditor.spec.jsx @@ -52,7 +52,7 @@ describe('', () => { }); }); - describe('creates', () => { + describe.skip('creates', () => { it(`user/user/single/1/single_add`, () => { const expName = 'user/user/single/1/single_add'; const saveFunc = sinon.spy(); diff --git a/src/components/toolchain/ToolchainEditor.spec.jsx b/src/components/toolchain/ToolchainEditor.spec.jsx new file mode 100644 index 0000000..2754e0f --- /dev/null +++ b/src/components/toolchain/ToolchainEditor.spec.jsx @@ -0,0 +1,47 @@ +// @flow +import React from 'react'; +import { expect } from 'chai'; +import { mount } from 'enzyme'; +import sinon from 'sinon'; +import { spies } from '@test'; + +import { ToolchainEditor as C } from '.'; + +import testTcs from '@test/test_tcs.json'; + +describe('', () => { + let wrapper; + + afterEach(() => { + if(wrapper && wrapper.unmount) + wrapper.unmount(); + }); + + describe('accepts', () => { + const tcs = [ + ].concat(testTcs); + + tcs.forEach(function(tc){ + const saveFunc = () => {}; + it(`${ tc.name }`, () => { + wrapper = mount( + + ); + + expect(wrapper).to.have.props( + ['data', 'toolchains', 'saveFunc'] + ).deep.equal( + [tc, tcs, saveFunc] + ); + }); + }); + }); + + describe('creates', () => { + + }); +}); -- GitLab From a0308edd0c504e68fa97851c1f85807add1a1e10 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 11:59:28 +0100 Subject: [PATCH 36/51] add tc connection tests --- .../toolchain/ToolchainConnection.jsx | 4 +- .../toolchain/ToolchainConnection.spec.jsx | 103 ++++++++++++++++++ 2 files changed, 105 insertions(+), 2 deletions(-) create mode 100644 src/components/toolchain/ToolchainConnection.spec.jsx diff --git a/src/components/toolchain/ToolchainConnection.jsx b/src/components/toolchain/ToolchainConnection.jsx index a00acac..41d86f5 100644 --- a/src/components/toolchain/ToolchainConnection.jsx +++ b/src/components/toolchain/ToolchainConnection.jsx @@ -54,7 +54,7 @@ class ToolchainConnection extends React.PureComponent { strokeWidth={10} x1={fromLoc.x + 2} y1={fromLoc.y + 9} - x2={toLoc.x + 1} + x2={toLoc.x + 2} y2={toLoc.y + 9} > Connection from {conn.from} to {conn.to} synchronized to the {conn.channel} channel @@ -65,7 +65,7 @@ class ToolchainConnection extends React.PureComponent { strokeWidth={2} x1={fromLoc.x + 2} y1={fromLoc.y + 6} - x2={toLoc.x + 1} + x2={toLoc.x + 2} y2={toLoc.y + 6} > Connection from {conn.from} to {conn.to} synchronized to the {conn.channel} channel diff --git a/src/components/toolchain/ToolchainConnection.spec.jsx b/src/components/toolchain/ToolchainConnection.spec.jsx new file mode 100644 index 0000000..fb4f913 --- /dev/null +++ b/src/components/toolchain/ToolchainConnection.spec.jsx @@ -0,0 +1,103 @@ +// @flow +import React from 'react'; +import { expect } from 'chai'; +import { mount } from 'enzyme'; +import sinon from 'sinon'; +import { spies } from '@test'; + +import C from './ToolchainConnection.jsx'; + +describe('', () => { + let wrapper; + + afterEach(() => { + if(wrapper && wrapper.unmount) + wrapper.unmount(); + }); + + const testLocMap = { + block1: { + inputs: { + input1: { + x: 1, + y: 1, + }, + }, + outputs: { + output1: { + x: 5, + y: 1, + }, + }, + }, + block2: { + inputs: { + input2: { + x: 1, + y: 6, + }, + }, + outputs: { + output2: { + x: 5, + y: 6, + }, + }, + }, + }; + + const testConn = { + from: 'block1.output1', + to: 'block2.input2', + channel: 'testChannel', + }; + + const testChannelColor = 'pink'; + + it('accepts the test connection with the right props', () => { + wrapper = mount( + + + + ); + const c = wrapper.children(); + + expect(c).to.have.props( + ['locMap', 'connection', 'channelColor'] + ).deep.equal( + [testLocMap, testConn, testChannelColor] + ); + }); + + it('correctly styles the visible line', () => { + wrapper = mount( + + + + ); + const c = wrapper.children().find('line + line'); + + const expectedProps = { + stroke: 'pink', + strokeWidth: 2, + x1: 5 + 2, + y1: 1 + 6, + x2: 1 + 2, + y2: 6 + 6, + }; + + expect(c).to.have.props( + Object.keys(expectedProps) + ).deep.equal( + Object.values(expectedProps) + ); + }); +}); -- GitLab From f9c4d1f2a25cea149e4b01d10c16e25d0f88ee7f Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 15:57:30 +0100 Subject: [PATCH 37/51] add group functionality to tc editor, add multiblock features, fix scroll messing up area select --- .../experiment/ExperimentEditor.jsx | 5 +- src/components/toolchain/GraphicalEditor.jsx | 142 ++++++++----- src/components/toolchain/ToolchainBlock.jsx | 2 - src/components/toolchain/ToolchainEditor.jsx | 190 +++++++++++++----- src/helpers/beat.js | 4 + 5 files changed, 247 insertions(+), 96 deletions(-) diff --git a/src/components/experiment/ExperimentEditor.jsx b/src/components/experiment/ExperimentEditor.jsx index cb4c026..c575821 100644 --- a/src/components/experiment/ExperimentEditor.jsx +++ b/src/components/experiment/ExperimentEditor.jsx @@ -997,7 +997,9 @@ export class ExperimentEditor extends React.Component { } renderGraphicalEditor = () => { - const {representation, blocks, datasets, analyzers, connections} = this.props.toolchain.contents; + const tc = this.props.toolchain; + const {representation, blocks, datasets, analyzers, connections} = tc.contents; + const groups = tc.extraContents ? tc.extraContents.groups : []; return ( @@ -1007,6 +1009,7 @@ export class ExperimentEditor extends React.Component { datasets={datasets} analyzers={analyzers} connections={connections} + groups={groups} handleBlockClick={this.handleBlockClick} /> diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index 5625428..cba44ee 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -10,6 +10,11 @@ import type { ConnectionType } from './ToolchainConnection.jsx'; import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; import { changeObjFieldName, generateNewKey } from '@helpers'; +export type Group = { + name: string, + blocks: string[], +}; + type Props = { // the representation data of the toolchain (block locations & channel colors) repData: { @@ -24,6 +29,8 @@ type Props = { analyzers: AnalyzerBlock[], // the connections in the toolchain connections: ConnectionType[], + // block groups (not a feature in beat web) + groups: Group[], handleBlockClick?: (blockName: string, set: BlockSet) => any, // updates a block location to col #x & row #y updateBlockLocation?: (blockName: string, x: number, y: number) => any, @@ -211,6 +218,8 @@ export default class GraphicalEditor extends React.Component { initD3Drag = () => { setTimeout(() => { const updateBlockLocation = this.props.updateBlockLocation; + if(!updateBlockLocation) + return; const that = this; // currently debouncing isnt necessary perf-wise //let debouceTimeLast = 0; @@ -291,31 +300,33 @@ export default class GraphicalEditor extends React.Component { const d3this = d3.select(this); const x = Number.parseInt(dRect.attr('x')) / gridDistance; const y = Number.parseInt(dRect.attr('y')) / gridDistance; + const xShift = x - startX; + const yShift = y - startY; + let bNames = []; if(d3this.classed('areaSelect')){ - // multiselect move - const xShift = x - startX; - const yShift = y - startY; - that.state.selectedBlocks.forEach(b => { - const el = d3.select(`#block_${ b.name }`); - const bx = Number.parseFloat(el.attr('x')) / gridDistance + xShift; - const by = Number.parseFloat(el.attr('y')) / gridDistance + yShift; - - if(updateBlockLocation) - updateBlockLocation(b.name, bx, by); - }); - + bNames = that.state.selectedBlocks.map(b => b.name); + } else if(d3this.classed('tcGroup')){ + const gId = d3this.attr('id').slice(6); + const g = that.props.groups.find(g => g.name === gId); + if(!g) + return; + bNames = g.blocks; } else { - // single block - const bId = d3.select(this).attr('id').slice(6); - //console.log(`${ bId }: ${ x } | ${ y }`); - if(updateBlockLocation) - updateBlockLocation(bId, x, y); + bNames = [d3this.attr('id').slice(6)]; } + + bNames.forEach(b => { + const el = d3.select(`#block_${ b }`); + const bx = Number.parseFloat(el.attr('x')) / gridDistance + xShift; + const by = Number.parseFloat(el.attr('y')) / gridDistance + yShift; + + updateBlockLocation(b, bx, by); + }); dRect.remove(); } // all block elements should be draggable - d3.selectAll('.fo,.areaSelect').call( + d3.selectAll('.fo,.areaSelect,.tcGroup').call( d3.drag() .on('start', startDrag) .on('end', endDrag) @@ -411,7 +422,7 @@ export default class GraphicalEditor extends React.Component { // draw the puck d3.select('svg') - .insert('circle', '.tcConnection') + .insert('circle', '.backgroundLimit') .attr('class', 'puck background') .attr('cx', 0) .attr('cy', 0) @@ -432,7 +443,6 @@ export default class GraphicalEditor extends React.Component { // if the click event's target is the svg background, // trigger the svg action at the puck's current point .on('contextmenu', () => { - console.log(d3.event); if(!Array.from(d3.event.target.classList).includes('background')) return; this.triggerSvgAction(cx / gridDistance, cy / gridDistance, d3.event); @@ -451,15 +461,14 @@ export default class GraphicalEditor extends React.Component { return `${ startX },${ startY } ${ startX },${ currY } ${ currX },${ currY } ${ currX },${ startY }`; }; function startDrag(d) { - const [x, y] = clampD3EventLocationToGrid(d3.event.x, d3.event.y); - console.log(x); - console.log(y); + const [rawx, rawy] = d3.mouse(document.querySelector('svg')); + const [x, y] = clampD3EventLocationToGrid(rawx, rawy); startX = x; startY = y; currX = x; currY = y; d3.select('svg') - .insert('polygon', '.tcConnection') + .insert('polygon', '.backgroundLimit') .attr('class', 'tmp') .attr('fill', 'grey') .attr('stroke', 'black') @@ -491,7 +500,6 @@ export default class GraphicalEditor extends React.Component { .map(name => findBlock(name)) ; - console.log(blocksInArea); selectBlocks(blocksInArea); p.remove(); @@ -503,7 +511,8 @@ export default class GraphicalEditor extends React.Component { // update the temp rect function dragged(d) { - const [x, y] = clampD3EventLocationToGrid(d3.event.x, d3.event.y); + const [rawx, rawy] = d3.mouse(document.querySelector('svg')); + const [x, y] = clampD3EventLocationToGrid(rawx, rawy); currX = x; currY = y; d3.select('polygon.tmp') @@ -528,20 +537,24 @@ export default class GraphicalEditor extends React.Component { // scales width/height to the zoomlevel so the background grid lines cover the entire svg const scaledSvgWidth = svgWidth * (this.state.zoomLevel / 3000); const scaledSvgHeight = svgHeight * (this.state.zoomLevel / 3000); - const selBlockLocs = this.state.selectedBlocks.map(b => locMap[b.name].block); - - const selX = Math.min(...selBlockLocs.map(l => l.x)); - const selY = Math.min(...selBlockLocs.map(l => l.y)); - const selWidth = Math.max(...selBlockLocs.map(l => l.x + l.width - selX)); - const selHeight = Math.max(...selBlockLocs.map(l => l.y + l.height - selY)); - - const selectBoxCoords = { - x: selX - gridDistance, - y: selY - gridDistance, - width: selWidth + gridDistance * 2, - height: selHeight + gridDistance * 2, + + const getBlocksBoundingBox = (names: string[]) => { + const blockLocs = names.map(n => locMap[n].block); + const xMin = Math.min(...blockLocs.map(l => l.x)); + const yMin = Math.min(...blockLocs.map(l => l.y)); + const width = Math.max(...blockLocs.map(l => l.x + l.width - xMin)); + const height = Math.max(...blockLocs.map(l => l.y + l.height - yMin)); + + return { + x: xMin - gridDistance, + y: yMin - gridDistance, + width: width + gridDistance * 2, + height: height + gridDistance * 2, + }; }; + const selectBoxCoords = getBlocksBoundingBox(this.state.selectedBlocks.map(b => b.name)); + return (
@@ -598,17 +611,52 @@ export default class GraphicalEditor extends React.Component { }) } + + + + { + this.props.groups.map(({name, blocks}, i) => { + const {x, y, width, height} = getBlocksBoundingBox(blocks); + const nameClipId = `groupClip_${ name }`; + return ( + ({ group: name })} + renderTag='g' + > + + + ); + }) + } + { Number.isFinite(selectBoxCoords.x) && - + ({ selection: this.state.selectedBlocks })} + > + + } { diff --git a/src/components/toolchain/ToolchainBlock.jsx b/src/components/toolchain/ToolchainBlock.jsx index 961158a..489dc80 100644 --- a/src/components/toolchain/ToolchainBlock.jsx +++ b/src/components/toolchain/ToolchainBlock.jsx @@ -107,8 +107,6 @@ class ToolchainBlock extends React.PureComponent { const inputClipId = `${ name }-input`; const outputClipId = `${ name }-output`; - //console.log(locMap); - return ( {/* right-click menu that wraps the background rectangle of the block */} diff --git a/src/components/toolchain/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx index 8488766..1bd37d0 100644 --- a/src/components/toolchain/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -47,6 +47,7 @@ import GraphicalEditor, { blockWidth, gridDistance, } from './GraphicalEditor.jsx'; +import type { Group } from './GraphicalEditor.jsx'; type Props = { // saved data for the current toolchain @@ -67,7 +68,7 @@ type State = { active: boolean, }, // the clipboard for copy/pasting blocks - clipboard?: BlockType | BlockType[], + clipboard?: BlockType[], }; // makes sure the toolchain object is valid before passing it to the ToolchainEditor @@ -75,6 +76,7 @@ const getValidObj = (data = {}) => { const getObj = { name: '', contents: {}, + extraContents: {}, ...JSON.parse(JSON.stringify(data)) }; @@ -93,6 +95,10 @@ const getValidObj = (data = {}) => { }, ...getObj.contents, }, + extraContents: { + groups: [], + ...getObj.extraContents + } }; return obj; @@ -134,6 +140,18 @@ export class ToolchainEditor extends React.Component { }); } + setGroups = (groups: Group[]) => { + this.setState({ + cache: { + ...this.state.cache, + extraContents: { + ...this.state.cache.extraContents, + groups, + } + } + }); + } + // validates the name of the toolchain validatorFunc = nameValidator('toolchain', this.props.toolchains.map(o => o.name)); @@ -180,27 +198,6 @@ export class ToolchainEditor extends React.Component { }); } - // deletes a block from the toolchain - deleteBlock = (name: string, set: BlockSet) => { - const rep = {...this.state.cache.contents.representation}; - rep.blocks = {...rep.blocks}; - delete rep.blocks[name]; - rep.connections = Object.entries(rep.connections).filter(([name, rep]) => { - const [from, to] = name.split('/'); - return from.split('.')[0] !== name && to.split('.')[0] !== name; - }) - .reduce((cs, c) => ({...cs, c}), {}) - ; - const newContents = { - ...this.state.cache.contents, - [set]: this.state.cache.contents[set].filter(s => s.name !== name), - connections: this.state.cache.contents.connections.filter(c => c.from.split('.')[0] !== name && c.to.split('.')[0] !== name), - representation: rep, - }; - - this.setContents(newContents); - } - // changes a block's name given the set it belongs to, the old name, and the new name updateBlockName = (set: BlockSet, oldName: string, newName: string) => { const updateConn = (from, to): string[] => { @@ -246,11 +243,17 @@ export class ToolchainEditor extends React.Component { representation: rep, }; + const newGroups = this.state.cache.extraContents.groups + .map(({ name, blocks }) => ({ name, blocks: blocks.map(n => n === oldName ? newName : n) })); this.setState({ ...this.state, cache: { ...this.state.cache, contents: newContents, + extraContents: { + ...this.state.cache.extraContents, + groups: newGroups, + }, }, modalBlockInfo: { active: true, @@ -313,9 +316,7 @@ export class ToolchainEditor extends React.Component { this.setContents(newContents); } - // adds a new block at a certain location - // optionally can pass a block to copy - addBlock = (blockName: string, set: BlockSet, x: number, y: number, copyBlock?: any) => { + generateNewBlockData = (blockName: string, set: BlockSet, x: number, y: number, copyBlock?: any) => { let newBlock = copyBlock; if(newBlock === undefined){ newBlock = {}; @@ -329,21 +330,45 @@ export class ToolchainEditor extends React.Component { } newBlock.name = blockName; - const rep = {...this.state.cache.contents.representation}; - - rep.blocks[blockName] = { + const repBlock = { col: x, row: y, height: 3, width: blockWidth / gridDistance, }; - if(set === 'datasets'){ - rep.channel_colors[blockName] = getRandomBrightColor(); - } + let newChannelColor = set === 'datasets' ? getRandomBrightColor() : null; + + return { + block: newBlock, + rep: repBlock, + channelColor: newChannelColor, + }; + } + + // adds a new block at a certain location + // optionally can pass a block to copy + addBlocks = (blockData: any[]) => { + const newBlocks = blockData.map(d => this.generateNewBlockData(...d)); + const sets = blockData.map(b => b[1]); + + const rep = { + ...this.state.cache.contents.representation, + blocks: { + ...this.state.cache.contents.representation.blocks, + ...newBlocks.reduce((newReps, b) => ({...newReps, [b.block.name]: b.rep}), {}), + }, + channel_colors: { + ...this.state.cache.contents.representation.channel_colors, + ...newBlocks.filter(b => b.channelColor !== null) + .reduce((newColors, b) => ({...newColors, [b.block.name]: b.channelColor}), {}), + } + }; const newContents = { - [set]: [...this.state.cache.contents[set], newBlock], + blocks: [...this.state.cache.contents.blocks, ...newBlocks.filter((b, i) => sets[i] === 'blocks').map(b => b.block)], + datasets: [...this.state.cache.contents.datasets, ...newBlocks.filter((b, i) => sets[i] === 'datasets').map(b => b.block)], + analyzers: [...this.state.cache.contents.analyzers, ...newBlocks.filter((b, i) => sets[i] === 'analyzers').map(b => b.block)], representation: rep, }; @@ -385,6 +410,7 @@ export class ToolchainEditor extends React.Component { .reduce((cs, c) => ({...cs, c}), {}) ; const newContents = { + ...this.state.cache.contents, [set]: this.state.cache.contents[set].filter(s => s.name !== blockName), connections: this.state.cache.contents.connections.filter(c => { if(c.to.startsWith(`${ blockName }.`) || c.from.startsWith(`${ blockName }.`)) @@ -393,6 +419,21 @@ export class ToolchainEditor extends React.Component { }), }; + const newGroups = this.state.cache.extraContents.groups + .map(({ name, blocks }) => ({ name, blocks: blocks.filter(n => n !== name) })) + .filter(g => g.blocks.length !== 0); + this.setState({ + ...this.state, + cache: { + ...this.state.cache, + contents: newContents, + extraContents: { + ...this.state.cache.extraContents, + groups: newGroups, + }, + } + }); + this.setContents(newContents); } @@ -513,20 +554,21 @@ export class ToolchainEditor extends React.Component { switch(clicked){ case 'addBlock': newBlockName = generateNewKey('block', usedNames); - this.addBlock(newBlockName, 'blocks', x, y); + this.addBlocks([[newBlockName, 'blocks', x, y]]); break; case 'addDataset': newBlockName = generateNewKey('dataset', usedNames); - this.addBlock(newBlockName, 'datasets', x, y); + this.addBlocks([[newBlockName, 'datasets', x, y]]); break; case 'addAnalyzer': newBlockName = generateNewKey('analyzer', usedNames); - this.addBlock(newBlockName, 'analyzers', x, y); + this.addBlocks([[newBlockName, 'analyzers', x, y]]); break; case 'paste': - if(!this.state.clipboard) + if(!this.state.clipboard || this.state.clipboard.length === 0) return; - const blocksToCopy = Array.isArray(this.state.clipboard) ? this.state.clipboard : [this.state.clipboard]; + const blocksToCopy = this.state.clipboard; + const sets = blocksToCopy.map(b => { if(!b.hasOwnProperty('inputs')) return 'datasets'; @@ -534,23 +576,20 @@ export class ToolchainEditor extends React.Component { return 'analyzers'; return 'blocks'; }); - - if(blocksToCopy.length === 0) - return; //first element in the blocksToCopy array is the one used to offset the other blocks const b0 = blocksToCopy[0]; const b0Rep = representation.blocks[b0.name]; const offsetX = x - b0Rep.col; const offsetY = y - b0Rep.row; - blocksToCopy.forEach((b, i, bs) => { + const newBlockData = blocksToCopy.map((b, i, bs) => { const bRep = representation.blocks[b.name]; const set = sets[i]; const newX = bRep.col + offsetX; const newY = bRep.row + offsetY; const newName = generateNewKey(b.name, usedNames); - this.addBlock(newName, set, newX, newY, {...b}); + return [newName, set, newX, newY, {...b}]; }); - + this.addBlocks(newBlockData); break; default: break; @@ -558,7 +597,7 @@ export class ToolchainEditor extends React.Component { } // copy either a block or array of blocks to the clipboard - copyToClipboard = (data: any | any[]) => { + copyToClipboard = (data: any[]) => { this.setState({ ...this.state, clipboard: data, @@ -573,7 +612,7 @@ export class ToolchainEditor extends React.Component { this.deleteBlock(name, set); break; case 'copy': - this.copyToClipboard(this.state.cache.contents[set].find(b => b.name === name)); + this.copyToClipboard([this.state.cache.contents[set].find(b => b.name === name)]); break; default: break; @@ -592,6 +631,42 @@ export class ToolchainEditor extends React.Component { } } + // handles a right click on a group + handleGroupContextMenu = (e: any, data: { group: string, clicked: string }) => { + const {group, clicked} = data; + const groups = this.state.cache.extraContents.groups; + switch(clicked){ + case 'delete': + this.setGroups(groups.filter(g => g.name !== group)); + break; + default: + break; + } + } + + // handles a right click on an area selection + handleAreaSelectContextMenu = (e: any, data: { selection: BlockType[], clicked: string }) => { + const {selection, clicked} = data; + const groups = this.state.cache.extraContents.groups; + switch(clicked){ + case 'createGroup': + const newGroupName = generateNewKey('group', groups.map(g => g.name)); + this.setGroups([ + ...groups, + { + name: newGroupName, + blocks: selection.map(b => b.name), + } + ]); + break; + case 'copy': + this.copyToClipboard(selection); + break; + default: + break; + } + } + // handles left clicking on a block handleBlockClick = (blockName: string, set: BlockSet) => { const newMBI = { @@ -619,6 +694,7 @@ export class ToolchainEditor extends React.Component { datasets={this.state.cache.contents.datasets} analyzers={this.state.cache.contents.analyzers} connections={this.state.cache.contents.connections} + groups={this.state.cache.extraContents.groups} handleBlockClick={this.handleBlockClick} updateBlockLocation={this.updateBlockLocation} createConnection={this.createConnection} @@ -675,6 +751,28 @@ export class ToolchainEditor extends React.Component { } + + + Delete Group + + + + + Copy Blocks + + + Create Group + + } > @@ -758,7 +856,7 @@ export class ToolchainEditor extends React.Component { className='tcName' placeholder='New toolchain name...' value={this.state.cache.name} - onChange={e => this.setState({ cache: {...this.state.cache, 'name': e.target.value}})} + onChange={e => this.setState({ ...this.state, cache: {...this.state.cache, 'name': e.target.value}})} validateFunc={str => this.nameIsValid(str)} /> diff --git a/src/helpers/beat.js b/src/helpers/beat.js index a6358bc..d46bc3e 100644 --- a/src/helpers/beat.js +++ b/src/helpers/beat.js @@ -2,8 +2,12 @@ export type BeatEntity = 'database' | 'library' | 'dataformat' | 'algorithm' | 'toolchain' | 'experiment'; export type BeatObject = { + // name of the object name: string, + // contents (whats stored in the JSON files in the beat prefix) contents: any, + // extra contents that are additions, arent relevant to the web platform, and dont conform to the BEAT schemas + extraContents?: any, }; export type BeatSettings = { -- GitLab From 8a07a16ec3b4c4aebf54a58e158d440f7b69b28a Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 16:11:06 +0100 Subject: [PATCH 38/51] rm need to scale d3 event loc by using d3.mouse --- src/components/toolchain/GraphicalEditor.jsx | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index cba44ee..7da5c72 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -197,9 +197,8 @@ export default class GraphicalEditor extends React.Component { }; clampD3EventLocationToGrid = (d3X: number, d3Y: number): [number, number] => { - const [sx, sy] = this.scaleD3EventLocation(d3X, d3Y); - const x = Math.round(sx / gridDistance) * gridDistance; - const y = Math.round(sy / gridDistance) * gridDistance; + const x = Math.round(d3X / gridDistance) * gridDistance; + const y = Math.round(d3Y / gridDistance) * gridDistance; return [x, y]; }; @@ -432,7 +431,8 @@ export default class GraphicalEditor extends React.Component { // needs to scale to the zoomlevel d3.select('svg') .on('mousemove', () => { - const [x, y] = clampD3EventLocationToGrid(d3.event.layerX, d3.event.layerY); + const [rawx, rawy] = d3.mouse(document.querySelector('svg')); + const [x, y] = clampD3EventLocationToGrid(rawx, rawy); cx = x; cy = y; d3.select('.puck') -- GitLab From 25a3ec09dedf0b8e4695b33205a2a8b93796bcd4 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 16:25:53 +0100 Subject: [PATCH 39/51] prod needs diff publicpath without dev server & add es6-compat uglify --- package-lock.json | 384 ++++++++++++++++++++++++++++++++++++++++++++-- package.json | 1 + webpack.config.js | 5 +- 3 files changed, 372 insertions(+), 18 deletions(-) diff --git a/package-lock.json b/package-lock.json index d2ca524..a3cad5f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -326,6 +326,12 @@ "normalize-path": "2.1.1" } }, + "aproba": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.2.0.tgz", + "integrity": "sha512-Y9J6ZjXtoYh8RnXVCMOU/ttDmk1aBjunq9vO0ta5x85WDQiQfUF9sIPBITdbiiIVcBo03Hi3jMxigBtsddlXRw==", + "dev": true + }, "argparse": { "version": "1.0.9", "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.9.tgz", @@ -2110,6 +2116,27 @@ "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=", "dev": true }, + "cacache": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/cacache/-/cacache-10.0.2.tgz", + "integrity": "sha512-dljb7dk1jqO5ogE+dRpoR9tpHYv5xz9vPSNunh1+0wRuNdYxmzp9WmsyokgW/DUF1FDRVA/TMsmxt027R8djbQ==", + "dev": true, + "requires": { + "bluebird": "3.5.0", + "chownr": "1.0.1", + "glob": "7.1.2", + "graceful-fs": "4.1.11", + "lru-cache": "4.1.1", + "mississippi": "1.3.0", + "mkdirp": "0.5.1", + "move-concurrently": "1.0.1", + "promise-inflight": "1.0.1", + "rimraf": "2.6.2", + "ssri": "5.0.0", + "unique-filename": "1.1.0", + "y18n": "3.2.1" + } + }, "cache-base": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", @@ -2355,6 +2382,12 @@ "readdirp": "2.1.0" } }, + "chownr": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-1.0.1.tgz", + "integrity": "sha1-4qdQQqlVGQi+vSW4Uj1fl2nXkYE=", + "dev": true + }, "ci-info": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.1.1.tgz", @@ -2522,6 +2555,7 @@ "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", "dev": true, + "optional": true, "requires": { "center-align": "0.1.3", "right-align": "0.1.3", @@ -2532,7 +2566,8 @@ "version": "0.0.2", "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", - "dev": true + "dev": true, + "optional": true } } }, @@ -2868,6 +2903,20 @@ "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=", "dev": true }, + "copy-concurrently": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/copy-concurrently/-/copy-concurrently-1.0.5.tgz", + "integrity": "sha512-f2domd9fsVDFtaFcbaRZuYXwtdmnzqbADSwhSWYxYB/Q8zsdUUFMXVRwXGDMWmbEzAn1kdRrtI1T/KTFOL4X2A==", + "dev": true, + "requires": { + "aproba": "1.2.0", + "fs-write-stream-atomic": "1.0.10", + "iferr": "0.1.5", + "mkdirp": "0.5.1", + "rimraf": "2.6.2", + "run-queue": "1.0.3" + } + }, "copy-descriptor": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", @@ -3237,6 +3286,12 @@ "integrity": "sha1-XQKkaFCt8bSjF5RqOSj8y1v9BCU=", "dev": true }, + "cyclist": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/cyclist/-/cyclist-0.2.2.tgz", + "integrity": "sha1-GzN5LhHpFKL9bW7WRHRkRE5fpkA=", + "dev": true + }, "d": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz", @@ -3945,6 +4000,18 @@ "readable-stream": "2.3.3" } }, + "duplexify": { + "version": "3.5.1", + "resolved": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", + "integrity": "sha512-j5goxHTwVED1Fpe5hh3q9R93Kip0Bg2KVAt4f8CEYM3UEwYcPSvWbXaUQOzdX/HtiNomipv+gU7ASQPDbV7pGQ==", + "dev": true, + "requires": { + "end-of-stream": "1.4.0", + "inherits": "2.0.3", + "readable-stream": "2.3.3", + "stream-shift": "1.0.0" + } + }, "ecc-jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", @@ -4002,6 +4069,15 @@ "iconv-lite": "0.4.19" } }, + "end-of-stream": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.0.tgz", + "integrity": "sha1-epDYM+/abPpurA9JSduw+tOmMgY=", + "dev": true, + "requires": { + "once": "1.4.0" + } + }, "engine.io": { "version": "3.1.4", "resolved": "https://registry.npmjs.org/engine.io/-/engine.io-3.1.4.tgz", @@ -5146,6 +5222,16 @@ "integrity": "sha512-aWKHYs3UECgpwrIDVUiABjSC8dgaKmonymQDWO+6FhGcp9lnnxdDBE6Sfm3F7YaRPfLYsWAY4lndBrfrfyn+9g==", "dev": true }, + "flush-write-stream": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/flush-write-stream/-/flush-write-stream-1.0.2.tgz", + "integrity": "sha1-yBuQ2HRnZvGmCaRoCZRsRd2K5Bc=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, "follow-redirects": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.0.0.tgz", @@ -5226,6 +5312,16 @@ "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=", "dev": true }, + "from2": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", + "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, "fs-access": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/fs-access/-/fs-access-1.0.1.tgz", @@ -5246,6 +5342,18 @@ "universalify": "0.1.1" } }, + "fs-write-stream-atomic": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/fs-write-stream-atomic/-/fs-write-stream-atomic-1.0.10.tgz", + "integrity": "sha1-tH31NJPvkR33VzHnCp3tAYnbQMk=", + "dev": true, + "requires": { + "graceful-fs": "4.1.11", + "iferr": "0.1.5", + "imurmurhash": "0.1.4", + "readable-stream": "2.3.3" + } + }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -5692,8 +5800,7 @@ "jsbn": { "version": "0.1.1", "bundled": true, - "dev": true, - "optional": true + "dev": true }, "json-schema": { "version": "0.2.3", @@ -6961,6 +7068,12 @@ "integrity": "sha1-vjPUCsEO8ZJnAfbwii2G+/0a0+Q=", "dev": true }, + "iferr": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/iferr/-/iferr-0.1.5.tgz", + "integrity": "sha1-xg7taebY/bazEEofy8ocGS3FtQE=", + "dev": true + }, "ignore": { "version": "3.3.7", "resolved": "https://registry.npmjs.org/ignore/-/ignore-3.3.7.tgz", @@ -9020,6 +9133,24 @@ "is-plain-obj": "1.1.0" } }, + "mississippi": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mississippi/-/mississippi-1.3.0.tgz", + "integrity": "sha1-0gFYPrEjJ+PFwWQqQEqcrPlONPU=", + "dev": true, + "requires": { + "concat-stream": "1.6.0", + "duplexify": "3.5.1", + "end-of-stream": "1.4.0", + "flush-write-stream": "1.0.2", + "from2": "2.3.0", + "parallel-transform": "1.1.0", + "pump": "1.0.3", + "pumpify": "1.3.5", + "stream-each": "1.2.2", + "through2": "2.0.3" + } + }, "mixin-deep": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.0.tgz", @@ -9158,6 +9289,20 @@ } } }, + "move-concurrently": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/move-concurrently/-/move-concurrently-1.0.1.tgz", + "integrity": "sha1-viwAX9oy4LKa8fBdfEszIUxwH5I=", + "dev": true, + "requires": { + "aproba": "1.2.0", + "copy-concurrently": "1.0.5", + "fs-write-stream-atomic": "1.0.10", + "mkdirp": "0.5.1", + "rimraf": "2.6.2", + "run-queue": "1.0.3" + } + }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", @@ -9969,6 +10114,17 @@ "integrity": "sha512-lQe48YPsMJAig+yngZ87Lus+NF+3mtu7DVOBu6b/gHO1YpKwIj5AWjZ/TOS7i46HD/UixzWb1zeWDZfGZ3iYcg==", "dev": true }, + "parallel-transform": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/parallel-transform/-/parallel-transform-1.1.0.tgz", + "integrity": "sha1-1BDwZbBdojCB/NEPKIVMKb2jOwY=", + "dev": true, + "requires": { + "cyclist": "0.2.2", + "inherits": "2.0.3", + "readable-stream": "2.3.3" + } + }, "param-case": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/param-case/-/param-case-2.1.1.tgz", @@ -12303,6 +12459,12 @@ "any-promise": "0.1.0" } }, + "promise-inflight": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/promise-inflight/-/promise-inflight-1.0.1.tgz", + "integrity": "sha1-mEcocL8igTL8vdhoEputEsPAKeM=", + "dev": true + }, "prop-types": { "version": "15.6.0", "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.6.0.tgz", @@ -12374,6 +12536,27 @@ "randombytes": "2.0.5" } }, + "pump": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/pump/-/pump-1.0.3.tgz", + "integrity": "sha512-8k0JupWme55+9tCVE+FS5ULT3K6AbgqrGa58lTT49RpyfwwcGedHqaC5LlQNdEAumn/wFsu6aPwkuPMioy8kqw==", + "dev": true, + "requires": { + "end-of-stream": "1.4.0", + "once": "1.4.0" + } + }, + "pumpify": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/pumpify/-/pumpify-1.3.5.tgz", + "integrity": "sha1-G2ccYZlAq8rqwK0OOjwWS+dgmTs=", + "dev": true, + "requires": { + "duplexify": "3.5.1", + "inherits": "2.0.3", + "pump": "1.0.3" + } + }, "punycode": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", @@ -13411,6 +13594,15 @@ "is-promise": "2.1.0" } }, + "run-queue": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/run-queue/-/run-queue-1.0.3.tgz", + "integrity": "sha1-6Eg5bwV9Ij8kOGkkYY4laUFh7Ec=", + "dev": true, + "requires": { + "aproba": "1.2.0" + } + }, "rw": { "version": "1.3.3", "resolved": "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz", @@ -13514,6 +13706,12 @@ "statuses": "1.3.1" } }, + "serialize-javascript": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-1.4.0.tgz", + "integrity": "sha1-fJWFFNtqwkQ6irwGLcn3iGp/YAU=", + "dev": true + }, "serve-index": { "version": "1.9.1", "resolved": "https://registry.npmjs.org/serve-index/-/serve-index-1.9.1.tgz", @@ -14167,6 +14365,15 @@ "tweetnacl": "0.14.5" } }, + "ssri": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/ssri/-/ssri-5.0.0.tgz", + "integrity": "sha512-728D4yoQcQm1ooZvSbywLkV1RjfITZXh0oWrhM/lnsx3nAHx7LsRGJWB/YyvoceAYRq98xqbstiN4JBv1/wNHg==", + "dev": true, + "requires": { + "safe-buffer": "5.1.1" + } + }, "stackframe": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/stackframe/-/stackframe-0.3.1.tgz", @@ -14283,6 +14490,16 @@ "readable-stream": "2.3.3" } }, + "stream-each": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/stream-each/-/stream-each-1.2.2.tgz", + "integrity": "sha512-mc1dbFhGBxvTM3bIWmAAINbqiuAk9TATcfIQC8P+/+HJefgaiTlMn2dHvkX8qlI12KeYKSQ1Ua9RrIqrn1VPoA==", + "dev": true, + "requires": { + "end-of-stream": "1.4.0", + "stream-shift": "1.0.0" + } + }, "stream-http": { "version": "2.7.2", "resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.7.2.tgz", @@ -14296,6 +14513,12 @@ "xtend": "4.0.1" } }, + "stream-shift": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/stream-shift/-/stream-shift-1.0.0.tgz", + "integrity": "sha1-1cdSgl5TZ+eG944Y5EXqIjoVWVI=", + "dev": true + }, "stream-splicer": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/stream-splicer/-/stream-splicer-2.0.0.tgz", @@ -15299,25 +15522,63 @@ "optional": true }, "uglifyjs-webpack-plugin": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/uglifyjs-webpack-plugin/-/uglifyjs-webpack-plugin-0.4.6.tgz", - "integrity": "sha1-uVH0q7a9YX5m9j64kUmOORdj4wk=", + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/uglifyjs-webpack-plugin/-/uglifyjs-webpack-plugin-1.1.6.tgz", + "integrity": "sha512-VUja+7rYbznEvUaeb8IxOCTUrq4BCb1ml0vffa+mfwKtrAwlqnU0ENF14DtYltV1cxd/HSuK51CCA/D/8kMQVw==", "dev": true, "requires": { - "source-map": "0.5.7", - "uglify-js": "2.8.29", - "webpack-sources": "1.1.0" + "cacache": "10.0.2", + "find-cache-dir": "1.0.0", + "schema-utils": "0.4.3", + "serialize-javascript": "1.4.0", + "source-map": "0.6.1", + "uglify-es": "3.3.5", + "webpack-sources": "1.1.0", + "worker-farm": "1.5.2" }, "dependencies": { - "uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", + "ajv": { + "version": "5.5.2", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", + "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", "dev": true, "requires": { - "source-map": "0.5.7", - "uglify-to-browserify": "1.0.2", - "yargs": "3.10.0" + "co": "4.6.0", + "fast-deep-equal": "1.0.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" + } + }, + "commander": { + "version": "2.12.2", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.12.2.tgz", + "integrity": "sha512-BFnaq5ZOGcDN7FlrtBT4xxkgIToalIIxwjxLWVJ8bGTpe1LroqMiqQXdA7ygc7CRvaYS+9zfPGFnJqFSayx+AA==", + "dev": true + }, + "schema-utils": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-0.4.3.tgz", + "integrity": "sha512-sgv/iF/T4/SewJkaVpldKC4WjSkz0JsOh2eKtxCPpCO1oR05+7MOF+H476HVRbLArkgA7j5TRJJ4p2jdFkUGQQ==", + "dev": true, + "requires": { + "ajv": "5.5.2", + "ajv-keywords": "2.1.0" + } + }, + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true + }, + "uglify-es": { + "version": "3.3.5", + "resolved": "https://registry.npmjs.org/uglify-es/-/uglify-es-3.3.5.tgz", + "integrity": "sha512-7IvaFuYtfbcXm0fGb13mmRYVQdzQDXETAtvYHbCDPt2V88Y8l2HaULOyW6ueoYA0JhGIcLK7dtHkDcBWySqnBw==", + "dev": true, + "requires": { + "commander": "2.12.2", + "source-map": "0.6.1" } } } @@ -15412,6 +15673,24 @@ "integrity": "sha1-/+3ks2slKQaW5uFl1KWe25mOawI=", "dev": true }, + "unique-filename": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.0.tgz", + "integrity": "sha1-0F8v5AMlYIcfMOk8vnNe6iAVFPM=", + "dev": true, + "requires": { + "unique-slug": "2.0.0" + } + }, + "unique-slug": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unique-slug/-/unique-slug-2.0.0.tgz", + "integrity": "sha1-22Z258fMBimHj/GWCXx4hVrp9Ks=", + "dev": true, + "requires": { + "imurmurhash": "0.1.4" + } + }, "unist-util-find-all-after": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/unist-util-find-all-after/-/unist-util-find-all-after-1.0.1.tgz", @@ -16009,6 +16288,65 @@ "has-flag": "2.0.0" } }, + "uglify-js": { + "version": "2.8.29", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", + "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", + "dev": true, + "requires": { + "source-map": "0.5.7", + "uglify-to-browserify": "1.0.2", + "yargs": "3.10.0" + }, + "dependencies": { + "camelcase": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", + "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", + "dev": true + }, + "cliui": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", + "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", + "dev": true, + "requires": { + "center-align": "0.1.3", + "right-align": "0.1.3", + "wordwrap": "0.0.2" + } + }, + "yargs": { + "version": "3.10.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", + "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", + "dev": true, + "requires": { + "camelcase": "1.2.1", + "cliui": "2.1.0", + "decamelize": "1.2.0", + "window-size": "0.1.0" + } + } + } + }, + "uglifyjs-webpack-plugin": { + "version": "0.4.6", + "resolved": "https://registry.npmjs.org/uglifyjs-webpack-plugin/-/uglifyjs-webpack-plugin-0.4.6.tgz", + "integrity": "sha1-uVH0q7a9YX5m9j64kUmOORdj4wk=", + "dev": true, + "requires": { + "source-map": "0.5.7", + "uglify-js": "2.8.29", + "webpack-sources": "1.1.0" + } + }, + "wordwrap": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", + "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", + "dev": true + }, "yargs": { "version": "8.0.2", "resolved": "https://registry.npmjs.org/yargs/-/yargs-8.0.2.tgz", @@ -16696,6 +17034,16 @@ "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=", "dev": true }, + "worker-farm": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/worker-farm/-/worker-farm-1.5.2.tgz", + "integrity": "sha512-XxiQ9kZN5n6mmnW+mFJ+wXjNNI/Nx4DIdaAKLX1Bn6LYBWlN/zaBhu34DQYPZ1AJobQuu67S2OfDdNSVULvXkQ==", + "dev": true, + "requires": { + "errno": "0.1.4", + "xtend": "4.0.1" + } + }, "worker-loader": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/worker-loader/-/worker-loader-1.1.0.tgz", @@ -16823,6 +17171,7 @@ "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", "dev": true, + "optional": true, "requires": { "camelcase": "1.2.1", "cliui": "2.1.0", @@ -16834,7 +17183,8 @@ "version": "1.2.1", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "dev": true + "dev": true, + "optional": true } } }, diff --git a/package.json b/package.json index 1ca3a2e..1bd6fc6 100644 --- a/package.json +++ b/package.json @@ -72,6 +72,7 @@ "stylelint": "^8.4.0", "stylelint-config-standard": "^18.0.0", "svg-inline-loader": "^0.8.0", + "uglifyjs-webpack-plugin": "^1.1.6", "webpack": "^3.10.0", "webpack-dev-server": "^2.10.1", "webpack-visualizer-plugin": "^0.1.11", diff --git a/webpack.config.js b/webpack.config.js index fdf016d..8176be2 100644 --- a/webpack.config.js +++ b/webpack.config.js @@ -4,6 +4,7 @@ var webpack = require('webpack') const VisualizerPlugin = require('webpack-visualizer-plugin'); const HtmlWebpackHarddiskPlugin = require('html-webpack-harddisk-plugin'); const HtmlWebpackPlugin = require('html-webpack-plugin'); +const UglifyJsPlugin = require('uglifyjs-webpack-plugin') const dist = resolve(__dirname, 'dist'); @@ -151,6 +152,7 @@ if(process.env.NODE_ENV === 'test'){ // PROD // TODO: pull out into different webpack config if (process.env.NODE_ENV === 'production') { + module.exports.output.publicPath = './'; // simpler source map alg module.exports.devtool = 'source-map'; // use [hash] to prevent using stale caches @@ -167,6 +169,7 @@ if (process.env.NODE_ENV === 'production') { new webpack.LoaderOptionsPlugin({ minimize: true, debug: false - }) + }), + new UglifyJsPlugin(), ].concat(module.exports.plugins); } -- GitLab From e1cca0d0f20068a30aa2a0614393aa6ac3fbcdb4 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 16:43:52 +0100 Subject: [PATCH 40/51] fix io name change changing other conns --- src/components/toolchain/ToolchainEditor.jsx | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/components/toolchain/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx index 1bd37d0..8ba4f6a 100644 --- a/src/components/toolchain/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -265,19 +265,20 @@ export class ToolchainEditor extends React.Component { // updates a block's input or output name updateBlockIOName = (blockName: string, set: BlockSet, ioType: 'input' | 'output', oldName: string, newName: string) => { + const combinedName = `${ blockName }.${ oldName }`; const updateConn = (from, to): string[] => { const fromSplit = from.split('.'); if(ioType === 'output') - fromSplit[1] = fromSplit[1] === oldName ? newName : fromSplit[1]; + fromSplit[1] = from === combinedName ? newName : fromSplit[1]; const toSplit = to.split('.'); if(ioType === 'input') - toSplit[1] = toSplit[1] === oldName ? newName : toSplit[1]; + toSplit[1] = to === combinedName ? newName : toSplit[1]; return [fromSplit.join('.'), toSplit.join('.')]; }; const rep = {...this.state.cache.contents.representation}; rep.connections = Object.entries(rep.connections).map(([name, rep]) => { - if(!name.includes(oldName)) + if(!name.includes(`.${ oldName }`)) return [name, rep]; const [from, to] = name.split('/'); @@ -302,7 +303,7 @@ export class ToolchainEditor extends React.Component { return newBlock; }), connections: this.state.cache.contents.connections.map(c => { - if((ioType === 'input' && !c.to.endsWith(oldName)) || (ioType === 'output' && !c.from.endsWith(oldName))) + if(!c.from.includes(`.${ oldName }`) && !c.to.includes(`.${ oldName }`)) return c; const updated = updateConn(c.from, c.to); return { -- GitLab From 029bcb25edcceb953966bf54f1669bc8f02ef61f Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Wed, 10 Jan 2018 16:55:53 +0100 Subject: [PATCH 41/51] fix exp creation test to use basic tc network integration --- .../experiment/ExperimentEditor.spec.jsx | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/src/components/experiment/ExperimentEditor.spec.jsx b/src/components/experiment/ExperimentEditor.spec.jsx index cd97c31..eef44f8 100644 --- a/src/components/experiment/ExperimentEditor.spec.jsx +++ b/src/components/experiment/ExperimentEditor.spec.jsx @@ -52,7 +52,7 @@ describe('', () => { }); }); - describe.skip('creates', () => { + describe('creates', () => { it(`user/user/single/1/single_add`, () => { const expName = 'user/user/single/1/single_add'; const saveFunc = sinon.spy(); @@ -69,9 +69,13 @@ describe('', () => { /> ); + //console.log('doing name'); + wrapper.find('.expName').find('input').simulate('change', { target: { value: expName }}); expect(wrapper.state('cache')).to.have.property('name', expName); + //console.log('finished name change, doing dataset'); + wrapper.find('div.dataset0 select').simulate('change', { target: { value: 'protocol/set (simple/1)'}}); expect(wrapper.state('cache').contents).to.have.deep.property('datasets', { 'set': { @@ -81,6 +85,9 @@ describe('', () => { } }); + //console.log('finished dataset, doing block'); + + wrapper.find('svg #block_echo').simulate('click'); wrapper.find('div.block0 div.algorithm select').at(0).simulate('change', { target: { value: 'user/integers_add/1'}}); expect(wrapper.state('cache').contents).to.have.deep.property('blocks', { 'echo': { @@ -95,7 +102,10 @@ describe('', () => { } }); - wrapper.find('div.block0 div.algorithm select').at(1).simulate('change', { target: { value: 'user/integers_echo_analyzer/1'}}); + //console.log('finished block, doing analyzer'); + + wrapper.find('svg #block_analysis').simulate('click'); + wrapper.find('div.block0 div.algorithm select').at(0).simulate('change', { target: { value: 'user/integers_echo_analyzer/1'}}); expect(wrapper.state('cache').contents).to.have.deep.property('analyzers', { 'analysis': { 'inputs': { @@ -106,6 +116,8 @@ describe('', () => { } }); + //console.log('finished analyzer, doing env'); + wrapper.find('input.queue').simulate('change', { target: { value: 'queue'}}); wrapper.find('input.envName').simulate('change', { target: { value: 'Python 2.7'}}); wrapper.find('input.envVersion').simulate('change', { target: { value: '1.2.0'}}); @@ -120,6 +132,8 @@ describe('', () => { }, }); + //console.log('finished env, doing cache check'); + expect(wrapper.state('cache')).to.be.deep.equal({ 'name': 'user/user/single/1/single_add', 'contents': { -- GitLab From 16c2a1a1c5dd4e4e43f104c0696edb8ecd580fce Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 09:33:05 +0100 Subject: [PATCH 42/51] rm react-konva --- package-lock.json | 23 ++--------------------- package.json | 1 - 2 files changed, 2 insertions(+), 22 deletions(-) diff --git a/package-lock.json b/package-lock.json index a3cad5f..00b680d 100644 --- a/package-lock.json +++ b/package-lock.json @@ -5800,7 +5800,8 @@ "jsbn": { "version": "0.1.1", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "json-schema": { "version": "0.2.3", @@ -12776,15 +12777,6 @@ } } }, - "react-konva": { - "version": "1.6.4", - "resolved": "https://registry.npmjs.org/react-konva/-/react-konva-1.6.4.tgz", - "integrity": "sha512-4K5VE2TsGfUmIXbPbZu2uHJYIysZxmx76/pqcAaWT9PiWrJJj2mfDPBeQGX8jDAL1nr9yg6nOThs1Frt4MYXaA==", - "requires": { - "fbjs": "0.8.16", - "react-reconciler": "0.5.0" - } - }, "react-popper": { "version": "0.7.5", "resolved": "https://registry.npmjs.org/react-popper/-/react-popper-0.7.5.tgz", @@ -12803,17 +12795,6 @@ "lodash": "4.17.4" } }, - "react-reconciler": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/react-reconciler/-/react-reconciler-0.5.0.tgz", - "integrity": "sha512-AXRcMbbOYU+Wq7Zb3CooX76b9+TNg6b518XfT+muVs0lPIvN9bvm1nqT5DuDwLcdto2LlcUSB+SwmmAbWOQEmA==", - "requires": { - "fbjs": "0.8.16", - "loose-envify": "1.3.1", - "object-assign": "4.1.1", - "prop-types": "15.6.0" - } - }, "react-redux": { "version": "5.0.6", "resolved": "https://registry.npmjs.org/react-redux/-/react-redux-5.0.6.tgz", diff --git a/package.json b/package.json index 1bd6fc6..825e879 100644 --- a/package.json +++ b/package.json @@ -87,7 +87,6 @@ "react": "^16.2.0", "react-contextmenu": "^2.9.2", "react-dom": "^16.2.0", - "react-konva": "^1.6.4", "react-popper": "^0.7.5", "react-redux": "^5.0.6", "react-router-dom": "^4.2.2", -- GitLab From a62891eefcab63a5a53e8cb24fe88cc86fdad9aa Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 11:49:25 +0100 Subject: [PATCH 43/51] added graph toolbar, maximize, help modal, block highlight when select; mouse actions now happen across entire block --- src/components/toolchain/GraphicalEditor.css | 36 +++- src/components/toolchain/GraphicalEditor.jsx | 56 +++++- .../toolchain/GraphicalEditorHelpModal.jsx | 190 ++++++++++++++++++ src/components/toolchain/ToolchainBlock.jsx | 77 +++---- src/components/toolchain/ToolchainEditor.css | 1 - src/components/toolchain/ToolchainEditor.jsx | 190 +++++++++--------- 6 files changed, 408 insertions(+), 142 deletions(-) create mode 100644 src/components/toolchain/GraphicalEditorHelpModal.jsx diff --git a/src/components/toolchain/GraphicalEditor.css b/src/components/toolchain/GraphicalEditor.css index e759f5f..1090005 100644 --- a/src/components/toolchain/GraphicalEditor.css +++ b/src/components/toolchain/GraphicalEditor.css @@ -3,14 +3,24 @@ svg { } .editorWrapper { - display: relative; height: 500px; width: 100%; background-color: grey; } -.editorWrapper > div { - display: absolute; +.editorWrapper.maximized { + position: fixed; + left: 5%; + top: 5%; + width: 90%; + height: 90%; + background-color: grey; + border: solid 1px grey; + border-radius: 2px; + box-shadow: 0 0 5px grey; +} + +.editorWrapper2 { height: 100%; width: 100%; background-color: white; @@ -25,3 +35,23 @@ svg { .fo:hover { filter: brightness(95%); } + +.tcBlock > .highlighted { + stroke-dasharray: 10, 10; +} + +.editorMenu { + background: rgba(255, 255, 255, 0.5); + position: absolute; + margin: auto; + margin-top: 0.5em; + right: 2em; +} + +.editorWrapper.maximized > .editorMenu { + right: 1em; +} + +text { + user-select: none; +} diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index 7da5c72..b44c7e6 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -2,11 +2,17 @@ import './GraphicalEditor.css'; import * as React from 'react'; import * as d3 from 'd3'; +import { + Button, + ButtonGroup, +} from 'reactstrap'; +import cn from 'classnames'; import Block from './ToolchainBlock.jsx'; import type { BlockType, NormalBlock, AnalyzerBlock, DatasetBlock } from './ToolchainBlock.jsx'; import type { BlockSet } from './ToolchainBlock.jsx'; import Connection from './ToolchainConnection.jsx'; import type { ConnectionType } from './ToolchainConnection.jsx'; +import HelpModal from './GraphicalEditorHelpModal.jsx'; import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; import { changeObjFieldName, generateNewKey } from '@helpers'; @@ -52,6 +58,8 @@ type State = { y: number, }, selectedBlocks: BlockType[], + maximized: boolean, + helpActive: boolean, }; // note: all measurements are in px by default for svg @@ -76,6 +84,8 @@ export default class GraphicalEditor extends React.Component { y: -1, }, selectedBlocks: [], + maximized: false, + helpActive: false, }; // initializes d3 behaviours (most SVG interactions) @@ -102,11 +112,15 @@ export default class GraphicalEditor extends React.Component { svgContextMenu = null; // adjusts the zoomlevel - setZoomLevel = (zoomLevel: number) => this.setState({...this.state, zoomLevel: zoomLevel}); + setZoomLevel = (zoomLevel: number) => this.setState({zoomLevel: zoomLevel}); // zoom out zoomOut = () => this.setZoomLevel(this.state.zoomLevel + zoomAdjustmentAmount); // zoom in zoomIn = () => this.setZoomLevel(this.state.zoomLevel - zoomAdjustmentAmount); + // toggle maximized + toggleMaximized = () => this.setState({ maximized: !this.state.maximized }); + // toggles the help modal + toggleHelp = () => this.setState({ helpActive: !this.state.helpActive }); // generates the string representing the viewbox of the svg. The first two numbers represent the offset, the last two the scaling. getSvgViewBox = () => `0 0 ${ this.state.zoomLevel } ${ this.state.zoomLevel }`; @@ -179,7 +193,6 @@ export default class GraphicalEditor extends React.Component { // manually triggers the svg's context menu triggerSvgAction = (x: number, y: number, clickEvent: any) => { this.setState({ - ...this.state, svgActionLocation: { x, y, @@ -204,7 +217,6 @@ export default class GraphicalEditor extends React.Component { selectBlocks = (blocks: BlockType[]) => { this.setState({ - ...this.state, selectedBlocks: blocks, }); this.initD3Drag(); @@ -556,8 +568,37 @@ export default class GraphicalEditor extends React.Component { const selectBoxCoords = getBlocksBoundingBox(this.state.selectedBlocks.map(b => b.name)); return ( -
-
+
+
+ + + + + + +
+
{ locMap={locMap[name]} data={data} set={set} + highlighted={isSelected !== undefined} handleClick={() => this.props.handleBlockClick ? this.props.handleBlockClick(name, set) : undefined} handleShiftClick={() => { const sels = this.state.selectedBlocks; @@ -740,6 +782,10 @@ export default class GraphicalEditor extends React.Component { { this.props.divChildren }
+
); } diff --git a/src/components/toolchain/GraphicalEditorHelpModal.jsx b/src/components/toolchain/GraphicalEditorHelpModal.jsx new file mode 100644 index 0000000..db5656a --- /dev/null +++ b/src/components/toolchain/GraphicalEditorHelpModal.jsx @@ -0,0 +1,190 @@ +// @flow +import * as React from 'react'; +import { + Container, + Row, + Col, + TabContent, TabPane, + Alert, + Badge, + Modal, ModalBody, ModalHeader, ModalFooter, + Table, +} from 'reactstrap'; + +type Props = { + // func to close modal + toggle: () => any, + // is the modal active? + active: boolean, +}; + +class GraphicalEditorHelpModal extends React.PureComponent { + constructor(props: Props){ + super(props); + } + + render = () => { + return ( + { + /* + const f = document.querySelector('#tcModalInitFocus'); + if(f && f.focus) + f.focus(); + */ + }} + > + + Graphical Editor + + +

Keyboard Shortcuts

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
ActionShortcutAdditional Info
+ Pan vertically +
+									Scroll up/down
+								
+ You can also manually drag the scroll bar on the right edge of the editor. +
+ Pan horizontally + +
Scroll left/right
+ {' '} + + or + + {' '} +
Left arrow key & Right arrow key
+
+ You can also manually drag the scroll bar on the bottom edge of the editor. To scroll left or right, three-button mice will usually let you click & hold on the middle button to scroll freely. +
+ Zoom in/out +
+									Shift + scroll up/down
+								
+ You can also use the {`"Zoom in"`} and {`"Zoom out"`} buttons in the top-right menu. +
+ Edit a block +
+									Left click
+								
+ Left-clicking a block will open a modal where you can edit the block name, the synchronized channel, inputs, and outputs. +
+ Move blocks +
+									Left click + drag
+								
+ You may move a block at a time by clicking & dragging on a block. You may move a selection or group of blocks by dragging the grey rectangle representing the selection or group. +
+ Open a context menu +
+									Right click
+								
+ There are context menus for: blocks, connections, area selections, groups, and the background. +
+ Select Multiple Blocks + +
+										Shift + left click
+									
+ {' '} + + or + + {' '} +
+										Click + drag
+									
+
+ Shift + left-clicking a block will toggle selection. +
+ Create a Connection between an output and an input + +
+										Left click + drag
+									
+ {' '} + + on the black rectangle next to the desired output, and release the drag on the black rectangle next to the desired input. + +
+
+ See more information + +
+										Hover
+									
+ {' '} + + Some elements in the editor have extra information found by hovering over the element for a couple seconds. + +
+
+
+ + +
+ ); + } +} + +export default GraphicalEditorHelpModal; diff --git a/src/components/toolchain/ToolchainBlock.jsx b/src/components/toolchain/ToolchainBlock.jsx index 489dc80..a6c9795 100644 --- a/src/components/toolchain/ToolchainBlock.jsx +++ b/src/components/toolchain/ToolchainBlock.jsx @@ -25,6 +25,7 @@ import { Badge, } from 'reactstrap'; import { ContextMenuTrigger } from 'react-contextmenu'; +import cn from 'classnames'; export type NormalBlock = { inputs: string[], @@ -72,6 +73,7 @@ export type Props = { handleShiftClick: (name: string, set: BlockSet) => any, // the color of the channel the block is sync'd to channelColor: string, + highlighted: boolean, }; type State = { @@ -109,30 +111,20 @@ class ToolchainBlock extends React.PureComponent { return ( - {/* right-click menu that wraps the background rectangle of the block */} - ({ name: props.name, set: props.set })} - renderTag='g' - > - {/* the background rectangle with the click handler */} - { - if(e.shiftKey) - this.props.handleShiftClick(name, this.props.set); - else - this.props.handleClick(name, this.props.set); - e.stopPropagation(); - e.preventDefault(); - }} - /> - - {/* block name clip path */} + + {/* rect indicating the sync'd channel */} + + {/* block name */} { { name } {/* the little upper-right block showing the color of the currently sync'd channel */} - - Synchronized to the {this.props.data.synchronized_channel || name} channel - { /* draws the inputs (both the black rects for connections and the corresponding input name */ @@ -221,7 +204,7 @@ class ToolchainBlock extends React.PureComponent { - + @@ -229,6 +212,32 @@ class ToolchainBlock extends React.PureComponent { + {/* right-click menu that wraps the background rectangle of the block */} + ({ name: props.name, set: props.set })} + renderTag='g' + > + {/* the background rectangle with the click handler */} + { + if(e.shiftKey) + this.props.handleShiftClick(name, this.props.set); + else + this.props.handleClick(name, this.props.set); + e.stopPropagation(); + e.preventDefault(); + }} + > + { name } synchronized to the {this.props.data.synchronized_channel || name} channel + + ); } diff --git a/src/components/toolchain/ToolchainEditor.css b/src/components/toolchain/ToolchainEditor.css index 0a3c27e..98e55a6 100644 --- a/src/components/toolchain/ToolchainEditor.css +++ b/src/components/toolchain/ToolchainEditor.css @@ -5,7 +5,6 @@ svg { text:hover { clip-path: none; - user-select: text; } .preInline { diff --git a/src/components/toolchain/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx index 8ba4f6a..e666d51 100644 --- a/src/components/toolchain/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -122,7 +122,6 @@ export class ToolchainEditor extends React.Component { componentWillReceiveProps = (nextProps: Props) => { this.setState({ - ...this.state, cache: getValidObj(nextProps.data), }); } @@ -246,7 +245,6 @@ export class ToolchainEditor extends React.Component { const newGroups = this.state.cache.extraContents.groups .map(({ name, blocks }) => ({ name, blocks: blocks.map(n => n === oldName ? newName : n) })); this.setState({ - ...this.state, cache: { ...this.state.cache, contents: newContents, @@ -424,7 +422,6 @@ export class ToolchainEditor extends React.Component { .map(({ name, blocks }) => ({ name, blocks: blocks.filter(n => n !== name) })) .filter(g => g.blocks.length !== 0); this.setState({ - ...this.state, cache: { ...this.state.cache, contents: newContents, @@ -600,7 +597,6 @@ export class ToolchainEditor extends React.Component { // copy either a block or array of blocks to the clipboard copyToClipboard = (data: any[]) => { this.setState({ - ...this.state, clipboard: data, }); } @@ -676,7 +672,6 @@ export class ToolchainEditor extends React.Component { active: true, }; this.setState({ - ...this.state, modalBlockInfo: newMBI, }); } @@ -687,98 +682,96 @@ export class ToolchainEditor extends React.Component { - - - - - Delete Block - - - Copy Block - - - - - Delete Connection - - - - - Add Block Here - - - Add Dataset Here - - - Add Analyzer Here - - { - this.state.clipboard !== undefined && - - Paste Here - - } - - - - Delete Group - - - - - Copy Blocks - - - Create Group - - - - } - > - - + + + + Delete Block + + + Copy Block + + + + + Delete Connection + + + + + Add Block Here + + + Add Dataset Here + + + Add Analyzer Here + + { + this.state.clipboard !== undefined && + + Paste Here + + } + + + + Delete Group + + + + + Copy Blocks + + + Create Group + + + + } + > + ); @@ -796,7 +789,6 @@ export class ToolchainEditor extends React.Component { active={active} toggle={() => { this.setState({ - ...this.state, modalBlockInfo: { ...this.state.modalBlockInfo, active: false, @@ -857,7 +849,7 @@ export class ToolchainEditor extends React.Component { className='tcName' placeholder='New toolchain name...' value={this.state.cache.name} - onChange={e => this.setState({ ...this.state, cache: {...this.state.cache, 'name': e.target.value}})} + onChange={e => this.setState({ cache: {...this.state.cache, 'name': e.target.value}})} validateFunc={str => this.nameIsValid(str)} /> -- GitLab From bb3d11ba199874c6bfbbba15ea771722b0663882 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 12:13:51 +0100 Subject: [PATCH 44/51] change to batch updating block locations for much better perf with many blocks --- src/components/toolchain/GraphicalEditor.jsx | 18 ++++++++++-------- .../toolchain/GraphicalEditorHelpModal.jsx | 5 +---- src/components/toolchain/ToolchainEditor.jsx | 14 ++++++-------- 3 files changed, 17 insertions(+), 20 deletions(-) diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index b44c7e6..684dc90 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -39,7 +39,7 @@ type Props = { groups: Group[], handleBlockClick?: (blockName: string, set: BlockSet) => any, // updates a block location to col #x & row #y - updateBlockLocation?: (blockName: string, x: number, y: number) => any, + updateBlockLocations?: (bLocs: {blockName: string, x: number, y: number}[]) => any, createConnection?: (from: string, to: string, channel: string) => any, // extra svg to be drawn after the blocks & connections svgChildren?: React.Node, @@ -228,8 +228,8 @@ export default class GraphicalEditor extends React.Component { // only at the end of the drag is the react state updated. initD3Drag = () => { setTimeout(() => { - const updateBlockLocation = this.props.updateBlockLocation; - if(!updateBlockLocation) + const updateBlockLocations = this.props.updateBlockLocations; + if(!updateBlockLocations) return; const that = this; // currently debouncing isnt necessary perf-wise @@ -326,13 +326,15 @@ export default class GraphicalEditor extends React.Component { bNames = [d3this.attr('id').slice(6)]; } - bNames.forEach(b => { - const el = d3.select(`#block_${ b }`); - const bx = Number.parseFloat(el.attr('x')) / gridDistance + xShift; - const by = Number.parseFloat(el.attr('y')) / gridDistance + yShift; + const bLocs = bNames.map(b => { + const el = document.querySelector(`#block_${ b }`); + const bx = Number.parseFloat(el.x.baseVal.value) / gridDistance + xShift; + const by = Number.parseFloat(el.y.baseVal.value) / gridDistance + yShift; - updateBlockLocation(b, bx, by); + return {blockName: b, x: bx, y: by}; }); + + updateBlockLocations(bLocs); dRect.remove(); } diff --git a/src/components/toolchain/GraphicalEditorHelpModal.jsx b/src/components/toolchain/GraphicalEditorHelpModal.jsx index db5656a..4b0acdf 100644 --- a/src/components/toolchain/GraphicalEditorHelpModal.jsx +++ b/src/components/toolchain/GraphicalEditorHelpModal.jsx @@ -169,12 +169,9 @@ class GraphicalEditorHelpModal extends React.PureComponent {
 										Hover
 									
- {' '} - - Some elements in the editor have extra information found by hovering over the element for a couple seconds. - + Some elements in the editor have extra information found by hovering over the element for a couple seconds. diff --git a/src/components/toolchain/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx index e666d51..90ea0ba 100644 --- a/src/components/toolchain/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -179,19 +179,17 @@ export class ToolchainEditor extends React.Component { } // updates a blocks location in the graphical editor by providing an x & y offset relative to the current location. - updateBlockLocation = (blockName: string, x: number, y: number) => { + updateBlockLocations = (bLocs: {blockName: string, x: number, y: number}[]) => { const rep = this.state.cache.contents.representation; - const block = rep.blocks[blockName]; + const newReps = bLocs + .map(bLoc => ({ [bLoc.blockName]: { ...rep.blocks[bLoc.blockName], col: bLoc.x, row: bLoc.y }})) + .reduce((o, bLoc) => ({ ...o, ...bLoc }), {});; this.setContents({ representation: { ...rep, blocks: { ...rep.blocks, - [blockName]: { - ...block, - col: x, - row: y, - } + ...newReps, } } }); @@ -691,7 +689,7 @@ export class ToolchainEditor extends React.Component { connections={this.state.cache.contents.connections} groups={this.state.cache.extraContents.groups} handleBlockClick={this.handleBlockClick} - updateBlockLocation={this.updateBlockLocation} + updateBlockLocations={this.updateBlockLocations} createConnection={this.createConnection} divChildren={ -- GitLab From b8814b39b1706e4c012518a8882bd6f813cb7955 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 12:21:21 +0100 Subject: [PATCH 45/51] try to autoclose context menus on mouseout --- src/components/toolchain/GraphicalEditor.jsx | 2 +- src/components/toolchain/ToolchainEditor.jsx | 43 +++++++++++++------- 2 files changed, 30 insertions(+), 15 deletions(-) diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index 684dc90..cd92827 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -13,7 +13,7 @@ import type { BlockSet } from './ToolchainBlock.jsx'; import Connection from './ToolchainConnection.jsx'; import type { ConnectionType } from './ToolchainConnection.jsx'; import HelpModal from './GraphicalEditorHelpModal.jsx'; -import { ContextMenu, MenuItem, ContextMenuTrigger } from 'react-contextmenu'; +import { ContextMenuTrigger } from 'react-contextmenu'; import { changeObjFieldName, generateNewKey } from '@helpers'; export type Group = { diff --git a/src/components/toolchain/ToolchainEditor.jsx b/src/components/toolchain/ToolchainEditor.jsx index 90ea0ba..758bea2 100644 --- a/src/components/toolchain/ToolchainEditor.jsx +++ b/src/components/toolchain/ToolchainEditor.jsx @@ -693,7 +693,10 @@ export class ToolchainEditor extends React.Component { createConnection={this.createConnection} divChildren={ - + { Copy Block - + { Delete Connection - + + { + this.state.clipboard !== undefined && + + Paste Here + + } { > Add Analyzer Here - { - this.state.clipboard !== undefined && - - Paste Here - - } - + { Delete Group - + Date: Thu, 11 Jan 2018 12:40:12 +0100 Subject: [PATCH 46/51] add a "how do i..." section to the graphical editor help --- .../toolchain/GraphicalEditorHelpModal.jsx | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/src/components/toolchain/GraphicalEditorHelpModal.jsx b/src/components/toolchain/GraphicalEditorHelpModal.jsx index 4b0acdf..3d43775 100644 --- a/src/components/toolchain/GraphicalEditorHelpModal.jsx +++ b/src/components/toolchain/GraphicalEditorHelpModal.jsx @@ -42,6 +42,23 @@ class GraphicalEditorHelpModal extends React.PureComponent { Graphical Editor +

How do I...

+
Add a block?
+

+ Right-clicking anywhere on the grid will open a menu for adding (or pasting) blocks to the grid point where the block dot is. +

+
Change the information of a block?
+

+ Left-clicking on a block will bring up the Block Editor modal, which lets you change the block name, add & remove & rename inputs and outputs, change the synchronized channel, and delete the block. +

+
Create a connection?
+

+ Connections are between an output of a block and an input of a block. To create a connection, click on the black rectangle to the right of the desired output, and drag onto the black rectangle next to the desired input. +

+
Delete a block or connection?
+

+ Besides being able to delete a block in the Block Editor, you can right-click blocks or connections to show a menu where you may delete the corresponding element. +

Keyboard Shortcuts

-- GitLab From d76e79e64718aa39c5c8b7f2d675e1512db36a70 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 15:06:33 +0100 Subject: [PATCH 47/51] integrate experiment editor with graphical editor more, fix odd exp behaviour --- .../experiment/ExperimentEditor.jsx | 20 ++++++++++++---- src/components/toolchain/GraphicalEditor.jsx | 20 ++++++++++------ src/components/toolchain/ToolchainBlock.jsx | 24 ++++++++++++++++++- 3 files changed, 51 insertions(+), 13 deletions(-) diff --git a/src/components/experiment/ExperimentEditor.jsx b/src/components/experiment/ExperimentEditor.jsx index c575821..92f7454 100644 --- a/src/components/experiment/ExperimentEditor.jsx +++ b/src/components/experiment/ExperimentEditor.jsx @@ -1000,16 +1000,26 @@ export class ExperimentEditor extends React.Component { const tc = this.props.toolchain; const {representation, blocks, datasets, analyzers, connections} = tc.contents; const groups = tc.extraContents ? tc.extraContents.groups : []; + const expData = [ + ...Object.entries(this.state.cache.contents.datasets) + .map(([name, ds]) => ({ [name]: datasetFieldToString(ds) })), + ...Object.entries(this.state.cache.contents.blocks) + .map(([name, b]) => ({ [name]: b.algorithm })), + ...Object.entries(this.state.cache.contents.analyzers) + .map(([name, a]) => ({ [name]: a.algorithm })), + ].reduce((o, data) => ({ ...o, ...data }), {}); + return ( diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index cd92827..b230eb5 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -47,6 +47,9 @@ type Props = { divChildren?: React.Node, // should the d3 behaviours be enabled? interactable?: boolean, + // map of block names to strings of text to display on the bottom of a block + // used for showing the selected dataset/algorithm in an exp + experimentData?: any, }; type State = { @@ -591,13 +594,15 @@ export default class GraphicalEditor extends React.Component { > Maximize - + { !this.props.experimentData && + + }
@@ -760,6 +765,7 @@ export default class GraphicalEditor extends React.Component { }} channelColor={this.props.repData.channel_colors[data.synchronized_channel || data.name]} opacity={isSelected ? 0.5 : 1} + experimentString={this.props.experimentData ? this.props.experimentData[name] || 'Not Selected' : undefined} /> ); }) diff --git a/src/components/toolchain/ToolchainBlock.jsx b/src/components/toolchain/ToolchainBlock.jsx index a6c9795..7e9ce60 100644 --- a/src/components/toolchain/ToolchainBlock.jsx +++ b/src/components/toolchain/ToolchainBlock.jsx @@ -73,7 +73,11 @@ export type Props = { handleShiftClick: (name: string, set: BlockSet) => any, // the color of the channel the block is sync'd to channelColor: string, + // highlighted blocks have a dashed border (see the 'highlighted' CSS class styling in GraphicalEditor.css) highlighted: boolean, + // string to show at the bottom of the block + // used to display the selected dataset/algorithm in the experiment editor + experimentString?: string, }; type State = { @@ -108,6 +112,7 @@ class ToolchainBlock extends React.PureComponent { const fullClipId = `${ name }-full`; const inputClipId = `${ name }-input`; const outputClipId = `${ name }-output`; + const expClipId = `${ name }-exp`; return ( @@ -133,6 +138,17 @@ class ToolchainBlock extends React.PureComponent { > { name } + {/* exp string */} + { this.props.experimentString && + + { this.props.experimentString } + + } {/* the little upper-right block showing the color of the currently sync'd channel */} { @@ -206,6 +222,9 @@ class ToolchainBlock extends React.PureComponent { + + + @@ -235,7 +254,10 @@ class ToolchainBlock extends React.PureComponent { e.preventDefault(); }} > - { name } synchronized to the {this.props.data.synchronized_channel || name} channel + + { name } synchronized to the {this.props.data.synchronized_channel || name} channel + { this.props.experimentString ? ` with "${ this.props.experimentString }" assigned to it` : ''} + -- GitLab From 111d860e59f74a88bb9b53ff1523b3d357043350 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 15:07:28 +0100 Subject: [PATCH 48/51] add new beat objects at the beginning instead of at the end --- src/store/reducers.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/store/reducers.js b/src/store/reducers.js index 80469db..2273cd5 100644 --- a/src/store/reducers.js +++ b/src/store/reducers.js @@ -30,7 +30,7 @@ const initialState: State = { }; const saveFunc = (state: BeatObject[], objs: BeatObject[]): BeatObject[] => [...objs]; -const addFunc = (state: BeatObject[], obj: BeatObject): BeatObject[] => [...state, obj]; +const addFunc = (state: BeatObject[], obj: BeatObject): BeatObject[] => [obj, ...state]; const deleteFunc = (state: BeatObject[], obj: BeatObject): BeatObject[] => state.filter(o => o.name !== obj.name); const updateFunc = (state: BeatObject[], { oldName, obj }): BeatObject[] => state.map(o => o.name === oldName ? obj : o); -- GitLab From dcc6dfa4950a9e975108b88ad9283653b97cf3f4 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 15:34:55 +0100 Subject: [PATCH 49/51] add some comments explaining the experiment editors funcs --- .../experiment/ExperimentEditor.jsx | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/src/components/experiment/ExperimentEditor.jsx b/src/components/experiment/ExperimentEditor.jsx index 92f7454..2ca0a2e 100644 --- a/src/components/experiment/ExperimentEditor.jsx +++ b/src/components/experiment/ExperimentEditor.jsx @@ -66,6 +66,7 @@ type State = { type ParameterValue = number | string | boolean; +// returns the default value for a specific parameter, given the parameter object const getDefaultParameterValue = (parameter: any): ParameterValue => { const parsedDefault = Number.parseFloat(parameter.default); if(parameter.default) @@ -161,10 +162,15 @@ const getValidObj = (data = {}, tc: BeatObject, algs: BeatObject[]) => { return obj; }; +// parses a string resulting from the "datasetFieldToString" function into the original database, protocol, and set const rxStringToDataset = /^(\S+)\/(\S+)\s\((\S+\/\d+)\)/; +// parses a string resulting from the "datasetProtocolFieldToString" function into the original database and protocol const rxStringToDatasetProtocol = /^(\S+)\s\((\S+\/\d+)\)/; +// given a dataset obj (with database, protocol, and set fields), return a user-readable string representing this dataset const datasetFieldToString = (dataset: any) => `${ dataset.protocol }/${ dataset.set } (${ dataset.database })`; +// given a dataset obj (with database, protocol, and set fields), return a user-readable string representing this dataset's protocol const datasetProtocolFieldToString = (dataset: any) => `${ dataset.protocol } (${ dataset.database })`; +// given an algorithm, returns maps of the inputs and outputs of the algorithm (the i/o name mapped to its type) const algIOs = (alg: any) => { const inputs = alg.contents.groups.map(g => { if(!g.inputs) @@ -192,6 +198,8 @@ const algIOs = (alg: any) => { ]; }; +// given a parameter obj, its current value, and an update function, +// return an input for the specific type of parameter const Parameter = ({ parameter, updateFunc, currVal }: { parameter: any, updateFunc: (ParameterValue) => any, currVal?: ParameterValue }) => { if((parameter === null || parameter === undefined) || !parameter.hasOwnProperty('type')) return ''; @@ -259,6 +267,8 @@ const Parameter = ({ parameter, updateFunc, currVal }: { parameter: any, updateF } }; +// given a block and the available algorithms, +// remap the chosen algorithm type data onto the block i/o names const getBlockIOTypes = (block: any, algs: any[]) => { const alg = algs.find(alg => alg.name === block.algorithm); const [ais, aos] = alg ? algIOs(alg) : [{}, {}]; @@ -268,10 +278,12 @@ const getBlockIOTypes = (block: any, algs: any[]) => { return [bis, bos]; }; +// generate a new lock map for the given toolchain const genLockMap = (toolchain: any): any => [...toolchain.contents.datasets, ...toolchain.contents.blocks, ...toolchain.contents.analyzers] .map(b => b.name) .reduce((o, name) => ({...o, [name]: false}), {}); +// checks if the given object is valid for the current entity given the i/o types and inferred types map const isValidEntity = ( entityName: string, blockTcEntity: {inputs?: [], outputs?: []} = {}, @@ -325,6 +337,7 @@ const dbSetIsValidForTcDataset = (dbSet, tcDs) => { return true; }; +// sorts an object's keys in alphabetical order const sortObject = (o) => Object.entries(o).sort(([n1, v1], [n2, v2]) => n1 > n2 ? 1 : -1).reduce((o, [n, v]) => ({...o, [n]: v}), {}); export class ExperimentEditor extends React.Component { @@ -362,8 +375,10 @@ export class ExperimentEditor extends React.Component { }); } + // func that checks if the given name is valid for this experiment validatorFunc = nameValidator('experiment', this.props.experiments.map(l => l.name)); + // checks if the given name is valid. if not, returns a message. nameIsValid = (str: string = this.state.cache.name): true | React.Node => { const err = @@ -388,6 +403,7 @@ export class ExperimentEditor extends React.Component { }); } + // gets parameter data for all the blocks with selected algorithms getParameterObjs = (): any[] => { const algs = [...this.props.normalBlocks, ...this.props.analyzerBlocks]; return Object.entries({...this.state.cache.contents.blocks, ...this.state.cache.contents.analyzers}) @@ -397,6 +413,10 @@ export class ExperimentEditor extends React.Component { ; } + // tries to infer the types of inputs & outputs given the structure of the toolchain, + // the algorithms currently chosen for blocks, + // and the database/protocol/set currently chosen for datasets. + // Does forward (from datasets to analyzers) and backward (from analyzers to datasets). getConnectionInferredTypes = (): any => { const isLocked = (name) => this.state.lockMap[name]; -- GitLab From acff31cce7ac0301a802fcdbea211f777cc5ee65 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 16:09:52 +0100 Subject: [PATCH 50/51] add onhover info for groups showing which blocks belong to it --- src/components/toolchain/GraphicalEditor.jsx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/components/toolchain/GraphicalEditor.jsx b/src/components/toolchain/GraphicalEditor.jsx index b230eb5..2a13c99 100644 --- a/src/components/toolchain/GraphicalEditor.jsx +++ b/src/components/toolchain/GraphicalEditor.jsx @@ -682,7 +682,9 @@ export default class GraphicalEditor extends React.Component { height={height} fill='grey' opacity='0.2' - /> + > + Contains { blocks.join(', ') } + ); }) -- GitLab From de33db590a451abf5af8e955791ebd8ff1534403 Mon Sep 17 00:00:00 2001 From: Jaden Diefenbaugh Date: Thu, 11 Jan 2018 16:59:24 +0100 Subject: [PATCH 51/51] fix name validation when creating new beat objects --- src/components/NewEntityModal.jsx | 37 +++++++++++++++++++++++-------- src/helpers/beat.js | 8 +++---- 2 files changed, 32 insertions(+), 13 deletions(-) diff --git a/src/components/NewEntityModal.jsx b/src/components/NewEntityModal.jsx index b644fe6..865aa4e 100644 --- a/src/components/NewEntityModal.jsx +++ b/src/components/NewEntityModal.jsx @@ -1,5 +1,5 @@ // @flow -import React from 'react'; +import * as React from 'react'; import { Button, Form, FormGroup, Label, Input, @@ -11,7 +11,11 @@ import { connect } from 'react-redux'; import { BEAT_ENTITIES, nameValidator } from '@helpers/beat'; import type { BeatEntity, BeatObject } from '@helpers/beat'; +import CacheInput from './CacheInput.jsx'; +import type { MapStateToProps, MapDispatchToProps } from 'react-redux'; + +import * as Selectors from '@store/selectors.js'; import * as Actions from '@store/actions'; type Props = { @@ -20,6 +24,7 @@ type Props = { entity: BeatEntity, copyObj?: BeatObject, create: (string, ?{}) => mixed, + data: BeatObject[], }; type State = { @@ -45,7 +50,17 @@ export class NewEntityModal extends React.Component { this.props.toggle(); } - nameIsValid = (name: string = this.state.name) => nameValidator(this.props.entity)(name); + validatorFunc = () => nameValidator(this.props.entity, this.props.data.map(d => d.name)); + + nameIsValid = (str: string = this.state.name): true | React.Node => { + const err = + + Please provide a unique and valid { this.props.entity } name + + ; + const isValid = this.validatorFunc()(str); + return isValid || err; + } handleInput = (str: string) => { this.setState({ @@ -60,16 +75,16 @@ export class NewEntityModal extends React.Component {
- this.handleInput(e.target.value)} + validateFunc={str => this.nameIsValid(str)} autoFocus /> - - Valid BEAT { this.props.entity } name -
@@ -82,8 +97,12 @@ export class NewEntityModal extends React.Component { } } +const mapStateToProps: MapStateToProps<*,*,*> = (state, ownProps) => ({ + data: Selectors[`${ ownProps.entity }Get`](state), +}); + const mapDispatchToProps = (dispatch, ownProps) => ({ create: (name: string, copyObj?: {} = {}) => dispatch(Actions[`${ ownProps.entity }Add`]({ contents: {}, ...copyObj, name })) }); -export default connect(undefined, mapDispatchToProps)(NewEntityModal); +export default connect(mapStateToProps, mapDispatchToProps)(NewEntityModal); diff --git a/src/helpers/beat.js b/src/helpers/beat.js index d46bc3e..3bb7519 100644 --- a/src/helpers/beat.js +++ b/src/helpers/beat.js @@ -75,6 +75,10 @@ export const pluralize = (be: BeatEntity): string => { }; export const nameValidator = (be: BeatEntity, allNames?: string[] = []) => (name: string): boolean => { + if(allNames.includes(name)){ + return false; + } + const rxThreeSeg = /^[A-Za-z0-9_-]+\/[A-Za-z0-9_-]+\/\d+$/; const rxTwoSeg = /^[A-Za-z0-9_-]+\/\d+$/; const rxFiveSeg = /^[A-Za-z0-9_-]+\/[A-Za-z0-9_-]+\/[A-Za-z0-9_-]+\/\d+\/[A-Za-z0-9_-]+$/; @@ -96,10 +100,6 @@ export const nameValidator = (be: BeatEntity, allNames?: string[] = []) => (name return false; } - if(allNames.includes(name)){ - return false; - } - return true; }; -- GitLab