my express backend which uses passport.js is returning false on the client but true when I go to the server using the browser

23 views Asked by At

this is my express backend which has a '/check-auth' api endpoint that returns authenticated: true on the server but when I am on using the react client returns authenticated: false

const express = require("express"); 
const mongoose = require("mongoose"); 
const cors = require("cors") 
require("dotenv").config() 
const session  = require("express-session");
const MongoStore = require('connect-mongo');
const passport = require("passport") 
const LocalStrategy  = require("passport-local").Strategy; 
const bcrypt = require("bcrypt"); 

const app = express()  
 



app.use(cors({ origin:'http://localhost:3000', credentials: true }));



mongoose.connect(process.env.DATABASE_URI) 
    .then(()=> console.log("connected to the Database") ) 
    .catch(error => console.log(error)) 




app.use(session({ 
    secret: 'thekey',
    resave: true,
    saveUninitialized: true,
    store:MongoStore.create({mongoUrl:process.env.DATABASE_URI}),
    cookie: {
      maxAge: 24 * 60 * 60 * 1000, // 1 day
    },
  
}));

app.use(passport.initialize()); 
app.use(passport.session());  

app.use(express.urlencoded({ extended: true }));
app.use(express.json())  


const courtSchema = new mongoose.Schema({

    name: String, 
    type: String, 
    address: String,
    floor:String,
    rim:String, 
    netType:String, 
    threePointLine:Boolean, 
    collegeThreePointLine:Boolean, 
    courtCount: Number,
    seats:Boolean

})   


const Court = mongoose.model("courts", courtSchema)  


const userSchema = new mongoose.Schema({
    username:{
        type:String,
        required: true
    } , 
    password: {
        type:String, 
        required: true
    },
    fullName:{
        type:String,
        required: true
    }, 
    number: {
        type:String, 
        required: true
    }

})


const User = mongoose.model("User", userSchema)      

//user profie schema 

const userProfileSchema = new mongoose.Schema({
    username:{
        type: mongoose.Schema.Types.ObjectId,
        ref: 'user'
        
    } , 
    email: {
        type:String, 
      
    },
    fullName:{
        type:String,
     
    }, 
    number: {
        type:String, 
        
    }, 
    city: {
        type:String, 
    }, 
    state: {
        type:String, 
       
    }, 
    favoritePark:{
        type:String, 
      
    },
    reviews:[{
        type:String,
       

    }]

})


const UserProfile = new mongoose.model("UserProfile", userProfileSchema)  





//passport.js 

app.use(passport.initialize()); 
app.use(passport.session());  



passport.serializeUser((user, done) => {  
        done(null, user.id);
  });

passport.deserializeUser(async (id, done) => { 
    try {  
        user = await User.findById(id); 

        if(!user) {
            return done(new Error('User not found'));
        }
        
        done(null, user)
    } catch (err) {
            done(err)
    }
    
  });



// Passport configuration
passport.use(new LocalStrategy(

    function(username, password, done) {
        User.findOne({ username: username })
          .then(user => {
            if (!user) {
              return done(null, false, { message: 'Incorrect username.' });
            }
            // Check password here and handle accordingly 
            if (user.password !== password) {
                return done(null, false, { message: 'Incorrect password.' });
              }
            
             return done(null, user); 
             
          })
          .catch(err => {
            return done(err);
          });
      }
  ));










//getting all the post 
app.get("/courts", async (req, res )=>{  
    const courts = await Court.find()  
    res.send(courts)
    
}) 

// getting one post

app.get("/courts/:id", async (req, res) => {
    const courts = await Court.findById(req.params.id)  
    res.send(courts)


}) 

//creating a post 
app.post("/courts", async(req, res)=>{
    const newCourt = new Post(req.body)
    const savedCourt = await newCourt.save()
    res.send(savedCourt)

}) 

