‫Palestrante: E agora para finalizar esse projeto,
‫vamos finalizar essa integração do Stripe com os webhooks.
‫Vamos começar a lembrar como nossa integração
‫Stripe realmente funciona agora.
‫Temos esse endpoint de sessão de
‫checkout, que é chamado de nosso front-end.
‫Isso então chamará a função getCheckoutSession, basicamente esta
‫aqui, que criará
‫uma sessão de checkout no servidor usando todas
‫essas informações aqui e, em seguida,
‫a enviará de volta ao cliente.
‫Depois que o processamento do pagamento
‫for feito com sucesso pelo
‫Stripe, redirecione o usuário para esta URL de sucesso,
‫esta que criamos.
‫Lembre-se de que neste URL adicionamos o ID do tour, o
‫ID do usuário e também o preço.
‫Fizemos isso para que, uma vez que este URL fosse chamado, nosso
‫aplicativo criasse um novo documento de reserva em
‫nosso banco de dados.
‫Como isso funcionou?
‫Na rota my-tours, temos um middleware para isso.
‫Lembre-se, aqui no viewRoutes, em my-tours,
‫temos este createBookingCheckout.
‫Esta função aqui, que basicamente a partir da consulta pega o
‫tour, o usuário e o preço, e
‫cria uma entrada no banco de dados usando esses dados.
‫Basicamente, colocamos esses dados no URL
‫sempre que o Stripe processa um pagamento com sucesso.
‫E então essa função de middleware que temos
‫aqui coleta os dados e cria uma nova reserva em nosso sistema
‫usando esses dados.
‫E depois disso, basicamente redirecionamos aqui para
‫o URL original sem a string de consulta.
‫Agora, o problema com isso é que não é realmente seguro.
‫Então, todos que conhecem essa estrutura de
‫URL, este aqui em cima, que tour, usuário e preço na
‫string de consulta, pode basicamente criar uma reserva em
‫nosso sistema sem realmente pagar.
‫Então, tudo o que teríamos que fazer é abrir este
‫URL com alguns
‫dados lá e, a partir daí, criar automaticamente uma
‫reserva sem passar pelo processo de Stripe.
‫Lembre-se de como eu disse que resolveríamos
‫isso usando algo chamado webhooks.
‫Então, fazemos isso agora.
‫Porque, para
‫isso, realmente precisamos que nosso site seja implantado.
‫Agora, neste ponto, esse é realmente o caso.
‫E agora podemos implementar esses webhooks.
‫Para isso, vamos ao nosso painel Stripe.
‫E na verdade eu já o abri aqui.
‫Em seguida, vá aqui para os desenvolvedores, escolha webhooks
‫e, aqui, adicione um novo endpoint.
‫Agora, o que é este ponto de extremidade aqui e este webhook?
‫Basicamente, vamos especificar um URL aqui para o
‫qual o Stripe enviará automaticamente uma solicitação POST sempre que uma
‫sessão de checkout for concluída com êxito, basicamente
‫sempre que um pagamento for bem-sucedido.
‫Com essa solicitação POST, o Stripe enviará de volta os dados
‫da sessão original que criamos na primeira etapa quando
‫criamos a sessão de verificação.
‫Essa é a razão pela qual realmente precisávamos que
‫nosso site fosse implantado aqui, porque agora precisamos especificar aquele
‫URL da vida real aqui.
‫Vamos pegar isso
‫daqui e, em seguida, adicionar nossa rota aqui, basicamente.
‫Vou chamar isso de webhook-checkout.
‫Não está na API e não está nas reservas.
‫Você verá em um momento o porquê disso.
‫Novamente, quando um pagamento foi bem-sucedido,
‫o Stripe postará automaticamente os
‫dados da sessão original neste URL.
‫Agora também precisamos selecionar o evento.
‫E você vê que há muitos eventos que poderíamos usar aqui.
‫O que estamos usando é checkout_session_completed.
‫Adicione isso.
‫Agora você precisa inserir sua senha aqui novamente.
‫E aí vamos nós.
‫Este webhook também tem um segredo aqui.
‫Este, nós também precisaremos em um segundo
‫quando realmente criarmos nossa rota para este URL aqui.
‫Na verdade, é exatamente o que vamos fazer a seguir.
‫Basicamente, em nosso sistema,
‫é claro, agora precisamos de uma rota para isso aqui,
‫de modo que quando o Stripe postar os dados em nosso
‫aplicativo, possamos realmente fazer algo com eles.
‫Vamos voltar aqui e abrir nosso aplicativo.
‫Na verdade, vamos adicionar essa rota aqui.
‫Novamente, vou explicar o porquê em um segundo.
‫Então, app. post
‫e rota padrão e então, é claro, precisamos
‫de uma função de manipulador para isso.
‫Vamos criá-lo rapidamente aqui em nosso bookingController.
‫Deixe-me chamar isso de exportação. webhookCheckout.
‫Agora terei que importar este controlador para o aplicativo. js.
‫Vamos fazer isso aqui mesmo depois do bookingRouter,
‫então este e este, controlador
‫e aqui também controlador.
‫Tudo bem.
‫Agora aqui embaixo, é o bookingController. webhookCheckout.
‫Agora, por que realmente definimos este webhook-checkout aqui
‫mesmo no aplicativo. js em vez de
‫fazê-lo, por exemplo, no bookingRouter.
‫A razão para isso é que nesta função de manipulador,
‫quando recebemos o corpo do Stripe, a
‫função Stripe que usaremos para
‫realmente ler o corpo precisa desse corpo em uma forma bruta,
‫basicamente como uma string e não como JSON.
‫Novamente, nesta rota aqui, precisamos que o
‫corpo que vem com a solicitação não esteja em JSON,
‫caso contrário, isso não vai funcionar de jeito nenhum.
‫Agora, o fato é que, assim que uma solicitação
‫chegar a este middleware aqui, o corpo será analisado
‫e convertido para JSON.
‫Em seguida, será colocado a pedido. corpo como um objeto JSON simples.
‫Novamente com isso, este manipulador de rota
‫aqui não funcionaria.
‫Essa é a razão pela qual precisamos colocar essa rota aqui antes
‫de chamarmos o analisador de corpo.
‫Agora ainda precisamos analisar o corpo, mas em
‫um formato denominado bruto.
‫No momento em que eu estava gravando este vídeo, não
‫podíamos fazer isso com o Express pronto para uso.
‫E então, neste vídeo, baixamos o analisador de corpo do npm e
‫o usamos como mostro no vídeo.
‫No entanto, cinco dias depois de gravar este
‫vídeo, o Express também adicionou o analisador bruto ao Express.
‫Agora podemos usar o expresso. raw em vez de instalar
‫o analisador de corpo ou middleware do npm.
‫Novamente, neste vídeo, irei instalar o analisador de corpo, mas
‫você realmente não precisa.
‫Você pode apenas usar expresso. em vez disso cru.
‫Npm instala o analisador
‫de corpo.
‫Isso provavelmente soa um pouco focado, e eu
‫entendo isso perfeitamente, mas é assim
‫que a documentação do Stripe funciona e nos obriga
‫a fazê-lo, de verdade.
‫Vamos voltar aqui para nossa rota.
‫Nesta rota, precisamos que o corpo esteja em um formato bruto.
‫Podemos adicionar isso como um middleware aqui entre a rota e
‫o manipulador final.
‫Aqui dizemos bodyParser. raw, e
‫também precisamos especificar aqui o
‫tipo muito rápido como application / json.
‫Agora adicionamos esta análise de corpo como um corpo bruto aqui nesta
‫pilha de middleware.
‫Tudo isso realmente começará a se
‫encaixar assim que começarmos a implementar essa função.
‫Na verdade, vamos fazer isso
‫agora, então bem aqui.
‫Mas antes de realmente fazermos
‫isso, vamos nos livrar de todo o código
‫que escrevemos para que funcione agora.
‫Então, basicamente essa função de middleware,
‫não precisamos mais dela.
‫Também aqui no
‫viewRoutes, não precisamos mais dele aqui também.
‫E, finalmente, no bookingController, vamos
‫também definir nosso URL de volta ao normal.
‫Vou apenas deixar tudo isso aqui para que
‫você possa mantê-lo como uma referência.
‫Mas agora o URL de sucesso deve ser apenas este.
‫Basicamente, após uma reserva bem-sucedida, ainda
‫queremos voltar para my-tours, mas sem todos
‫esses parâmetros de consulta
‫porque agora não é mais esta função aqui, que
‫se encarregará de criar a reserva, mas
‫em vez disso é esta função
‫aqui, que é de claro, aquele
‫que é chamado assim que o Stripe chama nosso webhook.
‫Agora vamos implementar isso.
‫A primeira coisa que
‫precisamos fazer é livrar essa assinatura Stripe de nossos cabeçalhos,
‫então assine e depois solicite. cabeçalhos e,
‫a partir daí, assinatura de faixa.
‫Basicamente, quando o Stripe chama nosso webhook,
‫ele adiciona um cabeçalho a
‫essa solicitação contendo uma assinatura especial para nosso webhook.
‫Se você está pensando que está apenas seguindo
‫cegamente o que estou fazendo
‫aqui, bem, (risos) isso é exatamente o que eu
‫fiz também com as documentações do Stripe.
‫Novamente, é realmente assim que o Stripe funciona, e não
‫há nada que possamos fazer contra isso.
‫De qualquer forma, a seguir, vamos criar
‫um evento Stripe, então o evento const é igual a stripe.
‫Para isso, é claro, precisamos da biblioteca Stripe
‫instalada, que temos aqui.
‫Então, stripe. webhooks. contructEvent.
‫Agora é aqui que finalmente esse corpo entra
‫em ação, então peça. corpo.
‫E lembre-se de que este corpo
‫aqui precisa estar na forma
‫bruta, então basicamente disponível como uma corda.
‫Mais uma vez, é por isso que colocamos essa rota
‫antes de todas as nossas
‫outras rotas e especialmente antes que o analisador de corpo pudesse
‫fazer seu trabalho de converter nosso corpo em um objeto JSON.
‫Além desse corpo, para o evento, precisamos de uma assinatura, basicamente a
‫assinatura que foi enviada junto
‫com o cabeçalho e, finalmente, nosso segredo do webhook.
‫Vamos começar aqui, copie.
‫Como é um segredo, devemos, como sempre, adicioná-lo aqui
‫ao nosso
‫arquivo de configuração, então STRIPE_WEBHOOK_SECRET.
‫E mais tarde, é claro, não se esqueça de
‫adicionar isso também à configuração do Heroku.
‫Vamos agora usar isso.
‫Adicionar processo. env.
‫Eu deveria ter apenas copiado
‫isso aqui.
‫Então, você vê, tudo isso é realmente para tornar
‫o processo super, super seguro.
‫Precisamos de todos esses dados, como
‫a assinatura e também o segredo, a fim de validar
‫basicamente os dados que vêm
‫no corpo para que ninguém possa realmente manipulá-los.
‫Agora, durante a criação deste evento,
‫podem ocorrer alguns
‫erros, por exemplo, se a assinatura
‫estiver errada ou se o segredo estiver errado.
‫E então, vamos embrulhar isso em um bloco try-catch.
‫OK.
‫Claro, agora precisamos do truque.
‫Caso haja um
‫erro, queremos enviar de volta um erro
‫para o Stripe, então retorne res. status 400 e, em seguida, basta usar enviar
‫erro do webhook e, em
‫seguida, vamos apenas adicionar o erro. mensagem.
‫Então, é o Stripe quem vai receber essa resposta aqui,
‫porque novamente é o Stripe quem vai realmente chamar a URL,
‫então nosso webhook, que vai chamar essa função.
‫Agora precisamos, é claro, também declarar esse evento aqui fora
‫do bloco try-catch, porque do
‫contrário não seremos capazes de usá-lo lá.
‫Então, deixe o evento e então reatribua aqui porque lembre-se de
‫que o ES6 const e let
‫têm escopo de bloco.
‫E assim, essa variável não estaria disponível fora
‫deste bloco.
‫Agora, vamos realmente usar esse evento.
‫Primeiro, precisamos testar se este é realmente o evento
‫que queremos.
‫Então, podemos fazer um evento. tipo é igual
‫a check-out. sessão. completo.
‫Lembre-se de que em nosso painel
‫do Stripe, esse é exatamente o tipo que definimos aqui.
‫Então, esse é o tipo de evento.
‫Agora estamos verificando se esse é realmente
‫o evento que estamos recebendo aqui, apenas para termos 100% de certeza.
‫Em caso afirmativo, queremos realmente usar o evento para criar nossa
‫reserva em nosso banco de dados.
‫Na verdade vamos fazer isso em uma função
‫separada e não aqui dentro de toda essa bagunça.
‫Para isso, vou criar uma função.
‫Na verdade, deixe-me
‫dar exatamente o mesmo nome, então, crieBookingCheckout.
‫Na verdade, era um bom nome, mas
‫agora não pode ser um middleware,
‫mas apenas uma função normal.
‫Esta função aceitará os dados da sessão.
‫E lembre-se de que os dados da sessão são exatamente esta sessão
‫que criamos aqui em primeiro lugar.
‫Se este for o evento correto,
‫então vamos realmente chamar essa
‫função, então crieBookingCheckout com a sessão, que está
‫no evento. dados. objeto.
‫E, finalmente,
‫vamos enviar de volta alguma resposta ao Stripe.
‫Então, status
‫200 e digamos algum recebimento
‫json definido como verdadeiro.
‫Faz sentido?
‫Mais uma vez, todo esse código
‫aqui será executado sempre que um pagamento for bem-sucedido.
‫O Stripe irá então chamar nosso webhook, que é a URL,
‫que irá chamar esta função.
‫E assim, esta função recebe um corpo da requisição, e
‫então junto com a assinatura e / ou segredo do webhook, cria
‫um evento, que irá conter a sessão.
‫E então, usando os dados da
‫sessão, podemos criar nossa nova reserva no banco de dados.
‫E então, isso será bem parecido com
‫o que tínhamos aqui antes.
‫Portanto, precisaremos dessa linha de código aqui novamente.
‫Portanto, esta também será uma função assíncrona.
‫E então, isso é exatamente o mesmo.
‫Agora, o que precisamos
‫aqui, é claro, é obter acesso ao tour, ao usuário e ao preço.
‫Mas esses dados mais uma vez são armazenados nessa sessão.
‫Então, vamos começar com o tour.
‫E lembre-se de como aqui, quando
‫criamos essa função de manipulador
‫pela primeira vez, eu especifiquei este campo client_reference_id
‫e adicionei o tourId a ele.
‫Lembre-se disso?
‫Fiz isso porque, na época,
‫já sabia que iríamos precisar desse tour ID um pouco mais tarde.
‫Agora é o momento em que realmente precisamos
‫do ID do tour para poder criar essa nova reserva.
‫E então, agora o ID do tour
‫de que precisamos está no ID de referência do cliente ponto da sessão.
‫Então, vamos copiar isso e dizer
‫sessão.
‫E, claro, aqui precisamos dizer tour.
‫Então, esse é o ID do tour.
‫Em seguida, precisamos do ID do usuário.
‫Agora, a informação que temos em
‫nossa sessão sobre o usuário é o e-mail do usuário.
‫E então, agora o
‫que precisamos fazer é basicamente obter o ID do usuário.
‫Para isso, faremos a consulta pelo email.
‫Isso não é problema porque o e-mail também é único.
‫Com base nisso, podemos encontrar o ID exclusivo.
‫Portanto, o usuário const está aguardando.
‫E acho que já temos o usuário aqui.
‫Não?
‫Não, na verdade não quero.
‫Então, vamos apenas fazer isso aqui.
‫E usuário aqui também.
‫OK.
‫Então, usuário. findOne e depois consulta via email, que
‫está no ponto da sessão, e acredito que seja o
‫email do cliente ou algo assim.
‫É cliente_email.
‫OK.
‫Mas isso retornará o documento inteiro, mas
‫queremos realmente o ID.
‫Então, vamos embrulhar tudo isso aqui entre
‫parênteses e então chamar o ID ali ou realmente ler o ID.
‫Então é isso.
‫E finalmente, o preço.
‫Onde o preço está armazenado?
‫Bem, está aqui em line_items.
‫Isso é uma matriz, portanto, no
‫elemento zero e a quantidade dividida por 100.
‫Então, multiplicamos aqui por 100 para obter centavos, mas agora
‫é claro que queremos de volta em dólares.
‫Então, precisamos basicamente dividir isso de volta.
‫E então, sessão. line_items e a
‫quantidade de pontos do primeiro elemento, se estou certo.
‫Sim.
‫Portanto, o valor é dividido por 100.
‫Deve ser isso.
‫Agora, vamos enviar nossas alterações para o repositório
‫e enviá-lo para o Stripe.
‫Então, git add all, é
‫claro, e git commit message
‫Implementação de stripe
‫aprimorada e git push heroku master.
‫Mais uma vez, isso levará algum tempo.
‫Vejo você quando terminar.
‫Tudo bem.
‫Agora não se esqueça de definir essa nova variável de ambiente.
‫Então, esse é o conjunto de dois pontos de configuração do
‫heroku e simplesmente copie-o daqui.
‫OK.
‫Isso então reinicia o aplicativo.
‫E é isso.
‫Então, vamos realmente prosseguir e testá-lo.
‫Tudo bem.
‫Ainda estamos aqui em nosso aplicativo.
‫Vamos ver quais tours a Laura já reservou.
‫Ela tem o Caminhante da Floresta.
‫Essa reserva ainda era feita usando o método antigo.
‫Mas esse método antigo não funciona mais.
‫Agora, se fizermos outra reserva e
‫funcionar, bem, isso significará
‫que, é claro, nossa nova implementação funciona.
‫Vamos testar isso aqui.
‫Como sempre, 4242.
‫Agora vamos esperar.
‫Bem, isso aparentemente não foi muito bem, porque
‫caso contrário, nossa segunda nova turnê já deveria
‫estar aqui em nossas reservas.
‫Vamos ver aqui em nosso painel.
‫Se recarregarmos
‫agora, veremos de fato que houve um evento bem-sucedido.
‫Então, esse é o evento que acabamos de
‫criar e que enviou este corpo aqui
‫e depois recebeu esta resposta.
‫Portanto, este recebimento definido como verdadeiro
‫é exatamente o que fizemos aqui em nosso código,
‫isso aqui.
‫Então, essa é a resposta
‫que enviamos e o corpo que recebemos contém todos esses dados.
‫E assim, podemos ver aqui a sessão
‫com o preço, com o email, com o tour.
‫E então, não sei por que não funcionou.
‫Então, vamos recarregar rapidamente aqui.
‫Então, na verdade, nossa implementação do Stripe deve estar correta, mas,
‫por algum motivo, nossa nova reserva não foi criada.
‫Vamos verificar isso também aqui no Compass.
‫E, de fato, não está lá.
‫Então, vamos voltar ao nosso código aqui.
‫Ah, e um erro que vejo imediatamente está aqui.
‫Portanto, deve ser concluído assim.
‫Então, isso é um erro estúpido.
‫Vamos ver se pode
‫haver outro erro aqui em createBookingCheckout.
‫Aqui temos
‫line_items.
‫Vamos ver se isso está correto.
‫E sim, parece ser.
‫Também podemos confirmar isso aqui novamente no nosso Stripe.
‫Na verdade, aqui é chamado display_items.
‫Isso é estranho.
‫Só para ter certeza, vamos chamá-lo de display_items
‫aqui em nosso código.
‫Outra coisa que notei ao
‫dar outra olhada aqui
‫é que ainda temos essa imagem codificada para este
‫outro tipo. dev.
‫Agora vamos corrigir isso porque, neste ponto, é claro,
‫nosso site já está ativo e implementado.
‫E então, podemos basicamente substituir isso pelo
‫mesmo que temos aqui.
‫Então, usamos essa parte aqui muitas vezes.
‫E então, é hora de usar isso novamente aqui.
‫Sim.
‫Vamos tentar reimplantar isso.
‫Então, git add all again.
‫E vamos chamar isso
‫aqui Implementação de fração aprimorada dois.
‫E então empurre novamente para Heroku.
‫OK.
‫Vamos tentar mais uma vez.
‫Vamos voltar aqui.
‫Agora vamos tentar reservar novamente para Park Camper.
‫Tudo bem.
‫Você deveria ver a imagem aparecendo aqui no lado esquerdo.
‫Isso significa que nossa nova integração de
‫imagem também funcionou bem.
‫Agora está em processamento.
‫Ah, agora está aqui.
‫Excelente.
‫Isso é bonito.
‫Agora realmente temos uma implementação de
‫Stripe segura e muito mais profissional em
‫nosso aplicativo.
‫Isso é ótimo.
‫Claro, se você recarregar
‫aqui, então você deverá ver este novo evento aqui, então
‫esta nova chamada para o nosso webhook,
‫que é claro novamente foi um sucesso.
‫Isso é ótimo.
‫Agora, há apenas uma última coisa que quero fazer,
‫que é basicamente dar ao usuário algum feedback na forma
‫de uma dessas mensagens verdes que usamos
‫também, por exemplo, no login.
‫No momento, nosso aplicativo não dá
‫nenhum tipo de feedback quando um novo tour foi agendado.
‫Agora eu quero mudar isso.
‫No entanto, fazer isso não é muito simples, pois
‫lembre-se de que essas
‫mensagens são, na verdade, exibidas por JavaScript.
‫Então, nos outros casos, fizemos uma chamada HTTP para nossa API.
‫E então, quando isso foi feito, usamos JavaScript para
‫exibir algum tipo de mensagem.
‫Mas agora não fazemos desta forma.
‫E assim, a mensagem já deve estar em algum lugar
‫do HTML assim que a
‫página carregar, para que então nosso JavaScript possa
‫pegar essa mensagem do HTML e exibi-la bem lá em
‫um desses banners.
‫E assim, vou colocar esses alertas no
‫HTML mais uma vez usando uma propriedade de dados.
‫Vamos começar implementando esse recurso ali mesmo em
‫nosso modelo principal.
‫Isso está aqui em visualizações, base.
‫Na verdade, irei adicionar essa mensagem de alerta
‫diretamente no elemento do corpo.
‫Aqui teremos uma propriedade de alerta de dados, que
‫na verdade só deve ser definida
‫se a variável de alerta estiver disponível aqui.
‫Então, vamos usar ES6, uma string de template, e
‫dizer se houver um alerta, então
‫use alert aqui, e então, uma string vazia.
‫E então, este alerta aqui será a mensagem de
‫alerta que o JavaScript irá então pegar e exibir na página.
‫Agora, como essa mensagem de alerta acaba realmente como uma
‫variável de alerta aqui em nosso modelo?
‫Bem, eu vim com uma solução que é reutilizável para
‫que possamos usar em todo o nosso aplicativo.
‫Ou seja, na string de consulta, adicionaremos alguma
‫palavra-chave de alerta e então teremos
‫um middleware, que pegará essa
‫palavra-chave do URL e, de acordo com a
‫palavra-chave que colocarmos lá, colocaremos uma mensagem
‫de alerta inteira na resposta . habitantes locais.
‫E então, lembre-se de que tudo está em resposta. locals está então disponível
‫como uma variável em todos os nossos modelos.
‫Então, nós realmente usamos isso antes
‫em nosso authController, eu acredito.
‫Muito rapidamente, deixe-me mostrar isso a você.
‫Bem aqui, dissemos resposta. local. usuário e
‫colocar o usuário atual lá.
‫Então, automaticamente em todos os modelos, temos
‫acesso a essa variável de usuário.
‫Então, vamos agora implementar o que acabei de
‫dizer e começar com a URL.
‫O que vou fazer aqui é realmente adicionar essa string de consulta
‫aqui ao URL de sucesso.
‫Aqui, direi reserva igual de alerta.
‫Agora eu poderia, em todos os outros URLS, também adicionar algum alerta e, em
‫seguida, com uma palavra-chave diferente aqui, é claro.
‫E faremos aqui apenas para esta reserva.
‫Mas, novamente, criei uma espécie de solução reutilizável aqui.
‫De qualquer forma, agora em nossas rotas, precisamos basicamente de um middleware,
‫que será executado para todas as solicitações.
‫E é esse middleware, que pegará o alerta
‫da string de consulta e colocará uma mensagem de alerta
‫em nossa resposta. habitantes locais.
‫Então, roteador.
‫use viewsController. alertas.
‫E, portanto, esta é uma
‫função de middleware, que basicamente será executada para cada solicitação que
‫chega a este roteador,
‫basicamente para todas as solicitações para nosso site.
‫Agora, vamos realmente criar esse middleware em
‫nosso viewsController.
‫Então, exportações. solicitação
‫de alertas, resposta e próximo.
‫E assim,
‫o alerta é pedido. inquerir. alerta.
‫E então, vamos usar essa estruturação aqui mais uma vez.
‫E digamos que alert é igual a reserva, então o
‫alerta que colocamos bem aqui na string de
‫consulta, bem,
‫nesse caso, digamos resposta. habitantes locais. alerta se a sua
‫reserva
‫for bem
‫sucedida, por favor
‫verifique o seu email para uma confirmação.
‫E devemos também adicionar alguma
‫outra frase, que é esta, se a sua reserva não, selecione
‫esta, não aparece aqui imediatamente, por favor volte
‫mais tarde.
‫E esta
‫última parte é porque o Stripe diz muito
‫especificamente em sua documentação que às vezes o webhook é chamado
‫um pouco depois que a URL de sucesso é chamada.
‫Nesse caso, esse URL de sucesso mostraria todos
‫os passeios atuais, mas somente depois disso, o
‫webhook seria chamado e
‫o passeio seria criado em nosso banco de dados.
‫Portanto, a nova reserva não aparecerá imediatamente
‫na página Minhas reservas.
‫Mas, claro, tudo ainda funcionou bem nesse caso.
‫E então, eu simplesmente recarrego, mas mais tarde iremos consertar esse problema.
‫Agora só precisamos chamar o próximo middleware.
‫E é isso mesmo.
‫Novamente, só fizemos isso aqui para alerta igual a reserva, mas agora
‫podemos usar isso em todo o lugar
‫em nosso site, definindo diferentes palavras-chave de alerta
‫e strings de consulta.
‫Com isso, colocamos essa mensagem aqui no res. habitantes locais. alerta.
‫Mais uma vez, nosso modelo de base pegará isso
‫e o exibirá aqui nesta propriedade de alerta de dados.
‫E então, tudo o que resta fazer agora é ir para o nosso índice. js e leia
‫o alerta aqui e depois exiba-o.
‫E então, isso deve ser bastante fácil.
‫Aqui em público, vamos realmente fazer isso direito no índice.
‫E a primeira coisa é que realmente precisamos importar a função
‫de alertas.
‫Isso não é um aplicativo.
‫Está aqui no índice.
‫OK.
‫E aqui embaixo, vamos basicamente ler esse alerta.
‫Portanto, const alertMessage, digamos, é um
‫documento. querySelector, o elemento
‫body e dot dataset. alerta.
‫E assim, apenas se houver um
‫alerta, é claro, mostre o alerta
‫com sucesso
‫e a mensagem de alerta.
‫E agora, uma pequena coisa que eu
‫quero fazer é mudar um pouco a função showAlert aqui, porque
‫na verdade temos muito texto agora.
‫E o tempo padrão em que o alerta
‫é mostrado não seria suficiente para realmente ler todo o texto.
‫Então, você vê aqui que depois de cinco segundos,
‫o alerta está oculto.
‫Vamos permitir que o usuário
‫especifique a quantidade de segundos que o alerta é mostrado.
‫Faremos isso como um padrão de cinco segundos.
‫Aqui, simplesmente calculamos o tempo vezes 1.000 para convertê-lo
‫em milissegundos.
‫Assim, todas as funções funcionarão em qualquer
‫lugar em cinco segundos.
‫Na verdade, vamos esperar sete segundos,
‫se não especificarmos nada.
‫Mas se quisermos, podemos substituir este sete.
‫E então, vou colocar
‫isso agora e colocar 20 segundos na tela.
‫Tudo bem.
‫Eu acho que deveria ser isso.
‫Espero que tenha feito sentido.
‫Vamos agora compilar rapidamente nosso pacote.
‫Isso é npm execute build e toque em autocomplete.
‫Isso também leva um pouco de tempo.
‫Mas agora está feito.
‫Vamos agora implantá-lo pela última vez, esperando
‫que funcione de verdade.
‫Então, git commit.
‫Então, mensagens do Stripe.
‫E uma última vez, git push heroku master.
‫Agora vamos testá-lo comprando mais um tour aqui.
‫Vamos pegar o City Wanderer desta vez.
‫Oh, acabei de ver que já existe uma mensagem aqui.
‫Isso não é bom.
‫E você vê que ele desapareceu após 20 segundos.
‫Então, parece que agora, por
‫padrão, ele sempre colocará essa classe de alerta aqui.
‫(risos)
‫Sim.
‫Isso porque aqui deve ser alertMessage e
‫não apenas alert.
‫De qualquer forma, vamos agora apenas testar se a
‫mensagem realmente está correta quando reservamos o passeio.
‫OK.
‫Agora vamos esperar.
‫Aqui vamos nós.
‫Na verdade, esta é a nossa mensagem.
‫Tão bonito.
‫Além disso, nosso tour aparece aqui.
‫E você vê que realmente fica aqui por muito tempo.
‫Então, isso também funciona.
‫Vamos muito rapidamente ...
‫E primeiro, precisamos reconstruir o pacote aqui.
‫Em seguida, podemos adicionar tudo à
‫nossa área de teste, Correção de bug de alerta de mensagem.
‫Então, essas
‫são algumas (risos) mensagens que soam realmente profissionais aqui.
‫Agora, um empurrão final para Heroku.
‫Agora, quando carregamos nossa página, não devemos
‫ver nenhuma mensagem de alerta.
‫E, de fato, agora tudo está limpo.
‫E então, agora posso dizer que pelo menos por
‫agora, esse projeto está realmente concluído.
‫Mais uma vez, ótimo trabalho, parabéns e muito bem
‫por provavelmente ser uma das poucas pessoas que realmente estão fazendo todo
‫o caminho até o final do projeto e
‫realmente construindo este lindo site e também a API que
‫você pode agora colocar em seu portfólio e mostre
‫ao mundo.