React shows another page and then the Homepage, whe navigating to Homepage

Viewed 32

I am new to React and I am using the Traversy crash course and the extra video about the react router 6+.

My Routes are like

import { BrowserRouter as Router, Route, Routes } from 'react-router-dom'

return (
  <div className="container">
    <Router>        
      <Header
        title='sikyona'
        onAdd={()=> setShowAddtask(!showAddTask)}
        showAdd={showAddTask}
      />
      <Routes>
        <Route 
          path='/'  
          element={
            <>
              {showAddTask && <AddTask onAdd={addTask} />}
              {tasks.length > 0
                ? <Tasks tasks={tasks} onDelete={deleteTask} />
                :<p>add tasks</p>  
              }
            </>
          } 
        />
        <Route path='/about' element={<About/>} />
      </Routes>
      <Footer />    
    </Router>  
  </div>
);

The problem is that when I navigate to the homepage http://localhost:3000/ I first see the About page for a second, and then the homepage (Route path='/'...)

I have "react-router-dom": "^6.4.1",

What is this happening and how can I fix it?

2 Answers

The issue isn't that the "About" page or About component is being rendered when the app is loading or navigating to "/" for the first time. It's that the app is actually on "/" and there's no tasks to display just yet and the UI is rendering the container, Header, the Route for path="/" with the "add tasks" text, and the Footer which renders a link to "/about".

Home page view with no tasks

Contrast this rendered UI with the actual "/about" path and About component.

enter image description here

Perhaps the UI/UX is fine for you with regards to this behavior and understanding what exactly is being rendered when, and for what reason. If on the other hand you don't want to see any of the UI until data has been loaded you can tweak the code to render nothing or some loading indicator while the tasks are fetched.

Example:

function App() {
  const [showAddTask, setShowAddtask] = useState(false);
  const [tasks, setTasks] = useState(); // <-- initially undefined

  useEffect(() => {
    const getTasks = async () => {
      try {
        const tasks = await fetchTasks();
        setTasks(tasks); // <-- defined and populated
      } catch(error) {
        // log errors, display message, etc... or ignore
        setTasks([]); // <-- defined and empty
      }
    };
    getTasks();
  }, []);

  ...

  if (!tasks) {
    return null; // <-- return null or loading indicator/spinner/etc
  }

  return (
    <div className="container">
      <Router>
        <Header
          title="hello"
          onAdd={() => setShowAddtask(show => !show)}
          showAdd={showAddTask}
        />
        <Routes>
          <Route
            path="/"
            element={
              <>
                {showAddTask && <AddTask onAdd={addTask} />}
                {tasks.length ? (
                  <Tasks tasks={tasks} onDelete={deleteTask} />
                ) : (
                  <p>add tasks</p>
                )}
              </>
            }
          />
          <Route path="/about" element={<About />} />
          <Route path="/task-details/:id" element={<TaskDetails />} />
        </Routes>
        <Footer />
      </Router>
    </div>
  );
}

Try to put your <Route path='/' /> last in the list.

Related