Skip to content

Commit

Permalink
Create react-docgen playground website (#322)
Browse files Browse the repository at this point in the history
* Create react-docgen playground website

* Fix name of browserlist file

* Remove logfile
  • Loading branch information
danez committed Feb 7, 2019
1 parent dde83eb commit 628041e
Show file tree
Hide file tree
Showing 14 changed files with 6,807 additions and 12 deletions.
4 changes: 3 additions & 1 deletion .eslintignore
@@ -1,3 +1,5 @@
src/__tests__/fixtures/
dist/
flow-typed/
flow-typed/
website/node_modules
website/dist/
27 changes: 16 additions & 11 deletions .eslintrc.js
@@ -1,12 +1,7 @@
module.exports = {
parser: 'babel-eslint',
extends: [
'eslint:recommended',
'prettier'
],
plugins:[
'prettier'
],
extends: ['eslint:recommended', 'prettier'],
plugins: ['prettier'],
rules: {
strict: ['error', 'never'],
'no-shadow': 'error',
Expand All @@ -16,11 +11,21 @@ module.exports = {
},
env: {
node: true,
es6: true
es6: true,
},
globals: {
ASTNode: true,
NodePath: true,
Recast: true
}
}
Recast: true,
},
overrides: [
{
files: 'website/**/*.js',
env: { browser: true },
rules: {
// conflicts with jsx
'no-unused-vars': 'off',
},
},
],
};
2 changes: 2 additions & 0 deletions .gitignore
Expand Up @@ -2,3 +2,5 @@
node_modules/
.idea/
coverage/
/website/dist
yarn-error.log
10 changes: 10 additions & 0 deletions .travis.yml
Expand Up @@ -11,3 +11,13 @@ cache:
- ".eslintcache"
- "node_modules"
script: yarn test:ci

after_success: yarn build:website
deploy:
provider: pages
skip_cleanup: true
github_token: $GITHUB_DEPLOY_TOKEN
local_dir: website/dist
on:
branch: master
node: "10"
2 changes: 2 additions & 0 deletions package.json
Expand Up @@ -21,10 +21,12 @@
"main": "dist/main.js",
"scripts": {
"build": "rimraf dist/ && babel src/ --out-dir dist/ --ignore **/__tests__,**/__mocks__,**/src/types.js",
"build:website":"cd website/ && yarn && yarn build",
"lint": "eslint . --report-unused-disable-directives",
"fix": "eslint . --fix --report-unused-disable-directives",
"prepublish": "yarn build",
"preversion": "yarn lint",
"start": "cd website && yarn && yarn start",
"test": "jest",
"test:ci": "yarn lint && yarn flow && yarn test --runInBand",
"watch": "yarn build --watch"
Expand Down
7 changes: 7 additions & 0 deletions website/.browserslistrc
@@ -0,0 +1,7 @@
# Browsers that we support
last 2 Chrome versions
last 2 Firefox versions
last 2 Edge versions
last 2 Safari versions
last 2 Opera versions
Firefox ESR
4 changes: 4 additions & 0 deletions website/babel.config.js
@@ -0,0 +1,4 @@
module.exports = {
presets: ['@babel/preset-env', '@babel/preset-react', '@babel/preset-flow'],
plugins: ['@babel/plugin-proposal-class-properties'],
};
37 changes: 37 additions & 0 deletions website/package.json
@@ -0,0 +1,37 @@
{
"name": "react-docgen-website",
"private": true,
"description": "Website of react-docgen",
"repository": {
"type": "git",
"url": "https://github.com/reactjs/react-docgen.git"
},
"bugs": "https://github.com/reactjs/react-docgen/issues",
"scripts": {
"build": "NODE_ENV=production webpack",
"start": "webpack-dev-server --open"
},
"dependencies": {},
"devDependencies": {
"@babel/core": "^7.2.2",
"@babel/plugin-proposal-class-properties": "^7.3.0",
"@babel/preset-env": "^7.3.1",
"@babel/preset-flow": "^7.0.0",
"@babel/preset-react": "^7.0.0",
"babel-loader": "^8.0.5",
"codemirror": "^5.43.0",
"css-loader": "^2.1.0",
"html-loader": "^0.5.5",
"html-webpack-plugin": "^3.2.0",
"less": "^3.9.0",
"less-loader": "^4.1.0",
"mini-css-extract-plugin": "^0.5.0",
"optimize-css-assets-webpack-plugin": "^5.0.1",
"react": "^16.7.0",
"react-dom": "^16.7.0",
"terser-webpack-plugin": "^1.2.1",
"webpack": "^4.29.0",
"webpack-cli": "^3.2.1",
"webpack-dev-server": "^3.1.14"
}
}
90 changes: 90 additions & 0 deletions website/src/CodeMirrorPanel.js
@@ -0,0 +1,90 @@
import React from 'react';
import CodeMirror from 'codemirror';
import 'codemirror/mode/javascript/javascript';
import 'codemirror/mode/jsx/jsx';

import 'codemirror/addon/fold/foldgutter';
import 'codemirror/addon/fold/brace-fold';
import 'codemirror/addon/fold/comment-fold';
import 'codemirror/addon/fold/xml-fold';
import 'codemirror/addon/fold/foldgutter.css';

export default class CodeMirrorPanel extends React.Component {
static defaultProps = {
lineNumbers: true,
tabSize: 2,
showCursorWhenSelecting: true,
autoCloseBrackets: true,
matchBrackets: true,
//keyMap: 'sublime',
};
constructor() {
super();
this._textareaRef = React.createRef();
this._codeMirror = null;
this._cached = '';
this.handleChange = this.handleChange.bind(this);
this.handleFocus = this.handleFocus.bind(this);
}

componentDidMount() {
const options = Object.assign(
{
foldGutter: true,
gutters: ['CodeMirror-linenumbers', 'CodeMirror-foldgutter'],
},
this.props,
);
delete options.value;
delete options.onChange;
delete options.codeSample;

this._codeMirror = CodeMirror.fromTextArea(
this._textareaRef.current,
options,
);
this._codeMirror.on('change', this.handleChange);
this._codeMirror.on('focus', this.handleFocus);

this.updateValue(this.props.value || '');
}

componentWillUnmount() {
this._codeMirror && this._codeMirror.toTextArea();
}

componentDidUpdate(prevProps) {
if (this.props.value !== this._cached && this.props.value != null) {
this.updateValue(this.props.value);
}
if (this.props.mode !== prevProps.mode && this.props.mode != null) {
this._codeMirror.setOption('mode', this.props.mode);
}
}

updateValue(value) {
this._cached = value;
this._codeMirror.setValue(value);
}

handleFocus(/* codeMirror, event */) {
if (this._codeMirror.getValue() === this.props.codeSample) {
this._codeMirror.execCommand('selectAll');
}
}

handleChange(doc, change) {
if (change.origin !== 'setValue') {
this._cached = doc.getValue();
this.props.onChange(this._cached);
}
}

render() {
return (
<div className="editor">
<textarea ref={this._textareaRef} />
</div>
);
}
}
45 changes: 45 additions & 0 deletions website/src/index.html
@@ -0,0 +1,45 @@
<!DOCTYPE html>
<head>
<meta charset="utf-8" />
<title>react-docgen Playground</title>
<meta
name="viewport"
content="initial-scale=1.0,user-scalable=no,maximum-scale=1,width=device-width"
/>
<meta name="keywords" content="react,reactjs,react-docgen,playground" />
<meta
name="description"
content="A CLI and toolbox to extract information from React component files for documentation generation purposes."
/>
<meta property="og:locale" content="en-us" />
<meta property="og:title" content="react-docgen" />
<meta
property="og:description"
content="A CLI and toolbox to extract information from React component files for documentation generation purposes."
/>
<meta property="og:url" content="http://reactcommunity.org/react-docgen" />
<meta property="og:site_name" content="react-docgen" />
<meta property="og:type" content="article" />
</head>
<body>
<header class="page-header">
<h1 class="page-title">react-docgen: <span class="subtitle">PLAYGROUND</span></h1>
<a class="nav-link" href="https://github.com/reactjs/react-docgen">
<span class="view-github">View on Github</span>
<svg
version="1.1"
width="16"
height="16"
viewBox="0 0 16 16"
class="octicon octicon-mark-github"
aria-hidden="true"
>
<path
fill-rule="evenodd"
d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0 0 16 8c0-4.42-3.58-8-8-8z"
></path>
</svg>
</div>
</header>
<div id="root"></div>
</body>
94 changes: 94 additions & 0 deletions website/src/index.js
@@ -0,0 +1,94 @@
import React from 'react';
import ReactDOM from 'react-dom';
import Panel from './CodeMirrorPanel';
import { parse } from 'react-docgen';

import 'codemirror/lib/codemirror.css';
import './react-docgen.less';

const codeSample = `import React, { Component } from 'react';
import PropTypes from 'prop-types';
/**
* General component description.
*/
class MyComponent extends Component {
render() {
// ...
}
}
MyComponent.propTypes = {
/**
* Description of prop "foo".
*/
foo: PropTypes.number.isRequired,
/**
* Description of prop "bar" (a custom validation function).
*/
bar: function(props, propName, componentName) {
// ...
},
baz: PropTypes.oneOfType([
PropTypes.number,
PropTypes.string
]),
};
MyComponent.defaultProps = {
foo: 42,
bar: 21
};
export default MyComponent;
`;

class App extends React.Component {
constructor() {
super();
this._jsonRef = React.createRef();
this.state = {
value: this.compile(codeSample),
mode: 'application/json',
content: codeSample,
};
}

compile(value) {
return JSON.stringify(parse(value), null, 2);
}

handleChange = value => {
let result;
let mode = 'text/plain';

try {
result = this.compile(value);
mode = 'application/json';
} catch (err) {
result = String(err);
}
this.setState({ value: result, mode, content: value });
};

render() {
return (
<>
<Panel
value={this.state.content}
mode="text/jsx"
codeSample={codeSample}
onChange={this.compile}
/>
<Panel
readOnly={true}
ref={this._jsonRef}
value={this.state.value}
mode={this.state.mode}
/>
</>
);
}
}

ReactDOM.render(<App />, document.getElementById('root'));

0 comments on commit 628041e

Please sign in to comment.