Yahoo.com PWA, Parte 1: Introdução

Pavan Ratnakar Blocked Unblock Seguir Seguindo 3 de dezembro

Breve história

Y ahoo recentemente abraçou Progressive Web App (PWA) e lançou um novo aplicativo móvel da Web independente chamado Yahoo Lite. O PWA é uma tecnologia empolgante que permite que nossos usuários em todo o mundo se beneficiem dos aprimoramentos que podem oferecer.

Já lançamos em mais de oito países (expandindo para muito mais). As melhorias de desempenho e o crescimento do engajamento do usuário da web móvel e do Yahoo Lite nos deram grande confiança nos recursos do PWA. No entanto, a criação de um PWA na escala do Yahoo exigiu que fizéssemos as coisas de maneira diferente.

Presumimos que você tenha alguma familiaridade com o Progressive Web App (PWA) . Caso contrário, leia a documentação do Google sobre o PWA . Queríamos compartilhar nossos aprendizados e experiências em três partes ( Post 2 e Post 3 ). Cada parte é dividida em quatro seções: What , How , Challenges and Conclusion . Esperamos que você ache essas postagens informativas e acreditamos firmemente que os PWAs ajudam a preencher a lacuna entre recursos nativos e da Web.

o que

Quando começamos nossa jornada, nos fizemos algumas perguntas:

  • Podemos construir simultaneamente um PWA para Android e iOS?
  • Devemos reconstruir nossa pilha de tecnologia e começar do zero?
  • Precisamos usar o modelo de shell do aplicativo?
  • Quem deve lidar com nossas estratégias de busca de chamadas XHR: service worker ou biblioteca de clientes?

Como

Nós já tínhamos começado a trabalhar em uma re-arquitetura para Web móvel do Yahoo.com Nossa nova biblioteca de clientes estava evoluindo, um investimento que nos ajudou a reduzir nosso tamanho de JS em 68%. Também conseguimos reduzir os tamanhos de HTML e CSS em 48% e 76% , respectivamente, com bons aprimoramentos nos seguintes tempos: AFT (tempo da dobra), tempo até o primeiro byte, início da renderização, tempo de resposta do serviço e tempo interativo do DOM . Sabíamos que poderíamos levar isso adiante adotando os recursos do PWA . Quando começamos a trabalhar no nosso PWA, o Safari tinha acabado de lançar suporte para o service worker. No entanto, após algumas experiências, percebemos que o suporte do Safari era limitado:

  • Modo autônomo é buggy. Estávamos enfrentando problemas com cookies persistentes entre o modo de web do Safari e o modo autônomo.
  • Todos os links abrem em uma nova janela para o modo autônomo (há uma solução , mas não é elegante).
  • O Safari não instala binário como o Android Web APK, fazendo com que adicionar à tela inicial apenas outro marcador, limitando suas capacidades e resultando em ícones duplicados.
  • O Service Worker no Safari ainda não está totalmente amadurecido.

Tendo em conta o modo autônomo do Safari e as limitações do trabalhador de serviço, decidimos começar com o Android

Como parte de nossa migração tecnológica, não quisemos introduzir novas mudanças radicais. Numerosos artigos como este um na web app progressiva também falar sobre Reagir. Embora o React seja incrível, infelizmente não se encaixou em nosso caso de uso da página inicial.

Decidimos continuar com nossa migração de tecnologia sem fazer nenhuma alteração significativa. Os benefícios progressivos do aplicativo da Web são agnósticos em bibliotecas e frameworks

A web móvel do Yahoo.com é um aplicativo de página única parcial. Temos diferentes stacks de tecnologia que alimentam diferentes páginas, então mudar para um modelo de shell de aplicativo exigiria muito mais mudanças e nós queremos servir o Yahoo start_url com conteúdo do servidor para fins de SEO. Temos uma boa mistura de navegações de páginas e navegações de clientes. Dados os benefícios limitados para nosso caso de uso:

Decidimos criar nosso aplicativo da Web progressivo e páginas em torno dele sem o modelo de shell do aplicativo

Como parte de nossa nova biblioteca de clientes, decidimos não aproveitar o service worker para as chamadas XHR, pois queríamos aprimorar nossa experiência em sistemas operacionais e navegadores. Nós não temos um service worker em todas as nossas propriedades e páginas. Se você tiver chamadas de pré-busca em lote como nós, o armazenamento em cache do service worker poderá não funcionar.

A adição de estratégias de busca no cliente nos deu muito mais flexibilidade e alcance

Como parte de nossa biblioteca de clientes, criamos um componente de busca muito poderoso. Fetch é o que usamos para fazer chamadas XHR e montar o novo DOM usando o fragmento de documento na página. Nós otimizamos isso ainda mais usando GPU para a maioria das nossas animações (vamos postar sobre isso no futuro).

Para adicionar aos nossos recursos de componentes de busca, também adicionamos as estratégias de busca ” Network First ” e ” Cache First “.

