본문 바로가기

OnePIC (Android App)/사진 편집 기능

[객체 감지] 공공 AI API 이용해서 객체 감지

반응형

OnePIC을 만들면서 필자가 겪었던 어려움들과 깨달음들에 대해서 포스팅 해보려고 한다.
 
이번 포스팅은 결국 사용하지 못하였지만(안하였지만),
처음 객체 감지를 도전했던 공공 AI API를 사용방법과 실패했던 부분에 대해 이야기하려고 한다.

 
 https://aiopen.etri.re.kr/guide/od

AI API/DATA

이미지에서 사람, 자동차 등 일반적으로 나타나는 다양한 종류의 객체 카테고리를 분류하고 객체의 위치정보(박스 좌표)를 감지할 수 있는 기술로 활용됩니다. 영상 데이터에서 다양한 형태의

aiopen.etri.re.kr


JAVA 초기 설정

 

1. gson.Gson 라이브러리 추가

  • 'gson.Gson' jar 다운로드 → 라이브러리 추가 (JAVA)

Maven Central: com.google.code.gson:gson:2.8.7

Discover gson in the com.google.code.gson namespace. Explore metadata, contributors, the Maven POM file, and more.

central.sonatype.com

 

  • Graddle에 'gson.Gson' 추가 (안드로이드)
dependencies {  
	implementation 'com.google.code.gson:gson:2.8.7'
}

 


 
앞서 말한 gson.Gson 라이브러리만 추가하고, 위에 공공 AI API 공식문서에서 제공해준 JAVA 코드를 사용한다면 문제 없이 객체 인식 결과를 받을 수 있을 줄 알았으나, 문제가 발생했고,,, 열심히 해결했다.
하지만 또 이를 안드로이드로 구현하려고 하니 몇가지 문제가 발생하였다. 

내가 겪었던 몇가지 문제에 대해 설명하려고 한다.

 

문제 1 : InputStream 받을 때 error 발생 

 

 InputStream is = con.getInputStream();

 
 
해당 코드에서 error 발생 → 왜일지 열심히 고민해본 결과 2가지 예상 문제는 다음과 같다.
 

1. API가 문제인가? (제한 시도횟수가 넘었나?)

→ API 문제인지 확인을 위해 python 코드로 실행해본 결과 매우 잘 된다. (문제 아님)

 
2. 요청 header, body가 문제인 것인가?

→ JAVA Request는 안되고 Python Request는 되니 두 Request의 header, body를 비교해봤다.
 
 공식 요청 메시지 예 

[HTTP Request Header]
"Authorization" : "YOUR_ACCESS_KEY"

[HTTP Request Body]
{
    "argument": {
        "file": "YOUR_file",
        "type": "YOUR_type"
    }
}

 
 JAVA Request 메시지 

[Header]
"Authorization" : "YOUR_ACCESS_KEY"

[Body]
"argument": {
    "file": "YOUR_file",
    "type": "YOUR_type"
 }

 
 Python Request 메시지 

[Header]
"Authorization" : "YOUR_ACCESS_KEY",
"Content-Type": "application/json; charset=UTF-8" 

[Body]
"argument": {
    "file": "YOUR_file",
    "type": "YOUR_type"
 }

 
JAVA와 Python Reqeust를 비교해보니 다 똑같지만, Header에 Content-Type 설정이 JAVA 코드에는 없었다.
 
→ 해당 부분을 JAVA 코드에 추가하니 JAVA로도 정상적으로 실행되었다.

아니 예전에는 분명 없었는데, 지금 확인해보니 위에 공식 문서 JAVA 코드에 Header에 Content-Type 설정 추가되어 있네..ㅜ

 
 

문제 2 : image Path 문제 

 
JAVA 코드를 확인하면 image path를 입력해서 이미지를 전달한다. 이를 안드로이드로 코드 변환 없이 가져오면 문제가 발생했다.
이 때는 필자가 안드로이드에서 이미지 path 관련해서 잘 알지 못해서 애를 많이 썼다.
 
찾아본 결과 한가지 사실을 알게 되었다.
안드로이드는 Path가 컴퓨터 Path가 아닌 해당 에뮬레이터/디바이스에서 Path를 나타낸다는 것이다.
 

즉, 다른 방법으로 이미지를 얻어와야 한다.

 
방법 1 : drawable 이미지를 bitmap으로 변환

Bitmap bitmap = BitmapFactory.decodeResource(this.getResources(), R.drawble.image);

 
방법 2 : Bitmap을 byteArray로 변환

Bitmap bitmap = BitmapFactory.decodeResource(this.getResources(), R.drawble.image);

ByteArrayOutputStream stream = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, stream);
byte [] imageBytes = stream.toByteArray();

 
 

문제 3 : 안드로이드로 실행시 response를 받지만, 여전히 body에 result가 없다.

 

InputStream is = con.getInputStream();

 
response를 받은 후 위 InputStream 제작 코드에서 디버깅해보니, JAVA에서 돌릴 때와는 다른 점 발견했다.
 

함수명안드로이드 response 결과JAVA response 결과
con.getResponseCode()200200
con.responseCode-1200
con.getResponseMessage()"OK""OK"
con.responseMessagenull"OK"

 
 
하지만 이 문제는 필자가 해결할 수 있는 부분이 아닌 것 같다. 
왜냐하면 API 전달 결과가 예상과 다른거라 방법이 없다고 판단했고, 해당 문제로 공공 API 이용을 포기했다.

반응형