Neu bei Web In Play

Seit der Einführung von Trusted Web Activity (Vertrauenswürdige Webaktivitäten) im letzten Jahr arbeitet das Chrome-Team weiter an dem Produkt, um die Nutzung mit Bubblewrap zu vereinfachen. Außerdem werden neue Funktionen wie die neue Google Play Billing-Integration hinzugefügt und auf weiteren Plattformen wie ChromeOS unterstützt. In diesem Artikel werden die neuesten und anstehenden Updates für Trusted Web Activity zusammengefasst.

Neue Bubblewrap- und vertrauenswürdige Webaktivitäten-Funktionen

Mit Bubblewrap können Sie Apps erstellen, mit denen Ihre PWAs innerhalb einer vertrauenswürdigen Webaktivität gestartet werden, ohne dass Sie sich mit plattformspezifischen Tools auskennen müssen.

Vereinfachter Einrichtungsablauf

Bisher war es für die Verwendung von Bubblewrap erforderlich, das Java Development Kit und das Android SDK manuell einzurichten, da beide fehleranfällig sind. Das Tool bietet jetzt die Möglichkeit, die externen Abhängigkeiten bei der ersten Ausführung automatisch herunterzuladen.

Sie können weiterhin eine vorhandene Installation der Abhängigkeiten verwenden. Der neue doctor-Befehl hilft beim Auffinden von Problemen und empfiehlt Fehlerbehebungen für die Konfiguration, die jetzt über die Befehlszeile mit dem Befehl updateConfig aktualisiert werden kann.

Verbesserter Assistent

Beim Erstellen eines Projekts mit init benötigt Bubblewrap Informationen zum Generieren der Android-App. Das Tool extrahiert Werte aus dem Web-App-Manifest und stellt nach Möglichkeit Standardwerte bereit.

Sie können diese Werte beim Erstellen eines neuen Projekts ändern, aber zuvor war die Bedeutung der einzelnen Felder nicht klar. Die Initialisierungsdialoge wurden mit besseren Beschreibungen und Validierungen für jedes Eingabefeld neu erstellt.

Display: Unterstützung für Vollbild und Ausrichtung

In einigen Fällen kann es sinnvoll sein, dass Ihre App einen möglichst großen Teil des Bildschirms nutzen soll. Wenn Sie PWAs erstellen, müssen Sie dazu das Feld display im Web-App-Manifest auf fullscreen setzen.

Wenn Bubblewrap die Vollbildoption im Web-App-Manifest erkennt, wird die Android-App so konfiguriert, dass sie gemäß Android-spezifischen Begriffen auch im Vollbildmodus bzw. im immersiven Modus gestartet wird.

Das Feld orientation aus dem Web-App-Manifest definiert, ob die App im Hochformat, im Querformat oder in der vom Gerät aktuell verwendeten Ausrichtung gestartet werden soll. Bubblewrap liest jetzt das Feld "Web App Manifest" und verwendet es beim Erstellen der Android-App als Standard.

Beide Konfigurationen lassen sich als Teil des bubblewrap init-Ablaufs anpassen.

Ausgabe von AppBundles

App Bundles ist ein Veröffentlichungsformat für Apps, das die endgültige APK-Generierung und die Anmeldung bei Google Play delegiert. Dadurch können Nutzern in der Praxis kleinere Dateien bereitgestellt werden, wenn sie die Anwendung aus dem Store herunterladen.

Bubblewrap verpackt die App jetzt als App Bundle in einer Datei namens app-release-bundle.aab. Wir empfehlen, dieses Format bei der Veröffentlichung von Apps im Play Store zu bevorzugen, da es ab der zweiten Jahreshälfte 2021 für den Play Store erforderlich sein wird.

Delegierung der Standortbestimmung

Nutzer erwarten, dass die auf ihren Geräten installierten Anwendungen unabhängig von der Technologie zuverlässig funktionieren. Wenn die Berechtigung GeoLocation in einer vertrauenswürdigen Webaktivität verwendet wird, kann sie jetzt an das Betriebssystem delegiert werden. Wenn sie aktiviert ist, sehen Nutzer dieselben Dialogfelder wie bei Apps, die mit Kotlin oder Java erstellt wurden. Außerdem finden sie Steuerelemente zum Verwalten der Berechtigung an einem zentralen Ort.