Fluxo simples de buscar

Primeira estratégia de rede

  • A busca tentará primeiro recuperar dados pela rede.
  • Em uma chamada de rede bem-sucedida, o componente Fetch responderá com dados e gravará os dados mais recentes no cache no modo assíncrono (não bloqueando a solicitação).
  • Se a rede falhar, ela procurará no cache e servirá do cache, se disponível.
  • A busca será exibida a partir do cache, mesmo se o cache for obsoleto.

Primeira estratégia de rede

Cache primeira estratégia

  • O Fetch tentará primeiro obter dados do cache com tempo limite de 1.000 ms.
  • Ele tentará servir a partir do cache se o cache existir e não tiver expirado.
  • Se o cache não existir, expirar ou o cache expirar, o Fetch será exibido na rede.
  • Em uma chamada de rede bem-sucedida, responderá com dados e gravará no cache no modo assíncrono (não bloqueando a solicitação).
  • Se a pesquisa de cache inicial e a rede falharem, ela será analisada novamente no cache com tempo limite maior e será atendida a partir do cache, se disponível. Usamos um tempo limite maior para a segunda pesquisa para levar em consideração a lentidão ocasional do IndexedDB que observamos como parte de nossas medições.
  • A busca será exibida a partir do cache, mesmo se o cache for obsoleto.

Cache primeira estratégia

Desafios

IndexedDB e nossos aprendizados

Estamos usando o IndexedDB para armazenamento em cache. O IndexedDB é realmente incrível e fornece um banco de dados assíncrono baseado em transação no navegador. No entanto, ainda tivemos nossa parcela de aprendizado ao usá-lo.

  • As operações de BD indexadas são assíncronas, mas as operações de leitura / gravação podem ser lentas ocasionalmente. Veja abaixo alguns dos nossos dados de outro projeto.

Tempo gasto para inicializar a conexão entre os navegadores no Android:

Inicialize o tempo indexedDB por 24 horas

<100ms = 48,9%

> 100 ms e <500 ms = 37,7%

> 500 ms e <1000 ms = 7,1%

> 1000ms = 6,2%

Tempo gasto para recuperação de registros da loja nos navegadores no Android

Registre o tempo de recuperação por 24 horas

<100ms = 13,1%

> 100 ms e <500 ms = 37,7%

> 500 ms e <1000 ms = 64,5%

> 1000ms = 12,8%

Tempo gasto para atualização de registro de loja em navegadores no Android

Atualizar o tempo por 24 horas

<100ms = 71%

> 100 ms e <500 ms = 22,8%

> 500 ms e <1000 ms = 3,5%

> 1000ms = 2,7%

  • Criar um índice no campo correto ao criar uma loja é essencial.
  • Use ‘onupgradeneeded’ cuidadosamente (consulte nosso código abaixo).
  • Não use DB para ler até que a loja seja criada.
  • Divida suas transações de leitura / gravação (consulte nosso código abaixo).

Aqui está um exemplo de como lidamos com nossos eventos de conexão, onerror e onupgradeedeeded . Se você perceber, temos várias verificações determinando quando podemos realizar operações. Garantir que o banco de dados e todas as lojas sejam criados é essencial, já que as lojas não seriam criadas nunca até que a versão do banco de dados seja atualizada .

Outro exemplo de como precisamos ser cuidadosos com transações indexedDB.

  • Certifique-se de que o banco de dados e a tabela sejam criados antes de executar qualquer operação.
  • No erro de transação, é altamente recomendável remover a tabela e recriar o banco de dados se você não se importar com a persistência de dados.

Obtenha implementação

Limitações de espaço em disco

O armazenamento temporário é compartilhado entre todos os aplicativos da Web em execução no navegador

O Fetch usa IndexedDB, que usa internamente espaço em disco. Lembre-se, o espaço em disco é compartilhado entre os sites e cada site tem dados limitados disponíveis. Leia isto se você planeja usar o IndexedDB e o armazenamento em cache do service worker. Mantendo o espaço em disco em mente, limpamos todos os dados criados antes de 24 horas da maioria de nossas lojas (a menos que a loja precise ser persistente).

Conclusão

Para criar o Progressive Web App, você não precisa reescrever sua pilha de tecnologia; trabalhador de serviço ( nós cobriremos isto em fora próximo post ) é a espinha dorsal do PWA. É importante planejar com antecedência e dividir as responsabilidades entre o prestador de serviços e o cliente. Começamos a nossa abordagem para tornar o nosso cliente mais poderoso e delegar o restante ao prestador de serviço.

Para experimentar a nossa experiência com o Yahoo Lite, basta visitar https://www.yahoo.com/ no seu telefone Android e adicioná-lo ao seu Home-screen. Com base na versão chrome, você seria solicitado de maneira diferente. Para navegadores Firefox e Samsung, adicionar à tela inicial faz parte da barra de navegação.