简体   繁体   English

无法使用 useEffect 在重新渲染 reactjs 时正确更新前端

[英]Cannot properly update frontend on rerender reactjs using useEffect

So I was making a blog application where only logged in users can add new blogs.所以我正在制作一个只有登录用户才能添加新博客的博客应用程序。 To start, when a user logs in, they will see all the blogs they have previously created on the frontend along with a form to add new ones.首先,当用户登录时,他们将看到他们之前在前端创建的所有博客以及添加新博客的表单。 However, when the logged in user tries to add a new blog, it updates on the frontend but returns back to the original list they had before when the page is refreshed.但是,当登录用户尝试添加新博客时,它会在前端更新,但在页面刷新时返回到他们之前的原始列表。 I can see the updated blog list when I log out and log back in again.当我注销并重新登录时,我可以看到更新的博客列表。 I actually used local storage to make sure that logged in users remain logged in after a new render.我实际上使用本地存储来确保登录用户在新渲染后保持登录状态。 I just need help in making sure the new blogs added after login remain on the frontend after a render.我只需要帮助确保登录后添加的新博客在渲染后保留在前端。

I think I have an idea why it is happening but I am not sure.我想我知道为什么会这样,但我不确定。 So whenever my loginService function is called within the handleLogin function, the server sends back the user info which includes all the blogs they have created.因此,每当在 handleLogin 函数中调用我的 loginService 函数时,服务器都会发回用户信息,其中包括他们创建的所有博客。 The problem with refreshing is due to the same list of blogs that were there at the time of login unless you log out and log in again.刷新的问题是由于登录时存在相同的博客列表,除非您注销并再次登录。

Any help would be greatly appreciated.任何帮助将不胜感激。

ReactJS code ReactJS 代码

import { useState, useEffect } from 'react'
import Blog from './components/Blog'
import blogService from './services/blogs'
import loginService from './services/login'
import userService from './services/user'

const App = () => {
  const [blogs, setBlogs] = useState([])
  const [newBlogs, setNewBlogs] = useState([])
  const [user, setUser] = useState(null)
  const [username, setUsername] = useState('')
  const [password, setPassword] = useState('')
  const [errorMsg, setErrorMsg] = useState('')

  const [blogTitle, setBlogTitle] = useState('')
  const [blogAuthor, setBlogAuthor] = useState('')
  const [blogUrl, setBlogUrl] = useState('')

  useEffect( () => {
    if(user != null){
      setBlogs(user.blog.concat(newBlog))
    }
    console.log("blogs is", blogs)
  }, [user])


//Seeing if a user is logged in on rerender

  useEffect(() => {
    const loggedInUser = window.localStorage.getItem('loggedBlogUser')
    if(loggedInUser){
      const user = JSON.parse(loggedInUser)
      setUser(user)
    }
  },[])


  
// Logging in users
  const handleLogin = async (event) => {
    event.preventDefault()
    console.log("Logging in,", username, password)
    try {
      const user = await loginService({username, password})
      blogService.setToken(user.token)
      window.localStorage.setItem('loggedBlogUser', JSON.stringify(user))
      setUser(user)
      setUsername('')
      setPassword('')
    }
    catch(error){
      setErrorMsg('Wrong credentials')
      setTimeout(() => {
        setErrorMsg(null)
      },[])
    }
  }

//Logging out users
  const handleLogout = () => {
    window.localStorage.removeItem('loggedBlogUser')
    setUser(null)
    setBlogs([])
  }

//Adding new blogs
  const addNewBlog = async (e) => {
    e.preventDefault()

    console.log("User here is", user)

    try {
      const newBlog = {
        title: blogTitle,
        author: blogAuthor,
        url: blogUrl
      }
      await blogService.createBlog(newBlog)
      setBlogs(blogs.concat(newBlog))
      setNewBlogs(newBlogs.concat(newBlog))
      setBlogTitle('')
      setBlogAuthor('')
      setBlogUrl('')
    }
    catch(error){
      console.log("error adding new blog", error)
    }

    console.log("blogs is", blogs)
  }

  return (
    <div>
      <h2>blogs</h2>
      {user == null && <div className="login-form">
      <form onSubmit={handleLogin}>
      <div className="username-container">
        username
        <input type='text' value={username} onChange={(e) => setUsername(e.target.value)} name='username'/>
      </div>
      <div className="password-container">
        password
        <input type='password' value={password} onChange={(e) => setPassword(e.target.value)} name='password'/>
      </div>
      <button type='submit'>Login</button>
      </form>
      </div>}
      {user != null && <div className="notes">
        <p>{user.name} logged in <button onClick={handleLogout}>logout</button></p>
      </div>}
      {user != null && <div className="addBlog-container">
      <b>create new</b>
      <form onSubmit={addNewBlog}>
        <label>Title:</label><input type="text" value={blogTitle} onChange={(e) => setBlogTitle(e.target.value)} name="blog-title"/>
        <label>Author:</label><input type="text" value={blogAuthor} onChange={(e) => setBlogAuthor(e.target.value)} name="blog-author"/>
        <label>Url:</label><input type="text" value={blogUrl} onChange={(e) => setBlogUrl(e.target.value)} name="blog-url"/>
        <button type='submit'>create blog</button>
      </form>
      </div>}
      {blogs != null && blogs.map(blog =>
        <Blog key={blog.id} blog={blog} />
      )}
    </div>
  )
}

export default App

At first you are updating blogs from user.blog but in update blog you are only updating blogs variable, that's why new blog disappears as soon as you refresh.起初你是从user.blog更新blogs ,但在更新博客中你只是更新blogs变量,这就是为什么新博客一刷新就会消失。 Try after updating user.blog with new blog.用新博客更新user.blog后尝试。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM