# x0
Document & develop React components without breaking a sweat
[![Build Status][build-badge]][build]
```sh
npm install -g @compositor/x0
```
[build-badge]: https://img.shields.io/travis/c8r/x0/master.svg?style=flat-square
[build]: https://travis-ci.org/c8r/x0
## Features
- Zero-config
- No plugins
- Components over configuration
- Use markdown, MDX, or React components
- Automatic file system based routing
- Completely customizable
- Export static sites
- Works as an isolated development environment
Read more about x0 in our [blog post](https://compositor.io/blog/x0-making-react-component-development-stupid-simple/).
## Isolated development environment
```sh
x0 components
```
Options:
```
-o --open Open dev server in default browser
-p --port Custom port for dev server
-t --template Path to custom HTML template
--webpack Path to custom webpack configuration
```
```sh
x0 components -op 8080
```
## Static Build
Export static HTML and client-side bundle
```sh
x0 build components
```
Export static HTML without bundle
```sh
x0 build components --static
```
Options
```
-d --out-dir Output directory (default dist)
-s --static Output static HTML without JS bundle
-t --template Path to custom HTML template
--webpack Path to custom webpack configuration
```
## Fetching Data
Use the async `getInitialProps` static method to fetch data for static rendering.
This method was inspired by [Next.js][nextjs].
```jsx
const Index = props => (
Hello {props.data}
)
Index.getInitialProps = async () => {
const fetch = require('isomorphic-fetch')
const res = await fetch('http://example.com/data')
const data = await res.json()
return { data }
}
```
## Custom App
A custom `App` component can be provided by including an `_app.js` file.
The `App` component uses the [render props][render-props] pattern to provide additional state and props to its child routes.
[render-props]: https://reactjs.org/docs/render-props.html
```jsx
// example _app.js
import React from 'react'
export default class extends React.Component {
state = {
count: 0
}
update = fn => this.setState(fn)
render () {
const { render, routes } = this.props
return render({
...this.state,
decrement: () => this.update(s => ({ count: s.count - 1 })),
increment: () => this.update(s => ({ count: s.count + 1 }))
})
}
}
```
### Layouts
The `App` component can also be used to provide a common layout for all routes.
```jsx
// example _app.js
import React from 'react'
import Nav from '../components/Nav'
import Header from '../components/Header'
import Footer from '../components/Footer'
export default class extends React.Component {
render () {
const {
render,
routes
} = this.props
const route = routes.find(route => route.path === props.location.pathname)
return (
{render()}
)
}
}
```
## CSS-in-JS
x0 supports server-side rendering for [styled-components][sc] and [emotion][emotion] with zero configuration.
### Styled Components
To enable CSS rendering for static export, ensure that `styled-components` is installed as a dependency in your `package.json`
```json
"dependencies": {
"styled-components": "^3.2.6"
}
```
### Emotion
Ensure `emotion` is installed as a dependency in your `package.json`
```json
"dependencies": {
"emotion": "^9.1.3"
}
```
## Configuration
Default options can be set in the `x0` field in `package.json`.
```json
"x0": {
"static": true,
"outDir": "site",
"title": "Hello",
}
```
## Head content
Head elements such as ``, ``, and `