Die Funktion kann über Bubblewrap hinzugefügt werden. Da durch sie zusätzliche Abhängigkeiten zum Android-Projekt hinzugefügt werden, solltest du sie nur aktivieren, wenn die Web-App die Berechtigung zur Standortbestimmung verwendet.

Optimierte Binärprogramme

Geräte mit begrenztem Speicherplatz sind in bestimmten Regionen der Welt üblich und Eigentümer dieser Geräte bevorzugen häufig kleinere Anwendungen. Anwendungen, die vertrauenswürdige Webaktivitäten verwenden, produzieren kleine Binärprogramme, wodurch diese Nutzer sich keine Sorgen machen müssen.

Bubblewrap wurde optimiert, indem die Liste der erforderlichen Android-Bibliotheken reduziert wurde. Dadurch sind die generierten Binärprogramme 800.000 kleiner. In der Praxis ist das weniger als die Hälfte der durchschnittlichen Größe, die von früheren Versionen generiert wurde. Um die kleineren Binärprogramme nutzen zu können, müssen Sie Ihre App nur mit der neuesten Version von Bubblewrap aktualisieren.

Vorhandene App aktualisieren

Eine von Bubblewrap generierte App besteht aus einer Webanwendung und einem schlanken Android-Wrapper, mit dem die PWA geöffnet wird. Auch wenn die PWA, die in einer vertrauenswürdigen Web Activity geöffnet wird, dieselben Aktualisierungszyklen wie jede andere Web-App ausführt, kann und sollte der native Wrapper aktualisiert werden.

Sie sollten Ihre Anwendung aktualisieren, damit sie die neueste Version des Wrappers mit den neuesten Fehlerkorrekturen und Funktionen verwendet. Wenn die neueste Version von Bubblewrap installiert ist, wendet der Befehl update die neueste Version des Wrappers auf ein vorhandenes Projekt an:

npm update -g @bubblewrap/cli
bubblewrap update
bubblewrap build

Ein weiterer Grund für die Aktualisierung dieser Anwendungen besteht darin, Änderungen am Web Manifest auf die Anwendung anzuwenden. Verwenden Sie dazu den neuen Befehl merge:

bubblewrap merge
bubblewrap update
bubblewrap build

Aktualisierung der Qualitätskriterien

In Chrome 86 wurden Änderungen an den Qualitätskriterien für vertrauenswürdige Webaktivitäten eingeführt, die unter Änderungen an den Qualitätskriterien für PWAs, die vertrauenswürdige Webaktivitäten verwenden, ausführlich erläutert werden.

Hier eine kurze Zusammenfassung: Achten Sie darauf, dass Ihre Anwendungen die folgenden Szenarien verarbeiten können, um einen Absturz zu verhindern:

  • Fehler bei der Verifizierung von Links zu digitalen Assets beim Start der App
  • Fehler bei der Rückgabe von HTTP 200 für eine Offline-Netzwerkressourcen-Anfrage
  • Rückgabe eines HTTP 404- oder 5xx-Fehlers in der Anwendung.

Abgesehen davon, dass die Anwendung die Digital Asset Links-Validierung besteht, können die verbleibenden Szenarien von einem Service Worker verarbeitet werden:

self.addEventListener('fetch', event => {
  event.respondWith((async () => {
    try {
      return await fetchAndHandleError(event.request);
    } catch {
      // Failed to load from the network. User is offline or the response
      // has a status code that triggers the Quality Criteria.
      // Try loading from cache.
      const cachedResponse = await caches.match(event.request);
      if (cachedResponse) {
        return cachedResponse;
      }
      // Response was not found on the cache. Send the error / offline
      // page. OFFLINE_PAGE should be pre-cached when the service worker
      // is activated.
      return await caches.match(OFFLINE_PAGE);
    }
  })());
});

async function fetchAndHandleError(request) {
  const cache = await caches.open(RUNTIME_CACHE);
  const response = await fetch(request);

  // Throw an error if the response returns one of the status
  // that trigger the Quality Criteria.
  if (response.status === 404 ||
      response.status >= 500 && response.status < 600) {
    throw new Error(`Server responded with status: ${response.status}`);
  }

  // Cache the response if the request is successful.
  cache.put(request, response.clone());
  return response;
}

Workbox integriert Best Practices und entfernt Boilerplate, wenn Service Worker verwendet werden. Alternativ können Sie für diese Szenarien die Verwendung eines Workbox-Plug-ins in Betracht ziehen:

export class FallbackOnErrorPlugin {
  constructor(offlineFallbackUrl, notFoundFallbackUrl, serverErrorFallbackUrl) {
    this.notFoundFallbackUrl = notFoundFallbackUrl;
    this.offlineFallbackUrl = offlineFallbackUrl;
    this.serverErrorFallbackUrl = serverErrorFallbackUrl;
  }

  checkTrustedWebActivityCrash(response) {
    if (response.status === 404 || response.status >= 500 && response.status <= 600) {
      const type = response.status === 404 ? 'E_NOT_FOUND' : 'E_SERVER_ERROR';
      const error = new Error(`Invalid response status (${response.status})`);
      error.type = type;
      throw error;
    }
  }

  // This is called whenever there's a network response,
  // but we want special behavior for 404 and 5**.
  fetchDidSucceed({response}) {
    // Cause a crash if this is a Trusted Web Activity crash.
    this.checkTrustedWebActivityCrash(response);

    // If it's a good response, it can be used as-is.
    return response;
  }

  // This callback is new in Workbox v6, and is triggered whenever
  // an error (including a NetworkError) is thrown when a handler runs.
  handlerDidError(details) {
    let fallbackURL;
    switch (details.error.details.error.type) {
      case 'E_NOT_FOUND': fallbackURL = this.notFoundFallbackUrl; break;
      case 'E_SERVER_ERROR': fallbackURL = this.serverErrorFallbackUrl; break;
      default: fallbackURL = this.offlineFallbackUrl;
    }

    return caches.match(fallbackURL, {
      // Use ignoreSearch as a shortcut to work with precached URLs
      // that have _WB_REVISION parameters.
      ignoreSearch: true,
    });
  }
}

Google Play Billing

Google Play Billing ermöglicht es deiner App nicht nur, digitale Waren und Abos im Play Store zu verkaufen, sondern bietet auch Tools zur Verwaltung deines Katalogs, deiner Preise und Abos, nützliche Berichte und einen Bezahlvorgang des Play Store, mit dem deine Nutzer bereits vertraut sind. Sie ist auch für im Play Store veröffentlichte Apps erforderlich, über die digitale Waren verkauft werden.

Chrome 88 wird mit einem Ursprungstest für Android eingeführt, der die Einbindung von vertrauenswürdigen Webaktivitäten, der Payment Request API und der Digital Goods API ermöglicht, um Kaufvorgänge über Google Play Billing zu implementieren. Dieser Ursprungstest wird voraussichtlich auch für ChromeOS unter Version 89 verfügbar sein.

Wichtig:Die Google Play Billing API hat eine eigene Terminologie und enthält Client- und Back-End-Komponenten. Dieser Abschnitt behandelt nur einen kleinen Teil der API, der speziell für die Verwendung der Digital Goods API und Trusted Web Activity gilt. Lesen Sie die Google Play Billing-Dokumentation und machen Sie sich mit den Konzepten vertraut, bevor Sie sie in eine Produktionsanwendung integrieren.

Grundlegender Ablauf

Play Console-Menü

Wenn Sie digitale Waren über den Play Store anbieten möchten, müssen Sie Ihren Katalog im Play Store konfigurieren und den Play Store als Zahlungsmethode über Ihre PWA verknüpfen.

Wenn Sie Ihren Katalog konfigurieren möchten, suchen Sie zuerst im linken Menü der Play Console nach dem Bereich „Produkte“:

