네, 화면을 보니 원인은 아주 단순합니다. 휴대폰 문제도 아니고 앱 문제도 아닙니다. 지금 PowerShell이 adb 프로그램 위치를 모르고 있는 상태입니다.

두 번째 사진처럼 Galaxy XXX가 Windows 탐색기에 보이는 것은 USB 연결(MTP)은 정상이라는 뜻입니다. 다만 이것과 ADB 연결은 별개입니다.

Android Studio를 설치하셨으니 ADB도 거의 확실히 설치되어 있을 겁니다. 지금 사용자 이름이 ico15이므로 PowerShell에서 아래 명령을 그대로 복사해서 실행해 보세요.

& "$env:LOCALAPPDATA\Android\Sdk\platform-tools\adb.exe" devices

정상이면 이런 식으로 나옵니다.

List of devices attached
R5XXXXXXXXX    device

처음 연결하는 경우 휴대폰에 "USB 디버깅을 허용하시겠습니까?" 창이 뜰 수 있습니다. 그때 이 컴퓨터에서 항상 허용 → 허용을 누르세요.

만약 이렇게 나온다면:

R5XXXXXXXXX    unauthorized

휴대폰 화면을 켜고 USB 디버깅 허용 창을 승인하면 됩니다.

그다음 앱 튕김 로그 보기

먼저 기존 로그를 지웁니다.

& "$env:LOCALAPPDATA\Android\Sdk\platform-tools\adb.exe" logcat -c

그리고 이것을 실행하세요.

& "$env:LOCALAPPDATA\Android\Sdk\platform-tools\adb.exe" logcat -b crash

이 상태로 PowerShell을 그대로 놔두고 휴대폰에서 문제의 앱을 실행합니다.

앱이 튕기면 PowerShell에 이런 식으로 내용이 나타날 겁니다.

FATAL EXCEPTION: main
Process: com.krdondon.xxxxx

java.lang.RuntimeException: ...

Caused by: java.lang.IllegalStateException: ...
    at com.krdondon.xxxxx.MainActivity.kt:123

그 화면 전체를 캡처해서 저에게 보여주시거나, 글자를 그대로 복사해서 보내주세요. 그러면 어떤 파일의 어느 부분 때문에 갤럭시에서 시작하자마자 튕기는지 같이 찾아볼 수 있습니다.

그리고 매번 긴 경로를 입력하기 귀찮으면 나중에 ADB를 Windows PATH에 등록하면 그냥

adb devices
adb logcat -b crash

처럼 사용할 수 있습니다. 하지만 지금은 PATH 등록하지 않아도 됩니다. 위의 $env:LOCALAPPDATA... 방식으로 먼저 에러부터 잡는 게 가장 빠릅니다.

 


네. 지금 화면을 보니 Android Studio가 이미 Galaxy AXX(SM-XXXX)를 인식하고 있습니다. 그래서 APK를 따로 만들어 옮길 필요 없이 Android Studio에서 바로 설치하는 게 가장 간단합니다.

지금 띄운 Generate Signed App Bundle or APK 창은 일단 Cancel 하셔도 됩니다. 이 창은 배포용/서명 APK를 만들 때 사용하는 쪽입니다.

가장 추천하는 방법: Android Studio에서 바로 설치

상단을 보면 이미 기기가 선택되어 있습니다.

SM-XXXX

따라서:

  1. 지금 창에서 Cancel
  2. 상단 실행 대상이 SM-XXXX인지 확인
  3. 실행 구성이 app인지 확인
  4. 위쪽의 ▶ Run 버튼 클릭

또는 단축키:

Shift + F10

그러면 Android Studio가 자동으로

APK 빌드 → Galaxy AXX에 설치 → 앱 실행

까지 해줍니다.

휴대폰에 USB 디버깅 허용 창이 나오면 허용을 눌러주세요.


지금 목적이 "튕기는 원인 찾기"라면 debug가 좋습니다

현재 보여주신 창에는

debug
release

가 있는데, 에러를 잡는 목적이라면 debug가 적합합니다.

특히 Android Studio에서 직접 ▶ 실행하면 기본적으로 디버그 버전을 설치하기 때문에 Logcat에서

FATAL EXCEPTION
Caused by:
MainActivity.kt:123

같은 정보를 확인하기가 쉽습니다.

Android Studio 아래쪽의 Logcat 창을 열고 앱을 실행해도 됩니다.

View
→ Tool Windows
→ Logcat

Galaxy A35를 선택하고 앱을 실행해서 튕기게 하면 에러가 바로 찍힙니다.


다만 중요한 점이 하나 있습니다.

전에 말씀하신 것처럼 Android Studio에서 실행하면 정상인데, APK로 설치했을 때만 튕기는 것이라면 이야기가 달라집니다.

