프로그램 자료/Java & Spring
okhttp3 사용해서 RESTful API 호출하기
motolies
2019. 7. 4. 17:02
이번 프로젝트를 하면서 RESTful API 연동을 하게 되었다.
다른 서버의 API를 호출해야하는데,
자바는 어떻게 사용하나 알아보니 okhttp3 를 많이 사용하는 것 같아 그걸로 구현하였다.
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<version>3.13.1</version>
</dependency>
우선 maven을 통해 다음을 추가한다.
일반 java 프로젝트면 해당 파일을 받아서 프로젝트에 추가하면 된다.
메인으로 사용할 helper class를 대략이나마 작성했다.
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.Map;
import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;
import okhttp3.Callback;
import okhttp3.Headers;
import okhttp3.MediaType;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;
public class ApiHelper {
private static OkHttpClient getUnsafeOkHttpClient() {
try {
// Create a trust manager that does not validate certificate chains
final TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager() {
@Override
public void checkClientTrusted(java.security.cert.X509Certificate[] chain, String authType)
throws CertificateException {
}
@Override
public void checkServerTrusted(java.security.cert.X509Certificate[] chain, String authType)
throws CertificateException {
}
@Override
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
} };
// Install the all-trusting trust manager
final SSLContext sslContext = SSLContext.getInstance("SSL");
sslContext.init(null, trustAllCerts, new java.security.SecureRandom());
// Create an ssl socket factory with our all-trusting manager
final SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
return new OkHttpClient.Builder().sslSocketFactory(sslSocketFactory, (X509TrustManager) trustAllCerts[0])
.hostnameVerifier(new HostnameVerifier() {
@Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
}).build();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
public String callGetUnsafe(String requestURL, Map<String, String> headerAttr) {
String rtn = "";
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder().url(requestURL).headers(headerbuild).build();
Response response = client.newCall(request).execute();
rtn = response.body().string();
return rtn;
} catch (Exception e) {
System.err.println(e.toString());
return null;
}
}
public String callGet(String requestURL, Map<String, String> headerAttr) {
String rtn = "";
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = new OkHttpClient();
Request request = new Request.Builder().url(requestURL).headers(headerbuild).build();
Response response = client.newCall(request).execute();
rtn = response.body().string();
return rtn;
} catch (Exception e) {
System.err.println(e.toString());
return null;
}
}
public void callGetUnsafeAsync(String requestURL, Map<String, String> headerAttr, Callback callBack) {
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder().url(requestURL).headers(headerbuild).build();
client.newCall(request).enqueue(callBack);
} catch (Exception e) {
System.err.println(e.toString());
}
}
public void callGetAsync(String requestURL, Map<String, String> headerAttr, Callback callBack) {
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = new OkHttpClient();
Request request = new Request.Builder().url(requestURL).headers(headerbuild).build();
client.newCall(request).enqueue(callBack);
} catch (Exception e) {
System.err.println(e.toString());
}
}
public String callPostUnsafe(String requestURL, Map<String, String> headerAttr, String jsonMessage) {
String rtn = "";
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder().url(requestURL)
.post(RequestBody.create(MediaType.parse("application/json"), jsonMessage)).headers(headerbuild)
.build();
Response response = client.newCall(request).execute();
rtn = response.body().string();
return rtn;
} catch (Exception e) {
System.err.println(e.toString());
return null;
}
}
public String callPostUrlencodedUnsafe(String requestURL, Map<String,String> param) {
String rtn = "";
try {
OkHttpClient client = getUnsafeOkHttpClient();
RequestBody requestBody = makeBuilderFromMap(param)
.build();
Request request = new Request.Builder()
.header("Content-Type", "application/x-www-form-urlencoded")
.url(requestURL)
.post(requestBody)
.build();
Response response = client.newCall(request).execute();
return response.body().string();
} catch (Exception e) {
log.debug(requestURL);
log.debug(e.getMessage(), e);
return null;
}
}
private FormBody.Builder makeBuilderFromMap(final Map<String, String> map) {
FormBody.Builder formBody = new FormBody.Builder();
for (final Map.Entry<String, String> entrySet : map.entrySet()) {
formBody.add(entrySet.getKey(), entrySet.getValue());
}
return formBody;
}
public String callPost(String requestURL, Map<String, String> headerAttr, String jsonMessage) {
String rtn = "";
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = new OkHttpClient();
Request request = new Request.Builder().url(requestURL)
.post(RequestBody.create(MediaType.parse("application/json"), jsonMessage)).headers(headerbuild)
.build();
Response response = client.newCall(request).execute();
rtn = response.body().string();
return rtn;
} catch (Exception e) {
System.err.println(e.toString());
return null;
}
}
public void callPostUnsafeAsync(String requestURL, Map<String, String> headerAttr, String jsonMessage,
Callback callBack) {
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder().url(requestURL)
.post(RequestBody.create(MediaType.parse("application/json"), jsonMessage)).headers(headerbuild)
.build();
client.newCall(request).enqueue(callBack);
} catch (Exception e) {
System.err.println(e.toString());
}
}
public void callPostAsync(String requestURL, Map<String, String> headerAttr, String jsonMessage,
Callback callBack) {
try {
Headers headerbuild = Headers.of(headerAttr);
OkHttpClient client = new OkHttpClient();
Request request = new Request.Builder().url(requestURL)
.post(RequestBody.create(MediaType.parse("application/json"), jsonMessage)).headers(headerbuild)
.build();
client.newCall(request).enqueue(callBack);
} catch (Exception e) {
System.err.println(e.toString());
}
}
}
대충 다음과 같이 쓸면 될 것 같더라.
비동기 같은 경우엔 콜백에 잘 사용해야 할 것 같다.
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.annotation.Commit;
import org.springframework.test.context.junit4.SpringRunner;
import kr.drsoft.nexon.api.ApiHelper;
import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.Response;
@RunWith(SpringRunner.class)
@SpringBootTest
@Commit
public class CallRestApiTest {
@Test
public void get_sync() {
// 동기
ApiHelper api = new ApiHelper();
Map<String, String> head = new HashMap<String, String>();
head.put("Content-Type", "application/json;charset=utf-8");
head.put("Authorization", "token.....");
String rtn = api.callGet("https://localhost/version", head);
System.out.println(rtn);
}
@Test
public void get_async() {
// 비동기
System.out.println("@@@@@start async");
new Thread() {
@Override
public void run() {
ApiHelper api = new ApiHelper();
Map<String, String> head = new HashMap<String, String>();
head.put("Content-Type", "application/json;charset=utf-8");
head.put("Authorization", "token.....");
api.callGetUnsafeAsync("https://localhost/version", head, callback);
}
}.start();
try {
// 새로운 스레드로 테스트하면 callback 호출되기전에 테스트 종료됨...
Thread.sleep(1000 * 999);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
private final Callback callback = new Callback() {
// callback 으로 돌아오면 할일....sample
@Override
public void onFailure(Call call, IOException e) {
System.out.println(e.getStackTrace());
}
@Override
public void onResponse(Call call, Response response) throws IOException {
String rtn = "init";
try {
rtn = response.body().string();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(rtn);
}
};
}