#7 Android MVVM Architecture Tutorial – Handling API Exceptions

여러분 안녕하세요! 이것은 Belal Khan이고 당신은 Simplified Coding을보고 있습니다 모든 것이 당신 편에 있기를 바랍니다

이 비디오를 진행하기 전에이 비디오를 일시 중지하고 앱 아래에 댓글을 달아주십시오 지금까지 일하고 있습니다 이 비디오에서는 API 호출 코드를 약간 변경합니다 잘 작동하지만 전화를 좀 더 추상적으로 만들고 싶습니다 또한 한 곳에서 오류를 처리하고 싶습니다

보시다시피 UserRepository 내에 userLogin이 있습니다 그리고 그것은 우리에게 AuthResponse 유형의 응답을 제공하지만 ViewModel에 대해 걱정하고 싶지 않습니다 확인해야 할 때마다 ViewModel에서 응답을 얻는 것처럼 응답 responseisSuccessful 한 곳에서이 작업을하고 싶습니다

이를 위해 API 요청을 수행하는 일반 함수를 작성해야합니다 응답을 반환합니다 따라서이 일반 함수에서 Response 유형의 Response를 직접 얻을 수 있습니다 이 경우에는 AuthResponse가 있습니다 따라서 네트워크 패키지 안에 클래스를 하나 더 만듭니다

여기서 오류를 처리하므로이 클래스의 이름을 SafeApiRequest로 지정하십시오 SafeApiRequest 파일이 있습니다이 파일 안에 추상 클래스를 만들겠습니다 SafeApiRequest 와이 클래스 내에서 또 다른 일시 중단 일시 중단 기능을 만들 것입니다 네트워크 작업을 수행하려고하며 비동기 작업입니다

비동기 작업에는 일시 중단을 사용합니다 그래서 우리는 재미를 중단했고이 함수는 일반적인 함수이므로 여기서 정의하겠습니다 Any 유형의 T 이 함수는 api를 수행하기 때문에이 함수의 이름을 apiRequest로 지정합니다 의뢰 이 함수는 T를 반환합니다

이제이 함수로 API 호출을 전달하고 이 호출은 또 다른 일시 중단 기능입니다 따라서 매개 변수가없는 일시 중단 기능이 있으며이 함수는 응답을 반환합니다 T 형으로 끝났습니다 이제이 함수 apiRequest 내에서 호출을 호출하고 응답을 얻습니다 따라서 val 응답은 call

invoke ()와 같습니다 이제 API 호출의 응답이 있으며 응답이 성공적인지 확인할 수 있습니다 responsebody를 반환하고 null이 아닌지 확인하십시오 응답이 성공하면 응답 본문이 있기 때문입니다 응답이 성공하지 못한 경우 오류를 처리하므로 먼저 응답 오류 본문에서 오류가 발생했습니다

val error = responseerrorBody ()가 있습니다 따라서 응답이 성공하지 못하면 본문을 얻을 수 없지만 errorBody () errorBody ()에서 문자열을 가져 오므로 오류에 응답이 무엇이든간에 그 문자열 형식을 가져옵니다 먼저 API를 보여 드리겠습니다 우린 POSTMAN이 있습니다

따라서 로그인 시도가 잘못되면 상태 코드가 401이며 401과 같은 응답 코드는 오류이므로 다른 것으로 들어갑니다 블록 else 블록 안에서 JSON 문자열 인이 문자열을 얻습니다 따라서 API 코드에서 정의한 오류 응답을 얻는 경우 좋아, JSON 응답을 구문 분석 할 수 있지만 때로는 404와 같은 오류가 발생할 수 있습니다 API를 찾을 수 없거나 호스트가 작동하지 않으므로 JSON을 얻지 못합니다

응답 본문 그러나 JSON의 유효성을 검사하기 전에이 오류가 null이 아닌지 확인해야합니다 그래서 우리는 error?let을 확인 하고이 let 블록 안에서이 오류를 변환 할 것입니다 JSON 객체에 대한 문자열입니다

그러나 오류 응답에 JSON 객체가있는 경우에만 JSON 객체로 변환 할 수 있습니다 따라서 API 에서이 오류를 코딩하면 JSON 응답, JSON 오류 응답이 있지만 오류가 다른 경우 API Not과 같은 JSOn 응답을 얻지 못합니다 찾거나 호스트가 작동하지 않습니다 따라서 JSON 공명을 변환하기 위해 시도하고 잡아야합니다 문자열을 확인하는 것은 JSON 객체로 변환 가능 여부입니다

