Make the google profile image larger size from Google Oauth using passport - passport.js

I am trying to get the full size image from google using passport Google Oauth.
I see from other questions that the small size is coming from the "/photo.jpg?sz=50'" at the end of the url string.
since i don't think there is a way to ask for the full size on initial load, what would be the way to remove that part of the url before it gets saved to the database.
One person said to put:
iamgeUrl=user[image][url].substr(0,user[image][url].indexOf('?str=')) + '?sz=100';
but not sure where that would go in my code...
passport.use(
new GoogleStrategy(
{
// options for google strategy
clientID: process.env.googleclientID,
clientSecret: process.env.googleclientSecret,
callbackURL: "/auth/google/redirect"
},
(accessToken, refreshToken, profile, done) => {
console.log(accessToken, refreshToken, profile)
// check if user already exists in our own db
User.findOne({ googleId: profile.id }).then(currentUser => {
if (currentUser) {
// already have this user
done(null, currentUser);
} else {
// if not, create user in our db
new User({
googleId: profile.id,
username: profile.displayName,
thumbnail: profile._json.image.url,
firstName: profile.name.givenName,
lastName: profile.name.familyName,
email: profile.emails[0].value,
})
.save()
.then(user => {
console.log("created new user: ", user);
done(null, user);
});
}
});
}
)
);

I figured it out. Just have to replace the "sz-50" with an empty string, when it gets called.
const ImgUrl = profile._json.image.url.replace("?sz=50", "")
// if not, create user in our db
new User({
googleId: profile.id,
username: profile.displayName,
thumbnail: ImgUrl,
firstName: profile.name.givenName,
lastName: profile.name.familyName,
email: profile.emails[0].value,
})

Related

MongoError: E11000 duplicate key error collection when trying to Log In

I logged in with google in my app without problems, I logged out and when logged in again I got this error:
"MongoError: E11000 duplicate key error collection: myAppDB.users index: username_1 dup key: { username: "John Doe" }"
I'm not creating a new user with the same name, I'd just need to log in.
App.js
mongoose.set("useCreateIndex", true);
const userSchema = new mongoose.Schema({
googleId: String,
profileImage: String,
myCollection: {
type: Object,
default: Object
},
games: {
type: Object,
default: Object
}
});
userSchema.plugin(passportLocalMongoose);
userSchema.plugin(findOrCreate);
const User = new mongoose.model("User", userSchema);
passport.use(new GoogleStrategy({
clientID: process.env.CLIENT_ID,
clientSecret: process.env.CLIENT_SECRET,
callbackURL: "http://localhost:3000/auth/google/myApp",
userProfileUrl: "https://www.googleapis.com/oauth2/v3/userinfo",
passReqToCallback: true
},
function(req, accessToken, refreshToken, profile, cb) {
console.log(profile);
User.findOrCreate({
googleId: profile.id,
username: profile.displayName,
profileImage: profile.photos[0].value,
myCollection: catalogDb,
games: {}
},
function(err, user) {
return cb(err, user);
});
}
));
passport.use(User.createStrategy());
passport.serializeUser(function(user, done) {
done(null, user.id);
});
passport.deserializeUser(function(id, done) {
User.findById(id, function(err, user) {
done(err, user);
});
});

ValidatorError: Path `lastName` is required

I'm new at Node.js and really a newbie at MongoDB.
I'm trying to make an authentication system using Google OAuth 2.0 and passport.
I keep getting this error:
Error: User validation failed: lastName: Path `lastName` is required.
Can you help me? I got this code from GitHub and I'm trying to modify it, but this error doesn't let me continue my project.
This is the problematic code:
const mongoose = require('mongoose')
const User = require('../models/User')
module.exports = function (passport) {
passport.use(
new GoogleStrategy(
{
clientID: process.env.GOOGLE_CLIENT_ID,
clientSecret: process.env.GOOGLE_CLIENT_SECRET,
callbackURL: '/auth/google/callback',
},
async (accessToken, refreshToken, profile, done) => {
const newUser = {
googleId: profile.id,
displayName: profile.displayName,
firstName: profile.name.givenName,
lastName: profile.name.familyName,
image: profile.photos[0].value,
}
try {
let user = await User.findOne({ googleId: profile.id })
if (user) {
done(null, user)
} else {
user = await User.create(newUser)
done(null, user)
}
} catch (err) {
console.error(err)
}
}
)
)
passport.serializeUser((user, done) => {
done(null, user.id)
})
passport.deserializeUser((id, done) => {
User.findById(id, (err, user) => done(err, user))
})
}

I am not able to insert facebook account to mongodb

