Javascript 通过路由器dom';s链接到外部库

Javascript 通过路由器dom';s链接到外部库,javascript,reactjs,react-router-dom,Javascript,Reactjs,React Router Dom,我正在从外部(节点\模块)模式库渲染组件。在我的主应用程序中,我将我的链接实例从react router dom传递到我的外部库组件中,如下所示: import { Link } from 'react-router-dom'; import { Heading } from 'my-external-library'; const articleWithLinkProps = { url: `/article/${article.slug}`, routerLink: Lin

我正在从外部(节点\模块)模式库渲染组件。在我的主应用程序中,我将我的
链接
实例从
react router dom
传递到我的外部库组件中,如下所示:

import { Link } from 'react-router-dom';
import { Heading } from 'my-external-library';

const articleWithLinkProps = {
    url: `/article/${article.slug}`,
    routerLink: Link,
  };

<Heading withLinkProps={articleWithLinkProps} />
RouterLink
似乎呈现正确,甚至在单击时导航到URL


我的问题是
RouterLink
似乎与我的应用程序的
react router dom
实例分离。当我点击
标题
时,它会“硬”导航,发回页面,而不是像
链接
通常那样无缝地发送到那里

我不确定在这一点上应该尝试什么来让它无缝导航。任何帮助或建议都将不胜感激,提前谢谢

编辑:显示如何设置路由器

import React from 'react';
import { hydrate, unmountComponentAtNode } from 'react-dom';
import { AppContainer } from 'react-hot-loader';
import { Provider } from 'react-redux';
import { createBrowserHistory } from 'history';
import { ConnectedRouter } from 'react-router-redux';
import RedBox from 'redbox-react';
import { Route } from 'react-router-dom';
import { Frontload } from 'react-frontload';
import App from './containers/App';

import configureStore from './redux/store';
import withTracker from './withTracker';

// Get initial state from server-side rendering
const initialState = window.__INITIAL_STATE__;
const history = createBrowserHistory();
const store = configureStore(history, initialState);
const mountNode = document.getElementById('react-view');
const noServerRender = window.__noServerRender__;

if (process.env.NODE_ENV !== 'production') {
  console.log(`[react-frontload] server rendering configured ${noServerRender ? 'off' : 'on'}`);
}

const renderApp = () =>
  hydrate(
    <AppContainer errorReporter={({ error }) => <RedBox error={error} />}>
      <Provider store={store}>
        <Frontload noServerRender={window.__noServerRender__}>
          <ConnectedRouter onUpdate={() => window.scrollTo(0, 0)} history={history}>
            <Route
              component={withTracker(() => (
                <App noServerRender={noServerRender} />
              ))}
            />
          </ConnectedRouter>
        </Frontload>
      </Provider>
    </AppContainer>,
    mountNode,
  );

// Enable hot reload by react-hot-loader
if (module.hot) {
  const reRenderApp = () => {
    try {
      renderApp();
    } catch (error) {
      hydrate(<RedBox error={error} />, mountNode);
    }
  };

  module.hot.accept('./containers/App', () => {
    setImmediate(() => {
      // Preventing the hot reloading error from react-router
      unmountComponentAtNode(mountNode);
      reRenderApp();
    });
  });
}

renderApp();
从“React”导入React;
从“react dom”导入{hydroge,unmountComponentAtNode};
从“react hot loader”导入{AppContainer};
从'react redux'导入{Provider};
从“历史”导入{createBrowserHistory};
从“react router redux”导入{ConnectedRouter};
从“RedBox react”导入RedBox;
从'react router dom'导入{Route};
从“react Frontload”导入{Frontload};
从“./containers/App”导入应用程序;
从“/redux/store”导入配置存储;
从“/withTracker”导入withTracker;
//从服务器端渲染获取初始状态
const initialState=window.\uuuu initialState\uuuuuu;
const history=createBrowserHistory();
常量存储=配置存储(历史记录,初始状态);
const mountNode=document.getElementById('react-view');
const noServerRender=窗口;
if(process.env.NODE_env!=“生产”){
log(`react frontload]服务器渲染配置${noServerRender?'off':'on'}`);
}
常量renderApp=()=>
水合物(
}>
scrollTo(0,0)}history={history}>
(
))}
/>
,
mountNode,
);
//通过react hot loader启用热重新加载
如果(模块热){
const reRenderApp=()=>{
试一试{
renderApp();
}捕获(错误){
水合物(,mountNode);
}
};
module.hot.accept('./容器/应用',()=>{
setImmediate(()=>{
//防止react路由器发生热重新加载错误
卸载组件节点(mountNode);
reRenderApp();
});
});
}
renderApp();

