Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding middleware to <RouterContext/> #3641

Closed
catamphetamine opened this issue Jul 16, 2016 · 4 comments
Closed

Adding middleware to <RouterContext/> #3641

catamphetamine opened this issue Jul 16, 2016 · 4 comments

Comments

@catamphetamine
Copy link

catamphetamine commented Jul 16, 2016

redux-router uses <RouterContext/> to make it work
https://github.com/acdlite/redux-router/blob/master/src/ReduxRouter.js#L106

        <RouterContext
          {...renderProps}
          createElement={makeCreateElement(renderProps.createElement)}
        />

scroll-behaviour tells in its docs to add a middleware to the render property
https://github.com/taion/react-router-scroll

import { applyRouterMiddleware, browserHistory, Router } from 'react-router';
import useScroll from 'react-router-scroll';

/* ... */

ReactDOM.render(
  <Router
    history={browserHistory}
    routes={routes}
    render={applyRouterMiddleware(useScroll())}
  />,
  container
);

But I don't see render property on <RouterContext/>.
Is there such a property I can set to make it work?

In applyRouterMiddleware source code I can see that it just (?) renders <RouterContext/>

  return (renderProps) => (
    withContext.reduceRight(
      (previous, renderRouterContext) => (
        renderRouterContext(previous, renderProps)
      ), (
        <RouterContext
          {...renderProps}
          createElement={makeCreateElement(renderProps.createElement)}
        />
      )
    )
  )

Does it mean that to make <RouterContext/> work with middleware the render property is not required, and instead <RouterContext/> may just (?) be wrapped (?) with the middleware of interest?

@catamphetamine catamphetamine changed the title How can I define "render" property of <RouterContext/>? Adding middleware to <RouterContext/> Jul 16, 2016
@catamphetamine
Copy link
Author

catamphetamine commented Jul 16, 2016

I think that might be the solution:

scroll-behaviour only has renderRouterContext set, so only renderRouterContext functionality is required
https://github.com/taion/react-router-scroll/blob/master/src/index.js#L7

export default function useScroll(shouldUpdateScroll) {
  return {
    renderRouterContext: (child, props) => (
      <ScrollBehaviorContainer
        shouldUpdateScroll={shouldUpdateScroll}
        routerProps={props}
      >
        {child}
      </ScrollBehaviorContainer>
    ),
  };
}

And applyRouterMiddleware really seems to just wrap those renderRouterContexts around the <RouterContext/>, so I might as well make scroll-behaviour work with this code:

      <ScrollBehaviorContainer
          shouldUpdateScroll={shouldUpdateScroll}
          routerProps={routerContextProps}>

          <RouterContext {...routerContextProps}/>

      </ScrollBehaviorContainer>

Do you think that would be a suitable solution?

@taion
Copy link
Contributor

taion commented Jul 16, 2016

This is a redux-router issue, not a React Router issue. If redux-router provides a different API, it's up to them to expose a way to use router middlewares.

@taion taion closed this as completed Jul 16, 2016
@perrin4869
Copy link
Contributor

@halt-hammerzeit It really seems to be a redux-router issue. applyRouterMiddleware basically outputs a RouterContext which you can then render. For example, in the server side, instead of rendering RouterContext directly, you would render the output of applyRouterMiddleware. redux-router have to provide an API for passing in a custom RouterContext.

@catamphetamine
Copy link
Author

catamphetamine commented Jul 17, 2016

@perrin4869 Thanks, the answer you provided is similar to the way I went yesterday. And it seems to work. Forgot to post a link here for googlers:
acdlite/redux-router#261

The key question was "How to add middleware feature to RouterContext" and the answer seems what you wrote:

instead of rendering <RouterContext/> directly, you would render the output of applyRouterMiddleware()

Maybe the formulation of the question doesn't make a lot of sense for a react-router guru, but for all googlers passing by this is what they're for.

@lock lock bot locked as resolved and limited conversation to collaborators Jan 21, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants