Using React-Router with a layout page or multiple components per page

后端 未结 4 880
走了就别回头了
走了就别回头了 2020-11-28 19:33

I am adding react router to an existing project.

At present a model is passed in to a root component which contains a navigation component for the sub navigation an

4条回答
  •  悲哀的现实
    2020-11-28 20:13

    To add upon Sebastien's answer, this seems to work for me, including a not found route and dynamic subroutes. The examples below make my LayoutAuthenticated and LayoutAnonymous just render once, not on every route change within routes that use that same layout. Also added the PageSettings example to show nested routes within this architecture. Hope this might help others!

    (examples include TypeScript)

    const publicRoutes = [
      {
        key: "login",
        path: "/login",
        component: PageLogin,
        exact: true
      },
      {
        key: "signup",
        path: "/signup",
        component: PageSignup,
        exact: true
      },
      {
        key: "forgot-password",
        path: "/forgot-password",
        component: PageForgotPassword,
        exact: true
      }
    ];
    
    const privateRoutes = [
      {
        key: "home",
        path: "/",
        component: PageHome,
        exact: true
      },
      {
        key: "settings",
        path: "/settings",
        component: PageSettings, // sub routing is handled in that component
        exact: false // important, PageSettings is just a new Router switch container
      }
    ];
    
    // Routes.tsx
    
    
      
        
          
            
              {privateRoutes.map(privateRouteProps => (
                
              ))}
            
          
        
    
        
          
            
              {publicRoutes.map(publicRouteProps => (
                
              ))}
            
          
        
    
        
          
            
              
            
          
        
      
    
    
    // LayoutAnonymous.tsx
    
    import React from 'react';
    
    export const LayoutAnonymous: React.FC<{}> = props => {
      return (
        
    {props.children}
    ) }
    // LayoutAuthenticated.tsx
    
    import React from 'react';
    import { MainNavBar } from '../components/MainNavBar';
    import { MainContent } from '../components/MainContent';
    
    export const LayoutAuthenticated: React.FC<{}> = props => {
      return (
        <>
          
          
            {props.children}
          
        
      )
    }
    
    
    
    // PrivateRoute.tsx
    
    import React from "react";
    import {
      Route,
      Redirect,
      RouteProps
    } from "react-router-dom";
    import { useSelector } from "react-redux";
    
    interface Props extends RouteProps {}
    
    export const PrivateRoute: React.FC = props => {
      const isAuthenticated: boolean = useSelector((stores) => stores.auth.isAuthenticated);
    
      const { component: Component, ...restProps } = props;
    
      if (!Component) return null;
    
      return (
        
            isAuthenticated ? (
              
            ) : (
              
            )
          }
        />
      )
    }
    
    // PublicRoute.tsx
    
    
    import React from "react";
    import { Route, RouteProps, Redirect } from "react-router-dom";
    import { useSelector } from "react-redux";
    
    interface Props extends RouteProps {}
    
    export const PublicRoute: React.FC = props => {
      const isAuthenticated: boolean = useSelector((stores) => stores.auth.isAuthenticated);
      const { component: Component, ...restProps } = props;
    
      if (!Component) return null;
    
      return (
         (
            !isAuthenticated ? (
              
            ) : (
              
            )
          )}
        />
      )
    }
    
    
    // PageSettings.tsx
    
    import React from "react";
    import { LinkContainer } from "react-router-bootstrap";
    import Button from "react-bootstrap/Button";
    import {
      Switch,
      useRouteMatch,
      Redirect,
      Switch
    } from "react-router-dom";
    
    import { PrivateRoute } from "../../routes/PrivateRoute";
    import { PageSettingsProfile } from "./profile";
    import { PageSettingsBilling } from "./billing";
    import { PageSettingsAccount } from "./account";
    
    export const PageSettings = () => {
      const { path } = useRouteMatch();
    
      return (
        

    Settings

    ); };

提交回复
热议问题