티스토리 뷰





발생일: 2016.06.15

키워드: 유니버셜 링크, universal link, smart banner, 스마트 배너, apple-app-site-association, applinks 

문제:
유니버셜 링크에 대한 처리를 앱에 추가하려고 한다.


해결책:

유니버셜 링크를 지원하려면, 먼저 앱에서 유니버셜 링크를 허용할 도메인을 추가해줘야 한다.

Xcode 프로젝트 > Target 메뉴의 대상 프로젝트 > Associated Domains 메뉴에서, applinks: 스킴으로 대상 도메인을 추가하면 된다.

예)
applinks:example.com
applinks:*.example.com

(사용자가 앱 설치 시, 여기에 등록된 도메인으로 apple-app-site-association 파일에 대한 요청을 보내게 된다.)








올바르게 추가되었다면, 유저가 유니버셜 링크를 탭하면 iOS가 앱을 실행하게 된다.

유니버셜 링크로 들어오는 요청은,
UIApplicationDelegate 의 application:continueUserActivity:restorationHandler: 메서드에서,
전달받은 NSUserActivity 객체을 사용해 처리할 수 있다.


- (BOOL)application:(UIApplication *)application continueUserActivity:(NSUserActivity *)userActivity restorationHandler:(void(^)(NSArray * __nullable restorableObjects))restorationHandler {
    if ([userActivity.activityType isEqualToString:NSUserActivityTypeBrowsingWeb]) { // NSUserActivityTypeBrowsingWeb 타입이다.
        // userActivity.webpageURL 로 대상 URL을 확인할 수 있다. 값이 없는 경우는 없다.
        ...
        return YES; // 처리하려면 YES
    }
    return NO; // 아니라면 NO
}



논의:

- applinks: 에 할당하는 도메인에서, * 는 상위 도메인을 포함하지 않는다. example.com 과 *.example.com 을 모두 허용하려면 두 가지를 모두 추가해줘야 한다.

  applinks:example.com
  applinks:*.example.com

- iOS는 유니버셜 링크로 앱을 실행하기 전에, 동일한 액션에 대해 사용자가 선택했던 액션을 먼저 확인한다.
  예를 들어, 사용자가 기존에 유니버셜 링크로 열었던 앱의 URL을, 다른 방법(롱탭 -> 사파리에서 열기)으로 브라우저에서 열었다면,
  이 URL은 앞으로도 계속 사파리에서 열린다. 사용자가 다시 앱에서 열기(롱탭 -> 앱에서 열기, 또는 웹사이트의 스마트 배너를 클릭)하지 않는 한 이 설정은 바뀌지 않는다.

- 만약, 링크 처리를 위해 SFSarafiViewController, WKWebView, UIWebView의 인스턴스를 새로 생성했다면, 앱으로 이동하는 대신 웹사이트를 연다.
  그렇지만, 사용자가 이미 만들어져있는 웹뷰 인스턴스 내에서 링크를 탭한 경우엔 유니버셜 링크가 동작한다.

  이런 이유 때문에, 웹뷰를 제공하는 특정 앱에서 테스트할 땐 좀 혼란스러울 수 있다.
  예를 들어, 에버노트의 노트에 올바르게 동작하는 유니버셜 링크를 입력하고 탭하는 경우엔 (웹뷰 인스턴스를 생성하므로) 웹뷰로 열리지만,
  에버노트에서 열어놓은 웹뷰 내에서 해당 링크를 탭하는 경우엔 올바르게 앱이 열린다.

- 앱 내에서 openURL: 메서드로 유니버셜 링크 대상인 URL을 호출하는 경우엔, 앱으로 리다이렉트 되지 않고 바로 사파리로 열린다.
  iOS에서 '앱에서 호출했으니, 앱이 아니라 웹페이지를 보려는 것'으로 판단했기 때문이다.

- 앱이 close 된 상태라면, application:continueUserActivity:restorationHandler: 가 호출되지 않는다.
  대신, didFinishLaunchingWithOptions: 메서드에서 옵션을 가져와 처리할 수 있다.

  // In application: didFinishLaunchingWithOptions:
  NSDictionary *activityDic = [launchOptions objectForKey:UIApplicationLaunchOptionsUserActivityDictionaryKey];

  if (activityDic) {
      // Continue activity here
  }


참고:




반응형
댓글
공지사항