ionic2, Angular에서 keycloak token 받아오는 법 개발/ionic2, Angular2019. 7. 25. 14:14
최근 회사에서 MSA를 도입하면서 keycloak을 처음 사용하게 되었다.
검색해보면 java에서 keycloak을 사용하는 법은 여러 가지로 많이 나오지만
ionic에서 keycloak을 사용하는 법은 쓸데없이 플러그인을 사용해서 하라고 한다.
나도 처음엔 플러그인으로 해보려 했지만(플러그인으로는 실패하였다) 그보다 간단히 되는 방법을 찾았다.
원래 java 소스였는데 그냥 http 통신하는 거라 ionic에도 쉽게 적용되었다.
이건 ionic-angular http만으로도 작동되지만, 혹시 필요한 사람을 위해 ionic-native http 버전도 함께 공유한다.
import { Component } from '@angular/core';
import { Platform } from 'ionic-angular';
import { Http, RequestOptions, Headers } from '@angular/http';
import { HTTP } from '@ionic-native/http';
@Component({
selector: 'page-home',
templateUrl: 'home.html'
})
export class HomePage {
keycloakConfig = {
url: 'https://your_keycloak_url/auth',
realm: 'your_realm',
client_id: 'your_client_id',
client_secret : 'your_client_secret'
};
constructor(public http: Http,
public n_http: HTTP,
public platform: Platform) {
this.getToken({email : "email@email.com"
pswd : "password!"}).then(res => {
console.log(res);
}).catch(error => {
console.log("Error", error);
});
}
getToken(userData) {
if (this.platform.is('cordova') == false){
return new Promise((resolve, reject) => {
var body = "grant_type=" + "password"+
"&client_id=" + this.keycloakConfig.client_id +
"&username=" + userData.email +
"&password=" + userData.pswd +
"&client_secret=" + this.keycloakConfig.client_secret;
var headers = new Headers();
headers.append('content-type','application/x-www-form-urlencoded');
let options = new RequestOptions({ headers:headers });
this.http.post(this.keycloakConfig.url+'/realms/'+this.keycloakConfig.realm+'/protocol/openid-connect/token', body, options).timeout(5000).subscribe(res => {
resolve(res.json());
}, (err) => {
reject(err);
});
});
} else {
return new Promise((resolve, reject) => {
var body = {grant_type: "password",
client_id: this.keycloakConfig.client_id,
username: userData.email,
password: userData.pswd,
client_secret: this.keycloakConfig.client_secret};
this.n_http.setSSLCertMode('nocheck');
this.n_http.setRequestTimeout(5);
this.n_http.setHeader('*', 'content-type', 'application/x-www-form-urlencoded');
this.n_http.post(this.keycloakConfig.url+'/realms/'+this.keycloakConfig.realm+'/protocol/openid-connect/token', body, {}).then(res =>{
resolve(JSON.parse(res.data));
}).catch(err =>{
reject(err);
});
});
}
}
}
}
이런 식으로 body만 아래 코드로 변경하여 토큰 리프레시도 가능하다.
var body = "grant_type=" + "refresh_token"+
"&client_id=" + this.keycloakConfig.client_id +
"&refresh_token=" + "your_refresh_token" +
"&client_secret=" + this.keycloakConfig.client_secret;
*참고 Java source
String uri = "http://localhost:7080/auth/realms/{RealmName}/protocol/openid-connect/token";
HttpClient client = HttpClientBuilder.create().build();
HttpPost post = new HttpPost(uri);
post.setHeader("User-Agent",
"Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36");
List<BasicNameValuePair> urlParameters = new ArrayList<BasicNameValuePair>();
urlParameters.add(new BasicNameValuePair("grant_type", "password"));
urlParameters.add(new BasicNameValuePair("client_id", {ClientName}));
urlParameters.add(new BasicNameValuePair("username", {UserName}));
urlParameters.add(new BasicNameValuePair("password", {Password}));
post.setEntity(new UrlEncodedFormEntity(urlParameters));
HttpResponse response = client.execute(post);
System.out.println("Response Code : " + response.getStatusLine().getStatusCode());
BufferedReader rd = new BufferedReader(new InputStreamReader(response.getEntity().getContent()));
StringBuffer result = new StringBuffer();
String line1 = "";
while ((line1 = rd.readLine()) != null) {
result.append(line1);
}
System.out.println(result);