그 경우에는 오히려 지금 화면에서 release를 선택해서 실제 Release APK를 만들어 테스트해야 합니다. minifyEnabled, R8/ProGuard, 서명, release 전용 설정 때문에 문제가 생기는 경우가 있기 때문입니다.

즉 현재 상황에서는:

① 폰 자체에서 왜 튕기는지 먼저 확인 → Android Studio ▶ Run(debug)
② debug는 정상인데 배포 APK만 튕김 → release APK 테스트

이 순서가 가장 좋습니다.

그리고 사진에 Selected Key key0 아래에 "different key" 경고가 보입니다. 이전 설치본과 다른 서명키를 사용하면 같은 패키지의 앱을 덮어쓸 수 없습니다. 다만 말씀하신 것처럼 기존 앱을 완전히 삭제했다면 새로 설치하는 것은 가능합니다.

우선 지금은 Cancel → 상단 ▶ 버튼을 누르시면 됩니다. 그 상태에서 앱이 튕기면 Android Studio Logcat 화면을 캡처해서 보여주세요. 그게 가장 빠릅니다.

 


네. 이 경우는 원인 범위가 꽤 좁혀집니다.

Android Studio에서 ▶ 실행한 debug 버전은 정상, 그런데 Google Play에서 받은 버전만 시작하자마자 튕긴다면, 휴대폰 호환성보다는 debug와 release(스토어 배포본)의 차이를 먼저 의심해야 합니다.

가장 흔한 원인은 다음 네 가지입니다.

  1. R8 / ProGuard 문제
  2. 앱의 release에서 보통 이런 설정을 사용합니다.
release {
    isMinifyEnabled = true
    isShrinkResources = true
}

R8이 사용되지 않는다고 판단한 클래스나 메서드를 제거했는데 실제 실행 중 reflection, serialization, Compose 관련 코드 등에서 필요하면 release에서만 크래시가 날 수 있습니다.

반면 Android Studio의 기본 Run은 보통:

debug
minify = false

라서 멀쩡하게 실행됩니다.

이 경우가 상당히 유력합니다.


  1. 서명키 차이

아까 올려주신 화면에도 중요한 문구가 있었습니다.

This package name (App ID) is registered by a verified developer with a different key.

Android Studio에서 직접 설치한 앱은 debug key 또는 본인이 선택한 키로 서명됩니다.

Google Play 버전은 Play App Signing 키로 서명될 수 있습니다.

즉:

Android Studio 실행
→ Debug 인증서

직접 만든 Release APK
→ Upload/Release 인증서

Google Play에서 설치
→ Play App Signing 인증서

처럼 인증서가 다를 수 있습니다.

앱 안에 인증서 SHA-1/SHA-256을 기준으로 동작하는 API가 있거나 인증서 검증을 직접 한다면 스토어 버전만 문제가 날 수도 있습니다.

다만 단순히 서명키가 다르다는 것 자체가 앱을 튕기게 하는 것은 아닙니다.


  1. Release에서만 실행되는 코드

코드에 이런 것이 있을 수도 있습니다.

if (BuildConfig.DEBUG) {
    // debug용
} else {
    // release용
}

또는 release 빌드에서만 다른 설정값, API 주소, 파일, 초기화 코드 등이 사용될 수 있습니다.

그래서 첫 화면을 띄우기 전에 release 전용 초기화가 실패하면 바로 종료됩니다.


  1. Google Play의 AAB 설치 방식

Play Store에서는 일반 APK 하나를 그대로 설치하는 것이 아니라 AAB에서 해당 휴대폰용 APK들을 생성해 설치합니다.

예를 들어 Galaxy A35에 맞춰:

base.apk
config.arm64_v8a.apk
config.xxhdpi.apk
config.ko.apk

등으로 나눠질 수 있습니다.

따라서 APK 직접 설치는 정상인데 Play Store 설치본만 문제라면 App Bundle / split APK / native library / resource shrinking 문제도 살펴봐야 합니다.


지금은 이렇게 테스트하는 게 제일 정확합니다

Play Store 버전을 설치한 상태를 그대로 유지하세요.

Android Studio에서 ▶ 버튼으로 다시 설치하면 debug 버전으로 덮어써져서 원인을 놓칠 수 있습니다.

휴대폰을 USB에 연결하고 PowerShell에서:

& "$env:LOCALAPPDATA\Android\Sdk\platform-tools\adb.exe" logcat -c

그다음:

& "$env:LOCALAPPDATA\Android\Sdk\platform-tools\adb.exe" logcat -b crash

이걸 켜놓고 Play Store에서 설치한 문제의 앱을 실행하세요.

튕기면 예를 들어:

FATAL EXCEPTION: main

Process: com.krdondon.week

