Как использовать Аналитику в компоненте WebView

Вызовы для регистрации событий или установки свойств пользователей, активированные в WebView, должны быть перенаправлены в нативный код, прежде чем их можно будет отправить в Google Analytics.

Как внедрить обработчик JavaScript

Чтобы использовать Google Analytics в компоненте WebView, для начала нужно создать функции JavaScript, которые будут пересылать свойства пользователей и события в нативный код. Ниже приведен пример реализации, совместимый с нативным кодом как Android, так и Apple:
function logEvent(name, params) {
  if (!name) {
    return;
  }

  if (window.AnalyticsWebInterface) {
    // Call Android interface
    window.AnalyticsWebInterface.logEvent(name, JSON.stringify(params));
  } else if (window.webkit
      && window.webkit.messageHandlers
      && window.webkit.messageHandlers.firebase) {
    // Call iOS interface
    var message = {
      command: 'logEvent',
      name: name,
      parameters: params
    };
    window.webkit.messageHandlers.firebase.postMessage(message);
  } else {
    // No Android or iOS interface found
    console.log("No native APIs found.");
  }
}

function setUserProperty(name, value) {
  if (!name || !value) {
    return;
  }

  if (window.AnalyticsWebInterface) {
    // Call Android interface
    window.AnalyticsWebInterface.setUserProperty(name, value);
  } else if (window.webkit
      && window.webkit.messageHandlers
      && window.webkit.messageHandlers.firebase) {
    // Call iOS interface
    var message = {
      command: 'setUserProperty',
      name: name,
      value: value
   };
    window.webkit.messageHandlers.firebase.postMessage(message);
  } else {
    // No Android or iOS interface found
    console.log("No native APIs found.");
  }
}

Как вызвать обработчик JavaScript из WebView

Чтобы правильно регистрировать события и задавать свойства пользователей в WebView, вызывайте функции JavaScript, которые вы определили на предыдущем шаге. В примере ниже показано, как правильно зарегистрировать событие покупки и задать пользовательское свойство:
function logEventExample() {
   
   // Log an event named "purchase" with parameters
   logEvent("purchase", {
      content_type: "product",
      value: 123,
      currency: "USD",
      quantity: 2,
      items: [{
        item_id: "sample-item-id",
        item_variant: "232323"
      }],
      transaction_id: "1234567"
   });
}

function logUserPropertyExample() {
   // Set a user property named 'favorite_genre'
   setUserProperty("favorite_genre", "comedy")    
}

Как внедрить нативный интерфейс

Вы можете реализовать нативный интерфейс для iOS или Android.

iOS

Для вызова нативного кода Apple из JavaScript создайте класс обработчика сообщений, соответствующий протоколу WKScriptMessageHandler. Вызовы Google Analytics можно совершать, используя функцию обратного вызова userContentController:didReceiveScriptMessage::

Swift

Примечание. Этот продукт Firebase недоступен для watchOS.
func userContentController(_ userContentController: WKUserContentController,
                         didReceive message: WKScriptMessage) {
  guard let body = message.body as? [String: Any] else { return }
  guard let command = body["command"] as? String else { return }
  guard let name = body["name"] as? String else { return }

  if command == "setUserProperty" {
    guard let value = body["value"] as? String else { return }
    Analytics.setUserProperty(value, forName: name)
  } else if command == "logEvent" {
    guard let params = body["parameters"] as? [String: NSObject] else { return }
    Analytics.logEvent(name, parameters: params)
  }
}

Objective-C

- (void)userContentController:(WKUserContentController *)userContentController
      didReceiveScriptMessage:(WKScriptMessage *)message {
  if ([message.body[@"command"] isEqual:@"setUserProperty"]) {
    [FIRAnalytics setUserPropertyString:message.body[@"value"] forName:message.body[@"name"]];
  } else if ([message.body[@"command"] isEqual: @"logEvent"]) {
    [FIRAnalytics logEventWithName:message.body[@"name"] parameters:message.body[@"parameters"]];
  }
}

Затем добавьте обработчик сообщений в контроллер пользовательского контента WebView:

Swift

Примечание. Этот продукт Firebase недоступен для watchOS.
self.webView.configuration.userContentController.add(self, name: "firebase")

Objective-C

Примечание. Этот продукт Firebase недоступен для watchOS.
[self.webView.configuration.userContentController addScriptMessageHandler:self
                                                                     name:@"firebase"];

Android

Для вызова нативного кода Android из JavaScript создайте класс с методами, помеченными @JavaScriptInterface:

public class AnalyticsWebInterface {

    public static final String TAG = "AnalyticsWebInterface";
    private FirebaseAnalytics mAnalytics;

    public AnalyticsWebInterface(Context context) {
        mAnalytics = FirebaseAnalytics.getInstance(context);
    }

    @JavascriptInterface
    public void logEvent(String name, String jsonParams) {
        LOGD("logEvent:" + name);
        mAnalytics.logEvent(name, bundleFromJson(jsonParams));
    }

    @JavascriptInterface
    public void setUserProperty(String name, String value) {
        LOGD("setUserProperty:" + name);
        mAnalytics.setUserProperty(name, value);
    }

    private void LOGD(String message) {
        // Only log on debug builds, for privacy
        if (BuildConfig.DEBUG) {
            Log.d(TAG, message);
        }
    }

    private Bundle bundleFromJson(String json) {
        // ...
    }

}

После создания нативного интерфейса зарегистрируйте его в своем WebView, чтобы он был виден работающему в этом компоненте коду JavaScript:

// Only add the JavaScriptInterface on API version JELLY_BEAN_MR1 and above, due to
// security concerns, see link below for more information:
// https://developer.android.com/reference/android/webkit/WebView.html#addJavascriptInterface(java.lang.Object,%20java.lang.String)
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
    mWebView.addJavascriptInterface(
            new AnalyticsWebInterface(this), AnalyticsWebInterface.TAG);
} else {
    Log.w(TAG, "Not adding JavaScriptInterface, API Version: " + Build.VERSION.SDK_INT);
}

Как вручную регистрировать события покупки в приложении в компоненте WebView на устройстве iOS

Вы можете вручную регистрировать события покупки в приложении в WebView с помощью Analytics SDK версии 12.5.0 или более поздней.

function logManualPurchaseEvent() {
  // For manually tracking in-app purchases within a WebView, log the in-app purchase event:
  logEvent("in_app_purchase", {
    currency: "USD",
    price: 0.99,
    product_id: "prod_123",
    product_name: "Product 123",
    quantity: 1,
    value: 0.99,
  });
}

Обратите внимание, что SDK продолжит автоматически регистрировать покупки в приложении, если это возможно, и не будет удалять дубликаты событий in_app_purchase, зарегистрированных вручную.

Дальнейшие действия

Полностью функциональную реализацию Google Analytics в WebView смотрите в примере analytics-webview.