Skip to content

Instantly share code, notes, and snippets.

@khaledosman
Created August 30, 2018 10:13
Show Gist options
  • Save khaledosman/7fc6cb27f6b968cbb58a6f14da10819a to your computer and use it in GitHub Desktop.
Save khaledosman/7fc6cb27f6b968cbb58a6f14da10819a to your computer and use it in GitHub Desktop.
PubNub functions implementation of Google OAUTH2 w/ Authorization code flow
// https://developers.google.com/actions/identity/oauth2?oauth=code
const kvstore = require('kvstore')
const base64 = require('codec/base64')
const GOOGLE_CLIENT_ID = 'google-client-id'
export default (request, response) => {
let headersObject = request.headers
let bodyString = request.body
let paramsObject = request.params
let methodString = request.method
console.log('params', paramsObject)
const { client_id: clientId, client_secret: clientSecret, grant_type: grantType, code: authorizationCode, refresh_token: refreshToken } = paramsObject
// Query parameters passed are parsed into the request.params object for you
// Set the status code - by default it would return 200
// Set the headers the way you like
response.status = 200
if (grantType === 'authorization_code') {
return kvstore.get(authorizationCode)
.then(authorizationCodeBody => {
authorizationCodeBody = JSON.parse(base64.atob(authorizationCode))
console.log('authcodeBody', authorizationCodeBody)
if (authorizationCodeBody && Date.now() < authorizationCodeBody.expiresAt && clientId === authorizationCodeBody.clientId) {
const encryptedEmail = authorizationCodeBody.encryptedEmail
const refreshTokenBody = JSON.stringify({
type: 'REFRESH_TOKEN',
encryptedEmail,
clientId: GOOGLE_CLIENT_ID,
expiresAt: null
})
const accessTokenBody = JSON.stringify({
type: 'ACCESS_TOKEN',
encryptedEmail,
GOOGLE_CLIENT_ID,
expiresAt: new Date().setHours(new Date().getHours() + 2)
})
const refreshToken = base64.btoa(refreshTokenBody)
const accessToken = base64.btoa(accessTokenBody)
return Promise.all([kvstore.set(refreshToken, refreshTokenBody), kvstore.set(accessToken, accessTokenBody)])
.then(() => {
return response.send(
{
'token_type': 'Bearer',
'access_token': accessToken,
'refresh_token': refreshToken,
'expires_in': (JSON.parse(accessTokenBody).expiresAt - Date.now()) / 1000
}
)
})
} else {
console.log('authCodeBody', authorizationCodeBody, 'clientId', clientId, 'actualId', authorizationCodeBody.clientId, Date.now() < authorizationCodeBody.expiresAt)
response.status = 400
return response.send({'error': 'invalid_grant'})
}
})
} else if (grantType === 'refresh_token') {
return kvstore.get(refreshToken)
.then(refreshTokenBody => {
refreshTokenBody = JSON.parse(base64.atob(refreshTokenBody))
if (refreshTokenBody.type === 'REFRESH_TOKEN' && clientId === refreshTokenBody.clientId) {
const encryptedEmail = refreshTokenBody.encryptedEmail
const accessTokenBody = JSON.stringify({
type: 'ACCESS_TOKEN',
encryptedEmail,
clientId: GOOGLE_CLIENT_ID,
expiresAt: new Date().setHours(new Date().getHours() + 2)
})
const accessToken = base64.btoa(accessTokenBody)
return kvstore.set(accessToken, accessTokenBody)
.then(() => {
return response.send({
'token_type': 'Bearer',
'access_token': accessToken,
'expires_in': (JSON.parse(accessTokenBody).expiresAt - Date.now()) / 1000
})
})
} else {
response.status = 400
console.log('refreshTokenBody', refreshTokenBody, 'clientId', clientId, 'actualId', refreshTokenBody.clientId, Date.now() < refreshTokenBody.expiresAt)
return response.send({'error': 'invalid_grant'})
}
})
} else {
response.status = 400
return response.send('unknown grant_type')
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment