diff --git a/package.json b/package.json index bd22d155..21c36f8d 100644 --- a/package.json +++ b/package.json @@ -24,6 +24,7 @@ "@fortawesome/react-fontawesome": "0.0.19", "axios": "^0.18.0", "bootstrap": "^4.1.1", + "bottlejs": "^1.7.1", "chart.js": "^2.7.2", "classnames": "^2.2.6", "csvjson": "^5.1.0", diff --git a/src/App.js b/src/App.js index f7203923..dce4f6e5 100644 --- a/src/App.js +++ b/src/App.js @@ -1,23 +1,21 @@ import React from 'react'; import { Route, Switch } from 'react-router-dom'; import './App.scss'; -import Home from './common/Home'; -import MainHeader from './common/MainHeader'; import MenuLayout from './common/MenuLayout'; import CreateServer from './servers/CreateServer'; -export default function App() { - return ( -
- +const App = (MainHeader, Home) => () => ( +
+ -
- - - - - -
+
+ + + + +
- ); -} +
+); + +export default App; diff --git a/src/common/Home.js b/src/common/Home.js index a3293d49..7acf4959 100644 --- a/src/common/Home.js +++ b/src/common/Home.js @@ -1,15 +1,13 @@ import chevronIcon from '@fortawesome/fontawesome-free-solid/faChevronRight'; import FontAwesomeIcon from '@fortawesome/react-fontawesome'; -import { isEmpty, pick, values } from 'ramda'; +import { isEmpty, values } from 'ramda'; import React from 'react'; -import { connect } from 'react-redux'; import { Link } from 'react-router-dom'; import { ListGroup, ListGroupItem } from 'reactstrap'; import PropTypes from 'prop-types'; -import { resetSelectedServer } from '../servers/reducers/selectedServer'; import './Home.scss'; -export class HomeComponent extends React.Component { +export default class Home extends React.Component { static propTypes = { resetSelectedServer: PropTypes.func, servers: PropTypes.object, @@ -50,7 +48,3 @@ export class HomeComponent extends React.Component { ); } } - -const Home = connect(pick([ 'servers' ]), { resetSelectedServer })(HomeComponent); - -export default Home; diff --git a/src/common/MainHeader.js b/src/common/MainHeader.js index 76836714..aa95cb06 100644 --- a/src/common/MainHeader.js +++ b/src/common/MainHeader.js @@ -2,7 +2,7 @@ import plusIcon from '@fortawesome/fontawesome-free-solid/faPlus'; import arrowIcon from '@fortawesome/fontawesome-free-solid/faChevronDown'; import FontAwesomeIcon from '@fortawesome/react-fontawesome'; import React from 'react'; -import { Link, withRouter } from 'react-router-dom'; +import { Link } from 'react-router-dom'; import { Collapse, Nav, Navbar, NavbarBrand, NavbarToggler, NavItem, NavLink } from 'reactstrap'; import classnames from 'classnames'; import PropTypes from 'prop-types'; @@ -10,7 +10,7 @@ import ServersDropdown from '../servers/ServersDropdown'; import './MainHeader.scss'; import shlinkLogo from './shlink-logo-white.png'; -export class MainHeaderComponent extends React.Component { +const MainHeader = () => class MainHeaderComponent extends React.Component { static propTypes = { location: PropTypes.object, }; @@ -62,8 +62,6 @@ export class MainHeaderComponent extends React.Component { ); } -} - -const MainHeader = withRouter(MainHeaderComponent); +}; export default MainHeader; diff --git a/src/common/ScrollToTop.js b/src/common/ScrollToTop.js index 789f1a33..c8624da0 100644 --- a/src/common/ScrollToTop.js +++ b/src/common/ScrollToTop.js @@ -1,8 +1,7 @@ import React from 'react'; -import { withRouter } from 'react-router-dom'; import PropTypes from 'prop-types'; -export class ScrollToTopComponent extends React.Component { +export default class ScrollToTop extends React.Component { static propTypes = { location: PropTypes.object, window: PropTypes.shape({ @@ -11,7 +10,7 @@ export class ScrollToTopComponent extends React.Component { children: PropTypes.node, }; static defaultProps = { - window, + window: global.window, }; componentDidUpdate(prevProps) { @@ -26,7 +25,3 @@ export class ScrollToTopComponent extends React.Component { return this.props.children; } } - -const ScrollToTop = withRouter(ScrollToTopComponent); - -export default ScrollToTop; diff --git a/src/container/index.js b/src/container/index.js new file mode 100644 index 00000000..2009c749 --- /dev/null +++ b/src/container/index.js @@ -0,0 +1,20 @@ +import Bottle from 'bottlejs'; +import { withRouter } from 'react-router-dom'; +import { connect } from 'react-redux'; +import { pick } from 'ramda'; +import App from '../App'; +import ScrollToTop from '../common/ScrollToTop'; +import MainHeader from '../common/MainHeader'; +import { resetSelectedServer } from '../servers/reducers/selectedServer'; +import Home from '../common/Home'; +import store from './store'; + +const bottle = new Bottle(); + +bottle.constant('store', store); +bottle.serviceFactory('App', App, 'MainHeader', 'Home'); +bottle.serviceFactory('MainHeader', () => withRouter(MainHeader())); +bottle.serviceFactory('ScrollToTop', () => withRouter(ScrollToTop)); +bottle.serviceFactory('Home', () => connect(pick([ 'servers' ]), { resetSelectedServer })(Home)); + +export default bottle.container; diff --git a/src/container/store.js b/src/container/store.js new file mode 100644 index 00000000..0d5b2b2d --- /dev/null +++ b/src/container/store.js @@ -0,0 +1,13 @@ +import ReduxThunk from 'redux-thunk'; +import { applyMiddleware, compose, createStore } from 'redux'; +import reducers from '../reducers'; + +const composeEnhancers = process.env.NODE_ENV !== 'production' && window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ + ? window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ + : compose; + +const store = createStore(reducers, composeEnhancers( + applyMiddleware(ReduxThunk) +)); + +export default store; diff --git a/src/index.js b/src/index.js index c0a4a375..62c93f92 100644 --- a/src/index.js +++ b/src/index.js @@ -3,23 +3,14 @@ import React from 'react'; import { render } from 'react-dom'; import { Provider } from 'react-redux'; import { BrowserRouter } from 'react-router-dom'; -import { applyMiddleware, compose, createStore } from 'redux'; -import ReduxThunk from 'redux-thunk'; import { homepage } from '../package.json'; -import App from './App'; -import './index.scss'; -import ScrollToTop from './common/ScrollToTop'; -import reducers from './reducers'; import registerServiceWorker from './registerServiceWorker'; +import container from './container'; import '../node_modules/react-datepicker/dist/react-datepicker.css'; import './common/react-tagsinput.scss'; +import './index.scss'; -const composeEnhancers = process.env.NODE_ENV !== 'production' && window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ - ? window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ - : compose; -const store = createStore(reducers, composeEnhancers( - applyMiddleware(ReduxThunk) -)); +const { App, ScrollToTop, store } = container; render( diff --git a/yarn.lock b/yarn.lock index c0d1c02c..14d4ca64 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1316,6 +1316,10 @@ bootstrap@^4.1.1: version "4.1.3" resolved "https://registry.yarnpkg.com/bootstrap/-/bootstrap-4.1.3.tgz#0eb371af2c8448e8c210411d0cb824a6409a12be" +bottlejs@^1.7.1: + version "1.7.1" + resolved "https://registry.yarnpkg.com/bottlejs/-/bottlejs-1.7.1.tgz#f2673c42feb2ba092d94b8add390e66b3f7d948f" + boxen@1.3.0, boxen@^1.2.1: version "1.3.0" resolved "https://registry.yarnpkg.com/boxen/-/boxen-1.3.0.tgz#55c6c39a8ba58d9c61ad22cd877532deb665a20b"