Created
August 12, 2013 15:19
-
-
Save rdmueller/6211786 to your computer and use it in GitHub Desktop.
oAuth2 as Grails Controller
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import grails.converters.JSON | |
class AuthController { | |
def login = { | |
//let's fetch everything which depends on the provider from the config | |
def config = grailsApplication.config.oauth.providers[params.provider] | |
def appKey = config.appKey | |
def secret = config.secret | |
def scope = config.scope | |
def callback = g.createLink(action:'callback',absolute:true) | |
def state = params.provider+":"+new Sha256Hash("3r89sd"+new Date()+Math.random()).toHex() | |
def url = config.url+"&scope=${->scope.encodeAsURL()}&redirect_uri=${->callback.encodeAsURL()}&state=${->state}&client_id=${->appKey.encodeAsURL()}" | |
session.state = state | |
redirect url:url | |
} | |
def callback() { | |
println params | |
//verify cross site forgery | |
if (params.state!=session.state) { | |
throw Exception("something nasty happened...") | |
} | |
def provider = params.state.split(':')[0] | |
def config = grailsApplication.config.oauth.providers[provider] | |
def appKey = config.appKey | |
def secret = config.secret | |
def scope = config.scope | |
def tokenUrl = config.tokenUrl | |
def state = session.state | |
def callback = g.createLink(action:'callback',absolute:true) | |
def tokenQuery = "code=${->params.code.encodeAsURL()}&client_id=${->appKey.encodeAsURL()}&client_secret=${->secret.encodeAsURL()}&redirect_uri=${->callback.encodeAsURL()}&grant_type=authorization_code" | |
def url = new URL(tokenUrl) | |
def connection = url.openConnection() | |
connection.setRequestMethod("POST") | |
connection.doOutput = true | |
def writer = new OutputStreamWriter(connection.outputStream) | |
writer.write(tokenQuery) | |
writer.flush() | |
writer.close() | |
connection.connect() | |
def body = connection.content.text | |
def response = JSON.parse(body) | |
if (response.size()==0) { | |
//for facebook, we get no JSON but URL params | |
body.split('&').inject([:]) {map, kv -> | |
def (key, value) = kv.split('=').toList() | |
if(value != null) { | |
response[key] = URLDecoder.decode(value) | |
} | |
} | |
} | |
def userinfo = config.identityApi+"?access_token=${->response.access_token}" | |
def profile = JSON.parse(new URL(userinfo).text) | |
def name = profile.name | |
def email = profile.email?:profile.emails?.preferred | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment