
Compartilhar:
Sina é um ex-membro da equipe da Vonage. Ele atuou como Java Developer Advocate na Vonage. Com formação acadêmica, ele tem uma curiosidade geral por tudo o que se relaciona a carros, computadores, programação, tecnologia e natureza humana. Em seu tempo livre, ele gosta de caminhar ou jogar videogames competitivos.
Anunciando o SDK Java da Vonage v9.0.0
Tempo de leitura: 13 minutos
Introdução
Muita coisa mudou no SDK do Java desde a última publicação de anúncio — mais de 39 mil linhas de código , na verdade! Essa versão importante demorou bastante para chegar, trazendo inúmeras melhorias e, sim, as inevitáveis mudanças que quebram a compatibilidade, resultado de remoções e refatorações. Estou animado para finalmente compartilhar essas atualizações com vocês, já que a qualidade do SDK subiu ainda mais de nível, com cobertura de teste de 100% como resultado — o mesmo vale para o nosso SDK em Kotlin!
Implementações atualizadas
Naturalmente, manter-se atualizado com a versão mais recente do SDK é a melhor maneira de garantir que todas as funcionalidades das APIs compatíveis estejam disponíveis, além, é claro, das correções de bugs e atualizações de segurança. Em particular, foram feitas várias atualizações na Messages API, com propriedades opcionais adicionais para mensagens recebidas e enviadas, novos tipos de mensagens suportados para MMS, mensagens de reação e botão do WhatsApp, a possibilidade de marcar mensagens do WhatsApp como lidas e, é claro, suporte para mensagens RCS. Na Video API, a implementação foi atualizada para oferecer suporte a Legendas ao Vivo, Conector de Áudio, Experience Composer, a função exclusiva para Editores nos tokens de sessão, criptografia de ponta a ponta, parâmetros de taxa de bits máxima e quantização para Arquivos, além de várias correções de bugs e inconsistências.
Os webhooks também passaram por uma reformulação e foram simplificados, tendo sido transferidos para os pacotes apropriados de suas respectivas APIs. Para o Voice, você pode usar AnswerWebhook e EventWebhook para deserializar webhooks dependendo do tipo (já que as URLs de resposta e de evento geralmente são enviadas para endpoints diferentes). Para a SMS API, use MessageEvent para analisar webhooks de mensagens recebidas.
Novas APIs
Três novas APIs compatíveis foram adicionadas desde a última versão principal:
Conversation API
A tão esperada implementação da Conversation API foi inicialmente adicionada ao SDK do Java na versão 8.4.0, mas, desde então, foi aprimorada com suporte para praticamente todos os tipos de eventos. Essa API de baixo nível sustenta o funcionamento interno da Voice API, oferecendo recursos mais poderosos para lidar com chamadas e bate-papos omnicanal com vários participantes. É, sem dúvida, a maior e mais complexa API suportada no SDK, que usuários avançados e experientes agora podem utilizar com uma implementação completa e fortemente tipada, em vez de depender da referência da API REST.
Troca de chip
A API de troca de SIM é uma das APIs de rede da Vonage. Ela permite que você verifique se o cartão SIM associado a um número foi transferido para um dispositivo diferente. Por padrão, a verificação abrange os últimos 10 dias, mas pode ser configurada para qualquer período dentro dos últimos 100 dias, com precisão de uma hora. Observe que, no momento, isso está disponível apenas para números alemães e espanhóis (consulte a disponibilidade das APIs de rede). Mesmo assim, você pode experimentá-la usando nosso Playground com operadoras virtuais. Embora a chamada à API seja um processo de três etapas devido ao OAuth, o SDK simplifica isso em uma única chamada de método que automatiza tudo para você.
Verificação do número
Não deve ser confundida com o Number Insight, a API de Verificação de Número é outra API de rede que permite aos desenvolvedores verificar se o dispositivo do usuário corresponde ao seu número de celular. Ela já está integrada ao fluxo de trabalho de Autenticação Silenciosa na Verify API — veja os trechos de código para exemplos de uso. A API de verificação de número é um pouco mais complexa, pois requer várias chamadas de API. A primeira etapa consiste em criar uma URL que você pode enviar ao usuário para que ele acesse em seu dispositivo conectado à rede. Isso resultará em um callback com um código enviado ao seu servidor, o qual você então passa para a API para verificar se o número e o dispositivo correspondem. Atualmente, aplicam-se as mesmas restrições da API de Troca de SIM descritas acima.
Melhorias na qualidade de vida
Lançamentos principais oferecem uma excelente oportunidade para lidar com a dívida técnica que se acumula naturalmente ao longo do ciclo de vida do SDK, à medida que ele evolui. Este lançamento não é exceção, com uma série de funcionalidades descontinuadas desde o último lançamento principal. Essas funcionalidades descontinuadas — exceto VonageClient.Builder#setHttpClient — foram todas removidas. O setHttpClient ainda existe para clientes que precisam de opções mais personalizadas, mas muitas delas podem ser obtidas usando httpConfig , como uso de proxy, tempos limite para solicitações e definição de URIs de base; todas essas opções estão disponíveis em HttpConfig.Builder.
Além da remoção das APIs em fase de descontinuação — Meetings API e Proactive Connect —, esta versão também corrige algumas imperfeições no SDK e encapsula ainda mais métodos, classes e construtores internos, a fim de oferecer uma maneira mais consistente e simplificada de interagir com o SDK e minimizar a confusão. Para citar o mantra do Python:
"Deve haver uma — e, de preferência, apenas uma — maneira óbvia de fazer isso."
Consequentemente, as alterações que exigem atualização nesta versão dizem respeito, principalmente, à correção de inconsistências. A maioria das refatorações e alterações não afetará a maioria dos usuários, e aquelas que afetam exigem refatorações mínimas. Os principais pontos a serem observados são enums realocados (explicados mais detalhadamente abaixo), tipos de retorno mais específicos em vez de `String`, quando aplicável, e alguns casos em que métodos foram renomeados em favor de alternativas mais consistentes ou mais simples. Esperamos que essas alterações sejam relativamente fáceis de resolver, especialmente com a ajuda do seu IDE e da documentação Javadocs abrangente; no entanto, pode ser útil consultar o changelog para ter uma visão geral de quaisquer alterações não descritas neste artigo. Para a maioria das funcionalidades obsoletas que foram removidas, a alternativa já terá sido descrita no Javadoc; portanto, pode ser mais fácil se concentrar em corrigir os usos obsoletos antes de atualizar para a v9.0.0, a fim de garantir uma transição mais suave.
Exploração madeireira
A depuração e a rastreabilidade são importantes em qualquer aplicação; por isso, esse aspecto foi aprimorado na versão 8.16.0. Dada a infinidade de frameworks de registro de logs no ecossistema Java e a agora infame vulnerabilidade do Log4j, descoberta há alguns anos, o SDK do Java conta com o java.util.logging , minimizando ainda mais as dependências e possíveis problemas de compatibilidade. O registro em log é realizado principalmente realizado em AbstractMethod#execute(REQ) se o nível de registro estiver definido como FINE. A solicitação é registrada antes da chamada à API ser feita — incluindo a URI completa, o método de solicitação, os parâmetros de consulta e o corpo da solicitação. Se a chamada for bem-sucedida, o corpo da resposta também é registrado, se houver. Para um nível de registro ainda mais detalhado, consulte DynamicEndpoint.parseResponse.
Objetos JSON padronizados
A partir da versão 7.7.0, uma refatoração substancial do SDK introduziu o interface Jsonable para objetos de solicitação e resposta. Agora, todos esses objetos estendem a classe JsonableBaseObject . Isso implementa o método equals, hashCode, e toString de forma reflexiva com base nos campos do objeto, e você pode tanto serializar quanto desserializar cargas de JSON com base no modelo de dados do objeto usando o método toJson e fromJson . O último é implementado como um método estático na classe interface Jsonable .
Análise de enums padronizadas
Uma das principais mudanças que quebram a compatibilidade nesta versão é a forma como as enums são tratadas. A maioria das enums foi transferida das classes internas para o nível superior, onde faz sentido fazê-lo, e algumas foram realocadas para o com.vonage.client.common , caso sejam utilizadas por várias APIs. Além disso, a desserialização foi padronizada de maneira geral, utilizando o método Jsonable.fromString . Se a representação em string não corresponder a um valor conhecido, o método retornará null em vez de lançar uma IllegalArgumentException. Isso permite que o restante do modelo de dados do objeto seja preenchido, o que, de outra forma, teria sido impedido. Para manter a consistência com essa abordagem, o valor UNKNOWN foi removido da maioria das enums, a menos que seja um valor literal válido que possa ser retornado pela API (como é o caso do Number Insight, por exemplo).
Tipagem mais forte
Aprofundando ainda mais o tema das alterações que exigem atualização do código, esta versão aprimora os tipos utilizados nos objetos do modelo de dados. Vários tipos de retorno foram alterados de strings para enums ou para um tipo mais apropriado, como UUID, URI, Double etc. A atualização de sua aplicação para funcionar com essas alterações deve ser simples e intuitiva, mas está descrita de forma mais detalhada no no changelog.
Voice API
As mudanças mais transformadoras ficam evidentes na Voice API . Todos os métodos e classes agora estão totalmente documentados, e muitas das inconsistências foram corrigidas. Todos os métodos setter foram removidos e substituídos por construtores. Além de novos recursos e correções de bugs, houve muitas mudanças na Voice API. Por exemplo, os construtores agora aceitarão apenas uma única URL para parâmetros como eventUrl. Embora isso deva ser encapsulado em um array ao ser serializado como JSON, o SDK oculta isso para evitar confusão. O mesmo se aplica aos endpoints em Call e ConnectAction — apenas um único endpoint pode ser usado, mas, anteriormente, o SDK dava a impressão de que vários endpoints de destino poderiam ser especificados, quando, na verdade, isso ocorre apenas porque o endpoint precisa ser encapsulado em um array JSON. Por falar em endpoints, você talvez tenha enfrentado alguma confusão ao usar NCCOs para conectar uma chamada, já que havia duas classes: com.vonage.client.voice.Endpoint e com.vonage.client.voice.ncco.Endpoint. A primeira é usada em Call, enquanto o segundo é usado no ConnectAction NCCO. Agora, elas foram renomeadas para CallEndpoint e ConnectEndpoint , respectivamente, para evitar conflitos e a necessidade de nomes de classe totalmente qualificados, de modo que você possa importar ambos. Por fim, houve uma padronização no CallsFilter (que agora herda de HalFilterRequest), que utiliza Instant em vez do obsoleto Date (trocadilho intencional!), e CallInfoPage, que agora herda de HalPageResponse. Observe que a classe EmbeddedCalls foi removida; portanto, você pode acessar a lista de chamadas de forma mais direta com o método método getCallInfos() no método CallInfoPage. Por fim, conforme mencionado anteriormente, utiliza-se tipagem mais forte sempre que aplicável (por exemplo, rate e price em CallInfo agora são do tipo Double em vez de String), e as enums foram removidas das classes internas.
API de Numbers
Na versão 8.10.0, a API do Numbers foi atualizada não apenas para adicionar propriedades que faltavam, mas também para melhorar a documentação. Os setters foram removidos em favor de builders, para manter a consistência com outras APIs. A vinculação de números a um aplicativo agora funciona conforme o esperado, já que a propriedade que faltava para isso foi adicionada. O método NumbersClient#listNumbers agora retorna uma List<OwnedNumber> em vez de ListNumbersResponse, poupando a você uma chamada de método adicional, já que esse encapsulamento extra é desnecessário.
Number Insight API
Os usuários da Number Insight API ficarão satisfeitos em saber que o suporte para Advanced Insight assíncrono já foi implementado corretamente, com os tipos corretos de solicitação e resposta, ao contrário da solução improvisada que definia um sinalizador booleano no insight avançado síncrono nas versões anteriores. O parâmetro callback é obrigatório para o insight avançado assíncrono, pois é nele que a resposta completa será entregue, podendo então ser analisada em AdvancedInsightResponse usando o método Jsonable.fromJson(String, Class) .
A título de observação, talvez você esteja se perguntando o que aconteceu com a Number Insight v2. Tecnicamente, essa API estava em fase beta e, por isso, foi removida nesta versão, tendo sido adicionada na v8.2.0. A API foi renomeada para Detecção de Fraudes, mas temos planos maiores para o futuro em relação à detecção e prevenção de fraudes, assim como para o Number Insight; portanto, fiquem ligados para mais atualizações.
Interfaces da Messages API
Se você já tentou criar mensagens multicanais ou multimídia usando a Messages API no SDK do Java, talvez tenha se deparado com a necessidade de lidar com cada combinação de canal e tipo individualmente, mesmo que o código para cada caso seja idêntico. Por exemplo, considere o código usado para demonstrar todas as combinações de canais e tipos de mensagem nesta esta aplicação SpringBoot. Qual é o ponto em comum? Bem, todas as mensagens de texto (ou seja, quando o MessageType é TEXT) possuem um text(String) no construtor. Da mesma forma, todas as mensagens de mídia (ou seja, quando o MessageType for FILE, IMAGE, ÁUDIO, Video, ou VCARD) possuem um url(String) em seus construtores. Há duas maneiras de refatorá-los para que a configuração seja feita em um único lugar, sem repetição. A solução alternativa, um pouco improvisada, é por meio da reflexão. Uma opção melhor seria por meio de uma interface. É exatamente isso que foi implementado a partir da versão 8.11.0. Agora você pode converter os construtores de mensagens de texto para TextMessageRequest.Builder, e MediaMessageRequest para mensagens com um campo de URL. Como alguns canais também suportam uma legenda opcional legenda , existe também o CaptionMediaMessageRequest, que estende MediaMessageRequest com essa propriedade. Consequentemente, a aplicação de uma URL, legenda ou texto agora pode ser realizada de forma polimórfica em vários canais.
API de aplicativos – Webhooks
Ao desenvolver o SDK do Kotlin no ano passado, percebi que a forma como o SDK do Java lida com os Capabilities na API de Aplicação deixava muito a desejar, devido à sua verbosidade desnecessária e ao fato de não ser correta por definição. A implementação do SDK do Kotlin corrigiu isso, garantindo que os tipos de webhooks (por exemplo, event_url, status_url, answer_url, etc.) só podiam ser aplicados a capacidades que os suportassem. Os construtores de capacidades no SDK Java foram atualizados para serem corretos por definição, o que significa que o addWebhook e removeWebhook foram substituídos por métodos específicos para cada tipo. Por exemplo, no classe com.vonage.client.application.capabilities.Voice.Builder , agora existem os métodos event, answer, e respostaAlternativa. Para o recurso Mensagens, há status e event. Cada um desses métodos definirá a propriedade apropriada na carga JSON, tornando os construtores mais declarativos, menos prolixos e corretos por construção. Para remover um webhook, basta passar null como entrada para esses métodos.
SDK do Kotlin v2.0.0
Como o SDK do Kotlin é baseado no SDK do Java, ele foi atualizado para ser compatível com as mudanças que quebram a compatibilidade introduzidas na versão 9.0.0, o que inclui a remoção de recursos obsoletos e de funcionalidades que não são mais suportadas, como a antiga API de preçose o fluxo de trabalho “WhatsApp Codeless” na Verify API. O SDK do Kotlin segue o o Versionamento Semântico , como seria de se esperar, daí a versão 2.0.0.
Trechos de código
Uma observação rápida sobre a documentação: embora seja possível encontrar a documentação do código embutida diretamente no seu IDE ou em um visualizador de Javadoc (funciona tanto para Java SDK e Kotlin SDK), e é claro que você pode encontrar trechos de código em nosso Portal do Desenvolvedor para cada produto, talvez você queira uma visão concisa, em uma única página, de exemplos de código que demonstrem como usar cada API com o SDK. Tenho o prazer de anunciar que a geração desse arquivo agora foi automatizada tanto para o Java quanto Kotlin, para que você possa usar o Ctrl+F à vontade!
Planos para o futuro
O SDK do Java (e, por extensão, do Kotlin) continua oferecendo suporte ao Java 8 como o ambiente de execução mínimo exigido, mesmo nesta versão principal. É incrível pensar que o Java 8, lançado há 11 anos no momento da redação deste artigo, ainda seja relevante e utilizado em 2025. No entanto, frameworks populares migraram para o Java 17 como requisito mínimo, e até mesmo as principais ferramentas de compilação das quais dependemos (Maven, Gradle) descontinuaram o suporte ao Java 8. Além disso, o Apache HTTP Client 4, no qual o SDK do Java se baseia, teve seu desenvolvimento ativo encerrado. Enquanto isso, o suporte a chamadas assíncronas/reativas já vem sendo solicitado há muito tempo. Para facilitar isso, e talvez apenas para atualizações de segurança, seria prudente mudar a versão de referência para o Java 11, que introduziu um cliente HTTP integrado no JDK. Ao utilizar esse recurso em vez de uma dependência externa, o tamanho do Client SDK pode ser ainda mais reduzido, ao mesmo tempo em que a carga de manutenção e segurança do cliente HTTP subjacente é transferida para a própria plataforma. Portanto, eu o encorajo a migrar do Java 8, tanto como uma boa prática geral quanto como preparação para a próxima versão principal.
Conclusão
E essas são todas as alterações que você precisa conhecer na versão 9.0.0 do Java SDK e na versão 2.0.0 do Kotlin SDK que a acompanha. Para um resumo mais abrangente das alterações, consulte CHANGELOG.md para Java e Kotlin , respectivamente. Caso encontre algum problema ou tenha sugestões de melhorias, fique à vontade para abrir uma solicitação no GitHub ou dar uma passada no nosso Slack da Comunidade. Espero que você tenha uma ótima experiência ao usar as APIs da Vonage com a versão mais recente dos SDKs para Java e Kotlin!
Compartilhar:
Sina é um ex-membro da equipe da Vonage. Ele atuou como Java Developer Advocate na Vonage. Com formação acadêmica, ele tem uma curiosidade geral por tudo o que se relaciona a carros, computadores, programação, tecnologia e natureza humana. Em seu tempo livre, ele gosta de caminhar ou jogar videogames competitivos.