Introduces a monorepo structure, relies on yarn workspaces to share
dependencies, and lerna for syncing versions across the monorepo.

* Create 2 workspaces:
    'packages' and 'website'
* Create 2 public packages:
    'babel-plugin-react-native-web' and 'react-native-web'
* Create 1 private package:
    'benchmarks'

A simple release script runs the tests, builds the package assets,
increments the package version numbers, git commits and tags, publishes
the package to npm, pushes the changes to github, and releases the
website update.

Close #657
This commit is contained in:
Nicolas Gallagher
2017-12-21 17:28:36 +00:00
parent 14d87f4b30
commit 3026465ae3
466 changed files with 4102 additions and 2912 deletions

8
.babelrc Normal file
View File

@@ -0,0 +1,8 @@
{
"presets": [
"react-native"
],
"plugins": [
[ "transform-react-remove-prop-types", { "mode": "wrap" } ]
]
}

View File

@@ -56,6 +56,7 @@
"no-dupe-class-members": 2,
"no-dupe-keys": 2,
"no-duplicate-case": 2,
"no-duplicate-imports": 2,
"no-empty-character-class": 2,
"no-empty-pattern": 2,
"no-eval": 2,

View File

@@ -1,13 +1,17 @@
[version]
^0.61.0
[ignore]
.*/__tests__/.*
.*/benchmarks/.*
.*/docs/.*
<PROJECT_ROOT>/.*/__tests__/.*
<PROJECT_ROOT>/packages/benchmarks/.*
<PROJECT_ROOT>/packages/.*/dist/.*
<PROJECT_ROOT>/website/.*
.*/node_modules/babel-plugin-transform-react-remove-prop-types/*
[include]
[libs]
types
<PROJECT_ROOT>/types
[options]
unsafe.enable_getters_and_setters=true

View File

@@ -25,6 +25,12 @@ yarn
## Automated tests
To run the linter:
```
yarn lint
```
To run flow:
```
@@ -40,16 +46,30 @@ yarn jest
…in watch mode:
```
yarn jest:watch
yarn jest --watch
```
To run all automated tests:
To run all these automated tests:
```
yarn test
```
## Visual tests
## Compile and build
To compile the `react-native-web` source code:
```
yarn compile
```
…in watch mode:
```
yarn compile --watch
```
## Website and visual tests
To run the interactive storybook:
@@ -57,32 +77,20 @@ To run the interactive storybook:
yarn docs:start
```
To generate a static build of the storybook:
When you're also making changes to the 'react-native-web' source files, run this command in another process:
```
yarn docs:build
yarn compile --watch
```
To run the performance benchmarks in a browser (opening `./benchmarks/index.html`):
## Benchmarks
To run the performance benchmarks in a browser (opening `./packages/benchmarks/index.html`):
```
yarn benchmark
```
## Compile and build
To compile the source code to `dist`:
```
yarn compile
```
To create a UMD bundle of the library:
```
yarn build
```
### Pre-commit
To format and lint code before commit:
@@ -95,7 +103,6 @@ To format and lint the entire project:
```
yarn fmt
yarn lint
```
### New Features

1
.gitignore vendored
View File

@@ -1,2 +1,3 @@
coverage
node_modules
dist

View File

@@ -1,8 +1,17 @@
language: node_js
node_js:
- "8"
before_script:
- export DISPLAY=:99.0
- sh -e /etc/init.d/xvfb start
before_install:
# Install Yarn
- curl -o- -L https://yarnpkg.com/install.sh | bash
- export PATH=$HOME/.yarn/bin:$PATH
cache:
yarn: true
directories:
- node_modules
script:
- yarn test

View File

@@ -27,19 +27,20 @@ Install in your existing app using `yarn` or `npm`:
```
yarn add react react-dom react-native-web
yarn add --dev babel-plugin-react-native-web
```
Add the `react-native-web/babel` plugin to your Babel configuration. This will
Add the `react-native-web` plugin to your Babel configuration. This will
alias `react-native` to `react-native-web` and exclude any modules not required
by the app.
```json
{
"plugins": [
"react-native-web/babel"
],
"presets": [
"react-native"
],
"plugins": [
"react-native-web"
]
}
```

File diff suppressed because it is too large Load Diff

10
lerna.json Normal file
View File

@@ -0,0 +1,10 @@
{
"lerna": "2.5.1",
"version": "0.2.2",
"npmClient": "yarn",
"useWorkspaces": true,
"packages": [
"packages/*",
"website"
]
}

View File

@@ -1,85 +1,28 @@
{
"name": "react-native-web",
"version": "0.2.2",
"description": "React Native for Web",
"main": "dist/index.js",
"files": [
"babel",
"dist",
"jest",
"src",
"!**/__tests__"
],
"private": true,
"name": "react-native-web-monorepo",
"scripts": {
"benchmark": "cd benchmarks && yarn && webpack && open index.html",
"build": "yarn clean-dist && yarn compile && webpack --config webpack.config.js --sort-assets-by --progress",
"clean-dist": "del ./dist && mkdir dist",
"compile": "babel src -d dist --ignore *-test.js",
"docs:build": "cd docs && yarn build",
"docs:start": "cd docs && yarn && yarn start",
"docs:release": "cd docs && yarn release",
"benchmark": "cd packages/benchmarks && yarn benchmark",
"clean": "del ./packages/*/dist",
"compile": "yarn clean && cd packages/react-native-web && babel src --optional runtime --out-dir dist --ignore \"__tests__\"",
"docs:start": "cd website && yarn start",
"docs:release": "cd website && yarn release",
"flow": "flow",
"fmt": "find babel benchmarks docs jest src -name '*.js' | grep -v -E '(node_modules|dist|vendor)' | xargs yarn fmt:cmd",
"fmt": "find packages scripts types website -name '*.js' | grep -v -E '(node_modules|dist|vendor)' | xargs yarn fmt:cmd",
"fmt:cmd": "prettier --print-width=100 --single-quote --write",
"jest": "jest",
"jest:watch": "yarn test --watch",
"lint": "yarn lint:cmd babel benchmarks docs jest src",
"lint:cmd": "eslint --ignore-path .gitignore --ignore-pattern '/src/vendor/*' --fix",
"jest": "jest --config ./scripts/jest/config.js",
"lint": "yarn lint:check --fix",
"lint:check": "yarn lint:cmd packages scripts website",
"lint:cmd": "eslint --ignore-path .gitignore --ignore-pattern 'packages/**/vendor/*'",
"precommit": "lint-staged",
"release": "yarn lint && yarn test && yarn build && npm publish",
"test": "flow && jest"
},
"babel": {
"presets": [
"react-native"
],
"plugins": [
[
"transform-react-remove-prop-types",
{
"mode": "wrap"
}
]
]
},
"jest": {
"testEnvironment": "jsdom",
"timers": "fake",
"setupFiles": [
"raf/polyfill"
],
"setupTestFrameworkScriptFile": "<rootDir>/jest-setup-framework.js",
"snapshotSerializers": [
"enzyme-to-json/serializer"
]
},
"lint-staged": {
"**/*.js": [
"fmt:cmd",
"git update-index --again",
"lint:cmd"
]
},
"dependencies": {
"array-find-index": "^1.0.2",
"babel-runtime": "^6.26.0",
"create-react-class": "^15.6.2",
"debounce": "^1.1.0",
"deep-assign": "^2.0.0",
"fbjs": "^0.8.16",
"hyphenate-style-name": "^1.0.2",
"inline-style-prefixer": "^3.0.8",
"normalize-css-color": "^1.0.2",
"prop-types": "^15.6.0",
"react-art": "^16.2.0",
"react-timer-mixin": "^0.13.3"
"release": "yarn test && yarn build && node ./scripts/release/publish.js && yarn docs:release",
"test": "yarn flow && yarn lint:check && yarn jest"
},
"devDependencies": {
"babel-cli": "^6.26.0",
"babel-core": "^6.26.0",
"babel-eslint": "^8.0.3",
"babel-loader": "^7.1.2",
"babel-plugin-tester": "^4.0.0",
"babel-plugin-transform-react-remove-prop-types": "^0.4.10",
"babel-preset-react-native": "^4.0.0",
"caniuse-api": "^2.0.0",
@@ -91,36 +34,24 @@
"eslint-config-prettier": "^2.9.0",
"eslint-plugin-promise": "^3.6.0",
"eslint-plugin-react": "^7.5.1",
"file-loader": "^1.1.5",
"flow-bin": "^0.60.1",
"flow-bin": "^0.61.0",
"jest": "^21.2.1",
"lerna": "^2.5.1",
"lint-staged": "^4.1.3",
"prettier": "^1.8.2",
"raf": "^3.4.0",
"react": "^16.2.0",
"react-dom": "^16.2.0",
"react-test-renderer": "^16.2.0",
"url-loader": "^0.6.2",
"webpack": "^3.9.1",
"webpack-bundle-analyzer": "^2.9.1"
"react-test-renderer": "^16.2.0"
},
"peerDependencies": {
"react": "16.x.x",
"react-dom": "16.x.x"
"workspaces": ["packages/*", "website"],
"lint-staged": {
"**/*.js": [
"fmt:cmd",
"git update-index --again",
"lint:cmd"
]
},
"author": "Nicolas Gallagher",
"license": "BSD-3-Clause",
"repository": {
"type": "git",
"url": "git://github.com/necolas/react-native-web.git"
},
"tags": [
"react"
],
"keywords": [
"react",
"react-component",
"react-native",
"web"
]
"license": "BSD-3-Clause"
}