java.lang.RuntimeException: Unable to start activity

Caused by: java.lang.ClassNotFoundException

또는

Caused by: java.lang.NoSuchMethodError

같은 것이 나올 겁니다.

특히 아래 종류가 나오면 바로 방향을 잡을 수 있습니다.

ClassNotFoundException
NoSuchMethodException
NoSuchMethodError
NullPointerException
SecurityException
Resources$NotFoundException
UnsatisfiedLinkError
IllegalStateException

지금 상황에서는 저는 R8/ProGuard 또는 release 전용 설정을 가장 먼저 확인하겠습니다.

그리고 아주 좋은 비교 실험이 하나 있습니다. 로컬에서 release APK를 만들 때 일시적으로:

release {
    isMinifyEnabled = false
    isShrinkResources = false
}

로 만들어 설치했을 때 정상 실행된다면, 거의 확실하게 R8/ProGuard/리소스 축소 쪽 문제입니다.

하지만 먼저 설정을 바꾸기보다 Play Store 버전 그대로 adb logcat -b crash를 잡는 것이 가장 좋습니다. 로그 화면을 보내주시면 Caused by:를 보고 실제 원인을 바로 좁혀드릴 수 있습니다.

 


네. 원인 확인용으로는 일단 둘 다 꺼보는 게 맞습니다. 그리고 그렇게 해도 앱이 망가지거나 배포가 불가능해지는 것은 아닙니다.

현재:

buildTypes {
    release {
        isMinifyEnabled = true
        isShrinkResources = true
    }
}

를 테스트용으로 이렇게 바꿔보세요.

buildTypes {
    release {
        isMinifyEnabled = false
        isShrinkResources = false
    }
}

역할은 이렇습니다.

  • isMinifyEnabled = true
    • R8이 사용되지 않는 코드 제거
    • 코드 최적화
    • 클래스/메서드 이름 난독화
    • APK/AAB 용량 감소
  • isShrinkResources = true
    • 사용하지 않는 이미지, XML, 문자열 등의 리소스를 제거
    • 역시 앱 용량 감소

예를 들어 코드에서 직접 참조하지 않고 문자열이나 reflection으로 클래스를 찾는 경우:

Class.forName("com.krdondon.week.SomeClass")

R8은 SomeClass가 실제로 사용된다는 걸 못 알아채고 제거할 수 있습니다.

그러면 debug에서는 잘 되는데 release에서:

ClassNotFoundException

이 나면서 튕길 수 있습니다.

리소스도 비슷합니다. 코드에서 동적으로:

resources.getIdentifier(...)

같이 찾으면 R8/리소스 축소기가 실제 사용 여부를 제대로 판단하지 못하는 경우가 있습니다.

꺼도 괜찮나요?

네. 기능적으로는 전혀 문제 없습니다.

대신 단점은:

앱 용량 약간 증가
난독화 안 됨
일부 최적화 안 됨

정도입니다.

일반적인 작은 Android 앱이라면 용량 차이가 몇 MB 수준인 경우도 많아서, 반드시 켜야 하는 옵션은 아닙니다.

특히 지금처럼 release/Play Store 버전만 튕긴다면, 우선 이것부터 꺼보는 것이 아주 좋은 진단 방법입니다.

제가 권하는 테스트 순서는 이겁니다.

release {
    isMinifyEnabled = false
    isShrinkResources = false
}

이 상태로 새로운 AAB를 만들어 내부 테스트나 비공개 테스트로 배포합니다.

그 버전이 Galaxy A35에서 정상 실행된다면:

기존:
minify = true
shrinkResources = true
→ 튕김

변경:
minify = false
shrinkResources = false
→ 정상

이면 R8/ProGuard/리소스 축소 문제가 거의 확실합니다.

그 후에는 계속 꺼놓아도 되고, 앱 크기를 줄이고 싶으면 원인을 찾아 proguard-rules.pro에 필요한 -keep 규칙을 추가한 뒤 다시 켜면 됩니다.

그리고 하나 더 중요한 점이 있습니다. 둘을 동시에 꺼서 정상화되면 어느 쪽이 문제인지 아직 정확히 구분되지 않습니다. 그다음에는 이렇게 하나씩 다시 켜보면 됩니다.

isMinifyEnabled = true
isShrinkResources = false

여기서 다시 튕긴다면 R8 코드 축소/난독화 쪽입니다.

반대로 이건 정상인데:

isMinifyEnabled = true
isShrinkResources = true

에서 튕기면 리소스 축소 쪽도 의심할 수 있습니다.

현재 증상이라면 저는 일단 둘 다 false로 만든 AAB를 한 번 테스트해 보는 것을 권합니다. 가장 빠르게 원인을 절반 이상 좁힐 수 있습니다.

반응형

+ Recent posts