Things take time

[Android] Webview 사용 시 History back이 안되는 문제 본문

Android(Error)

[Android] Webview 사용 시 History back이 안되는 문제

겸손할 겸 2017. 12. 18. 14:21

[상황]


여태까지 잘만 사용하던 하이브리드앱에서 history.back()을 해도 뒷 페이지로 이동되지 않는 문제가 발생했다. 그로 인해 백버튼을 감지하하여 사용하던 webview.back()도 당연히 되지 않는 상황

즉, 웹페이지내의 history가 쌓이지 않는 문제였다.



[원인]


결과적으로는 시스템 웹뷰라는 앱 때문이다. 일단 안드로이드 폰은 시스템 웹뷰라는 앱이 기본적을 설치되어 있다.

마시멜로이하의 버전은 설정 -> 앱 -> 모든 앱 보기(혹은 시스템 앱 보기, 전체 앱 보기 등)에서 확인할 수 있고, 누가이상의 버전에서는 크롬앱 안에 시스템 웹뷰가 내장, 연결되어 있다고 한다.


이 앱들을 업데이트 삭제하거나, 삭제해버리면 되긴 한다. 시스템 웹뷰가 버전업이 되면서 점점 기능이 진화되면서 웹뷰를 체크하는 로직에서 나타나는 문제로 보인다.


버그이다라고도 토론되는 내용이더라.

https://developers.google.com/web/updates/2017/12/nic63



[해결]


나같은 경우 웹뷰에서 사용하는 WebViewClient의 shouldOverrideUrlLoading에서 해결했다.


마시멜로 이하

@Override public boolean shouldOverrideUrlLoading(WebView view, String url) { if (view.canGoBack()) { view.loadUrl(url); return true; } return false; }

누가 이상

@TargetApi(Build.VERSION_CODES.N) @Override public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {

if (request.isRedirect()){ view.loadUrl(url); return true; } return false; }

여기서 shouldOverrideUrlLoading의 리턴값인 Bool의 의미를 먼저 알아야한다.


공식 홈페이지에서 가져온 도큐먼트다.


기본적으로 페이지가 이동될 때마다 호출되는 함수이며 간략하게 설명하면, 만약 웹뷰 클라이언트를 웹뷰에 따로 할당하지 않으면 기본적으로 액티비티 매니저가 url에 따른 핸들러를 자기가 알아서 해준다. 웹뷰에 할당하게 되면 false는 디폴트와 같이 현재 설정된 웹뷰(안드로이드 내장 시스템 웹뷰를 의미함)에서 핸들러의 역할을 수행하고, true의 경우에는 호스트, 즉 개발자가 설정한 코드에 따라 하겠다는 것이다.


그리고 loadUrl을 사용할 거면 그 이후에 return true를 하라 뭐 이런 뜻인데.. 어쨌든 그 결과값에 주목하면 된다.



이전 버전의 경우에는 위의 소스에서 isRedirect()로 들어왔다. 그래서 내가 원하는 url로 이동하게 하고 true를 리턴하면 됐는데, 이제는 저 request.isRedirect()가 false로 나오게 된다. 그래서 저 소스로 돌지 않고 리턴값을 정해야하는데, 나같은 경우 이전에는 저 마지막 return false가 return true로 되어있었다. 어차피 request.isRedirect()가 항상 true로 왔기 때문에(결제 앱을 키거나 하지 않는 한), 저 밑에 있는 리턴값이 중요하지 않았다.


그러나 이제 저 조건문이 돌지 않고 있기때문에, 아무런 조건에 만족하지 않을 때 리턴하는 값을 false로 넘겨서, 기본 시스템웹뷰에게 권한을 위임하는 것이다. 그렇게 되면 히스토리가 쌓이지 않는 문제도 웹뷰가 알아서 잡는듯.. 그래서 webView.canGoBack()도 false만 뜨다 true로 뜨게 된다.


개인적으로는 나중에 고쳐지지 않을까 싶다.

이렇게 되면 개발자가 직접 loadUrl()함수를 쓰는 의미가 없어질테니