requestAutocomplete

Weź moje pieniądze, nie czas

Jake Archibald
Jake Archibald

Wstęp

Lubię internet. W każdym przypadku uważam, że to całkiem dobry pomysł. Dlatego biorę udział w debatach w internecie i narodowych. Nie musi minąć długo, zanim druga osoba zacznie mówić o łatwości płatności w systemach natywnych. Zwykle reaguję na to, żeby zrzucić bombę dymną i wybiegać z pomieszczenia ze śmiechu, bo to nie jest argument do wygrania. Liczba porzuceń koszyka w internecie mobilnym może wynosić nawet 97%. Wyobraź to sobie w prawdziwym świecie. Wyobraź sobie 97% supermarketów z koszykiem pełnym interesujących ich rzeczy, odwracającego koszyk i wychodząc. Niektórzy z tych osób po prostu podnoszą ceny i nigdy nie planowali zakupu, ale fatalne wrażenia użytkowników związane z zakupami w internecie mają istotny wpływ na ich ceny. Nakładamy na użytkowników podatki na porządek. Pomyśl o swoich wrażeniach związanych z płatnościami w internecie, zwłaszcza na urządzeniach mobilnych. To sklep z aplikacjami, prawda? Możesz też użyć podobnego zamkniętego systemu, który już posiada dane do płatności. To jest problem. Witryny muszą zobowiązać się do współpracy z konkretnym dostawcą usług płatniczych, u którego użytkownik musi już mieć konto i się na niej zalogować lub zobowiązać się do korzystania z platformy wymagającej zalogowania się u określonego dostawcy usług płatniczych (np. w sklepach z aplikacjami, które wymagają kodowania wyłącznie na tę platformę). Jeśli nie wykonasz żadnej z tych czynności, użytkownik będzie skazany na skasowanie ekranu lub klawiatury, aż do wykończenia skóry lub poddaje się. Musimy to naprawić.

requestAutocomplete

W świecie WebGL, WebRTC i innych zaawansowanych interfejsów API, które zaczynają się od „Web”, requestAutocomplete jest raczej nietypowe. Jest jednak superbohaterem w beżowej ubraniu. Mały, nudny interfejs API, który może przebić się przez wampir do płatności internetowych.

Zamiast korzystać z usług konkretnego dostawcy usług płatniczych, żąda ona od przeglądarki informacji o płatności i zapisuje je w imieniu użytkownika. Wersja requestAutocomplete() dotycząca Chrome integruje się też z Portfelem Google tylko dla użytkowników w Stanach Zjednoczonych (obecnie). Wypróbuj tę funkcję w witrynie testowej.

form.requestAutocomplete

Elementy formularzy udostępniają jedną nową metodę, requestAutocomplete, która prosi przeglądarkę o wypełnienie formularza. W przeglądarce pojawi się okno z prośbą o pozwolenie, w którym użytkownik może wybrać, jakie informacje chce podać. Nie możesz go wywołać za każdym razem, gdy chcesz. Musisz je wywołać podczas wykonywania określonych zdarzeń interakcji, takich jak kliknięcie w górę/w dół, kliknięcie, naciśnięcie oraz dotknięcie. Jest to celowe ograniczenie bezpieczeństwa.

button.addEventListener('click', function(event) {
  form.requestAutocomplete();
  event.preventDefault();
});

// TODO: listen for autocomplete events on the form

Zanim zajmiemy się zdarzeniami, musimy się upewnić, że przeglądarka poprawnie zinterpretuje pola formularza.

Wymagania dotyczące formularza

W czasach, gdy internet był czarno-biały, przeglądarka Internet Explorer 5 przyjmowała nowy atrybut – autocomplete – elementy wprowadzania danych. Można je wyłączyć, aby przeglądarka przestała wyświetlać sugestie. Ten interfejs API został rozszerzony, dzięki czemu możesz określić oczekiwaną zawartość pola bez modyfikowania atrybutu „name”. To właśnie requestAutocomplete używa do łączenia pól formularza z danymi użytkownika.

<input name="fullname" autocomplete="name">

Zgodnie ze specyfikacją requestAutocomplete nie dotyczy płatności, ale obecne wdrożenie Chrome w większości tak. W przyszłości przeglądarki będą mogły obsługiwać inne rodzaje danych, np. dane logowania, generator haseł, informacje z paszportu, a nawet przesyłanie awatara.

Obecnie w Chrome requestAutocomplete rozpoznaje te elementy:

płatność,

  • email
  • cc-name – imię i nazwisko na karcie
  • cc-number – numer karty
  • cc-exp-month – miesiąc ważności karty podany w postaci 2 cyfr
  • cc-exp-year – rok ważności karty składający się z 4 cyfr
  • cc-csc – 3-4-cyfrowy kod zabezpieczający karty
<input type="email" autocomplete="email" name="email">
<input type="text" autocomplete="cc-name" name="card-name">
<input type="text" autocomplete="cc-number" name="card-num">
<input type="text" autocomplete="cc-exp-month" name="card-exp-month">
<input type="text" autocomplete="cc-exp-year" name="card-exp-year">
<input type="text" autocomplete="cc-csc" name="card-csc">

Używany przeze mnie powyżej atrybut „name” to tylko przykłady. Nie ma wymogu używania konkretnych wartości. Jeśli będziesz ponownie używać tego formularza w przypadku użytkowników, którzy nie używają języka requestAutocomplete (a jest to idealne rozwiązanie), dodaj etykiety, układ i podstawową weryfikację HTML5.

Nie masz też ograniczenia do elementów wejściowych – możesz używać dowolnego typu wprowadzania danych. Możesz na przykład wpisać <select> w polach dotyczących terminu wygaśnięcia karty.

Szczegółowy komunikat w konsoli.
Szczegółowy komunikat w konsoli

Adres

  • name (nazwa) – imię i nazwisko. Zarejestrowanie imienia i nazwiska jako jednego pola jest znacznie lepsze niż w przypadku wielu pól. Różne pola, takie jak imię i nazwisko, wykazują tendencję do Zachodu i mogą nie mieć sensu w innych kulturach. Łatwiej je też wpisać w jednym polu.

  • tel: pełny numer telefonu wraz z kodem kraju, który może być alternatywnie podzielony na

    • tel-country-code – np. +44
    • tel-national - reszta
  • street-address – pełny adres ze składnikami rozdzielonymi przecinkami, który można podzielić na

    • pierwszy wiersz adresu
    • drugi wiersz adresu – może być pusty
  • rejon - miasto/miasteczko

  • region – kod stanu, hrabstwo lub kanton

  • kod pocztowy – kod pocztowy, kod pocztowy, kod pocztowy;

  • country

Powyższego opisu należy używać w połączeniu z: – płatnościami, – dostawą.

<input type="text" autocomplete="billing name" required name="billing-name">
<input type="tel" autocomplete="billing tel" required name="billling-tel">
<input type="text" autocomplete="billing address-line1" required name="billing-address1">
<input type="text" autocomplete="billing address-line2" required name="billing-address2">
<input type="text" autocomplete="billing locality" required name="billing-locality">
<input type="text" autocomplete="billing region" required name="billing-region">
<input type="text" autocomplete="billing postal-code" required name="billing-postal-code">
<select autocomplete="billing country" required name="billing-country">
  <option value="US">United States</option>
  …
</select>

<input type="text" autocomplete="shipping name" name="shipping-name">
…

Przypominamy, że atrybuty nazw są tylko przykładami, których możesz używać w dowolny sposób. Oczywiście nie we wszystkich formularzach należy podawać adres dostawy. Na przykład nie pytajcie mnie, gdzie chcę otrzymać pokój hotelowy – często atrakcyjna jest aktualna lokalizacja. Mamy formularz i wiemy, jak poprosić o autocompletion. Ale...

Kiedy ma być wywoływane żądanie requestAutocomplete?

Najlepiej byłoby wyświetlać okno requestAutocomplete zamiast wczytywania strony, na której wyświetla się formularz płatności. Jeśli wszystko pójdzie dobrze, użytkownik w ogóle nie powinien widzieć formularza.

Proces płatności

Typowym przykładem jest strona koszyka z przyciskiem „Zapłać”, prowadzącym do formularza szczegółów płatności. W takiej sytuacji chcesz wczytać formularz rozliczeniowy na stronie koszyka, ale ukryć go przed użytkownikiem i wywołać metodę requestAutocomplete, gdy użytkownik kliknie przycisk „Zapłać”. Pamiętaj, że musisz udostępniać stronę koszyka przez SSL, aby uniknąć ostrzeżenia Skeletor. Najpierw musimy ukryć przycisk płatności, aby użytkownik nie mógł go kliknąć, dopóki nie wszystko będzie gotowe. Chcemy to jednak zrobić tylko w przypadku użytkowników JavaScript. W nagłówku strony:

<script>document.documentElement.className += ' js';</script>

W Twojej usłudze porównywania cen:

.js #checkout-button,
#checkout-form.for-autocomplete {
  display: none;
}

Na stronie koszyka musimy dodać formularz rozliczeniowy. Możesz go umieścić w dowolnym miejscu. Powyższy kod CSS gwarantuje, że nie będzie on widoczny dla użytkownika.

<form id="checkout-form" class="for-autocomplete" action="/checkout" method="post">
  …fields for payment, billing address &amp; shipping if relevant…
</form>

Teraz nasz JavaScript może rozpocząć konfigurowanie:

function enhanceForm() {
  var button = document.getElementById('checkout-button');
  var form = document.getElementById('checkout-form');

  // show the checkout button
  button.style.display = 'block';

  // exit early if there's no requestAutocomplete support
  if (!form.requestAutocomplete) {
    // be sure to show the checkout button so users can
    // access the basic payment form!
    return;
  }

  button.addEventListener('click', function(event) {
    form.requestAutocomplete();
    event.preventDefault();
  });

  // TODO: listen for autocomplete events on the form
}

Wywołujesz metodę enhanceForm na stronie koszyka zaraz po tym, jak formularz i przycisk płatności. Przeglądarki obsługujące requestAutocomplete będą mogły korzystać z nowej, zaawansowanej wersji, a inne przeglądarki powrócą do normalnej formy płatności. Aby zdobyć dodatkowe punkty, możesz załadować kod HTML formularza za pomocą XHR w ramach usługi enhanceForm. Oznacza to, że możesz wczytywać formularz tylko w przeglądarkach, które obsługują requestAutocomplete, i nie musisz pamiętać o dodawaniu formularza do każdej strony, na której możesz wywołać metodę enhanceForm. Tak działa witryna demonstracyjna.

Nazwałaś żądanie autouzupełniania i co teraz?

Proces autouzupełniania jest asynchroniczny, requestAutocomplete zwraca od razu. Aby dowiedzieć się, jak nam poszło, słuchamy kilku nowych wydarzeń:

form.addEventListener('autocomplete', function() {
  // hurrah! You got all the data you needed
});

form.addEventListener('autocompleteerror', function(event) {
  if (event.reason == 'invalid') {
    // the form was populated, but it failed html5 validation
    // eg, the data didn't match one of your pattern attributes
  }
  else if (event.reason == 'cancel') {
    // the user aborted the process
  }
  else if (event.reason == 'disabled') {
    // the browser supports requestAutocomplete, but it's not
    // available at this time. Eg, it wasn't called from an
    // interaction event or the page is insecure
  }
});

Jeśli wszystko zadziałało, z danymi możesz zrobić, co tylko chcesz. Najprostszym sposobem jest przesłanie formularza. Serwer może wtedy zweryfikować dane i wyświetlić użytkownikowi stronę potwierdzenia wraz z kosztem dostawy. Jeśli dane są nieprawidłowe, możesz wyświetlić formularz i wyróżnić pola, które użytkownik musi poprawić. Możesz też po prostu przesłać formularz, a wtedy zwykła weryfikacja po stronie serwera zostanie przejęta. Jeśli użytkownik anulował ten proces, nie musisz nic robić. Jeśli ta funkcja jest wyłączona, skieruj użytkownika do zwykłego formularza. W większości przypadków Twoi słuchacze będą wyglądać bardzo podobnie do...

form.addEventListener('autocomplete', function() {
  form.submit();
});

form.addEventListener('autocompleteerror', function(event) {
  if (event.reason == 'invalid') {
    form.submit();
  }
  else if (event.reason != 'cancel') {
    window.location = '/checkout-page/';
  }
});

Gdzie przeglądarka przechowuje moje dane?

Specyfikacja nie określa, gdzie mają być przechowywane dane, co umożliwia przeglądarkom wprowadzanie innowacji. Jeśli zalogujesz się w Chrome, zobaczysz opcję zapisania szczegółów w Portfelu Google, dzięki czemu będą one dostępne na innych urządzeniach, na których się zalogujesz. Jeśli przechowujesz swoje dane w Portfelu, requestAutocomplete nie ujawnia prawdziwego numeru Twojej karty, co zwiększa bezpieczeństwo. Jeśli nie zalogujesz się w Chrome lub nie zdecydujesz się na korzystanie z Portfela Google, Twoje dane będą opcjonalnie przechowywane lokalnie w przeglądarce, aby możliwe było ich ponowne wykorzystanie. W tej chwili tak się dzieje, ale w przyszłości Chrome i inne przeglądarki mogą ująć dodatkowych dostawców usług płatniczych.

Ułatwianie płatności

To trochę dziwne, że użytkownicy, którzy chcą coś kupić, muszą ciągle wpisywać dane karty. Sytuacja staje się łatwiejsza, gdy witryna przechowuje dane do płatności. Nie mam pewności, w ilu witrynach są przechowywane dane mojej karty. To idealny problem w przypadku standardów internetowych. requestAutocomplete umożliwia dokonywanie płatności jednym kliknięciem w całym internecie bez uzależnienia się od usługi czy platformy – i nie tylko.

Runda dodatkowa: Obsługa formularzy wielostronicowych

Znacznie lepiej zadzwonić do firmy requestAutocomplete i zebrać wszystkie potrzebne dane. Jeśli nie możesz zmodyfikować serwera tak, aby odbierał wszystkie te dane naraz, pobierz dane z wypełnionego formularza i prześlij je w sposób, który jest dla Ciebie najkorzystniejszy. Możesz użyć tej niewielkiej funkcji, aby rejestrować wszystkie aktualnie obsługiwane dane w formie prostego obiektu bez konieczności samodzielnego tworzenia formularza. Gdy masz już dane, możesz je przekształcić do formatu wymaganego przez serwer i opublikować je w kilku krokach.

checkoutButton.addEventListener('click', function() {
  requestUserData({
    billing: true,
    shipping: true
  }, function(response) {
    if (response.err == 'cancel') {
      // exit silently
      return;
    }
    if (response.err) {
      // fall back to normal form
      window.location.href = '/normal-checkout-form/';
      return;
    }

    // the rest is just made-up pseudo code as an example
    postToServer(data.shipping).then(function() {
      return postToServer(data.billing);
    }).then(function() {
      return postToServer(data.cc);
    }).catch(function() {
      // handle error
    });
  });
});