<repo_name>MikeQin/ninja-oauth<file_sep>/app.js
const express = require('express');
const authRoutes = require('./routes/auth-routes');
const profileRoutes = require('./routes/profile-routes');
const passportSetup = require('./config/passport-setup');
const mongoose = require('mongoose');
const { mongodb, session } = require('./config/keys');
const cookieSession = require('cookie-session');
const passport = require('passport');

const app = express();

// set view engine
app.set('view engine', 'ejs');

// use cookie
app.use(cookieSession({
  maxAge: 24 * 60 * 60 * 1000,
  keys: [session.cookieKey] // for example: 'my_secret_sessionKey'
}));

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

// body-parser
//app.use(express.json());
// Error Handler Middleware
app.use((err, req, res, next) => {
  if (err) {
    console.log(err);
    res.status(422).send({ code: err.code, error: err.errmsg });
  }
});

// set up routes
app.use('/auth', authRoutes);
app.use('/profile', profileRoutes);

// create home route
app.get('/', (req, res) => {
  res.render('home', { user: req.user });
});

// connnect to mongodb
mongoose.connect(mongodb.dbURI, {
  useNewUrlParser: true,
  useFindAndModify: false,
  useCreateIndex: true,
  authSource: "admin"
},
  (error, db) => {
    console.log('connected to mongodb...');
    if (error) console.log(error);
  }
);
mongoose.Promise = global.Promise;

const port = process.env.PORT || 3000;
app.listen(port, () => {
  console.log('app now listening for request on port ' + port);
});<file_sep>/README.md
# Node OAuth 2.0 Tutorial

### Install
```
npm install ejs express

npm install passport passport-google-oauth20

npm install mongoose

npm install cookie-session
```

### To Run
`npm start`

### The OAuth 2.0 Authorization Code Flow

Authentication with Goole+:

  1. User authenticates with Google (username, password), and Google returns auth_code
  2. Browser sends auth_code, Node Server then sends (auth_code, clientId, clientSecret) 
     and {scope: ['profile']} to google
  3. Google validates (auth_code, clientId, clientSecret), then returns access_token, and profile in callback
  4. Google redirects the request to redirect_url

### Google Cloud Platform (Developer APIs)

Configure your OAuth Client Credentials
https://console.cloud.google.com

### MongoDB

Install MongoDB in Ubuntu (Virtual Box) or use [mLab](https://mlab.com/)<file_sep>/config/passport-setup.js
const passport = require('passport');
const GoogleStrategy = require('passport-google-oauth20/');
const { google } = require('./keys');
const User = require('../models/user');

passport.serializeUser((user, done) => {
  console.log('passport.serializeUser...');
  console.log("user.id", user.id);
  console.log("user._id", user._id);
  done(null, user.id);
});

passport.deserializeUser((id, done) => {
  console.log('passport.deserializeUser...');
  User.findById(id).then((user) => {
    console.log('user from cookie', user);
    done(null, user);
  }).catch(err => {
    console.log(err);
  })
});

passport.use(new GoogleStrategy({
  // options for the google strategy
  callbackURL: '/auth/google/redirect',
  clientID: google.clientID,
  clientSecret: google.clientSecret
}, (accessToken, refreshToken, profile, done) => {
  // passport callback
  console.log("passport callback fired...");
  console.log('accessToken', accessToken);
  console.log('profile', profile);

  User.findOne({ userId: profile.id }).then((currentUser) => {
    if (currentUser) {
      // already have the user
      console.log('[*] current user', currentUser);
      done(null, currentUser);
    }
    else {
      // create a new user
      User.create({
        userName: profile.displayName,
        userId: profile.id,
        thumbnail: profile._json.picture
      }).then((user) => {
        console.log('[*] new user created', user);
        done(null, user);
      }).catch((error) => {
        console.log(error);
      });
    }
  })


})
);