diff --git a/package.json b/package.json index f9c75c60d1..91f463c176 100644 --- a/package.json +++ b/package.json @@ -24,7 +24,7 @@ "build-storybook": "build-storybook -o docs", "precommit": "pretty-quick --staged && yarn run test", "build": - "rm -rf dist && rollup -c rollup.config.js && cp package.json dist/package.json", + "rm -rf dist && rollup -c rollup.config.js && node ./scripts/flow-copy-src.js && cp package.json dist/package.json", "unit-test": "yarn jest --coverage", "e2e": "node ./e2e/e2e.js", "build-e2e": "rollup -c rollup.config_e2e.js", @@ -68,6 +68,7 @@ "eslint-plugin-prettier": "^2.6.1", "eslint-plugin-react": "^7.10.0", "flow-bin": "^0.75.0", + "flow-copy-source": "^2.0.2", "geckodriver": "^1.11.0", "husky": "^0.14.3", "jest": "^23.3.0", diff --git a/rollup.config.js b/rollup.config.js index e4e041b001..22557fa332 100644 --- a/rollup.config.js +++ b/rollup.config.js @@ -9,6 +9,8 @@ import commonjs from 'rollup-plugin-commonjs'; import fs from 'fs'; import path from 'path'; +import flowEntry from './scripts/rollup-plugin-flow-entry'; + function getComponents() { return fs.readdirSync('./src/components').filter(filename => { const {ext, name} = path.parse(filename); @@ -70,6 +72,7 @@ function getSharedConfig({filePath, name}) { }), visualizer(), filesize(), + flowEntry(), ], }; } diff --git a/scripts/flow-copy-src.js b/scripts/flow-copy-src.js new file mode 100644 index 0000000000..dc17bed966 --- /dev/null +++ b/scripts/flow-copy-src.js @@ -0,0 +1,19 @@ +// @flow +const flowCopySource = require('flow-copy-source'); + +async function run() { + await flowCopySource([`${__dirname}/../src`], `${__dirname}/../dist/src`, { + ignore: [ + '**/*.test.js', + '**/*.setup.js', + '**/*stories.js', + 'test/**/*.js', + '**/__mocks__/*.js', + '**/e2e.js', + 'coverage/**/*.js', + '**/*examples.js', + ], + }); +} + +run(); diff --git a/scripts/rollup-plugin-flow-entry.js b/scripts/rollup-plugin-flow-entry.js new file mode 100644 index 0000000000..47baa13ce6 --- /dev/null +++ b/scripts/rollup-plugin-flow-entry.js @@ -0,0 +1,87 @@ +// @flow +import fs from 'fs'; +import path from 'path'; + +/* +We can consider this as well: +https://github.com/RichieAHB/rollup-plugin-flow-defs/blob/master/src/index.js +This code is inspired by that npm package anyway. + +The reason why we don't use that is because: +* Package depends on `mkdirp`. It's just one dependency, but it's an extra dep for such a simple thing to do. +* We cannot override the output path for the flow entry file content + +Hence, it's easier to write our own so we can do full modifications as needed. + */ + +function getFlowFileContent(filePath) { + /* + Since we're running this during rollup process, it will be relative to the main `src` directory. + We do not want that. + We want to make it point to the `src` directory that will be created with our scripts later in the build process + from `flow-copy-src.js`. + + Hence, instead of `../src` and `../../src`, they will become `./src` and `../src` respectively. + */ + + // Find `../` pattern in the `filePath` + const regex = new RegExp(/\.\.\//, 'g'); + // We want to know how many `../` is inside the file path + const matched = filePath.match(regex); + if (matched && matched.length > 0) { + // Check whether it's only one `../` + if (matched.length === 1) { + // Only 1, replace it with `./` + filePath = filePath.replace('../', './'); + } else { + // Must be more than 1, then just remove one `../` + filePath = filePath.replace('../', ''); + } + } + // Remove the `.js` extension, if any, so that it could point to `.js.flow` automatically + filePath = filePath.replace('.js', ''); + return `// @flow +export * from '${filePath}';`; +} + +export default function flowEntry() { + let input; + return { + name: 'rollup-plugin-flow-entry', + // $FlowFixMe can't have annotations here since it's for rollup + options(opts) { + input = opts.input; + }, + // $FlowFixMe can't have annotations here since it's for rollup + async generateBundle(opts) { + const {file = ''} = opts || {}; + + // Create file path if does not exist + await new Promise(resolve => { + const dirname = path.dirname(file); + if (!fs.existsSync(dirname)) { + fs.mkdirSync(dirname); + } + resolve('ok'); + }); + + await new Promise((resolve, reject) => { + /* + path.dirname(input); // src/components/popover + path.basename(input); // index.js + path.dirname(file); // this is output, `dist/popover` + */ + const relativePath = path.join( + path.relative(path.dirname(file), path.dirname(input)), + path.basename(input), + ); + fs.writeFile(`${file}.flow`, getFlowFileContent(relativePath), err => { + if (err) { + reject(err); + } + resolve('ok'); + }); + }); + }, + }; +} diff --git a/src/components/checkbox/index.js b/src/components/checkbox/index.js index e240b743f4..071506732d 100644 --- a/src/components/checkbox/index.js +++ b/src/components/checkbox/index.js @@ -10,3 +10,6 @@ export { Label as StyledLabel, Input as StyledInput, } from './styled-components'; + +// Flow +export * from './types'; diff --git a/src/components/input/index.js b/src/components/input/index.js index 8f593e8b67..a1b439d794 100644 --- a/src/components/input/index.js +++ b/src/components/input/index.js @@ -13,3 +13,6 @@ export { Caption as StyledCaption, } from './styled-components'; export {STATE_CHANGE_TYPE, ADJOINED, SIZE} from './constants'; + +// Flow +export * from './types'; diff --git a/src/components/popover/index.js b/src/components/popover/index.js index f32311034a..ca53bd5b56 100644 --- a/src/components/popover/index.js +++ b/src/components/popover/index.js @@ -16,3 +16,6 @@ export { Inner as StyledInner, Padding as StyledPadding, } from './styled-components'; + +// Flow +export * from './types'; diff --git a/src/components/tooltip/index.js b/src/components/tooltip/index.js index a9234188e1..f4a56fe888 100644 --- a/src/components/tooltip/index.js +++ b/src/components/tooltip/index.js @@ -15,3 +15,6 @@ export { Body as StyledBody, Inner as StyledInner, } from './styled-components'; + +// Flow +export * from './types'; diff --git a/yarn.lock b/yarn.lock index e0d1c2c94f..56a4bd72aa 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2319,7 +2319,7 @@ chokidar@^1.6.1: optionalDependencies: fsevents "^1.0.0" -chokidar@^2.0.2: +chokidar@^2.0.0, chokidar@^2.0.2: version "2.0.4" resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-2.0.4.tgz#356ff4e2b0e8e43e322d18a372460bbcf3accd26" dependencies: @@ -2934,6 +2934,12 @@ decamelize@^1.0.0, decamelize@^1.1.0, decamelize@^1.1.1, decamelize@^1.1.2: version "1.2.0" resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290" +decamelize@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-2.0.0.tgz#656d7bbc8094c4c788ea53c5840908c9c7d063c7" + dependencies: + xregexp "4.0.0" + decode-uri-component@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/decode-uri-component/-/decode-uri-component-0.2.0.tgz#eb3913333458775cb84cd1a1fae062106bb87545" @@ -4053,6 +4059,12 @@ find-up@^2.0.0, find-up@^2.1.0: dependencies: locate-path "^2.0.0" +find-up@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-3.0.0.tgz#49169f1d7993430646da61ecc5ae355c21c97b73" + dependencies: + locate-path "^3.0.0" + flat-cache@^1.2.1: version "1.3.0" resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-1.3.0.tgz#d3030b32b38154f4e3b7e9c709f490f7ef97c481" @@ -4070,6 +4082,16 @@ flow-bin@^0.75.0: version "0.75.0" resolved "https://registry.yarnpkg.com/flow-bin/-/flow-bin-0.75.0.tgz#b96d1ee99d3b446a3226be66b4013224ce9df260" +flow-copy-source@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/flow-copy-source/-/flow-copy-source-2.0.2.tgz#096e579a9bb63a38afc5d4dd68ac847a5be27594" + dependencies: + chokidar "^2.0.0" + fs-extra "^7.0.0" + glob "^7.0.0" + kefir "^3.7.3" + yargs "^12.0.1" + flush-write-stream@^1.0.0: version "1.0.3" resolved "https://registry.yarnpkg.com/flush-write-stream/-/flush-write-stream-1.0.3.tgz#c5d586ef38af6097650b49bc41b55fabb19f35bd" @@ -4128,6 +4150,14 @@ fs-constants@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad" +fs-extra@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.0.tgz#8cc3f47ce07ef7b3593a11b9fb245f7e34c041d6" + dependencies: + graceful-fs "^4.1.2" + jsonfile "^4.0.0" + universalify "^0.1.0" + fs-minipass@^1.2.5: version "1.2.5" resolved "https://registry.yarnpkg.com/fs-minipass/-/fs-minipass-1.2.5.tgz#06c277218454ec288df77ada54a03b8702aacb9d" @@ -4377,7 +4407,7 @@ got@5.6.0: unzip-response "^1.0.0" url-parse-lax "^1.0.0" -graceful-fs@^4.1.11, graceful-fs@^4.1.2, graceful-fs@^4.1.3, graceful-fs@^4.1.4: +graceful-fs@^4.1.11, graceful-fs@^4.1.2, graceful-fs@^4.1.3, graceful-fs@^4.1.4, graceful-fs@^4.1.6: version "4.1.11" resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.1.11.tgz#0e8bdfe4d1ddb8854d64e04ea7c00e2a026e5658" @@ -5671,6 +5701,12 @@ json5@^0.5.0, json5@^0.5.1: version "0.5.1" resolved "https://registry.yarnpkg.com/json5/-/json5-0.5.1.tgz#1eade7acc012034ad84e2396767ead9fa5495821" +jsonfile@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb" + optionalDependencies: + graceful-fs "^4.1.6" + jsonify@~0.0.0: version "0.0.0" resolved "https://registry.yarnpkg.com/jsonify/-/jsonify-0.0.0.tgz#2c74b6ee41d93ca51b7b5aaee8f503631d252a73" @@ -5704,6 +5740,12 @@ jszip@^3.1.3: pako "~1.0.2" readable-stream "~2.0.6" +kefir@^3.7.3: + version "3.8.3" + resolved "https://registry.yarnpkg.com/kefir/-/kefir-3.8.3.tgz#8e0ab10084ed8a01cbb5d4f7f18a0b859f7b9bd9" + dependencies: + symbol-observable "1.0.4" + kew@^0.7.0: version "0.7.0" resolved "https://registry.yarnpkg.com/kew/-/kew-0.7.0.tgz#79d93d2d33363d6fdd2970b335d9141ad591d79b" @@ -5823,6 +5865,13 @@ locate-path@^2.0.0: p-locate "^2.0.0" path-exists "^3.0.0" +locate-path@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-3.0.0.tgz#dbec3b3ab759758071b58fe59fc41871af21400e" + dependencies: + p-locate "^3.0.0" + path-exists "^3.0.0" + lodash-es@^4.2.1: version "4.17.10" resolved "https://registry.yarnpkg.com/lodash-es/-/lodash-es-4.17.10.tgz#62cd7104cdf5dd87f235a837f0ede0e8e5117e05" @@ -6752,12 +6801,24 @@ p-limit@^1.1.0: dependencies: p-try "^1.0.0" +p-limit@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-2.0.0.tgz#e624ed54ee8c460a778b3c9f3670496ff8a57aec" + dependencies: + p-try "^2.0.0" + p-locate@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" dependencies: p-limit "^1.1.0" +p-locate@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-3.0.0.tgz#322d69a05c0264b25997d9f40cd8a891ab0064a4" + dependencies: + p-limit "^2.0.0" + p-map@^1.1.1: version "1.2.0" resolved "https://registry.yarnpkg.com/p-map/-/p-map-1.2.0.tgz#e4e94f311eabbc8633a1e79908165fca26241b6b" @@ -6766,6 +6827,10 @@ p-try@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3" +p-try@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-2.0.0.tgz#85080bb87c64688fa47996fe8f7dfbe8211760b1" + pako@~1.0.2, pako@~1.0.5: version "1.0.6" resolved "https://registry.yarnpkg.com/pako/-/pako-1.0.6.tgz#0101211baa70c4bca4a0f63f2206e97b7dfaf258" @@ -8861,6 +8926,10 @@ symbol-observable@1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/symbol-observable/-/symbol-observable-1.0.1.tgz#8340fc4702c3122df5d22288f88283f513d3fdd4" +symbol-observable@1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/symbol-observable/-/symbol-observable-1.0.4.tgz#29bf615d4aa7121bdd898b22d4b3f9bc4e2aa03d" + symbol-observable@^1.0.3: version "1.2.0" resolved "https://registry.yarnpkg.com/symbol-observable/-/symbol-observable-1.2.0.tgz#c22688aed4eab3cdc2dfeacbb561660560a00804" @@ -9207,6 +9276,10 @@ unique-slug@^2.0.0: dependencies: imurmurhash "^0.1.4" +universalify@^0.1.0: + version "0.1.2" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66" + unpipe@1.0.0, unpipe@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" @@ -9589,6 +9662,10 @@ xmlbuilder@~9.0.1: version "9.0.7" resolved "https://registry.yarnpkg.com/xmlbuilder/-/xmlbuilder-9.0.7.tgz#132ee63d2ec5565c557e20f4c22df9aca686b10d" +xregexp@4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/xregexp/-/xregexp-4.0.0.tgz#e698189de49dd2a18cc5687b05e17c8e43943020" + xtend@^4.0.0, xtend@~4.0.1: version "4.0.1" resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.1.tgz#a5c6d532be656e23db820efb943a1f04998d63af" @@ -9597,7 +9674,7 @@ y18n@^3.2.1: version "3.2.1" resolved "https://registry.yarnpkg.com/y18n/-/y18n-3.2.1.tgz#6d15fba884c08679c0d77e88e7759e811e07fa41" -y18n@^4.0.0: +"y18n@^3.2.1 || ^4.0.0", y18n@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/y18n/-/y18n-4.0.0.tgz#95ef94f85ecc81d007c264e190a120f0a3c8566b" @@ -9609,6 +9686,12 @@ yallist@^3.0.0, yallist@^3.0.2: version "3.0.2" resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.0.2.tgz#8452b4bb7e83c7c188d8041c1a837c773d6d8bb9" +yargs-parser@^10.1.0: + version "10.1.0" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-10.1.0.tgz#7202265b89f7e9e9f2e5765e0fe735a905edbaa8" + dependencies: + camelcase "^4.1.0" + yargs-parser@^7.0.0: version "7.0.0" resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-7.0.0.tgz#8d0ac42f16ea55debd332caf4c4038b3e3f5dfd9" @@ -9638,6 +9721,23 @@ yargs@^11.0.0: y18n "^3.2.1" yargs-parser "^9.0.2" +yargs@^12.0.1: + version "12.0.1" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-12.0.1.tgz#6432e56123bb4e7c3562115401e98374060261c2" + dependencies: + cliui "^4.0.0" + decamelize "^2.0.0" + find-up "^3.0.0" + get-caller-file "^1.0.1" + os-locale "^2.0.0" + require-directory "^2.1.1" + require-main-filename "^1.0.1" + set-blocking "^2.0.0" + string-width "^2.0.0" + which-module "^2.0.0" + y18n "^3.2.1 || ^4.0.0" + yargs-parser "^10.1.0" + yargs@^8.0.2: version "8.0.2" resolved "https://registry.yarnpkg.com/yargs/-/yargs-8.0.2.tgz#6299a9055b1cefc969ff7e79c1d918dceb22c360"