我已经在
codesandbox.io
中重建了您的用例,“转换”工作正常。所以,也许检查一下我的实现可能会对您有所帮助。但是,我用文件导入替换了库导入,所以我不知道这是否是在不重新加载整个页面的情况下无法工作的决定性因素

顺便问一下,你说的“无缝”到底是什么意思?是否有保留在每个页面上的元素,在单击链接时不应再次重新加载?这就像我在沙箱中实现的一样,每个页面的顶部都有一张静态图片


看看这本书

这是
example.js
文件

//此沙盒与此帖子相关https://stackoverflow.com/q/59630138/965548
从“React”导入React;
从“react Router dom”导入{BrowserRouter as Router,Route,Link};
从“/myexternallibrary.js”导入{Heading};
导出默认函数App(){
返回(
);
}
const Welcome=()=>{
const articleWithLinkProps={
url:`/article/coolArticle`,
路由器链接:链接
};
返回(
这是一个超级别致的主页;)
);
};
常量CoolArticleComponent=()=>(
这是一个手工制作的文章组件

返回 );
这是
my external library.js
文件:

从“React”导入React;
导出常量标题=({withLinkProps})=>{
const RouterLink=withLinkProps.RouterLink;
返回超链接;
};

为什么不将
组件作为参数或道具传递到外部库?这将允许更大的灵活性和更干净的导航方式。你能展示一下你是如何设置你的路由器的吗?它是浏览器、内存还是静态路由器?@mamounothman-这就是目前的做法,但似乎会影响它导航到回发的方式。您使用的是不推荐使用的库
react Router redux
(),除非你有一个特殊的约束来强制使用过时版本的<代码> ReaveRux和<代码>对路由器库进行反应,你应该考虑移动到新版本,因为它可能会修复你的问题。您可以进行升级,也可以提供项目当前使用的
react
react-router-redux
react-redux
react-router-dom
的确切版本,这样我们就有机会找到修补解决方案。如果链接直接与同一URL一起使用,您能否确认一切正常(不是先将其代理到库)?您好,非常感谢您的回答!似乎只有在通过节点_模块时才会出现问题。
import React from 'react';
import { hydrate, unmountComponentAtNode } from 'react-dom';
import { AppContainer } from 'react-hot-loader';
import { Provider } from 'react-redux';
import { createBrowserHistory } from 'history';
import { ConnectedRouter } from 'react-router-redux';
import RedBox from 'redbox-react';
import { Route } from 'react-router-dom';
import { Frontload } from 'react-frontload';
import App from './containers/App';

import configureStore from './redux/store';
import withTracker from './withTracker';

// Get initial state from server-side rendering
const initialState = window.__INITIAL_STATE__;
const history = createBrowserHistory();
const store = configureStore(history, initialState);
const mountNode = document.getElementById('react-view');
const noServerRender = window.__noServerRender__;

if (process.env.NODE_ENV !== 'production') {
  console.log(`[react-frontload] server rendering configured ${noServerRender ? 'off' : 'on'}`);
}

const renderApp = () =>
  hydrate(
    <AppContainer errorReporter={({ error }) => <RedBox error={error} />}>
      <Provider store={store}>
        <Frontload noServerRender={window.__noServerRender__}>
          <ConnectedRouter onUpdate={() => window.scrollTo(0, 0)} history={history}>
            <Route
              component={withTracker(() => (
                <App noServerRender={noServerRender} />
              ))}
            />
          </ConnectedRouter>
        </Frontload>
      </Provider>
    </AppContainer>,
    mountNode,
  );

// Enable hot reload by react-hot-loader
if (module.hot) {
  const reRenderApp = () => {
    try {
      renderApp();
    } catch (error) {
      hydrate(<RedBox error={error} />, mountNode);
    }
  };

  module.hot.accept('./containers/App', () => {
    setImmediate(() => {
      // Preventing the hot reloading error from react-router
      unmountComponentAtNode(mountNode);
      reRenderApp();
    });
  });
}

renderApp();