rturnq / solid-router

A router for solid-js
MIT License
42 stars 1 forks source link

re render parent. #9

Closed kapilpipaliya closed 3 years ago

kapilpipaliya commented 4 years ago

When I navigate from one route to another route, it unnecessary re-render parent component.

rturnq commented 4 years ago

Without a code example, I'm not sure exactly what you are seeing; however, I played around with a couple patterns and was able to produce unnecessary remounting when using the function form of a route (ie. using the render prop).

It looks like this is due to the fact I am passing values to the render function instead of the signals. Originally I just wanted really easy access to those values but it is really antithetical to the way solid works. I hadn't really considered it at the time but basically the render function wrapper was subscribing to all of the parameters which causes the render function to execute any time there is a route change.

In order to solve this issue I'm going to have to pass in the signal getters instead of the values as parameters to the render function which will be a breaking change. This would make it align more closely to using the useRoute "hook" in a component. I might also take this opportunity to change additional things. For instance I was thinking about removing the render property all together and making children so it could either be a function or a JSX element.

kapilpipaliya commented 4 years ago

I have OrgLayout component which has this code:

const OrgLayout = () => (
       // fetching data and set state...
        <Switch>
          <Match when={state.isLoading}>Loading...</Match>
          <Match when={!state.authorized}>{state.er}</Match>
          <Match when={state.fetch_data}>
            <Switch>
              <MatchRoute path="/organization/:org" render={OrgIndex} />
              <MatchRoute path="/organization/:org/index" render={OrgIndex} />
              <MatchRoute path="/organization/:org/project/:project" render={ProjectLayout} />
            </Switch>
          </Match>
        </Switch>
)

When i navigate between organization routes it re fetch data and I see Loading... on the screen.

rturnq commented 4 years ago

Where does the fetch happen, in OrgIndex or ProjectLayout?

If OrdIndex and ProjectLayout are components you could change the inner switch to

<Switch>
  <MatchRoute path="/organization/:org"><OrgIndex /></MatchRoute />
  <MatchRoute path="/organization/:org/index"><OrgIndex /></MatchRoute />
  <MatchRoute path="/organization/:org/project/:project"><ProjectLayout /></MatchRoute />
</Switch>

Then too access the org id within those components you can the use the useRoute hook to access the path params. This form shouldn't suffer from the issue affecting the render prop.

I'm going to work on fixing the render prop issue but like I said it will be a breaking change and I may take the opportunity to tweak other parts of the API.

kapilpipaliya commented 4 years ago

I am fetching data in OrgLayout component. i changed to useRoute and used children pattern instead of render function. It works.

but if I add this code in OrgLayout it still refetch data when changing route, when getParmas is not changed:

 const { getParams } = useRoute();
  createEffect(() => {
      if (getParams().org) {
        reFetch();
      }
  });
kapilpipaliya commented 4 years ago

I have links for path '/' and '/contact` when '/contact' is active, it also highlight '/'.

kapilpipaliya commented 4 years ago

I am waiting for <NavLink/> component fix so it match full path. do you fix this until you release next major version?

rturnq commented 4 years ago

This behavior is intended and configurable using the end property which is available on NavLink, ShowRoute and MatchRoute components. By default (end == false), their path will match against all child paths. By setting end to true you can tell the component you want it to only match that path and not any child paths.

Here is an example: https://codesandbox.io/s/rturnq-solid-router-nav-link-ytg9x

You'll see that with end set to true to the home link, so it will only be active when the path is '/'. Also, notice I have end on the MatchRoute for home which means it only matches the '/' path and lets '/baz' through to the switch's fallback.

kapilpipaliya commented 4 years ago

Thank you so much. It solved the problem.