Hier findest du die Option zum Anzeigen deiner vorhandenen In-App-Produkte und Abos sowie die Schaltfläche „Erstellen“, um neue hinzuzufügen.

In-App-Produkte

Produktdetails

Um ein neues In-App-Produkt zu erstellen, benötigen Sie eine Produkt-ID, einen Namen, eine Beschreibung und einen Preis. Es ist wichtig, aussagekräftige und leicht zu merkende Produkt-IDs zu erstellen. Sie benötigen sie später und die IDs können nach dem Erstellen nicht mehr geändert werden.

Beim Erstellen von Abos müssen Sie auch einen Abrechnungszeitraum angeben. Du hast die Möglichkeit, deine Abovorteile aufzulisten und Funktionen hinzuzufügen, z. B. ein Probeabo, einen Einführungspreis, einen Kulanzzeitraum und die Möglichkeit, ein neues Abo abzuschließen.

Nachdem Sie alle Produkte erstellt haben, können Sie sie über Ihre App verfügbar machen, indem Sie sie aktivieren.

Wenn Sie möchten, können Sie Ihre Produkte auch über die Play Developers API hinzufügen.

Sobald Ihr Katalog konfiguriert ist, müssen Sie im nächsten Schritt den Bezahlvorgang über die PWA konfigurieren. Dazu verwenden Sie eine Kombination aus der Digital Goods API und der Payment Request API.

Produktpreis mit der Digital Goods API abrufen

Bei der Verwendung von Google Play Billing sollte der Preis, der Nutzern angezeigt wird, mit dem Preis aus dem Store-Eintrag übereinstimmen. Diese Preise manuell zu synchronisieren, ist unmöglich. Daher bietet die Digital Goods API der Webanwendung die Möglichkeit, Preise vom zugrunde liegenden Zahlungsdienstleister abzufragen:

// The SKU for the product, as defined in the Play Store interface
async function populatePrice(sku) {
  try {
    // Check if the Digital Goods API is supported by the browser.
    if (window.getDigitalGoodsService) {
      // The Digital Goods API can be supported by other Payments provider.
      // In this case, we're retrieving the Google Play Billing provider.
      const service =
          await window.getDigitalGoodsService("https://play.google.com/billing");

      // Fetch product details using the `getDetails()` method.
      const details = await service.getDetails([sku]);

      if (details.length === 0) {
        console.log(`Could not get SKU: "${sku}".`);
        return false;
      }

      // The details will contain both the price and the currenncy.
      item = details[0];
      const value = item.price.value;
      const currency = item.price.currency;

      const formattedPrice = new Intl.NumberFormat(navigator.language, {
        style: 'currency', currency: currency }).format(value);

      // Display the price to the user.
      document.getElementById("price").innerHTML = formattedPrice;
    } else {
      console.error("Could not get price for SKU \"" + sku + "\".");
    }
  } catch (error) {
    console.log(error);
  }
  return false;
}

Wenn Sie wissen möchten, ob die Digital Goods API unterstützt wird, prüfen Sie, ob getDigitalGoodsService() für das window-Objekt verfügbar ist.

Rufen Sie dann window.getDigitalGoodsService() mit der Google Play Billing-ID als Parameter auf. Dadurch wird eine Dienstinstanz für Google Play Billing zurückgegeben. Andere Anbieter können die Unterstützung für die Digital Goods API implementieren und haben andere Kennzeichnungen.

Rufen Sie schließlich getDetails() für den Verweis auf das Google Play Billing-Objekt auf und übergeben Sie die Artikelnummer für den Artikel als Parameter. Die Methode gibt ein Detailobjekt zurück, das sowohl den Preis als auch die Währung für den Artikel enthält, der dem Nutzer angezeigt werden kann.

Kaufvorgang starten

Die Payment Request API aktiviert Kaufabläufe im Web und wird auch für die Einbindung von Google Play Billing verwendet. Unter Funktionsweise der Payment Request API findest du weitere Informationen, wenn du die Payment Request API noch nicht verwendest.

