본문 바로가기

공부/유니티

[Unity] HTTP 접속 오류 해결 방법

상황

구글 애드몹 UMP(GDPR 개인정보 동의 팝업)를 연동하거나 앱 내 웹뷰(WebView)를 통해 특정 웹페이지를 띄우려고 할 때, 화면이 정상적으로 출력되지 않고 새하얗게 변하면서 ERR_CLEARTEXT_NOT_PERMITTED 에러가 발생하는 경우가 있다.

나의 경우, 예전에 만들어둔 애드몹 GDPR 설정 때문인지 세팅을 정상적으로 마쳤음에도 불구하고 링크가 HTTP로 강제 연결되는 현상이 있었다. 이로 인해 갤럭시 스토어 심사에서 "개인정보 팝업이 제대로 나오지 않는다"며 리젝트를 당했고, 수정 후 다시 올려달라는 요청을 받아 삽질하며 해결한 과정을 정리해 본다.


원인

안드로이드 9.0(API 28)부터는 보안 강화를 위해 암호화되지 않은 HTTP(일반 텍스트) 통신을 기본적으로 원천 차단하고 HTTPS만 허용한다. 따라서 애드몹 캐시나 연동 문제로 인해 주소가 http://로 호출되면, OS 보안망에 걸려 앱 내에서 페이지가 강제로 막히는 것이다.

이를 해결하려고 구글링을 해보면 AndroidManifest.xml에 android:usesCleartextTraffic="true" 속성을 넣으라는 글이 많다. 하지만 이는 앱의 모든 HTTP 통신을 무방비로 허용하는 설정이라, 스토어 보안 검수에서 또 다른 기각 사유가 된다.


해결 방법

가장 안전하고 확실한 방법은 앱의 모든 통신을 여는 것이 아니라, 내가 사용하는 특정 사이트의 도메인만 콕 집어 예외적으로 HTTP 통신을 허용하는 네트워크 보안 설정을 적용하는 것이다.

참고로 최신 유니티 버전에서는 Assets/Plugins/Android/res 폴더에 xml 리소스를 생으로 넣으면 빌드 에러

(OBSOLETE - Providing Android resources...)가 발생한다. 따라서 반드시 아래처럼 .androidlib(안드로이드 라이브러리) 구조로 폴더를 만들어 배치해야 한다.

 

1. 프로젝트 내에 폴더 및 파일 구성하기

유니티 Assets/Plugins/Android/ 경로 아래에 다음과 같이 폴더 구조를 만든다. (폴더명 뒤에 .androidlib를 반드시 붙여야 유니티가 정상적인 라이브러리로 인식한다.)

Assets/
└── Plugins/
    └── Android/
        ├── AndroidManifest.xml (기존에 사용 중인 메인 Manifest)
        └── MyCustomResources.androidlib/
            ├── AndroidManifest.xml (라이브러리 선언용 가짜 Manifest)
            └── res/
                └── xml/
                    └── network_security_config.xml (도메인 예외 설정 XML)

 

2. 각 파일 코드 작성하기

[MyCustomResources.androidlib / AndroidManifest.xml]
유니티 빌드 시스템을 통과하기 위해 필요한 껍데기용(가짜) Manifest 파일이다.

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
          package="com.company.customresources">
    <application>
    </application>
</manifest>

[MyCustomResources.androidlib / res / xml / network_security_config.xml]
허용할 도메인 주소를 적어준다.

<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
    <domain-config cleartextTrafficPermitted="true">
        <!-- includeSubdomains="true"를 설정하면 서브 도메인까지 전부 포함된다 -->
        <domain includeSubdomains="true">domain.com</domain>
    </domain-config>
</network-security-config>

 

※ 주의: <domain> 태그 안에는 http://... 같은 전체 URL이나 쿼리스트링을 다 적으면 안 되고, 오직 서버의 이름(도메인명)만 적어야 안드로이드 시스템이 제대로 인식한다.

 

3. 메인 AndroidManifest.xml에 연결하기

마지막으로 기존에 쓰던 메인 AndroidManifest.xml 파일을 열고, <application> 태그 시작 부분에 방금 만든 설정을 연결하는 속성을 딱 한 줄만 추가해 준다.

<application 
    android:label="@string/app_name" 
    android:icon="@drawable/app_icon"
    android:networkSecurityConfig="@xml/network_security_config">

 

이렇게 세팅 후 빌드하면, 애드몹 동의 캐시가 꼬여 http:// 주소로 열리더라도 안드로이드 OS가 차단하지 않고 깨끗하게 페이지를 열어준다. 전체 허용 옵션을 쓰지 않았기 때문에 스토어 보안 심사도 아주 안전하게 프리패스할 수 있다.