app.delete("/courts/:id", async (req , res) => {
    await Court.findByIdAndDelete(req.params.id) 
    res.status(200).send("post deleted")

}) 


app.post('/signin', passport.authenticate('local'), (req, res) => {
    console.log('User:', req.user);
    res.json({ isAuthenticated: req.isAuthenticated(), user: req.user });  
  });





app.post("/signup", async(req, res)=>{ 
   // console.log(req.body)     
    const {username , password ,fullName, number } = req.body

    try{ 
        const hashedPass = await bcrypt.hash(req.body.password,10)  
        console.log(hashedPass) 
        const newUser = new User({
                username,
               // password:hashedPass,
                password:password,
                fullName:fullName,
                number:number
        }) 

        const newUserProfile = new  UserProfile({ 
            username: newUser.id, 
          
            email:null,
            fullName:fullName,
            number:number,
            city:null,
            state:null, 
            favoritePark:null, 
            reviews:null,

        })        
         
        console.log(newUser)  
        console.log(newUserProfile)
        newUser.save() 
        newUserProfile.save()
    }
    catch(err){ 
        console.error("failed to sign up", err)

    }

}) 




  
  app.get('/check-auth', (req, res) => {
    if (req.isAuthenticated()) {
      // User is authenticated
      return res.json({ authenticated: true, user: req.user });
    } else {
      // User is not authenticated
     return res.json({ authenticated: false, user: null });
    }
  });
  



app.listen(3400 , ()=> {
    console.log("port is running on port 3400")
}) 

This is my react front-end Home page component which has a checkAuth function which makes a get request to my express backend server.

the responce should return true with and obeject containing the user who is currently logged in.
it the responce is only returning true.

const HomePage = (props) => { 
    const [courts , setCourts ] = useState([]) 
    const navigate = useNavigate();


    useEffect(()=> {
        const grabCourts = async () =>{
            const res = await axios.get(`http://localhost:3400/courts`)
            setCourts(res.data)  
            
        } 
        grabCourts()  
    },[])


    //const isAuth = useContext(AuthContext)  

    const [isAuth ,setIsAuth] = useContext(AuthContext)



    useEffect(() =>  { 

        const checkAuth = async () => {


            try{
                const res = await axios.get(`http://localhost:3400/check-auth`)
                .then((res)=>{  
                
                console.log(res)
                
                })
            } 
            catch(err){
                console.log(`error : ${err}`)
            }

            
        }
           checkAuth()
    }, [] ) 




    return( 
        <div className="container" >  

          <Top/>


            <h1 className="top-heading">Top Courts</h1>
            <div className="cards">
                
                
                {  

            courts.slice(0,3).map((court)=>(
                    <div className="card" key="_id">
                        <h1>
                            {court.name}
                        </h1> 

                        <h2>
                            {court.address}
                        </h2>   

                        <div className="court-type">

                         <img src={bb} className="bb-image"></img> 
                         
                         
                         <p className="court-num">{court.courtCount} x</p> 

                        <Link to={`/courts/${court._id}`}>
                          <button className="read-more">More Info</button>
                        </Link>
                       
                            
                        </div>  
                    
                    </div>
            ))}
            </div>
        </div>

    )
    
} 


export default HomePage

is there something wrong with the way I am using the req.isAuthenticated() method on my server?

I had tried console.logging '/checkauth' api endpoint step by step and i think problem source is the isAuthenticated().

1

There are 1 answers

0
Mr. Terminix On

Passport adds the session to the cookie. Axios do not add cookies by default. You have to write:

useEffect(() => {
    const checkAuth = () => {
        axios
            .get(`http://localhost:3400/check-auth`, {
                withCredentials: true,
            })
            .then((res) => {
                console.log(res);
                console.log(res.data);
            })
            .catch((error) => console.log(error));
    };
    checkAuth();
}, []);

The key is to add option withCredentials: true. Btw I would recommend to format your code and to not combine async/await with .then/.catch syntax.