Wenn Sie die API mit Google Play Billing verwenden möchten, müssen Sie ein Zahlungsmittel mit dem unterstützten Format https://play.google.com/billing hinzufügen. Fügen Sie außerdem die Artikelnummer als Teil der Daten für das Zahlungsmittel hinzu:

const supportedInstruments = [{
  supportedMethods: "https://play.google.com/billing",
  data: {
    sku: sku
  }
}];

Erstellen Sie dann wie gewohnt ein PaymentRequest-Objekt und verwenden Sie wie gewohnt die API.

const request = new PaymentRequest(supportedInstruments, details);

Kauf bestätigen

Sobald die Transaktion abgeschlossen ist, müssen Sie die Digital Goods API verwenden, um die Zahlung zu bestätigen. Das Antwortobjekt aus dem PaymentRequest enthält ein Token, mit dem Sie die Transaktion bestätigen:

const response = await request.show();
const token = response.details.token;
const service =
          await window.getDigitalGoodsService("https://play.google.com/billing");
await service.acknowledge(token, 'onetime');

Die Digital Goods API und die Payment Request API kennen die Identität des Nutzers nicht. Daher liegt es an dir, den Kauf mit dem Nutzer in deinem Backend zu verknüpfen und dafür zu sorgen, dass er Zugriff auf die gekauften Artikel hat. Wenn du den Kauf mit einem Nutzer verknüpfst, denke daran, das Kauftoken zu speichern. Du benötigst es möglicherweise, um zu prüfen, ob der Kauf storniert oder erstattet wurde oder ob ein Abo noch aktiv ist. Sehen Sie sich die Real Time Developer Notifications API und die Google Play Developer API an, da sie Endpunkte für die Bearbeitung dieser Fälle in Ihrem Backend bieten.

Auf vorhandene Berechtigungen prüfen

Ein Nutzer hat möglicherweise einen Gutscheincode eingelöst oder hat ein bestehendes Abo für Ihr Produkt. Um zu prüfen, ob der Nutzer die entsprechenden Berechtigungen hat, kannst du den Befehl listPurchases() für den Dienst für digitale Waren aufrufen. Dadurch werden alle Käufe zurückgegeben, die der Kunde in deiner App getätigt hat. Außerdem kannst du dort nicht bestätigte Käufe bestätigen, damit der Nutzer seine Berechtigungen korrekt einlöst.

const purchases = await itemService.listPurchases();
for (p of purchases) {
  if (!p.acknowledged) {
    await itemService.acknowledge(p.purchaseToken, 'onetime');
  }
}

In den ChromeOS Play Store hochladen

Vertrauenswürdige Webaktivitäten sind auch seit Chrome 85 im ChromeOS Play Store verfügbar. Die Auflistung Ihrer App im Store funktioniert bei ChromeOS genauso wie bei Android.

Nachdem Sie Ihr App Bundle erstellt haben, werden Sie in der Play Console durch die erforderlichen Schritte zum Auflisten der App im Play Store geführt. In der Play Console-Dokumentation finden Sie Hilfe zum Erstellen Ihres App-Eintrags, zum Verwalten Ihrer APK-Dateien und anderer Einstellungen sowie eine Anleitung zum Testen und sicheren Veröffentlichen Ihrer App.

Wenn Sie Ihre Anwendung nur auf Chromebooks beschränken möchten, fügen Sie beim Initialisieren der Anwendung in Bubblewrap das Flag --chromeosonly hinzu:

bubblewrap init --manifest="https://example.com/manifest.json" --chromeosonly

Wenn Sie Ihre App manuell und ohne Bubblewrap erstellen, fügen Sie Ihrem Android-Manifest das Flag uses-feature hinzu:

<uses-feature  android:name="org.chromium.arc" android:required="true"/>

Wenn Ihr Eintrag für eine Android-App freigegeben ist, muss die Version des reinen ChromeOS-Pakets immer höher als die Version des Android-App-Pakets sein. Die Zahl der ChromeOS-Bundles ist viel höher als die der Android-Version, sodass Sie nicht bei jedem Release beide Versionen aktualisieren müssen.