내부에서 문자열을 JSON 객체로 변환하면 오류 메시지가 나타납니다 내 API를 디자인 할 때 오류 응답의 경우 항상이 메시지 키가 있습니다 오류 메시지를 포함합니다 그래서 당신은 또한 내 API를 사용하고 있으므로이 경우 아무런 문제가 없습니다 그러나 애플리케이션에서 작업 할 때 이에 따라 API를 설계해야합니다

여기이 문자열에있는 JSON 객체에서 오류 메시지가 나타납니다 또는이 문자열에있을 수도 있습니다 JSONObject를 작성하고 전달한 다음이 JSONObject에서 문자열이며 메시지입니다 따라서 오류 응답에 JSON 응답이 있으면 메시지가 표시되지만 오류 응답에 json 응답이 없으므로이 catch 블록 안에 들어갑니다 하지만이 캐치 블록 안에서는 아무것도하지 않습니다

catch 블록 우리는 오류 코드 인 응답 코드 만 표시하지만 오류가있을 때 표시 할 메시지가 표시됩니다 여기서 내가 할 일은 StringBuilder를 만들어서 이 StringBuilder 이제이 메시지를 작성하는 대신 여기에 messageappend를 작성할 수 있습니다 우리가 가진 오류 메시지

잘라서 붙여 넣습니다 그래서 우리는이 StringBuilder 안에 오류 메시지를 가지고 있습니다 내 메시지에 새로운 줄 새로운 줄을 추가해 봅시다 그리고이 let 블록 다음에 메시지 StringBuilder에 오류 코드를 추가합니다

그래서 여기에 messageappend를 작성하고 오류 코드를 추가하고 이 응답 객체의 오류 코드 여기에 $ {responsecode ()} 응답을 작성하겠습니다 우리는 메시지를 받았습니다 첫 번째 줄에는 오류 메시지가 있고 두 번째 줄에는 에러 코드

그런 다음 우리는 예외를 던질 것입니다 API 예외를 처리하기 위해 사용자 정의 클래스 ApiException을 만듭니다 이 프로젝트에서 원하는 모든 사용자 정의 예외는 유틸리티 패키지 여기에 새로운 kotlin 파일을 만들어 보도록하겠습니다 그리고이 파일 안에 모든 클래스를 만들 것입니다

우리가 원하는 첫 번째 클래스는 ApiException이며이 클래스는 문자열 유형의 메시지를받습니다 생성자 매개 변수로 사용하면 IOException이 상속됩니다 그리고 우리는 메시지를 IOException에 전달할 것입니다 이제 SafeApiRequest로 돌아와서 여기서 ApiException을 발생시킵니다 따라서 throw ApiException ()을 작성하고 message

toString ()을 전달합니다 메시지를 보내면이 메시지를 문자열로 변환합니다 따라서 오류가 발생하면 ApiException이 발생합니다 이제 일반 함수가 준비되었으며이 함수를 사용하여 API를 수행합니다 의뢰

따라서 UserRepository 클래스에 들어가면이 클래스는 SafeApiRequest를 확장합니다 이제 여기에서 만든이 함수를 사용할 수 있습니다 API를 수행하기위한 apiRequest입니다 UserRepository 클래스 내부에서 요청하십시오 그래서 내가 할 일은 여기에 apiRequest를 반환 하고이 apiRequest 안에 MyApi ()를 호출 한 다음 userLogin 및 이메일 비밀번호를 입력하십시오

이제 반환 유형을 AuthResponse로 변경할 수 있습니다 이제 함수가 AuthResponse를 직접 반환하므로 AuthViewModel로 돌아와서 여기서 AuthResponse를 직접받습니다 val authResponse = UserRepository () userLogin ()과 같이하겠습니다 이메일과 비밀번호도 마찬가지입니다

실제로 authResponse와 동일한 줄을 작성했지만 여기서는 응답이 성공적인지 확인하지만이 authResponse를 try 및 잡기 그리고 우리는 ApiException을 잡아야합니다 우리는 ApiException 타입의 e를 가지고 있습니다 이제 오류가 발생하면 authListener? onFailure ()를 호출하고 전달합니다