View File

@@ -0,0 +1,39 @@
# babel-plugin-react-native-web
A Babel plugin that will alias `react-native` to `react-native-web` and exclude
any modules not required by your app (keeping bundle size down).
## Installation
```
yarn add --dev babel-plugin-react-native-web
```
## Usage
**.babelrc**
```
{
"plugins": ["react-native-web"]
}
```
## Example
NOTE: `react-native-web` internal paths are _not stable_ and you must not rely
on them. Always use the Babel plugin to optimize your build. What follows is an
example of the rewrite performed by the plugin.
**Before**
```js
import { StyleSheet, View } from 'react-native';
```
**After**
```js
import StyleSheet from 'react-native-web/dist/apis/StyleSheet';
import View from 'react-native-web/dist/components/View';
```

View File

@@ -0,0 +1 @@
module.exports = require('./src');

View File

@@ -0,0 +1,15 @@
{
"name": "babel-plugin-react-native-web",
"version": "0.2.2",
"description": "Babel plugin for React Native for Web",
"main": "index.js",
"devDependencies": {
"babel-plugin-tester": "^4.0.0"
},
"author": "Nicolas Gallagher",
"license": "MIT",
"repository": {
"type": "git",
"url": "git://github.com/necolas/react-native-web.git"
}
}

View File

