From 0a7163bfd585e78d0fa3497dd93b7660079269c3 Mon Sep 17 00:00:00 2001 From: Norbert de Langen Date: Mon, 17 Apr 2017 16:37:37 +0200 Subject: [PATCH 01/37] ADD stricter eslint rules --- .eslintrc.js | 19 +++++++++++++++++-- package.json | 1 + 2 files changed, 18 insertions(+), 2 deletions(-) diff --git a/.eslintrc.js b/.eslintrc.js index ea25eb04850a..ed96f7762d01 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -1,9 +1,17 @@ +const error = 2; +const warn = 1; +const ignore = 0; + module.exports = { extends: [ - './node_modules/eslint-config-airbnb-base/rules/es6.js', + // './node_modules/eslint-config-airbnb-base/rules/es6.js', + 'airbnb-base', + 'plugin:jest/recommended', ], plugins: [ 'prettier', + 'jest', + 'react', ], parser: 'babel-eslint', parserOptions: { @@ -12,9 +20,10 @@ module.exports = { env: { es6: true, node: true, + 'jest/globals': true, }, rules: { - strict: 0, + strict: [error, "never"], 'prettier/prettier': ['warn', { printWidth: 100, tabWidth: 2, @@ -24,5 +33,11 @@ module.exports = { }], quotes: ['warn', 'single'], 'arrow-parens': ['warn', 'as-needed'], + 'space-before-function-paren': ignore, + 'import/no-extraneous-dependencies': [error, { devDependencies: true }], + 'import/prefer-default-export': ignore, + 'react/jsx-uses-react': error, + 'react/jsx-uses-vars': error, + 'react/react-in-jsx-scope': error, }, } diff --git a/package.json b/package.json index f666e60f96cc..ba194352e744 100644 --- a/package.json +++ b/package.json @@ -10,6 +10,7 @@ "eslint-plugin-import": "^2.2.0", "eslint-plugin-jest": "^19.0.1", "eslint-plugin-prettier": "^2.0.1", + "eslint-plugin-react": "^6.10.3", "jest": "^19.0.2", "jest-enzyme": "^3.0.1", "lerna": "2.0.0-rc.2", From 26f7ca5c9e434e91ed6969f17a8f213f80ba97d8 Mon Sep 17 00:00:00 2001 From: Norbert de Langen Date: Mon, 17 Apr 2017 16:37:49 +0200 Subject: [PATCH 02/37] FIX linting --- .eslintignore | 2 + .eslintrc.js | 3 +- packages/addon-graphql/.storybook/config.js | 1 + packages/addon-graphql/package.json | 1 + packages/addon-graphql/src/preview.js | 7 ++- packages/addon-info/package.json | 1 + packages/addon-info/src/components/Node.js | 60 +++++++++---------- .../addon-info/src/components/PropTable.js | 20 +++---- packages/addon-info/src/components/PropVal.js | 2 +- packages/addon-info/src/components/Props.js | 4 +- packages/addon-info/src/components/Story.js | 4 +- .../src/components/markdown/code.js | 1 + packages/addon-info/src/index.js | 7 ++- packages/addon-knobs/package.json | 5 +- packages/addon-knobs/src/KnobManager.js | 6 +- .../addon-knobs/src/components/PropField.js | 2 + .../addon-knobs/src/components/PropForm.js | 2 + .../addon-knobs/src/components/WrapStory.js | 2 + .../addon-knobs/src/components/types/Array.js | 9 +-- .../src/components/types/Boolean.js | 10 +--- .../addon-knobs/src/components/types/Color.js | 10 +--- .../src/components/types/Date/index.js | 9 +-- .../src/components/types/Number.js | 9 +-- .../src/components/types/Object.js | 10 +--- .../src/components/types/Select.js | 11 ++-- .../addon-knobs/src/components/types/Text.js | 9 +-- packages/addon-notes/package.json | 1 + packages/addon-options/manager.js | 1 + packages/addon-options/preview.js | 1 + packages/addon-options/src/manager/index.js | 1 - packages/addons/src/index.js | 2 + packages/channel-postmessage/package.json | 1 + packages/channel-postmessage/src/index.js | 28 +++++---- packages/channel-websocket/package.json | 3 +- packages/channel-websocket/src/index.js | 13 ++-- packages/channel/src/index.js | 2 + packages/channel/src/index.test.js | 2 + packages/decorator-centered/package.json | 8 ++- packages/getstorybook/bin/generate.js | 16 ++--- packages/getstorybook/generators/.eslintrc.js | 14 +++++ .../getstorybook/generators/METEOR/index.js | 3 +- .../getstorybook/generators/REACT/index.js | 2 +- .../REACT/template/stories/Welcome.js | 4 +- .../generators/REACT_NATIVE/index.js | 2 +- .../storybook/stories/Welcome/index.js | 2 + .../generators/REACT_SCRIPTS/index.js | 4 +- .../template/src/stories/Welcome.js | 4 +- .../generators/WEBPACK_REACT/index.js | 2 +- .../WEBPACK_REACT/template/stories/Welcome.js | 4 +- packages/getstorybook/lib/helpers.js | 15 ++--- packages/getstorybook/package.json | 6 ++ packages/react-native-storybook/package.json | 4 +- .../src/manager/index.js | 1 + .../src/preview/index.js | 5 +- .../src/preview/story_kind.js | 2 + .../src/preview/story_store.js | 8 ++- .../src/server/config.js | 2 +- .../src/server/config/webpack.config.js | 2 +- .../src/server/config/webpack.config.prod.js | 2 +- .../src/server/index.js | 4 +- .../src/server/middleware.js | 6 +- .../demo/src/stories/Welcome.js | 4 +- packages/react-storybook/package.json | 1 + .../react-storybook/scripts/mocha_runner.js | 25 -------- .../src/client/preview/client_api.js | 2 + .../src/client/preview/client_api.test.js | 2 + .../src/client/preview/config_api.js | 4 +- .../src/client/preview/story_store.js | 8 ++- packages/react-storybook/src/server/config.js | 2 +- .../config/WatchMissingNodeModulesPlugin.js | 2 +- .../server/config/defaults/webpack.config.js | 3 +- packages/react-storybook/src/server/index.js | 1 + .../react-storybook/src/server/track_usage.js | 2 +- packages/react-storybook/src/server/utils.js | 8 +-- packages/storybook-ui/example/package.json | 26 ++++---- packages/storybook-ui/example/server.js | 11 ++-- packages/storybook-ui/package.json | 2 + packages/storybook-ui/src/index.js | 8 +-- .../src/modules/api/actions/api.test.js | 6 +- .../src/modules/api/configs/init_api.test.js | 16 ++--- .../ui/components/layout/dimensions.js | 6 +- .../src/modules/ui/components/layout/index.js | 7 ++- .../ui/components/layout/index.test.js | 2 +- .../ui/components/left_panel/header.test.js | 2 +- .../modules/ui/components/left_panel/index.js | 2 +- .../src/modules/ui/components/search_box.js | 13 ++-- .../modules/ui/configs/handle_keyevents.js | 1 + .../ui/configs/handle_keyevents.test.js | 3 +- .../src/modules/ui/configs/handle_routing.js | 2 + .../modules/ui/configs/handle_routing.test.js | 3 +- .../modules/ui/containers/shortcuts_help.js | 3 +- .../modules/ui/libs/gen_podda_loader.test.js | 2 +- packages/storyshots/package.json | 4 +- packages/storyshots/src/index.js | 15 ++--- packages/storyshots/src/require_context.js | 6 +- .../required_with_context/Button.stories.js | 3 +- .../stories/required_with_context/Welcome.js | 4 +- 97 files changed, 317 insertions(+), 278 deletions(-) create mode 100644 packages/getstorybook/generators/.eslintrc.js delete mode 100755 packages/react-storybook/scripts/mocha_runner.js diff --git a/.eslintignore b/.eslintignore index 398ff439977d..323c8631ee1b 100644 --- a/.eslintignore +++ b/.eslintignore @@ -2,3 +2,5 @@ dist build coverage node_modules +**/example/** +**/demo/** diff --git a/.eslintrc.js b/.eslintrc.js index ed96f7762d01..ec5543c22beb 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -32,9 +32,10 @@ module.exports = { singleQuote: true, }], quotes: ['warn', 'single'], + 'class-methods-use-this': ignore, 'arrow-parens': ['warn', 'as-needed'], 'space-before-function-paren': ignore, - 'import/no-extraneous-dependencies': [error, { devDependencies: true }], + 'import/no-extraneous-dependencies': [error, { devDependencies: true, peerDependencies: true }], 'import/prefer-default-export': ignore, 'react/jsx-uses-react': error, 'react/jsx-uses-vars': error, diff --git a/packages/addon-graphql/.storybook/config.js b/packages/addon-graphql/.storybook/config.js index c4434721049e..0f14ab35ccd4 100644 --- a/packages/addon-graphql/.storybook/config.js +++ b/packages/addon-graphql/.storybook/config.js @@ -1,2 +1,3 @@ import * as storybook from '@kadira/storybook'; + storybook.configure(() => require('./stories'), module); diff --git a/packages/addon-graphql/package.json b/packages/addon-graphql/package.json index 3c509b483f88..81e07b4d5820 100644 --- a/packages/addon-graphql/package.json +++ b/packages/addon-graphql/package.json @@ -35,6 +35,7 @@ "react": "*" }, "dependencies": { + "global": "^4.3.1", "graphiql": "^0.7.8", "graphql": "^0.7.0" } diff --git a/packages/addon-graphql/src/preview.js b/packages/addon-graphql/src/preview.js index 54807c35c078..fdaf3881dd85 100644 --- a/packages/addon-graphql/src/preview.js +++ b/packages/addon-graphql/src/preview.js @@ -1,7 +1,8 @@ +import { fetch } from 'global'; import React from 'react'; import GraphiQL from 'graphiql'; -import FullScreen from './components/FullScreen'; import 'graphiql/graphiql.css'; +import FullScreen from './components/FullScreen'; const FETCH_OPTIONS = { method: 'post', @@ -9,7 +10,7 @@ const FETCH_OPTIONS = { }; function getDefautlFetcher(url) { - return function(params) { + return params => { const body = JSON.stringify(params); const options = Object.assign({ body }, FETCH_OPTIONS); return fetch(url, options).then(res => res.json()); @@ -23,7 +24,7 @@ function reIndentQuery(query) { } export function setupGraphiQL(config) { - return function(_query, variables = '{}') { + return (_query, variables = '{}') => { const query = reIndentQuery(_query); const fetcher = config.fetcher || getDefautlFetcher(config.url); return () => ( diff --git a/packages/addon-info/package.json b/packages/addon-info/package.json index c847b85b515e..6dd871a98e6a 100644 --- a/packages/addon-info/package.json +++ b/packages/addon-info/package.json @@ -34,6 +34,7 @@ }, "dependencies": { "babel-runtime": "^6.5.0", + "global": "^4.3.1", "markdown-to-react-components": "^0.2.1", "prop-types": "^15.5.7", "react-addons-create-fragment": "^15.5.3" diff --git a/packages/addon-info/src/components/Node.js b/packages/addon-info/src/components/Node.js index c2892317fba7..7e19034d4173 100644 --- a/packages/addon-info/src/components/Node.js +++ b/packages/addon-info/src/components/Node.js @@ -8,13 +8,42 @@ const stylesheet = { }, }; +function getData(element) { + const data = { + name: null, + text: null, + children: null, + }; + + if (typeof element === 'string') { + data.text = element; + return data; + } + + if (typeof element === 'number') { + data.text = String.toString(element); + return data; + } + + data.children = element.props.children; + const type = element.type; + + if (typeof type === 'string') { + data.name = type; + } else { + data.name = type.displayName || type.name || 'Unknown'; + } + + return data; +} + export default class Node extends React.Component { render() { const { node, depth } = this.props; const { tagStyle, containerStyle } = stylesheet; const leftPad = { - paddingLeft: 3 + (depth + 1) * 15, + paddingLeft: 3 + ((depth + 1) * 15), // eslint-disable-line paddingRight: 3, }; @@ -63,32 +92,3 @@ export default class Node extends React.Component { ); } } - -function getData(element) { - const data = { - name: null, - text: null, - children: null, - }; - - if (typeof element == 'string') { - data.text = element; - return data; - } - - if (typeof element === 'number') { - data.text = String.toString(element); - return data; - } - - data.children = element.props.children; - const type = element.type; - - if (typeof type === 'string') { - data.name = type; - } else { - data.name = type.displayName || type.name || 'Unknown'; - } - - return data; -} diff --git a/packages/addon-info/src/components/PropTable.js b/packages/addon-info/src/components/PropTable.js index 7b200a2c751e..9c18f1a8b524 100644 --- a/packages/addon-info/src/components/PropTable.js +++ b/packages/addon-info/src/components/PropTable.js @@ -3,9 +3,9 @@ import React from 'react'; import PropVal from './PropVal'; const PropTypesMap = new Map(); -for (const typeName in PropTypes) { - if (!PropTypes.hasOwnProperty(typeName)) { - continue; +for (const typeName in PropTypes) { // eslint-disable-line + if (!PropTypes.hasOwnProperty(typeName)) { // eslint-disable-line + continue; // eslint-disable-line } const type = PropTypes[typeName]; PropTypesMap.set(type, typeName); @@ -31,9 +31,9 @@ export default class PropTable extends React.Component { const props = {}; if (type.propTypes) { - for (const property in type.propTypes) { - if (!type.propTypes.hasOwnProperty(property)) { - continue; + for (const property in type.propTypes) { // eslint-disable-line + if (!type.propTypes.hasOwnProperty(property)) { // eslint-disable-line + continue; // eslint-disable-line } const typeInfo = type.propTypes[property]; const propType = PropTypesMap.get(typeInfo) || 'other'; @@ -43,13 +43,13 @@ export default class PropTable extends React.Component { } if (type.defaultProps) { - for (const property in type.defaultProps) { - if (!type.defaultProps.hasOwnProperty(property)) { - continue; + for (const property in type.defaultProps) { // eslint-disable-line + if (!type.defaultProps.hasOwnProperty(property)) { // eslint-disable-line + continue; // eslint-disable-line } const value = type.defaultProps[property]; if (value === undefined) { - continue; + continue; // eslint-disable-line } if (!props[property]) { props[property] = { property }; diff --git a/packages/addon-info/src/components/PropVal.js b/packages/addon-info/src/components/PropVal.js index f03af69feb4b..5aa548c27369 100644 --- a/packages/addon-info/src/components/PropVal.js +++ b/packages/addon-info/src/components/PropVal.js @@ -82,7 +82,7 @@ function previewProp(val) { content = {val}; } else if (typeof val === 'string') { if (val.length > 50) { - val = `${val.slice(0, 50)}…`; + val = `${val.slice(0, 50)}…`; // eslint-disable-line } content = "{val}"; braceWrap = false; diff --git a/packages/addon-info/src/components/Props.js b/packages/addon-info/src/components/Props.js index ae7c3c835e43..075bbf33a2c0 100644 --- a/packages/addon-info/src/components/Props.js +++ b/packages/addon-info/src/components/Props.js @@ -15,13 +15,13 @@ export default class Props extends React.Component { return ; } - const { propStyle, propValueStyle, propNameStyle } = stylesheet; + const { propValueStyle, propNameStyle } = stylesheet; const names = Object.keys(props).filter( name => name[0] !== '_' && name !== 'children' && - (!defaultProps || props[name] != defaultProps[name]), + (!defaultProps || props[name] !== defaultProps[name]), ); const breakIntoNewLines = names.length > 3; diff --git a/packages/addon-info/src/components/Story.js b/packages/addon-info/src/components/Story.js index be70e3a1fff0..78293fd6b18e 100644 --- a/packages/addon-info/src/components/Story.js +++ b/packages/addon-info/src/components/Story.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import PropTypes from 'prop-types'; import React from 'react'; import MTRC from 'markdown-to-react-components'; @@ -293,8 +295,6 @@ export default class Story extends React.Component { {propTables} ); - - return; } render() { diff --git a/packages/addon-info/src/components/markdown/code.js b/packages/addon-info/src/components/markdown/code.js index 0e54a1c7fbc8..be0e64b2ac77 100644 --- a/packages/addon-info/src/components/markdown/code.js +++ b/packages/addon-info/src/components/markdown/code.js @@ -1,3 +1,4 @@ +import { Prism } from 'global'; import React from 'react'; export class Code extends React.Component { diff --git a/packages/addon-info/src/index.js b/packages/addon-info/src/index.js index a2f6f78081c3..b77729190162 100644 --- a/packages/addon-info/src/index.js +++ b/packages/addon-info/src/index.js @@ -1,6 +1,7 @@ import React from 'react'; import _Story from './components/Story'; import { H1, H2, H3, H4, H5, H6, Code, P, UL, A, LI } from './components/markdown'; + export const Story = _Story; const defaultOptions = { @@ -28,9 +29,9 @@ export default { addWithInfo(storyName, info, storyFn, _options) { if (typeof storyFn !== 'function') { if (typeof info === 'function') { - _options = storyFn; - storyFn = info; - info = ''; + _options = storyFn; // eslint-disable-line + storyFn = info; // eslint-disable-line + info = ''; // eslint-disable-line } else { throw new Error('No story defining function has been specified'); } diff --git a/packages/addon-knobs/package.json b/packages/addon-knobs/package.json index e39c43ed932e..f2d9adee0552 100644 --- a/packages/addon-knobs/package.json +++ b/packages/addon-knobs/package.json @@ -15,6 +15,7 @@ }, "devDependencies": { "@kadira/storybook": "*", + "@kadira/storybook-addons": "*", "@types/node": "^7.0.12", "@types/react": "^15.0.21", "babel-cli": "^6.24.1", @@ -26,6 +27,7 @@ "babel-preset-es2015": "^6.24.1", "babel-preset-react": "^6.24.1", "babel-preset-stage-2": "^6.24.1", + "enzyme": "^2.8.2", "git-url-parse": "^6.2.2", "raw-loader": "^0.5.1", "react": "^15.5.4", @@ -35,13 +37,14 @@ "typescript-definition-tester": "^0.0.5" }, "peerDependencies": { - "@kadira/storybook-addons": "*", "react": "*", "react-dom": "*" }, "dependencies": { + "@kadira/storybook-addons": "*", "babel-runtime": "^6.23.0", "deep-equal": "^1.0.1", + "global": "^4.3.1", "insert-css": "^1.0.0", "moment": "^2.18.1", "prop-types": "^15.5.8", diff --git a/packages/addon-knobs/src/KnobManager.js b/packages/addon-knobs/src/KnobManager.js index fb83c872fa4b..a6062715f780 100644 --- a/packages/addon-knobs/src/KnobManager.js +++ b/packages/addon-knobs/src/KnobManager.js @@ -1,7 +1,9 @@ +/* eslint no-underscore-dangle: 0 */ + import React from 'react'; +import deepEqual from 'deep-equal'; import WrapStory from './components/WrapStory'; import KnobStore from './KnobStore'; -import deepEqual from 'deep-equal'; // This is used by _mayCallChannel to determine how long to wait to before triggering a panel update const PANEL_UPDATE_INTERVAL = 400; @@ -41,7 +43,7 @@ export default class KnobManager { let knobStore = this.knobStoreMap[key]; if (!knobStore) { - knobStore = this.knobStoreMap[key] = new KnobStore(); + knobStore = this.knobStoreMap[key] = new KnobStore(); // eslint-disable-line } this.knobStore = knobStore; diff --git a/packages/addon-knobs/src/components/PropField.js b/packages/addon-knobs/src/components/PropField.js index 32f5aa01ac43..fc81128deea1 100644 --- a/packages/addon-knobs/src/components/PropField.js +++ b/packages/addon-knobs/src/components/PropField.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import PropTypes from 'prop-types'; import React from 'react'; import TypeMap from './types'; diff --git a/packages/addon-knobs/src/components/PropForm.js b/packages/addon-knobs/src/components/PropForm.js index 19a92f055741..77f31f55f0b9 100644 --- a/packages/addon-knobs/src/components/PropForm.js +++ b/packages/addon-knobs/src/components/PropForm.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import PropTypes from 'prop-types'; import React from 'react'; diff --git a/packages/addon-knobs/src/components/WrapStory.js b/packages/addon-knobs/src/components/WrapStory.js index 1293a070ec86..9e6ae22fd3f0 100644 --- a/packages/addon-knobs/src/components/WrapStory.js +++ b/packages/addon-knobs/src/components/WrapStory.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import PropTypes from 'prop-types'; import React from 'react'; diff --git a/packages/addon-knobs/src/components/types/Array.js b/packages/addon-knobs/src/components/types/Array.js index 259a9bec4093..30fa28c2b2f8 100644 --- a/packages/addon-knobs/src/components/types/Array.js +++ b/packages/addon-knobs/src/components/types/Array.js @@ -36,12 +36,7 @@ ArrayType.propTypes = { onChange: PropTypes.func, }; -ArrayType.serialize = function(value) { - return value; -}; - -ArrayType.deserialize = function(value) { - return value; -}; +ArrayType.serialize = value => value; +ArrayType.deserialize = value => value; export default ArrayType; diff --git a/packages/addon-knobs/src/components/types/Boolean.js b/packages/addon-knobs/src/components/types/Boolean.js index ea261e5cfca0..40dd84af8588 100644 --- a/packages/addon-knobs/src/components/types/Boolean.js +++ b/packages/addon-knobs/src/components/types/Boolean.js @@ -34,13 +34,7 @@ BooleanType.propTypes = { onChange: PropTypes.func, }; -BooleanType.serialize = function(value) { - return String(value); -}; - -BooleanType.deserialize = function(value) { - if (!value) return false; - return value.trim() === 'true'; -}; +BooleanType.serialize = value => String(value); +BooleanType.deserialize = value => (typeof value === 'string' ? value.match('true') : false); export default BooleanType; diff --git a/packages/addon-knobs/src/components/types/Color.js b/packages/addon-knobs/src/components/types/Color.js index 04c82af7574e..94fb75fb5ae3 100644 --- a/packages/addon-knobs/src/components/types/Color.js +++ b/packages/addon-knobs/src/components/types/Color.js @@ -1,3 +1,4 @@ +import { document } from 'global'; import PropTypes from 'prop-types'; import React from 'react'; import { SketchPicker } from 'react-color'; @@ -90,12 +91,7 @@ ColorType.propTypes = { onChange: PropTypes.func, }; -ColorType.serialize = function(value) { - return value; -}; - -ColorType.deserialize = function(value) { - return value; -}; +ColorType.serialize = value => value; +ColorType.deserialize = value => value; export default ColorType; diff --git a/packages/addon-knobs/src/components/types/Date/index.js b/packages/addon-knobs/src/components/types/Date/index.js index e7ad0197c9e8..916d0ff84fc7 100644 --- a/packages/addon-knobs/src/components/types/Date/index.js +++ b/packages/addon-knobs/src/components/types/Date/index.js @@ -42,12 +42,7 @@ DateType.propTypes = { onChange: PropTypes.func, }; -DateType.serialize = function(value) { - return String(value); -}; - -DateType.deserialize = function(value) { - return parseFloat(value); -}; +DateType.serialize = value => String(value); +DateType.deserialize = value => parseFloat(value); export default DateType; diff --git a/packages/addon-knobs/src/components/types/Number.js b/packages/addon-knobs/src/components/types/Number.js index 211d9403edbc..4f6a3ffab40e 100644 --- a/packages/addon-knobs/src/components/types/Number.js +++ b/packages/addon-knobs/src/components/types/Number.js @@ -67,12 +67,7 @@ NumberType.propTypes = { onChange: PropTypes.func, }; -NumberType.serialize = function(value) { - return String(value); -}; - -NumberType.deserialize = function(value) { - return parseFloat(value); -}; +NumberType.serialize = value => String(value); +NumberType.deserialize = value => parseFloat(value); export default NumberType; diff --git a/packages/addon-knobs/src/components/types/Object.js b/packages/addon-knobs/src/components/types/Object.js index f08aab7aa0a6..d78a7a5aa88f 100644 --- a/packages/addon-knobs/src/components/types/Object.js +++ b/packages/addon-knobs/src/components/types/Object.js @@ -83,13 +83,7 @@ ObjectType.propTypes = { onChange: PropTypes.func, }; -ObjectType.serialize = function(object) { - return JSON.stringify(object); -}; - -ObjectType.deserialize = function(value) { - if (!value) return {}; - return JSON.parse(value); -}; +ObjectType.serialize = object => JSON.stringify(object); +ObjectType.deserialize = value => (value ? JSON.parse(value) : {}); export default ObjectType; diff --git a/packages/addon-knobs/src/components/types/Select.js b/packages/addon-knobs/src/components/types/Select.js index 3198f9db9a10..5b6f3cd6a01f 100644 --- a/packages/addon-knobs/src/components/types/Select.js +++ b/packages/addon-knobs/src/components/types/Select.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import PropTypes from 'prop-types'; import React from 'react'; @@ -56,12 +58,7 @@ SelectType.propTypes = { onChange: PropTypes.func, }; -SelectType.serialize = function(value) { - return value; -}; - -SelectType.deserialize = function(value) { - return value; -}; +SelectType.serialize = value => value; +SelectType.deserialize = value => value; export default SelectType; diff --git a/packages/addon-knobs/src/components/types/Text.js b/packages/addon-knobs/src/components/types/Text.js index f1ebb3fb6e5a..1327a7b45398 100644 --- a/packages/addon-knobs/src/components/types/Text.js +++ b/packages/addon-knobs/src/components/types/Text.js @@ -37,12 +37,7 @@ TextType.propTypes = { onChange: PropTypes.func, }; -TextType.serialize = function(value) { - return value; -}; - -TextType.deserialize = function(value) { - return value; -}; +TextType.serialize = value => value; +TextType.deserialize = value => value; export default TextType; diff --git a/packages/addon-notes/package.json b/packages/addon-notes/package.json index 7d4bbd691da0..2e2f16969e79 100644 --- a/packages/addon-notes/package.json +++ b/packages/addon-notes/package.json @@ -14,6 +14,7 @@ }, "devDependencies": { "@kadira/storybook": "*", + "@kadira/storybook-addons": "*", "babel-cli": "^6.5.0", "babel-core": "^6.5.0", "babel-loader": "^6.2.4", diff --git a/packages/addon-options/manager.js b/packages/addon-options/manager.js index 68d13f4d0bf1..67d49f75b482 100644 --- a/packages/addon-options/manager.js +++ b/packages/addon-options/manager.js @@ -1,2 +1,3 @@ const manager = require('./dist/manager'); + manager.init(); diff --git a/packages/addon-options/preview.js b/packages/addon-options/preview.js index 85f8d690af28..5511788a140a 100644 --- a/packages/addon-options/preview.js +++ b/packages/addon-options/preview.js @@ -1,3 +1,4 @@ const preview = require('./dist/preview'); + exports.setOptions = preview.setOptions; preview.init(); diff --git a/packages/addon-options/src/manager/index.js b/packages/addon-options/src/manager/index.js index 6a56184c6ca2..ece4b5c746c8 100644 --- a/packages/addon-options/src/manager/index.js +++ b/packages/addon-options/src/manager/index.js @@ -1,4 +1,3 @@ -import React from 'react'; import addons from '@kadira/storybook-addons'; import { ADDON_ID, EVENT_ID } from '../shared'; diff --git a/packages/addons/src/index.js b/packages/addons/src/index.js index e141acb35c33..881010f417ad 100644 --- a/packages/addons/src/index.js +++ b/packages/addons/src/index.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + export class AddonStore { constructor() { this._loaders = {}; diff --git a/packages/channel-postmessage/package.json b/packages/channel-postmessage/package.json index b0928ea61d11..bae01179cab4 100644 --- a/packages/channel-postmessage/package.json +++ b/packages/channel-postmessage/package.json @@ -14,6 +14,7 @@ }, "dependencies": { "@kadira/storybook-channel": "*", + "global": "^4.3.1", "json-stringify-safe": "^5.0.1" } } diff --git a/packages/channel-postmessage/src/index.js b/packages/channel-postmessage/src/index.js index d3a73b82db33..4dfa5a897780 100644 --- a/packages/channel-postmessage/src/index.js +++ b/packages/channel-postmessage/src/index.js @@ -1,13 +1,11 @@ +/* eslint no-underscore-dangle: 0 */ + +import { window, document } from 'global'; import Channel from '@kadira/storybook-channel'; import stringify from 'json-stringify-safe'; export const KEY = 'storybook-channel'; -export default function createChannel({ page }) { - const transport = new PostmsgTransport({ page }); - return new Channel({ transport }); -} - export class PostmsgTransport { constructor(config) { this._config = config; @@ -58,22 +56,26 @@ export class PostmsgTransport { return window.parent; } - _handleEvent(e) { - if (!e.data || typeof e.data !== 'string') { + _handleEvent(event) { + if (!event.data || typeof event.data !== 'string') { return; } let data; try { - data = JSON.parse(e.data); - } catch (e) { - return null; + data = JSON.parse(event.data); + } catch (error) { + data = null; } if (!data || typeof data !== 'object') { - return null; + return; } - const { key, event } = data; + const { key, event: eventData } = data; if (key === KEY) { - this._handler(event); + this._handler(eventData); } } } +export default function createChannel({ page }) { + const transport = new PostmsgTransport({ page }); + return new Channel({ transport }); +} diff --git a/packages/channel-websocket/package.json b/packages/channel-websocket/package.json index 9c928c7a7418..94322011d535 100644 --- a/packages/channel-websocket/package.json +++ b/packages/channel-websocket/package.json @@ -14,6 +14,7 @@ "shelljs": "^0.7.3" }, "dependencies": { - "@kadira/storybook-channel": "^1.0.1" + "@kadira/storybook-channel": "^1.0.1", + "global": "^4.3.1" } } diff --git a/packages/channel-websocket/src/index.js b/packages/channel-websocket/src/index.js index 17c059d13b22..91b678341066 100644 --- a/packages/channel-websocket/src/index.js +++ b/packages/channel-websocket/src/index.js @@ -1,9 +1,7 @@ -import Channel from '@kadira/storybook-channel'; +/* eslint no-underscore-dangle: 0 */ -export default function createChannel({ url }) { - const transport = new WebsocketTransport({ url }); - return new Channel({ transport }); -} +import { WebSocket } from 'global'; +import Channel from '@kadira/storybook-channel'; export class WebsocketTransport { constructor({ url }) { @@ -59,3 +57,8 @@ export class WebsocketTransport { }; } } + +export default function createChannel({ url }) { + const transport = new WebsocketTransport({ url }); + return new Channel({ transport }); +} diff --git a/packages/channel/src/index.js b/packages/channel/src/index.js index 6bc528542402..fd7a3c9ae1fb 100644 --- a/packages/channel/src/index.js +++ b/packages/channel/src/index.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + export default class Channel { constructor({ transport }) { this._sender = this._randomId(); diff --git a/packages/channel/src/index.test.js b/packages/channel/src/index.test.js index 8f70cee8a6ab..987edb2f6829 100644 --- a/packages/channel/src/index.test.js +++ b/packages/channel/src/index.test.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import Channel from './'; describe('Channel', () => { diff --git a/packages/decorator-centered/package.json b/packages/decorator-centered/package.json index 10f7d4b70577..0a9b5f072fab 100644 --- a/packages/decorator-centered/package.json +++ b/packages/decorator-centered/package.json @@ -13,11 +13,17 @@ "babelify" ] }, + "peerDependencies": { + "react": "*", + "react-dom": "*" + }, "devDependencies": { "babel-cli": "^6.24.1", "babel-core": "^6.24.1", "babel-preset-es2015": "^6.24.1", "babel-preset-react": "^6.24.1", - "babel-preset-stage-0": "^6.24.1" + "babel-preset-stage-0": "^6.24.1", + "react": "^15.5.4", + "react-dom": "^15.5.4" } } diff --git a/packages/getstorybook/bin/generate.js b/packages/getstorybook/bin/generate.js index 24697a093fa5..fecb082e14e9 100755 --- a/packages/getstorybook/bin/generate.js +++ b/packages/getstorybook/bin/generate.js @@ -10,10 +10,10 @@ const commandLog = require('../lib/helpers').commandLog; const codeLog = require('../lib/helpers').codeLog; const paddedLog = require('../lib/helpers').paddedLog; const installDeps = require('../lib/helpers').installDeps; -const logger = console; - const pkg = require('../package.json'); +const logger = console; + program .version(pkg.version) .option('-f --force', 'Forcely add storybook') @@ -59,7 +59,7 @@ switch (projectType) { break; case types.REACT_SCRIPTS: done = commandLog('Adding storybook support to your "Create React App" based project'); - require('../generators/REACT_SCRIPTS'); + require('../generators/REACT_SCRIPTS'); // eslint-disable-line done(); installDeps(npmOptions); @@ -71,7 +71,7 @@ switch (projectType) { case types.REACT: done = commandLog('Adding storybook support to your "React" app'); - require('../generators/REACT'); + require('../generators/REACT'); // eslint-disable-line done(); installDeps(npmOptions); @@ -83,7 +83,7 @@ switch (projectType) { case types.REACT_NATIVE: done = commandLog('Adding storybook support to your "React Native" app'); - require('../generators/REACT_NATIVE'); + require('../generators/REACT_NATIVE'); // eslint-disable-line done(); installDeps(npmOptions); @@ -95,7 +95,7 @@ switch (projectType) { case types.METEOR: done = commandLog('Adding storybook support to your "Meteor" app'); - require('../generators/METEOR'); + require('../generators/METEOR'); // eslint-disable-line done(); installDeps(npmOptions); @@ -107,7 +107,7 @@ switch (projectType) { case types.WEBPACK_REACT: done = commandLog('Adding storybook support to your "Webpack React" app'); - require('../generators/WEBPACK_REACT'); + require('../generators/WEBPACK_REACT'); // eslint-disable-line done(); installDeps(npmOptions); @@ -119,7 +119,7 @@ switch (projectType) { case types.REACT_PROJECT: done = commandLog('Adding storybook support to your "React" library'); - require('../generators/REACT'); + require('../generators/REACT'); // eslint-disable-line done(); installDeps(npmOptions); diff --git a/packages/getstorybook/generators/.eslintrc.js b/packages/getstorybook/generators/.eslintrc.js new file mode 100644 index 000000000000..1daf50a7c3f2 --- /dev/null +++ b/packages/getstorybook/generators/.eslintrc.js @@ -0,0 +1,14 @@ +const error = 2; +const warn = 1; +const ignore = 0; + +module.exports = { + rules: { + 'import/no-extraneous-dependencies': ignore, + 'import/no-unresolved': ignore, + 'import/extensions': ignore, + 'import/extensions': ignore, + 'no-new-func': ignore, + 'global-require': ignore, + }, +}; diff --git a/packages/getstorybook/generators/METEOR/index.js b/packages/getstorybook/generators/METEOR/index.js index f6f9a54254f4..8a9f0db99f63 100644 --- a/packages/getstorybook/generators/METEOR/index.js +++ b/packages/getstorybook/generators/METEOR/index.js @@ -2,7 +2,6 @@ const mergeDirs = require('merge-dirs').default; const helpers = require('../../lib/helpers'); const path = require('path'); const fs = require('fs'); -const sh = require('shelljs'); const JSON5 = require('json5'); mergeDirs(path.resolve(__dirname, 'template/'), '.', 'overwrite'); @@ -40,7 +39,7 @@ fs.writeFileSync('.babelrc', JSON.stringify(babelrc, null, 2), 'utf8'); // write the new package.json. packageJson.devDependencies['@kadira/storybook'] = '^2.21.0'; -packageJson.scripts['storybook'] = 'start-storybook -p 6006'; +packageJson.scripts.storybook = 'start-storybook -p 6006'; packageJson.scripts['build-storybook'] = 'build-storybook'; // add react packages. diff --git a/packages/getstorybook/generators/REACT/index.js b/packages/getstorybook/generators/REACT/index.js index c20fac033bef..a15f20fe9fb8 100644 --- a/packages/getstorybook/generators/REACT/index.js +++ b/packages/getstorybook/generators/REACT/index.js @@ -11,7 +11,7 @@ packageJson.devDependencies = packageJson.devDependencies || {}; packageJson.devDependencies['@kadira/storybook'] = '^2.21.0'; packageJson.scripts = packageJson.scripts || {}; -packageJson.scripts['storybook'] = 'start-storybook -p 6006'; +packageJson.scripts.storybook = 'start-storybook -p 6006'; packageJson.scripts['build-storybook'] = 'build-storybook'; helpers.writePackageJson(packageJson); diff --git a/packages/getstorybook/generators/REACT/template/stories/Welcome.js b/packages/getstorybook/generators/REACT/template/stories/Welcome.js index 4e9ee8eb7317..069bf85d3c30 100644 --- a/packages/getstorybook/generators/REACT/template/stories/Welcome.js +++ b/packages/getstorybook/generators/REACT/template/stories/Welcome.js @@ -50,7 +50,9 @@ export default class Welcome extends React.Component { {' '} directory.
- A story is a single state of one or more UI components. You can have as many stories as you want. + A story is a single state of one or more UI components. + {' '} + You can have as many stories as you want.
(Basically a story is like a visual test case.)

diff --git a/packages/getstorybook/generators/REACT_NATIVE/index.js b/packages/getstorybook/generators/REACT_NATIVE/index.js index 00e9c7cfdae0..73e55ad64049 100644 --- a/packages/getstorybook/generators/REACT_NATIVE/index.js +++ b/packages/getstorybook/generators/REACT_NATIVE/index.js @@ -22,6 +22,6 @@ packageJson.devDependencies = packageJson.devDependencies || {}; packageJson.devDependencies['@kadira/react-native-storybook'] = '^2.0.0'; packageJson.scripts = packageJson.scripts || {}; -packageJson.scripts['storybook'] = 'storybook start -p 7007'; +packageJson.scripts.storybook = 'storybook start -p 7007'; helpers.writePackageJson(packageJson); diff --git a/packages/getstorybook/generators/REACT_NATIVE/template/storybook/stories/Welcome/index.js b/packages/getstorybook/generators/REACT_NATIVE/template/storybook/stories/Welcome/index.js index 2305b830c30f..a0677d8def7d 100644 --- a/packages/getstorybook/generators/REACT_NATIVE/template/storybook/stories/Welcome/index.js +++ b/packages/getstorybook/generators/REACT_NATIVE/template/storybook/stories/Welcome/index.js @@ -1,3 +1,5 @@ +/* eslint max-len: 0 */ + import React from 'react'; import { View, Text } from 'react-native'; diff --git a/packages/getstorybook/generators/REACT_SCRIPTS/index.js b/packages/getstorybook/generators/REACT_SCRIPTS/index.js index ad50743aff9c..59e662ee05a1 100644 --- a/packages/getstorybook/generators/REACT_SCRIPTS/index.js +++ b/packages/getstorybook/generators/REACT_SCRIPTS/index.js @@ -9,12 +9,12 @@ const packageJson = helpers.getPackageJson(); // TODO: Get the latest version of storybook here. packageJson.devDependencies['@kadira/storybook'] = '^2.21.0'; -packageJson.scripts['storybook'] = 'start-storybook -p 9009'; +packageJson.scripts.storybook = 'start-storybook -p 9009'; packageJson.scripts['build-storybook'] = 'build-storybook'; if (fs.existsSync(path.resolve('./public'))) { // has a public folder and add support to it. - packageJson.scripts['storybook'] += ' -s public'; + packageJson.scripts.storybook += ' -s public'; packageJson.scripts['build-storybook'] += ' -s public'; } diff --git a/packages/getstorybook/generators/REACT_SCRIPTS/template/src/stories/Welcome.js b/packages/getstorybook/generators/REACT_SCRIPTS/template/src/stories/Welcome.js index 2b20b2a1b4a4..7a0673ed0731 100644 --- a/packages/getstorybook/generators/REACT_SCRIPTS/template/src/stories/Welcome.js +++ b/packages/getstorybook/generators/REACT_SCRIPTS/template/src/stories/Welcome.js @@ -68,7 +68,9 @@ export default class Welcome extends React.Component { {' '} directory.
- A story is a single state of one or more UI components. You can have as many stories as you want. + A story is a single state of one or more UI components. + {' '} + You can have as many stories as you want.
(Basically a story is like a visual test case.)

diff --git a/packages/getstorybook/generators/WEBPACK_REACT/index.js b/packages/getstorybook/generators/WEBPACK_REACT/index.js index c20fac033bef..a15f20fe9fb8 100644 --- a/packages/getstorybook/generators/WEBPACK_REACT/index.js +++ b/packages/getstorybook/generators/WEBPACK_REACT/index.js @@ -11,7 +11,7 @@ packageJson.devDependencies = packageJson.devDependencies || {}; packageJson.devDependencies['@kadira/storybook'] = '^2.21.0'; packageJson.scripts = packageJson.scripts || {}; -packageJson.scripts['storybook'] = 'start-storybook -p 6006'; +packageJson.scripts.storybook = 'start-storybook -p 6006'; packageJson.scripts['build-storybook'] = 'build-storybook'; helpers.writePackageJson(packageJson); diff --git a/packages/getstorybook/generators/WEBPACK_REACT/template/stories/Welcome.js b/packages/getstorybook/generators/WEBPACK_REACT/template/stories/Welcome.js index acd48b6409bc..1a80ed915df7 100644 --- a/packages/getstorybook/generators/WEBPACK_REACT/template/stories/Welcome.js +++ b/packages/getstorybook/generators/WEBPACK_REACT/template/stories/Welcome.js @@ -54,7 +54,9 @@ export default class Welcome extends React.Component { {' '} directory.
- A story is a single state of one or more UI components. You can have as many stories as you want. + A story is a single state of one or more UI components. + {' '} + You can have as many stories as you want.
(Basically a story is like a visual test case.)

diff --git a/packages/getstorybook/lib/helpers.js b/packages/getstorybook/lib/helpers.js index 38a4f40c8f02..8c3bc969e60d 100644 --- a/packages/getstorybook/lib/helpers.js +++ b/packages/getstorybook/lib/helpers.js @@ -1,9 +1,10 @@ const path = require('path'); const fs = require('fs'); const chalk = require('chalk'); -const logger = console; const spawnSync = require('spawn-sync'); +const logger = console; + exports.getPackageJson = function getPackageJson() { const packageJsonPath = path.resolve('package.json'); if (!fs.existsSync(packageJsonPath)) { @@ -23,7 +24,7 @@ exports.writePackageJson = function writePackageJson(packageJson) { exports.commandLog = function commandLog(message) { process.stdout.write(chalk.cyan(' • ') + message); - const done = function(errorMessage, errorInfo) { + const done = (errorMessage, errorInfo) => { if (errorMessage) { process.stdout.write(`. ${chalk.red('✖')}\n`); logger.error(`\n ${chalk.red(errorMessage)}`); @@ -41,7 +42,7 @@ exports.commandLog = function commandLog(message) { return done; }; -exports.paddedLog = function(message) { +exports.paddedLog = function paddedLog(message) { const newMessage = message.split('\n').map(line => ` ${line}`).join('\n'); logger.log(newMessage); @@ -49,7 +50,7 @@ exports.paddedLog = function(message) { exports.getChars = function getChars(char, amount) { let line = ''; - for (let lc = 0; lc < amount; lc++) { + for (let lc = 0; lc < amount; lc++) { // eslint-disable-line line += char; } @@ -75,10 +76,10 @@ exports.codeLog = function codeLog(codeLines, leftPadAmount) { logger.log(finalResult); }; -exports.installDeps = function(options) { +exports.installDeps = function installDeps(options) { let done = exports.commandLog('Preparing to install dependencies'); done(); - console.log(); + logger.log(); let result; if (options.useYarn) { @@ -87,7 +88,7 @@ exports.installDeps = function(options) { result = spawnSync('npm', ['install'], { stdio: 'inherit' }); } - console.log(); + logger.log(); done = exports.commandLog('Installing dependencies'); if (result.status !== 0) { done('An error occurred while installing dependencies.'); diff --git a/packages/getstorybook/package.json b/packages/getstorybook/package.json index 6db47b5f7279..08fb648774f5 100644 --- a/packages/getstorybook/package.json +++ b/packages/getstorybook/package.json @@ -27,5 +27,11 @@ "shelljs": "^0.7.7", "spawn-sync": "^1.0.15", "update-notifier": "^2.1.0" + }, + "devDependencies": { + "@kadira/storybook": "^2.35.3", + "prop-types": "^15.5.8", + "react": "^15.5.4", + "react-dom": "^15.5.4" } } diff --git a/packages/react-native-storybook/package.json b/packages/react-native-storybook/package.json index de9c4225503e..1bb608134900 100644 --- a/packages/react-native-storybook/package.json +++ b/packages/react-native-storybook/package.json @@ -61,6 +61,7 @@ "events": "^1.1.1", "express": "^4.15.2", "file-loader": "^0.11.1", + "global": "^4.3.1", "json-loader": "^0.5.4", "json5": "^0.5.1", "postcss-loader": "^1.3.3", @@ -70,6 +71,7 @@ "uuid": "^3.0.1", "webpack": "^2.4.1", "webpack-dev-middleware": "^1.10.1", - "webpack-hot-middleware": "^2.18.0" + "webpack-hot-middleware": "^2.18.0", + "ws": "^2.2.3" } } diff --git a/packages/react-native-storybook/src/manager/index.js b/packages/react-native-storybook/src/manager/index.js index 84b2619d9275..dfc4333cc53d 100644 --- a/packages/react-native-storybook/src/manager/index.js +++ b/packages/react-native-storybook/src/manager/index.js @@ -1,3 +1,4 @@ +import { document, location, window } from 'global'; import renderStorybookUI from '@kadira/storybook-ui'; import Provider from './provider'; diff --git a/packages/react-native-storybook/src/preview/index.js b/packages/react-native-storybook/src/preview/index.js index a3c6b029ee11..9483b980e85f 100644 --- a/packages/react-native-storybook/src/preview/index.js +++ b/packages/react-native-storybook/src/preview/index.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import React from 'react'; import addons from '@kadira/storybook-addons'; import createChannel from '@kadira/storybook-channel-websocket'; @@ -66,10 +68,11 @@ export default class Preview { channel = createChannel({ url }); addons.setChannel(channel); } - channel.on('getStories', d => this._sendSetStories()); + channel.on('getStories', () => this._sendSetStories()); channel.on('setCurrentStory', d => this._selectStory(d)); this._sendSetStories(); this._sendGetCurrentStory(); + // finally return the preview component return ; }; diff --git a/packages/react-native-storybook/src/preview/story_kind.js b/packages/react-native-storybook/src/preview/story_kind.js index 1c91a6d85b1a..ddf0004cda18 100644 --- a/packages/react-native-storybook/src/preview/story_kind.js +++ b/packages/react-native-storybook/src/preview/story_kind.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + export default class StoryKindApi { constructor(stories, addons, decorators, kind) { this.kind = kind; diff --git a/packages/react-native-storybook/src/preview/story_store.js b/packages/react-native-storybook/src/preview/story_store.js index 65a8d40df25a..86021172b09f 100644 --- a/packages/react-native-storybook/src/preview/story_store.js +++ b/packages/react-native-storybook/src/preview/story_store.js @@ -1,4 +1,5 @@ -let cnt = 0; +/* eslint no-underscore-dangle: 0 */ +let count = 0; export default class StoryStore { constructor() { @@ -6,17 +7,18 @@ export default class StoryStore { } addStory(kind, name, fn) { + count += 1; if (!this._data[kind]) { this._data[kind] = { kind, - index: cnt++, + index: count, stories: {}, }; } this._data[kind].stories[name] = { name, - index: cnt++, + index: count, fn, }; } diff --git a/packages/react-native-storybook/src/server/config.js b/packages/react-native-storybook/src/server/config.js index d715cff14b43..d524394816c1 100644 --- a/packages/react-native-storybook/src/server/config.js +++ b/packages/react-native-storybook/src/server/config.js @@ -101,7 +101,7 @@ export default function(configType, baseConfig, projectDir, configDir) { customConfigPath = path.resolve(__dirname, './config/defaults/webpack.config.js'); } - const customConfig = require(customConfigPath); + const customConfig = require(customConfigPath); // eslint-disable-line if (typeof customConfig === 'function') { logger.info('=> Loading custom webpack config (full-control mode).'); diff --git a/packages/react-native-storybook/src/server/config/webpack.config.js b/packages/react-native-storybook/src/server/config/webpack.config.js index 5f069df7932a..ddd38a20d004 100644 --- a/packages/react-native-storybook/src/server/config/webpack.config.js +++ b/packages/react-native-storybook/src/server/config/webpack.config.js @@ -23,7 +23,7 @@ const config = { { test: /\.jsx?$/, loader: require.resolve('babel-loader'), - query: require('./babel.js'), + query: require('./babel.js'), // eslint-disable-line include: includePaths, exclude: excludePaths, }, diff --git a/packages/react-native-storybook/src/server/config/webpack.config.prod.js b/packages/react-native-storybook/src/server/config/webpack.config.prod.js index 80a9c34d8719..f1601b63bfa6 100644 --- a/packages/react-native-storybook/src/server/config/webpack.config.prod.js +++ b/packages/react-native-storybook/src/server/config/webpack.config.prod.js @@ -43,7 +43,7 @@ const config = { { test: /\.jsx?$/, loader: require.resolve('babel-loader'), - query: require('./babel.prod.js'), + query: require('./babel.prod.js'), // eslint-disable-line include: includePaths, exclude: excludePaths, }, diff --git a/packages/react-native-storybook/src/server/index.js b/packages/react-native-storybook/src/server/index.js index 862347ec7197..36522b31a859 100755 --- a/packages/react-native-storybook/src/server/index.js +++ b/packages/react-native-storybook/src/server/index.js @@ -22,14 +22,14 @@ export default class Server { : {}; if (params.pairedId) { - socket.pairedId = params.pairedId; + socket.pairedId = params.pairedId; // eslint-disable-line } } socket.on('message', data => { this.wsServer.clients.forEach(c => { if (!this.options.manualId || (socket.pairedId && socket.pairedId === c.pairedId)) { - return c.send(data); + c.send(data); } }); }); diff --git a/packages/react-native-storybook/src/server/middleware.js b/packages/react-native-storybook/src/server/middleware.js index 7b9ad36028d3..7517cd85d496 100644 --- a/packages/react-native-storybook/src/server/middleware.js +++ b/packages/react-native-storybook/src/server/middleware.js @@ -12,13 +12,13 @@ import getIndexHtml from './index.html'; function getMiddleware(configDir) { const middlewarePath = path.resolve(configDir, 'middleware.js'); if (fs.existsSync(middlewarePath)) { - let middlewareModule = require(middlewarePath); - if (middlewareModule.__esModule) { + let middlewareModule = require(middlewarePath); // eslint-disable-line + if (middlewareModule.__esModule) { // eslint-disable-line middlewareModule = middlewareModule.default; } return middlewareModule; } - return function() {}; + return () => {}; } export default function({ projectDir, configDir, ...options }) { diff --git a/packages/react-storybook/demo/src/stories/Welcome.js b/packages/react-storybook/demo/src/stories/Welcome.js index 5886c30148ad..033352a3f9c0 100644 --- a/packages/react-storybook/demo/src/stories/Welcome.js +++ b/packages/react-storybook/demo/src/stories/Welcome.js @@ -68,7 +68,9 @@ export default class Welcome extends React.Component { {' '} directory.
- A story is a single state of one or more UI components. You can have as many stories as you want. + A story is a single state of one or more UI components. + {' '} + You can have as many stories as you want.
(Basically a story is like a visual test case.)

diff --git a/packages/react-storybook/package.json b/packages/react-storybook/package.json index 152c36b2d022..a559687db706 100644 --- a/packages/react-storybook/package.json +++ b/packages/react-storybook/package.json @@ -39,6 +39,7 @@ "express": "^4.15.2", "file-loader": "^0.11.1", "find-cache-dir": "^0.1.1", + "global": "^4.3.1", "json-loader": "^0.5.4", "json-stringify-safe": "^5.0.1", "json5": "^0.5.1", diff --git a/packages/react-storybook/scripts/mocha_runner.js b/packages/react-storybook/scripts/mocha_runner.js deleted file mode 100755 index 4b6b7654db95..000000000000 --- a/packages/react-storybook/scripts/mocha_runner.js +++ /dev/null @@ -1,25 +0,0 @@ -require('babel-core/register'); -require('babel-polyfill'); - -// Add jsdom support, which is required for enzyme. -const jsdom = require('jsdom').jsdom; - -const exposedProperties = ['window', 'navigator', 'document']; - -global.document = jsdom(''); -global.window = document.defaultView; -Object.keys(document.defaultView).forEach(property => { - if (typeof global[property] === 'undefined') { - exposedProperties.push(property); - global[property] = document.defaultView[property]; - } -}); - -global.navigator = { - userAgent: 'node.js', -}; - -process.on('unhandledRejection', error => { - console.error('Unhandled Promise Rejection:'); - console.error((error && error.stack) || error); -}); diff --git a/packages/react-storybook/src/client/preview/client_api.js b/packages/react-storybook/src/client/preview/client_api.js index ecbabc571fae..ae5047fe8fe6 100644 --- a/packages/react-storybook/src/client/preview/client_api.js +++ b/packages/react-storybook/src/client/preview/client_api.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + export default class ClientApi { constructor({ channel, storyStore }) { // channel can be null when running in node diff --git a/packages/react-storybook/src/client/preview/client_api.test.js b/packages/react-storybook/src/client/preview/client_api.test.js index 56f1c7783d37..acb45b425c1f 100644 --- a/packages/react-storybook/src/client/preview/client_api.test.js +++ b/packages/react-storybook/src/client/preview/client_api.test.js @@ -1,3 +1,5 @@ +/* eslint no-underscore-dangle: 0 */ + import ClientAPI from './client_api'; class StoryStore { diff --git a/packages/react-storybook/src/client/preview/config_api.js b/packages/react-storybook/src/client/preview/config_api.js index ccc58b7b4545..cc0bbea3af3e 100644 --- a/packages/react-storybook/src/client/preview/config_api.js +++ b/packages/react-storybook/src/client/preview/config_api.js @@ -1,7 +1,7 @@ -/* globals location */ +/* eslint no-underscore-dangle: 0 */ +import { location } from 'global'; import { setInitialStory, setError, clearError } from './actions'; - import { clearDecorators } from './'; export default class ConfigApi { diff --git a/packages/react-storybook/src/client/preview/story_store.js b/packages/react-storybook/src/client/preview/story_store.js index 0cdb82fb0122..b7051c1ea3be 100644 --- a/packages/react-storybook/src/client/preview/story_store.js +++ b/packages/react-storybook/src/client/preview/story_store.js @@ -1,8 +1,10 @@ -let cnt = 0; +/* eslint no-underscore-dangle: 0 */ + +let count = 0; function getId() { - cnt += 1; - return cnt; + count += 1; + return count; } export default class StoryStore { diff --git a/packages/react-storybook/src/server/config.js b/packages/react-storybook/src/server/config.js index 362abe070876..cb61b450ef41 100644 --- a/packages/react-storybook/src/server/config.js +++ b/packages/react-storybook/src/server/config.js @@ -42,7 +42,7 @@ export default function(configType, baseConfig, configDir) { customConfigPath = path.resolve(__dirname, './config/defaults/webpack.config.js'); } - const customConfig = require(customConfigPath); + const customConfig = require(customConfigPath); // eslint-disable-line if (typeof customConfig === 'function') { logger.info('=> Loading custom webpack config (full-control mode).'); diff --git a/packages/react-storybook/src/server/config/WatchMissingNodeModulesPlugin.js b/packages/react-storybook/src/server/config/WatchMissingNodeModulesPlugin.js index 1d6fd4802aa2..b6a74311c324 100644 --- a/packages/react-storybook/src/server/config/WatchMissingNodeModulesPlugin.js +++ b/packages/react-storybook/src/server/config/WatchMissingNodeModulesPlugin.js @@ -16,7 +16,7 @@ function WatchMissingNodeModulesPlugin(nodeModulesPath) { this.nodeModulesPath = nodeModulesPath; } -WatchMissingNodeModulesPlugin.prototype.apply = function(compiler) { +WatchMissingNodeModulesPlugin.prototype.apply = function apply(compiler) { compiler.plugin('emit', (compilation, callback) => { const missingDeps = compilation.missingDependencies; const nodeModulesPath = this.nodeModulesPath; diff --git a/packages/react-storybook/src/server/config/defaults/webpack.config.js b/packages/react-storybook/src/server/config/defaults/webpack.config.js index 69ec7d68f6ab..75ab902f919c 100644 --- a/packages/react-storybook/src/server/config/defaults/webpack.config.js +++ b/packages/react-storybook/src/server/config/defaults/webpack.config.js @@ -1,5 +1,6 @@ +import webpack from 'webpack'; import autoprefixer from 'autoprefixer'; -import { includePaths } from '../utils'; +import { includePaths, excludePaths } from '../utils'; // Add a default custom config which is similar to what React Create App does. module.exports = storybookBaseConfig => { diff --git a/packages/react-storybook/src/server/index.js b/packages/react-storybook/src/server/index.js index 7a347c540884..3fa2a36f6dac 100755 --- a/packages/react-storybook/src/server/index.js +++ b/packages/react-storybook/src/server/index.js @@ -1,6 +1,7 @@ #!/usr/bin/env node import express from 'express'; +import https from 'https'; import favicon from 'serve-favicon'; import program from 'commander'; import path from 'path'; diff --git a/packages/react-storybook/src/server/track_usage.js b/packages/react-storybook/src/server/track_usage.js index 835d62e152c4..0f00e42065da 100644 --- a/packages/react-storybook/src/server/track_usage.js +++ b/packages/react-storybook/src/server/track_usage.js @@ -58,7 +58,7 @@ export function track() { store.set('userId', userId); } - const pkg = require('../../package.json'); + const pkg = require('../../package.json'); // eslint-disable-line // We don't wanna worry about the success or failure of this. request.post( diff --git a/packages/react-storybook/src/server/utils.js b/packages/react-storybook/src/server/utils.js index 19811869d4fd..3961915ba6f7 100644 --- a/packages/react-storybook/src/server/utils.js +++ b/packages/react-storybook/src/server/utils.js @@ -20,7 +20,7 @@ export function getEnvConfig(program, configEnv) { const envVarName = configEnv[fieldName]; const envVarValue = process.env[envVarName]; if (envVarValue) { - program[fieldName] = envVarValue; + program[fieldName] = envVarValue; // eslint-disable-line } }); } @@ -28,11 +28,11 @@ export function getEnvConfig(program, configEnv) { export function getMiddleware(configDir) { const middlewarePath = path.resolve(configDir, 'middleware.js'); if (fs.existsSync(middlewarePath)) { - let middlewareModule = require(middlewarePath); - if (middlewareModule.__esModule) { + let middlewareModule = require(middlewarePath); // eslint-disable-line + if (middlewareModule.__esModule) { // eslint-disable-line middlewareModule = middlewareModule.default; } return middlewareModule; } - return function() {}; + return () => {}; } diff --git a/packages/storybook-ui/example/package.json b/packages/storybook-ui/example/package.json index bd44ab791365..9756c848a6ef 100644 --- a/packages/storybook-ui/example/package.json +++ b/packages/storybook-ui/example/package.json @@ -6,20 +6,20 @@ "author": "", "license": "ISC", "devDependencies": { - "babel-core": "^6.0.20", - "babel-eslint": "^4.1.3", - "babel-loader": "^6.0.1", - "babel-preset-es2015": "^6.0.15", - "babel-preset-react": "^6.0.15", - "babel-preset-stage-0": "^6.0.15", - "eslint": "^1.10.3", - "eslint-plugin-react": "^3.6.2", - "webpack": "^1.12.2", - "webpack-dev-server": "^1.12.1" + "babel-core": "^6.24.1", + "babel-eslint": "^7.2.2", + "babel-loader": "^6.4.1", + "babel-preset-es2015": "^6.24.1", + "babel-preset-react": "^6.24.1", + "babel-preset-stage-0": "^6.24.1", + "eslint": "^3.19.0", + "eslint-plugin-react": "^6.10.3", + "webpack": "^2.4.1", + "webpack-dev-server": "^2.4.2" }, "dependencies": { - "keycode": "^2.1.2", - "react": "^15.0.1", - "react-dom": "^15.0.1" + "keycode": "^2.1.8", + "react": "^15.5.4", + "react-dom": "^15.5.4" } } diff --git a/packages/storybook-ui/example/server.js b/packages/storybook-ui/example/server.js index 8867ab57f46d..834f6655f1f5 100644 --- a/packages/storybook-ui/example/server.js +++ b/packages/storybook-ui/example/server.js @@ -6,9 +6,8 @@ new WebpackDevServer(webpack(config), { publicPath: config.output.publicPath, hot: false, historyApiFallback: true, -}).listen(9999, 'localhost', (err, result) => { - if (err) { - return console.log(err); - } - console.log('Listening at http://localhost:9999/'); -}); +}).listen( + 9999, + 'localhost', + err => (err ? console.log(err) : console.log('Listening at http://localhost:9999/')), +); diff --git a/packages/storybook-ui/package.json b/packages/storybook-ui/package.json index d7ac3ed36b5c..56df195e4ab6 100644 --- a/packages/storybook-ui/package.json +++ b/packages/storybook-ui/package.json @@ -22,6 +22,7 @@ "babel-preset-es2015": "^6.24.1", "babel-preset-react": "^6.24.1", "babel-preset-stage-0": "^6.24.1", + "enzyme": "^2.8.2", "react": "^15.5.4", "react-dom": "^15.5.4" }, @@ -35,6 +36,7 @@ "deep-equal": "^1.0.1", "events": "^1.1.1", "fuzzysearch": "^1.0.3", + "global": "^4.3.1", "json-stringify-safe": "^5.0.1", "keycode": "^2.1.8", "lodash.pick": "^4.4.0", diff --git a/packages/storybook-ui/src/index.js b/packages/storybook-ui/src/index.js index d340875523d6..7ce871295f5f 100644 --- a/packages/storybook-ui/src/index.js +++ b/packages/storybook-ui/src/index.js @@ -1,18 +1,18 @@ import { createApp } from 'mantra-core'; import Podda from 'podda'; -import buildContext from './context.js'; +import buildContext from './context'; import shortcutsModule from './modules/shortcuts'; import apiModule from './modules/api'; import uiModule from './modules/ui'; import { setContext, setActions } from './compose'; export class Provider { - renderPreview(selectedKind, selectedStory) { + renderPreview() { throw new Error('Provider.renderPreview() is not implemented!'); } - handleAPI(api) { + handleAPI() { throw new Error('Provider.handleAPI() is not implemented!'); } } @@ -38,7 +38,7 @@ export default function(domNode, provider) { app.loadModule(uiModule); setContext(context); - setActions(app._bindContext(app.actions)); + setActions(app._bindContext(app.actions)); // eslint-disable-line app.init(); } diff --git a/packages/storybook-ui/src/modules/api/actions/api.test.js b/packages/storybook-ui/src/modules/api/actions/api.test.js index 04a04f87d769..3536069941d3 100755 --- a/packages/storybook-ui/src/modules/api/actions/api.test.js +++ b/packages/storybook-ui/src/modules/api/actions/api.test.js @@ -124,7 +124,7 @@ describe('manager.api.actions.api', () => { describe('has enough stories', () => { it('should select the next story', () => { const clientStore = new MockClientStore(); - actions.jumpToStory({ clientStore }, 1); + actions.jumpToStory({ clientStore }, 1); // eslint-disable-line const state = { stories, @@ -140,7 +140,7 @@ describe('manager.api.actions.api', () => { it('should select the prev story', () => { const clientStore = new MockClientStore(); - actions.jumpToStory({ clientStore }, -1); + actions.jumpToStory({ clientStore }, -1); // eslint-disable-line const state = { stories, @@ -158,7 +158,7 @@ describe('manager.api.actions.api', () => { describe('has not enough stories', () => { it('should select the current story', () => { const clientStore = new MockClientStore(); - actions.jumpToStory({ clientStore }, 1); + actions.jumpToStory({ clientStore }, 1); // eslint-disable-line const state = { stories, diff --git a/packages/storybook-ui/src/modules/api/configs/init_api.test.js b/packages/storybook-ui/src/modules/api/configs/init_api.test.js index 43586b3d2fbc..0d695f10f748 100644 --- a/packages/storybook-ui/src/modules/api/configs/init_api.test.js +++ b/packages/storybook-ui/src/modules/api/configs/init_api.test.js @@ -74,14 +74,14 @@ describe('manager.api.config.initApi', () => { const provider = { handleAPI(api) { - let cnt = 0; + let count = 0; api.onStory(() => { - cnt++; + count += 1; }); api.onStory(() => { - cnt++; - expect(cnt).toBe(2); + count += 1; + expect(count).toBe(2); done(); }); }, @@ -107,15 +107,15 @@ describe('manager.api.config.initApi', () => { const provider = { handleAPI(api) { - let cnt = 0; + let count = 0; const stop = api.onStory(() => { - cnt++; + count += 1; }); stop(); api.onStory(() => { - cnt++; - expect(cnt).toBe(1); + count += 1; + expect(count).toBe(1); done(); }); }, diff --git a/packages/storybook-ui/src/modules/ui/components/layout/dimensions.js b/packages/storybook-ui/src/modules/ui/components/layout/dimensions.js index 631aeb6f191d..61c9a5d58de3 100644 --- a/packages/storybook-ui/src/modules/ui/components/layout/dimensions.js +++ b/packages/storybook-ui/src/modules/ui/components/layout/dimensions.js @@ -33,7 +33,7 @@ class Dimensions extends React.Component { isVisible: false, }; - this._hideTimeout = null; + this.hideTimeout = null; } componentWillReceiveProps({ width, height }) { @@ -43,13 +43,13 @@ class Dimensions extends React.Component { } componentWillUnmount() { - clearTimeout(this._hideTimeout); + clearTimeout(this.hideTimeout); } onChange(width, height) { this.setState({ isVisible: true }); - this._hideTimeout = setTimeout(() => { + this.hideTimeout = setTimeout(() => { // Ensure the dimensions aren't still changing if (width === this.props.width && height === this.props.height) { this.setState({ isVisible: false }); diff --git a/packages/storybook-ui/src/modules/ui/components/layout/index.js b/packages/storybook-ui/src/modules/ui/components/layout/index.js index 0271e34704c7..6fc1060cd5dd 100755 --- a/packages/storybook-ui/src/modules/ui/components/layout/index.js +++ b/packages/storybook-ui/src/modules/ui/components/layout/index.js @@ -1,10 +1,11 @@ import PropTypes from 'prop-types'; import React from 'react'; +import { window, document, localStorage } from 'global'; +import SplitPane from '@kadira/react-split-pane'; import VSplit from './vsplit'; import HSplit from './hsplit'; import Dimensions from './dimensions'; -import SplitPane from '@kadira/react-split-pane'; const rootStyle = { height: '100vh', @@ -60,11 +61,11 @@ const fullScreenPreviewStyle = { const vsplit = ; const hsplit = ; -const onDragStart = function() { +const onDragStart = () => { document.body.classList.add('dragging'); }; -const onDragEnd = function() { +const onDragEnd = () => { document.body.classList.remove('dragging'); }; diff --git a/packages/storybook-ui/src/modules/ui/components/layout/index.test.js b/packages/storybook-ui/src/modules/ui/components/layout/index.test.js index a4c1e93331c5..49e486a468a8 100755 --- a/packages/storybook-ui/src/modules/ui/components/layout/index.test.js +++ b/packages/storybook-ui/src/modules/ui/components/layout/index.test.js @@ -1,6 +1,6 @@ import React from 'react'; import { shallow } from 'enzyme'; -import Layout from './index.js'; +import Layout from './index'; describe('manager.ui.components.layout.index', () => { describe('with default options', () => { diff --git a/packages/storybook-ui/src/modules/ui/components/left_panel/header.test.js b/packages/storybook-ui/src/modules/ui/components/left_panel/header.test.js index 506044fb1986..9d65d36d6c5f 100755 --- a/packages/storybook-ui/src/modules/ui/components/left_panel/header.test.js +++ b/packages/storybook-ui/src/modules/ui/components/left_panel/header.test.js @@ -1,6 +1,6 @@ import React from 'react'; import { shallow } from 'enzyme'; -import Header from './header.js'; +import Header from './header'; describe('manager.ui.components.left_panel.header', () => { test('should fire openShortcutsHelp when clicked on shortcut button', () => { diff --git a/packages/storybook-ui/src/modules/ui/components/left_panel/index.js b/packages/storybook-ui/src/modules/ui/components/left_panel/index.js index 974a5dc69263..924bf7571843 100755 --- a/packages/storybook-ui/src/modules/ui/components/left_panel/index.js +++ b/packages/storybook-ui/src/modules/ui/components/left_panel/index.js @@ -1,9 +1,9 @@ import PropTypes from 'prop-types'; import React from 'react'; +import pick from 'lodash.pick'; import Header from './header'; import Stories from './stories'; import TextFilter from './text_filter'; -import pick from 'lodash.pick'; const scrollStyle = { height: 'calc(100vh - 105px)', diff --git a/packages/storybook-ui/src/modules/ui/components/search_box.js b/packages/storybook-ui/src/modules/ui/components/search_box.js index 28c58f073175..e95922439257 100644 --- a/packages/storybook-ui/src/modules/ui/components/search_box.js +++ b/packages/storybook-ui/src/modules/ui/components/search_box.js @@ -14,21 +14,23 @@ const searchBoxStyle = { ...baseFonts, }; -const formatStories = function(stories) { +const formatStories = stories => { const formattedStories = []; let i = 0; stories.forEach(val => { + i += 1; formattedStories.push({ type: 'kind', value: val.kind, - id: i++, + id: i, }); val.stories.forEach(story => { + i += 1; formattedStories.push({ type: 'story', value: story, - id: i++, + id: i, kind: val.kind, }); }); @@ -37,8 +39,8 @@ const formatStories = function(stories) { return formattedStories; }; -const suggestionTemplate = function(props, state, styles) { - return state.results.map((val, i) => { +const suggestionTemplate = (props, state, styles) => + state.results.map((val, i) => { const style = state.selectedIndex === i ? styles.selectedResultStyle : styles.resultsStyle; return (
@@ -49,7 +51,6 @@ const suggestionTemplate = function(props, state, styles) {
); }); -}; export default class SearchBox extends React.Component { constructor(props) { diff --git a/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.js b/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.js index b5aa1deac660..73bdc51ab729 100755 --- a/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.js +++ b/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.js @@ -1,3 +1,4 @@ +import { window } from 'global'; import keyEvents from '../../../libs/key_events'; export default function(actions) { diff --git a/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.test.js b/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.test.js index 168a1543c77f..74fb207ae8c8 100755 --- a/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.test.js +++ b/packages/storybook-ui/src/modules/ui/configs/handle_keyevents.test.js @@ -1,5 +1,6 @@ -import handleKeyEvents from './handle_keyevents'; +import { window } from 'global'; import keycode from 'keycode'; +import handleKeyEvents from './handle_keyevents'; describe('manager.ui.config.handle_keyevents', () => { test('should call the correct action', () => { diff --git a/packages/storybook-ui/src/modules/ui/configs/handle_routing.js b/packages/storybook-ui/src/modules/ui/configs/handle_routing.js index 9504af9cdf9f..b283a9a7e654 100755 --- a/packages/storybook-ui/src/modules/ui/configs/handle_routing.js +++ b/packages/storybook-ui/src/modules/ui/configs/handle_routing.js @@ -1,4 +1,6 @@ +import { window } from 'global'; import qs from 'qs'; + export const config = { insidePopState: false, }; diff --git a/packages/storybook-ui/src/modules/ui/configs/handle_routing.test.js b/packages/storybook-ui/src/modules/ui/configs/handle_routing.test.js index e8aa611776cc..f8493a632b7a 100755 --- a/packages/storybook-ui/src/modules/ui/configs/handle_routing.test.js +++ b/packages/storybook-ui/src/modules/ui/configs/handle_routing.test.js @@ -1,3 +1,4 @@ +import { window } from 'global'; import { changeUrl, handleInitialUrl, config } from './handle_routing'; describe('manager.ui.config.handle_routing', () => { @@ -42,7 +43,7 @@ describe('manager.ui.config.handle_routing', () => { customText: 'test', }; const originalPushState = window.history.pushState; - window.history.pushState = function(s, t, u) { + window.history.pushState = (s, t, u) => { expect(s).toEqual(pushState); expect(u).toBe(pushState.url); done(); diff --git a/packages/storybook-ui/src/modules/ui/containers/shortcuts_help.js b/packages/storybook-ui/src/modules/ui/containers/shortcuts_help.js index 10495eb79887..09c43e40619b 100755 --- a/packages/storybook-ui/src/modules/ui/containers/shortcuts_help.js +++ b/packages/storybook-ui/src/modules/ui/containers/shortcuts_help.js @@ -1,4 +1,5 @@ -import ShortcutsHelp from '../components/shortcuts_help'; +import { window } from 'global'; +import { ShortcutsHelp } from '../components/shortcuts_help'; import genPoddaLoader from '../libs/gen_podda_loader'; import compose from '../../../compose'; diff --git a/packages/storybook-ui/src/modules/ui/libs/gen_podda_loader.test.js b/packages/storybook-ui/src/modules/ui/libs/gen_podda_loader.test.js index 3d35acc2affa..c715c69265a2 100644 --- a/packages/storybook-ui/src/modules/ui/libs/gen_podda_loader.test.js +++ b/packages/storybook-ui/src/modules/ui/libs/gen_podda_loader.test.js @@ -1,5 +1,5 @@ -import genPoddaLoader from './gen_podda_loader'; import Podda from 'podda'; +import genPoddaLoader from './gen_podda_loader'; describe('manager.ui.libs.gen_podda_loader', () => { describe('mapper', () => { diff --git a/packages/storyshots/package.json b/packages/storyshots/package.json index 9739ad9e2b97..194a6735d641 100644 --- a/packages/storyshots/package.json +++ b/packages/storyshots/package.json @@ -19,12 +19,14 @@ "babel-preset-es2015": "^6.18.0", "babel-preset-react": "^6.16.0", "react": "^15.5.4", - "react-dom": "^15.5.4" + "react-dom": "^15.5.4", + "react-test-renderer": "^15.5.4" }, "dependencies": { "@kadira/storybook": "*", "@kadira/storybook-addons": "*", "@kadira/storybook-channel": "*", + "babel-core": "^6.24.1", "babel-runtime": "^6.20.0", "prop-types": "^15.5.7", "read-pkg-up": "^2.0.0" diff --git a/packages/storyshots/src/index.js b/packages/storyshots/src/index.js index e91c11601fe6..3306586b3796 100644 --- a/packages/storyshots/src/index.js +++ b/packages/storyshots/src/index.js @@ -4,6 +4,7 @@ import readPkgUp from 'read-pkg-up'; import addons from '@kadira/storybook-addons'; import runWithRequireContext from './require_context'; import createChannel from './storybook-channel-mock'; + const { describe, it, expect } = global; let storybook; @@ -24,16 +25,16 @@ export default function testStorySnapshots(options = {}) { if (isStorybook) { storybook = require.requireActual('@kadira/storybook'); - const loadBabelConfig = require('@kadira/storybook/dist/server/babel_config').default; + const loadBabelConfig = require('@kadira/storybook/dist/server/babel_config').default; // eslint-disable-line const configDirPath = path.resolve(options.configPath || '.storybook'); configPath = path.join(configDirPath, 'config.js'); + const babelConfig = loadBabelConfig(configDirPath); const content = babel.transformFileSync(configPath, babelConfig).code; const contextOpts = { filename: configPath, dirname: configDirPath, }; - const babelConfig = loadBabelConfig(configDirPath); runWithRequireContext(content, contextOpts); } else if (isRNStorybook) { @@ -54,18 +55,18 @@ export default function testStorySnapshots(options = {}) { const stories = storybook.getStorybook(); // Added not to break existing storyshots configs (can be removed in a future major release) - options.storyNameRegex = options.storyNameRegex || options.storyRegex; + options.storyNameRegex = options.storyNameRegex || options.storyRegex; // eslint-disable-line - for (const group of stories) { + for (const group of stories) { // eslint-disable-line if (options.storyKindRegex && !group.kind.match(options.storyKindRegex)) { - continue; + continue; // eslint-disable-line } describe(suit, () => { describe(group.kind, () => { - for (const story of group.stories) { + for (const story of group.stories) { // eslint-disable-line if (options.storyNameRegex && !story.name.match(options.storyNameRegex)) { - continue; + continue; // eslint-disable-line } it(story.name, () => { diff --git a/packages/storyshots/src/require_context.js b/packages/storyshots/src/require_context.js index de0b60261937..ff77a6902e89 100644 --- a/packages/storyshots/src/require_context.js +++ b/packages/storyshots/src/require_context.js @@ -11,7 +11,7 @@ function requireModules(keys, root, directory, regExp, recursive) { // TODO: Check this in windows const entryKey = `./${path.join(directory, filename)}`; if (regExp.test(entryKey)) { - keys[entryKey] = require(path.join(root, directory, filename)); + keys[entryKey] = require(path.join(root, directory, filename)); // eslint-disable-line return; } @@ -45,10 +45,10 @@ export default function runWithRequireContext(content, options) { const newRequire = request => { if (isRelativeRequest(request)) { - return require(path.resolve(dirname, request)); + return require(path.resolve(dirname, request)); // eslint-disable-line } - return require(request); + return require(request); // eslint-disable-line }; newRequire.resolve = require.resolve; diff --git a/packages/storyshots/stories/required_with_context/Button.stories.js b/packages/storyshots/stories/required_with_context/Button.stories.js index ba6a7a3d8d25..3419c791c631 100644 --- a/packages/storyshots/stories/required_with_context/Button.stories.js +++ b/packages/storyshots/stories/required_with_context/Button.stories.js @@ -1,7 +1,6 @@ import React from 'react'; -import { storiesOf, action, linkTo } from '@kadira/storybook'; +import { storiesOf, action } from '@kadira/storybook'; import Button from './Button'; -import Welcome from './Welcome'; storiesOf('Button', module) .add('with text', () => ) diff --git a/packages/storyshots/stories/required_with_context/Welcome.js b/packages/storyshots/stories/required_with_context/Welcome.js index 4e9ee8eb7317..069bf85d3c30 100644 --- a/packages/storyshots/stories/required_with_context/Welcome.js +++ b/packages/storyshots/stories/required_with_context/Welcome.js @@ -50,7 +50,9 @@ export default class Welcome extends React.Component { {' '} directory.
- A story is a single state of one or more UI components. You can have as many stories as you want. + A story is a single state of one or more UI components. + {' '} + You can have as many stories as you want.
(Basically a story is like a visual test case.)

From a37eb1140f46e67ea817fb8887a6d51346d1f05c Mon Sep 17 00:00:00 2001 From: Norbert de Langen Date: Fri, 28 Apr 2017 15:24:09 +0200 Subject: [PATCH 03/37] FIX for https://github.com/storybooks/storybook/commit/fc7e09b810678c8db2235c397a49df35dc667ef2?diff=split#commitcomment-21940155 --- packages/addon-info/src/components/PropVal.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/addon-info/src/components/PropVal.js b/packages/addon-info/src/components/PropVal.js index 5aa548c27369..fb4b0223150e 100644 --- a/packages/addon-info/src/components/PropVal.js +++ b/packages/addon-info/src/components/PropVal.js @@ -107,7 +107,7 @@ function previewProp(val) { } if (!braceWrap) return content; - return {{ content }}; + return {`{ ${content} }`}; } export default class PropVal extends React.Component { From b801d6f0a439bd10f67412ceb0eb2a194d3ef8e8 Mon Sep 17 00:00:00 2001 From: Norbert de Langen Date: Fri, 28 Apr 2017 17:25:45 +0200 Subject: [PATCH 04/37] FIX linting --- .eslintrc.js | 17 ++--- package.json | 7 ++- .../manager/components/CommentForm/index.js | 2 +- packages/addon-info/src/components/Node.js | 6 +- packages/react-storybook/src/server/config.js | 62 +++++++++---------- packages/storybook-ui/package.json | 4 +- .../modules/ui/components/shortcuts_help.js | 10 ++- .../stories/directly_required/Button.js | 3 + .../stories/required_with_context/Welcome.js | 18 +++++- scripts/prepublish.js | 1 + 10 files changed, 80 insertions(+), 50 deletions(-) diff --git a/.eslintrc.js b/.eslintrc.js index ec5543c22beb..02c4ca4ed80e 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -3,11 +3,7 @@ const warn = 1; const ignore = 0; module.exports = { - extends: [ - // './node_modules/eslint-config-airbnb-base/rules/es6.js', - 'airbnb-base', - 'plugin:jest/recommended', - ], + extends: ['airbnb', 'prettier', 'plugin:jest/recommended'], plugins: [ 'prettier', 'jest', @@ -23,7 +19,7 @@ module.exports = { 'jest/globals': true, }, rules: { - strict: [error, "never"], + strict: [error, 'never'], 'prettier/prettier': ['warn', { printWidth: 100, tabWidth: 2, @@ -35,10 +31,17 @@ module.exports = { 'class-methods-use-this': ignore, 'arrow-parens': ['warn', 'as-needed'], 'space-before-function-paren': ignore, - 'import/no-extraneous-dependencies': [error, { devDependencies: true, peerDependencies: true }], + 'import/no-extraneous-dependencies': [error, { + devDependencies: true, + peerDependencies: true + }], 'import/prefer-default-export': ignore, 'react/jsx-uses-react': error, 'react/jsx-uses-vars': error, 'react/react-in-jsx-scope': error, + 'react/jsx-filename-extension': [warn, { + extensions: ['.js', '.jsx'] + }], + 'react/no-unescaped-entities': ignore, }, } diff --git a/package.json b/package.json index af3709a56419..2a2858b9167e 100644 --- a/package.json +++ b/package.json @@ -9,13 +9,17 @@ "babel-preset-env": "^1.4.0", "babel-preset-react": "^6.11.1", "babel-preset-stage-0": "^6.5.0", + "chalk": "^1.1.3", "codecov": "^2.1.0", "enzyme": "^2.8.2", "enzyme-to-json": "^1.5.1", "eslint": "^3.19.0", + "eslint-config-airbnb": "^14.1.0", "eslint-config-airbnb-base": "^11.1.3", + "eslint-config-prettier": "^1.7.0", "eslint-plugin-import": "^2.2.0", "eslint-plugin-jest": "^19.0.1", + "eslint-plugin-jsx-a11y": "^4.0.0", "eslint-plugin-prettier": "^2.0.1", "eslint-plugin-react": "^6.10.3", "jest": "^19.0.2", @@ -25,11 +29,12 @@ "react": "^15.5.4", "react-addons-test-utils": "^15.5.1", "react-dom": "^15.5.4", + "react-test-renderer": "^15.5.4", "shelljs": "^0.7.7" }, "scripts": { "bootstrap": "lerna bootstrap", - "lint": "eslint .", + "lint": "eslint . --cache --cache-location ./.cache/eslint", "test": "jest --config ./.jestrc", "test:watch": "npm test -- --watch", "test-examples": "CI=true lerna run test", diff --git a/packages/addon-comments/src/manager/components/CommentForm/index.js b/packages/addon-comments/src/manager/components/CommentForm/index.js index c2259db8fdcb..a6ea751e3f87 100644 --- a/packages/addon-comments/src/manager/components/CommentForm/index.js +++ b/packages/addon-comments/src/manager/components/CommentForm/index.js @@ -58,7 +58,7 @@ export default class CommentForm extends Component { if (!this.props.user) { return (
-