이 예외 인스턴스에서 가져올 메시지 emessage를 전달할 수 있습니다 그리고 null이 아닌지 확인할 수 있습니다 authResponse가있는 경우 authListener? onSuccess ()를 호출하면 authResponse의 사용자이므로 authResponse

user를 작성하면됩니다 null이므로 여기에 authResponse? user를 작성하고 사용자가 null이 아니다 사용자가 null이 아닌 경우 onSuccess를 호출하고 전달합니다 null이 아니다 사용자가 null 인 경우 다시 onFailure ()를 호출하여 메시지를 얻을 수 있습니다 authResponse에서 authResponse

message !!를 작성합니다 이 성공 후에는 return을 호출하여이 행을 실행하지 않습니다 성공하면 끝입니다 나는 그것이 작동해야한다고 생각하므로 응용 프로그램을 실행 해 봅시다 빈 값을 입력하면 유효하지 않은 이메일 또는 비밀번호가 표시됩니다

올바른 값을 입력하면 "Belal Khan이 로그인되었습니다"라는 메시지가 나타납니다 그래서 그것은 절대적으로 잘 작동합니다 오류가있는 경우이 작업도 시도해보십시오 잘못된 이메일 또는 비밀번호, 오류 코드 401이 표시됩니다 그래서 그것은 절대적으로 잘 작동합니다

그러나이 토스트 대신 스낵바를 표시하고 싶습니다 레이아웃 파일에서 볼 수 있듯이 coordinator_layout을 사용했습니다 coordinator_layout입니다 토스트 대신 스낵바를 사용하고 싶기 때문에이 레이아웃을 사용합니다 그리고 다시 스낵바를 위해 하나 이상의 확장 기능을 만들 것이므로 ViewUtils에 들어 오십시오

여기에서는 View의 확장 기능을 만듭니다 그래서 재미있는 Viewsnackbar를 작성 하고이 함수는 우리가 원하는 메시지를 가져옵니다 이 스낵바 안에 표시합니다 그리고 여기에 snackbar

make를 작성할 수 있으며 그것이 취하는 첫 번째 매개 변수는 View입니다 이 함수는 View의 확장이기 때문에 여기에 View가 있으므로 간단히 전달할 수 있습니다 여기 요 그런 다음 두 번째 매개 변수에 대해 표시하려는 메시지와 세 번째 매개 변수는 스낵바의 길이를 가지므로 스낵바를 갖습니다 그리고 나는 또한 쓸 것이다 그리고 이것은 또한 우리에게 스낵바를 줄 것이다 이제이 스낵바에 다음과 같이 조치를 설정하여 snackbar

setAction 및 버튼 이름을 Ok로 지정하고 클릭 기능 내부에 있습니다 이 함수 내에서 실제로 람다, 또는 람다 나는 스낵바를 닫을 것입니다 그래서 snackbardissmiss ()를 작성하고 마지막으로이 중괄호 뒤에 스낵바를 표시하려면 show () 토스트 대신에이 스낵바를 사용할 수 있지만이 스낵바를 사용하는 것은 매우 쉽습니다

coordinator_layout이 필요합니다이 coordinator_layout에 root_layout 인 id입니다 그래서 이것을 사용할 수 있으므로 LoginActivity로 돌아와서 토스트 대신 root_layoutsnackbar를 작성합니다 그런 다음 표시하려는 것과 동일한 문자열을 전달합니다

이제 토스트를 삭제하면 어디에서나 같은 것을 사용할 수 있습니다 따라서 실패의 경우 실패 메시지를 표시하고 양호합니다 따라서 응용 프로그램을 다시 실행하면 이번에는 스낵바가 표시됩니다 스낵바가 작동하는 것을 볼 수 있습니다 이제 잘못된 비밀번호를 입력하십시오

그리고 잘 작동하고 있습니다 토스트보다 낫다고 생각합니다 이 비디오 친구를위한 모든 것입니다이 강의를 즐기 셨으면 좋겠습니다 네 편이야 문제가있는 경우 아래 의견에 알려주십시오

이 비디오를 좋아하고 친구들에게 공유하십시오 이것이 지금 Signing Off 인 Belal Khan입니다