@@ -1,10 +1,9 @@
# Performance
# benchmarks
To run these benchmarks from the root of the project:
To run these benchmarks:
```
yarn benchmark
open ./benchmarks/index.html
```
Append `?fastest` to the URL to include the fastest "other libraries", and
@@ -25,7 +24,7 @@ Typical render timings*: mean ± two standard deviations.
| Implementation | Deep tree (ms) | Wide tree (ms) | Tweets (ms) |
| :--- | ---: | ---: | ---: |
| `css-modules` | `80.47` `±25.13` | `144.87` `±32.70` | |
| `react-native-web@0.2.1` | `88.68` `±28.78` | `178.17` `±39.90` | `13.78` `±2.90ms` |
| `react-native-web@0.2.2` | `88.68` `±28.78` | `178.17` `±39.90` | `13.78` `±2.90ms` |
Other libraries

View File

@@ -1,6 +1,10 @@
{
"name": "benchmarks",
"private": true,
"name": "benchmarks",
"version": "0.2.2",
"scripts": {
"benchmark": "webpack --config ./webpack.config.js && open index.html"
},
"dependencies": {
"aphrodite": "^1.2.5",
"classnames": "^2.2.5",
@@ -8,7 +12,10 @@
"glamor": "^2.20.40",
"marky": "^1.2.0",
"radium": "^0.19.6",
"react": "^16.2.0",
"react-dom": "^16.2.0",
"react-jss": "^8.2.0",
"react-native-web": "^0.2.2",
"reactxp": "^0.46.6",
"styled-components": "^2.3.2",
"styletron-client": "^3.0.0-rc.5",
@@ -16,6 +23,8 @@
},
"devDependencies": {
"css-loader": "^0.28.7",
"style-loader": "^0.19.1"
"style-loader": "^0.19.1",
"webpack": "^3.10.0",
"webpack-bundle-analyzer": "^2.9.1"
}
}

View File

@@ -51,7 +51,7 @@ module.exports = {
],
resolve: {
alias: {
'react-native': path.join(__dirname, '../src')
'react-native': 'react-native-web'
}
}
};

View File