I am trying to sign up my users using facebook using passportjs. I am using mongodb as database and using mongoose to interact with it.
const userSchema = mongoose.Schema({
email: String,
password: String,
googleId: String,
facebookId: String,
secret: [String],
});
const User = mongoose.model("users", userSchema);
This is the schema.
passport.use(new FacebookStrategy({
clientID: process.env.APP_ID,
clientSecret: process.env.APP_SECRET,
callbackURL: process.env.CALLBACK_URL,
profileFields: ['id', 'displayName', 'photos', 'email']
},
function (accessToken, refreshToken, profile, done) {
//check user table for anyone with a facebook ID of profile.id
console.log(profile);
User.findOne({
facebookId: profile.id
}, function (err, user) {
if (err) {
return done(err);
}
//No user was found... so create a new user with values from Facebook (all the profile. stuff)
if (!user) {
user = new User({
name: profile.displayName,
email: profile.emails[0].value,
username: profile.username,
provider: 'facebook',
User.findOne({'facebook.id': profile.id } will match because of this next line
facebook: profile._json
});
user.save(function (err) {
if (err) console.log(err);
return done(err, user);
});
} else {
//found user. Return
return done(err, user);
}
});
}
));
This is the code of facebook strategy. I can sign up succesfully using facebook but I am not able to add the user to my database. I have the same code for my google oauth and it seems to work in google.

Using passport-google-oauth20, trying to create item mongo for picture URL

I'm trying to create an item in a mongoDB table that contains the 'picture' URL from the profile of a google user logging in to my app using passport-google-oauth20.
The following is my schema:
const userSchema = new mongoose.Schema ({
name: String,
picture: String,
googleId: String,
});
The following is the google strategy:
passport.use(new GoogleStrategy({
clientID: process.env.CLIENT_ID,
clientSecret: process.env.CLIENT_SECRET,
callbackURL: "https://localhost:3000/auth/google/secrets",
userProfileURL: "https://www.googleapis.com/oauth2/v3/userinfo"
},
function(accessToken, refreshToken, profile, cb) {
console.log(profile);
console.log(profile._json.picture);
const customerEmail = profile._json.email;
User.findOrCreate(
{ googleId: profile.id },
{ name: profile.displayName },
{ picture: profile._json.picture },
function (err, user) {
return cb(err, user);
});
}
));
in my mongo table it will create items for the 'googleId' and 'name', but will not create an item for 'picture'. and no error messages for this.
however interestingly i can console.log(profile._json.picture); and it does actually log the string (which is a URL - unsure if the fact its a URL has anything to do with this??)
Any idea what I'm doing wrong here? My assumption is that its an issue at the MongoDB side, as the URL string is being returned in the console.log.
Thanks to #Tunmee and his answer on this link.
I was not using the findOrCreate method correctly. I have change my function as follows:
function(accessToken, refreshToken, profile, cb) {
console.log(profile);
var profilePicture = profile._json.picture;
console.log(profilePicture + "inside function");
const customerEmail = profile._json.email;
User.findOrCreate(
{ googleId: profile.id, name: profile.displayName, picture: profile._json.picture },
function (err, user) {
return cb(err, user);
});
Previously the other keys and values that I wanted in my MongoDB documents were passed as the different arguments, rather than just the conditions argument.

Can't get email information from Facebook passport

currently I am working on a project to store information from Facebook Authentication, I already checked Passport-facebook doesn't get email to see the solution, and here is my code
passport.use(new FacebookStrategy(
{
clientID: 'xxxxxxxxxxxxx',
clientSecret: 'xxxxxxxxxxxxxxxx',
callbackURL: 'http://1bc600b4.ngrok.io/auth/facebook/callback',
profileFields: ['id', 'displayName', 'name', 'photos', 'email'],
},
(accessToken, refreshToken, profile, done) => {
console.log(profile);
models.User.findOne({ where: { facebookID: profile.id } }).then((existinguser) => {
if (existinguser) {
// Nothing will happen, the ID already exists
done(null, existinguser);
} else {
models.User.create({
// email: profile.emails[0].value,
username: 'hello',
firstname: profile.name.givenName,
lastname: profile.name.familyName,
facebookID: profile.id,
avatar: `https://graph.facebook.com/${profile.id}/picture?redirect=true&height=470&width=470`,
avatarThumb: profile.photos[0].value,
last_login: Date.now(), }).then(user => done(null, user));
}
});
},
));
app.use(passport.initialize());
app.get('/flogin', passport.authenticate(
'facebook',
passport.authenticate('facebook', { scope: ['profile', 'email'] }),
));
app.get(
'/auth/facebook/callback',
passport.authenticate('facebook', { session: false }),
(req, res) => {
res.send('AUTH WAS GOOD!');
},
);
I don't understand why I use this way and the email information still not show up, which makes me lose a lot of information, can anyone give me a hint on solving this prob? Thank you!
This problem has been there for a while, you need to include email scope and even then it might not send facebook email because of user privacy settings or if the user's email is not verified at the facebook's end.
You could add scope like this:
passport.use(
new FacebookStrategy({
clientID: 'CLIENT_ID',
clientSecret: 'CLIENT_SECRET',
callbackURL: "http://www.example.com/auth/facebook/callback"
passReqToCallback : true,
profileFields: ['emails'] // email should be in the scope.
})
)
Also you would need to add this to your authorize route as well,
app.get('/login/facebook', passport.authorize('facebook', { scope : ['email'] }));
If the emails return, It will be an list of it and you could access them like this:
1. profile.emails // [email1#example.com, somerandomdude#gmail.com]
2. profile.emails[1].value // randomdude#yahoo.com
If it doesn't return, you can use their username or id and create a facebook email atleast temporarily like this:
username#facebook.com // this exists.

Resources