Note: the eventual goal of this repo is to fork it into a full-stack starter kit (or possibly a yo generator), but for now it's just a place for me to try out different ways of structuring a react-redux UI.
Slideshow example app built with React, Redux, Webpack, Babel, & Karma.
This is obviously waaay over-engineered for a simple slideshow that could have been built in vanilla js. But this stack/setup represents how I would (currently) approach building a large-scale application.
Slideshow features include json config file, settings panel for transitions/image size, and view count.
- Node & NPM should be installed globally
- Clone this repo
npm i
- install all project dependenciesnpm run dev
- run local dev server with hot module reloading*
*Hot module reloading is enabled. Example video link - normally in this flow we'd have to reload the page, navigate back to the final image, and view it 4 times in order to test this change. With hot module reloading the component is updated instantly in the current app state.
- If a bug surfaces in the platform it should not be difficult to find the origin.
- It should be entirely modular in that each piece of functionality (component) should be able to work independently of the rest of the app.
- The platform should be easy to edit or add to.
- It should be able to be entirely covered with unit tests.
npm run test
This script runs all karma unit tests (any*.spec.js
file in/src
) then generates a code coverage report.
Code coverage report is provided via Istanbul and highlights which parts of the app are not covered. This report can be viewed in code-coverage-report/html/index.html
after running npm run test
:
npm run dist
This script compiles, compresses, and copies all assets to be deployed to a/dist
directory.
- Components receive props and dispatch actions (when the user interacts with them)
- Reducers handle these dispatched actions and modify application state at the root level
- Application state is propagated back down the React component tree and UI is updated
- ????
- Profit
In this flow components are de-coupled from the state, they do not worry about anything that's going on around them; they just know they're supposed to receive certain properties and render. Also, since the entire state exists at the root level of the application, any component can easily be granted access to any part of the state and we can track every user interaction with the app and how it modifies state. Really useful for debugging.
With this approach it is easy to add & modify functionality anywhere in the app without worrying about how it might affect other parts of the application. Each component folder in this app could be used anywhere.
Components, actions, and reducers (state) can be individually unit tested as they are functional code islands.
While most of the dependencies are for local build & unit tests, there is still 9 dependencies included in the final dist bundle. Lately I've been exploring Riot which seems promising in terms of cutting down final build size while still maintaining a similar app structure.
For developers that haven't used React or Redux before there would certainly be a bit of ramp-up time. However, as long as the documentation is good it should be fairly straightforward.
This project has quite a few dependencies, but the list below represents the key tools, and why I decided to include them.
- Babel
- To be able to use es6 when developing locally. Super handy for a number of reasons.
- Enzyme
- Eslint
- My favorite tool for linting javascript. Not only does it report errors, but it is very extendable so you can add custom (personal preference) rules to ensure all developers on a project will produce similar looking code.
- Karma/Mocha/Chai
- Easy to use, configurable test runner that also produces some handy code coverage reports (see Unit Tests section above ^)
- PostCSS
- SASS/LESS include a bunch of functionality out-of-the-box, but PostCSS is a customizable, extendable css processing tool. Here's a great breakdown of why this is useful.
- React
- Redux
- Great way of managing application state as 1 huge data object at the root level. Makes the app more predictable, and it's very easy to track every single user interaction (what they did, previous state, and next state after their action). Very handy for debugging.
- Webpack
- I've been using webpack as a build tool for pretty much every project now. I used to use grunt/gulp, but webpack requires a lot less custom code to work (more of a config file really).
Note: usually for large data applications I would also include Immutable which provides an extra layer of predictability and security to application state. It would be very easy to modify reducers to use Immutable for this example. I just left it out because there is not much data in this example app.
- Add router and routes for each image
- Add image preloader for each image
Please email me at me@justin-schrader.com or submit an issue if you have any questions or issues with this repo. Suggestions and PRs also welcome!