React-router browserHistory OVH

时间:2016-11-10 17:12:01

标签: javascript reactjs webpack react-router browser-history

我正在尝试ReactJS,一切都很好,直到制作...... 我的意思是,我有一个OVH网站(它是我自己的,它是一个共享主机)。

在开发时,我使用React Router和browserHistory以及historyApiFallback用于我的webpack-dev-server。一切都很好。

但是当我使用webpack构建我的应用程序时,在生产时,当我重新加载页面时,我得到了404。

我无法在我的网站上运行像express这样的服务器,它是一个共享主机。任何解决方案?


build.js

const webpack = require('webpack')
const conf = require('./webpack.prod')
const ora = require('ora')
const spinner = ora('Building...')
const path = require('path')
const root = path.resolve(__dirname, '../')
require('shelljs/global')

spinner.start()
rm('-rf', 'build')
mkdir('-p', path.join(root, 'build'))
cp(path.join(root, 'source/index-build.html'), path.join(root, 'build/index.html'))

webpack(conf, (err, stats) => {
  spinner.stop()
  if (err) throw err

  process.stdout.write(`${stats.toString({
    colors: true,
    modules: false,
    children: false,
    chunks: false,
    chunkModules: false
  })}\n`)
})


webpack.prod.js

const webpack = require('webpack')
const config = require('./webpack.base')

const ExtractTextPlugin = require('extract-text-webpack-plugin')
const extractCSS = new ExtractTextPlugin('bundle.css')

config.plugins = config.plugins.concat([
  extractCSS,
  new webpack.optimize.UglifyJsPlugin({
    comments: false,
    warnings: false,
  }),
  new webpack.DefinePlugin({
    'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV || 'production')
  })
])

const cssLoaders = config.module.loaders[0].loaders
config.module.loaders[0].loaders = null
config.module.loaders[0].loader = extractCSS.extract(cssLoaders.slice(1, cssLoaders.length))

module.exports = config


webpack.base.js

const path = require('path')
const root = path.resolve(__dirname, '../')

const StyleLintPlugin = require('stylelint-webpack-plugin')

module.exports = {
  entry: {
    app: [
      path.join(root, 'source/styles/styles.scss'),
      path.join(root, 'source/scripts/index.js')
    ]
  },
  output: {
    path: path.join(root, 'build'),
    filename: 'bundle.js',
    publicPath: '/build/'
  },
  module: {
    preLoaders: [{
      test: /\.js$/,
      exlude: /(node_modules|bower_components)/,
      loader: 'eslint'
    }],
    loaders: [{
      test: /\.scss$/,
      loaders: ['style', 'css', 'sass', 'sass-resources']
    }, {
      test: /\.js$/,
      exlude: /(node_modules|bower_components)/,
      loader: 'babel'
    }, {
      test: /\.(jpg|jpeg|png|gif|svg)$/,
      loader: 'url',
      query: {
        limit: 100,
        name: 'images/[name]-[hash:16].[ext]'
      },
      include: path.join(root, 'source/static/images')
    }, {
      test: /\.(woff2|ttf|eog|svg)$/,
      loader: 'file',
      query: {
        limit: 1,
        name: 'fonts/[name]-[hash:16].[ext]'
      },
      include: path.join(root, 'source/static/fonts')
    }, {
      test: /\.json$/,
      loader: 'url',
      query: {
        name: 'json/[name]-[hash:16].[ext]'
      },
      include: path.join(root, 'source/static/json')
    }, {
      test: /\.mp4$|\.webm$/,
      loader: 'url',
      query: {
        limit: 3000,
        name: 'videos/[name]-[hash:16].[ext]'
      },
      include: path.join(__dirname, 'source/static/video')
    }]
  },
  plugins: [
    new StyleLintPlugin({
      files: './source/**/*.scss'
    })
  ],
  sassResources: [
    path.join(root, 'source/styles/_variables.scss'),
    path.join(root, 'source/styles/_functions.scss'),
    path.join(root, 'source/styles/_mixins.scss')
  ],
  eslint: {
    configFile: path.join(root, '.eslintrc'),
    formatter: require('eslint-friendly-formatter')
  },
  sasslint: {
    configFile: path.join(root, '.sass-lint.yml')
  }
}


index.js

import React from 'react'
import { createStore, applyMiddleware, compose } from 'redux'
import { render } from 'react-dom'
import { Provider } from 'react-redux'
import { Router, Route, browserHistory, IndexRedirect } from 'react-router'
import { syncHistoryWithStore, routerMiddleware } from 'react-router-redux'
import thunk from 'redux-thunk'

import App from './containers/App'
import Projects from './components/Projects'
import Work from './components/Work'
import Profile from './components/Profile'

import routes from './constants/routes'
import reducers from './reducers'

const middleware = [
  thunk,
  routerMiddleware(browserHistory)
]

// Create stores
const store = createStore(
  reducers,
  compose(
    applyMiddleware(...middleware),
    window.devToolsExtension ? window.devToolsExtension() : f => f
  )
)

// History
const history = syncHistoryWithStore(browserHistory, store)

render ((
  <Provider store={store}>
    <Router history={history}>
      <Route path={routes.ROOT} component={App}>

        <IndexRedirect to="/door-opener" />

        <Route path={routes.PROFILE} component={Profile} />
        <Route path={routes.PROJECTS} component={Projects} />
        <Route path={routes.WORK} component={Work} />
      </Route>
    </Router>
  </Provider>),
  document.getElementById('root')
)

if (module.hot) {
  // Enable Webpack hot module replacement for reducers
  module.hot.accept('./reducers', () => {
    const nextReducer = require('./reducers/index').default
    store.replaceReducer(nextReducer)
  })
}

2 个答案:

答案 0 :(得分:0)

如果共享主机不允许您配置服务器,则无法执行此操作,您需要能够重新路由URL。

https://github.com/ReactTraining/react-router/blob/master/docs/guides/Histories.md

答案 1 :(得分:0)

我找到了解决方案。这只是一个htaccess问题。

的.htaccess

RewriteEngine On
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -f [OR]
RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -d
RewriteRule ^ - [L]

RewriteRule ^ /index.html [L]