React Native引入Redux Store报错:Can't find variable: document
解决React Native中使用redux-saga/connected-react-router时的
ReferenceError: Can't find variable: document错误 这个错误的根源非常明确:你在React Native项目中使用了createBrowserHistory,而这个API是专门为Web浏览器环境设计的——它依赖浏览器的document对象来操作地址栏和历史记录,但React Native是移动端原生环境,根本不存在document这个浏览器专属的全局变量。
解决方案:替换为createMemoryHistory
history库提供了不依赖浏览器环境的createMemoryHistory,它完全在内存中管理历史记录,非常适合React Native这样的非Web环境。
修改你的Redux Store文件如下:
import {applyMiddleware, compose, createStore} from 'redux'; import reducers from '../reducers/index'; // 替换createBrowserHistory为createMemoryHistory import {createMemoryHistory} from 'history' import {routerMiddleware} from 'connected-react-router'; import createSagaMiddleware from 'redux-saga'; import rootSaga from '../sagas/index'; // 用createMemoryHistory创建history实例 const history = createMemoryHistory(); const routeMiddleware = routerMiddleware(history); const sagaMiddleware = createSagaMiddleware(); const middlewares = [sagaMiddleware, routeMiddleware]; const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose; export default function configureStore(initialState) { const store = createStore(reducers(history), initialState, composeEnhancers(applyMiddleware(...middlewares))); sagaMiddleware.run(rootSaga); if (module.hot) { // Enable Webpack hot module replacement for reducers module.hot.accept('../reducers/index', () => { const nextRootReducer = require('../reducers/index'); store.replaceReducer(nextRootReducer(history)); // 热重载时也要传入history,避免出错 }); } return store; } export {history};
额外注意事项
- 确认reducer配置正确:你的根reducer应该已经用
connectRouter(history)包裹了router reducer,确保这部分逻辑没问题:
// reducers/index.js示例 import { combineReducers } from 'redux'; import { connectRouter } from 'connected-react-router'; // 你的其他reducers import authReducer from './auth'; export default (history) => combineReducers({ router: connectRouter(history), auth: authReducer, // ...其他业务reducers });
- React Navigation与connected-react-router的取舍:如果你同时在使用React Navigation,其实可以考虑直接用React Navigation自带的导航状态管理,避免同时维护两套路由状态。但如果你的业务逻辑已经深度依赖connected-react-router,上面的修改就能快速解决问题。
- Redux DevTools兼容性:React Native中使用Redux DevTools可能需要额外配置(比如用
remote-redux-devtools),不过当前代码中window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__的fallback逻辑已经做了兼容,无需额外修改。
这样修改后,你的store就不会再依赖浏览器的document对象,错误应该就能消失了。
内容的提问来源于stack exchange,提问作者HuLu ViCa




