Home >Web Front-end >JS Tutorial >Building a React Universal Blog App: Implementing Flux
This tutorial demonstrates building a scalable React Universal Blog App using Flux architecture. Part two focuses on content management and application scaling.
Key Concepts:
routes.js
into smaller, more manageable components for improved organization.Refactoring routes.js
:
To improve organization, the routes.js
file is refactored to separate page routes into individual components. The updated code includes the AppStore
for data management.
<code class="language-javascript">// routes.js import React from 'react' import { Route, IndexRoute } from 'react-router' import AppStore from './stores/AppStore' import App from './components/App' import Blog from './components/Pages/Blog' import Default from './components/Pages/Default' import Work from './components/Pages/Work' import NoMatch from './components/Pages/NoMatch' export default ( <route path="/" data="{AppStore.data}" component="{App}"> <indexroute component="{Blog}/"> <route path="about" component="{Default}/"> <route path="contact" component="{Default}/"> <route path="work" component="{Work}/"> <route path="/work/:slug" component="{Work}/"> <route path="/blog/:slug" component="{Blog}/"> <route path="*" component="{NoMatch}/"> </route> )</route></route></route></route></route></indexroute></route></code>
The Store: Single Source of Truth
The Flux Store
acts as the single source of truth for application data. Key principles include:
The AppStore.js
file implements this:
<code class="language-javascript">// AppStore.js import { EventEmitter } from 'events' import _ from 'lodash' export default _.extend({}, EventEmitter.prototype, { data: { ready: false, globals: {}, pages: [], item_num: 5 }, emitChange: function(){ this.emit('change') }, addChangeListener: function(callback){ this.on('change', callback) }, removeChangeListener: function(callback) { this.removeListener('change', callback) } })</code>
React Components: Smart and Dumb
Data-altering actions are confined to higher-level (smart) components, while lower-level (dumb) components render UI based on props. The App.js
component demonstrates this:
<code class="language-javascript">// App.js import React, { Component } from 'react' import AppDispatcher from '../dispatcher/AppDispatcher' import AppStore from '../stores/AppStore' import Nav from './Partials/Nav' import Footer from './Partials/Footer' import Loading from './Partials/Loading' export default class App extends Component { componentDidMount(){ AppStore.addChangeListener(this._onChange.bind(this)) } componentWillUnmount(){ AppStore.removeChangeListener(this._onChange.bind(this)) } _onChange(){ this.setState(AppStore) } getStore(){ AppDispatcher.dispatch({ action: 'get-app-store' }) } render(){ const data = AppStore.data if(!data.ready){ document.body.className = '' this.getStore() let style = { marginTop: 120 } return (<div classname="container text-center" style="{style}"><loading></loading></div>) } const Routes = React.cloneElement(this.props.children, { data: data }) return ( <div> <nav data="{data}/"> {Routes} <footer data="{data}/"> </footer></nav> </div> ) } }</code>
The Blog.js
and BlogList.js
components illustrate how data flows from higher-level to lower-level components:
<code class="language-javascript">//Blog.js (excerpt) getPageData(){ AppDispatcher.dispatch({ action: 'get-page-data', page_slug: 'blog', post_slug: this.props.params.slug }) } //BlogList.js (excerpt) render(){ let data = this.props.data let articles = data.articles // ...rest of the component articles = _.take(articles, item_num) let articles_html = articles.map(( article ) => { // ...map through articles }) return ( <div> <div>{ articles_html }</div> { load_more } </div> ) }</code>
(Note: The complete code for other components like AppDispatcher.js
, actions.js
, config.js
, and app-server.js
is omitted for brevity but is available in the referenced GitHub repository.)
Cosmic JS Configuration and Server-Side Rendering
The config.js
file is used to connect to the Cosmic JS CMS. The app-server.js
file handles server-side rendering using ReactDOMServer.renderToStaticMarkup
. The package.json
scripts are configured for development and production builds.
Conclusion
This tutorial provides a foundation for building a robust and scalable React Universal Blog App. The use of Flux architecture and server-side rendering enhances performance, SEO, and maintainability. The complete code is available on GitHub. The FAQ section addresses common questions about Flux, React, and universal applications.
The above is the detailed content of Building a React Universal Blog App: Implementing Flux. For more information, please follow other related articles on the PHP Chinese website!