@@ -0,0 +1,127 @@
# React Native for Web
[![Build Status][travis-image]][travis-url]
[![npm version][npm-image]][npm-url]
"React Native for Web" brings the platform-agnostic Components and APIs of
[React Native][react-native-url] to the Web.
Browse the [interactive
documentation](https://necolas.github.io/react-native-web/storybook/) or [try
it out](https://glitch.com/edit/#!/react-native-web-playground) on Glitch.
## Features
* Interoperability with ReactDOM components.
* Native-like touch handling.
* Built-in integration with web accessibility APIs.
* Built-in support for LTR and RTL layouts.
* Built-in expressive and reliable subset of CSS.
* Optimized, vendor-prefixed CSS with [good runtime performance](benchmarks/README.md).
* Server-side rendering of HTML and critical CSS.
* Browser support: Chrome, Firefox, Safari >= 7, IE 10, Edge.
## Quick start
Install in your existing app using `yarn` or `npm`:
```
yarn add react react-dom react-native-web
yarn add --dev babel-plugin-react-native-web
```
Add the `react-native-web` plugin to your Babel configuration. This will
alias `react-native` to `react-native-web` and exclude any modules not required
by the app.
```json
{
"presets": [
"react-native"
],
"plugins": [
"react-native-web"
]
}
```
(For React/ReactDOM 15.4 15.6 support, install `react-native-web@<0.1.0`)
See the [Getting Started](docs/guides/getting-started.md) guide for more details.
## Documentation
The [interactive
documentation](https://necolas.github.io/react-native-web/storybook/) shows all
the supported APIs and Components.
Guides:
* [Getting started](docs/guides/getting-started.md)
* [Style](docs/guides/style.md)
* [Accessibility](docs/guides/accessibility.md)
* [Direct manipulation](docs/guides/direct-manipulation.md)
* [Internationalization](docs/guides/internationalization.md)
* [Advanced use](docs/guides/advanced.md)
* [Known issues](docs/guides/known-issues.md)
## Example code
```js
import React from 'react'
import { AppRegistry, Image, StyleSheet, Text, View } from 'react-native'
// Components
const Card = ({ children }) => <View style={styles.card}>{children}</View>
const Title = ({ children }) => <Text style={styles.title}>{children}</Text>
const Photo = ({ uri }) => <Image source={{ uri }} style={styles.image} />
const App = () => (
<Card>
<Title>App Card</Title>
<Photo uri="/some-photo.jpg" />
</Card>
)
// Styles
const styles = StyleSheet.create({
card: {
flexGrow: 1,
justifyContent: 'center'
},
title: {
fontSize: '1.25rem',
fontWeight: 'bold'
},
image: {
height: 40,
marginVertical: 10,
width: 40
}
})
// App registration and rendering
AppRegistry.registerComponent('MyApp', () => App)
AppRegistry.runApplication('MyApp', { rootTag: document.getElementById('react-root') })
```
## Starter kits
* [Glitch](https://glitch.com/edit/#!/react-native-web-playground)
* [create-react-app](https://github.com/facebookincubator/create-react-app)
## Related projects
* [react-primitives](https://github.com/lelandrichardson/react-primitives/)
* [react-sketchapp](https://github.com/airbnb/react-sketchapp)
* [reactxp](https://github.com/microsoft/reactxp)
* [react-native-web-player](https://github.com/dabbott/react-native-web-player)
## License
React Native for Web is [BSD licensed](LICENSE).
[npm-image]: https://badge.fury.io/js/react-native-web.svg
[npm-url]: https://yarnpkg.com/en/package/react-native-web
[react-native-url]: https://facebook.github.io/react-native/
[travis-image]: https://travis-ci.org/necolas/react-native-web.svg?branch=master
[travis-url]: https://travis-ci.org/necolas/react-native-web

View File

@@ -0,0 +1,45 @@
{
"name": "react-native-web",
"version": "0.2.2",
"description": "React Native for Web",
"main": "dist/index.js",
"files": [
"dist",
"jest",
"src",
"!**/__tests__"
],
"dependencies": {
"array-find-index": "^1.0.2",
"babel-runtime": "^6.26.0",
"create-react-class": "^15.6.2",
"debounce": "^1.1.0",
"deep-assign": "^2.0.0",
"fbjs": "^0.8.16",
"hyphenate-style-name": "^1.0.2",
"inline-style-prefixer": "^3.0.8",
"normalize-css-color": "^1.0.2",
"prop-types": "^15.6.0",
"react-art": "^16.2.0",
"react-timer-mixin": "^0.13.3"
},
"peerDependencies": {
"react": "16.x.x",
"react-dom": "16.x.x"
},
"author": "Nicolas Gallagher",
"license": "BSD-3-Clause",
"repository": {
"type": "git",
"url": "git://github.com/necolas/react-native-web.git"
},
"tags": [
"react"
],
"keywords": [
"react",
"react-component",
"react-native",
"web"
]
}

Some files were not shown because too many files have changed in this diff Show More