ID TECH
Contato
Todos os posts técnicos

Post Técnico

Conecte-se a Leitores de Cartão USB com Websockets

É possível conectar qualquer leitor de cartão USB a qualquer navegador web usando Websockets e NodeJS. Isso significa que você pode realizar transações EMV a partir de um Terminal Virtual. Veja como fazer isso a seguir!

Na última vez, mostrei como configurar a conectividade USB via JavaScript usando NodeJS e um módulo chamado node-hid. O resultado foi que conseguimos obter acesso programático a dispositivos USB, via JavaScript, em apenas cerca de 75 linhas de código. Nosso script implementou detecção e conexão automática de dispositivos, e nos forneceu um identificador de dispositivo para leitura e gravação de dados USB.

Tudo isso é suficiente, caso você precise apenas de acesso programático a dados USB dentro de um script Node.

Mas e se você quiser comunicar esses dados a outro processo? E se, por exemplo, quiser enviar dados USB para um navegador web? Ou transmiti-los para um servidor?

Sem problema. É possível fazer isso. É simples!

WEBSOCKETS AO RESGATE

O Protocolo Websocket (especificação IETF aqui) é um dos padrões Web mais incrivelmente úteis a surgir em muito, muito tempo. E, felizmente, é implementado por todos os navegadores modernos. Além disso, está disponível para scripts Node. O que significa que seu código Node pode se comunicar com seus scripts de navegador com bastante facilidade, bastando criar uma conexão de socket que une esses dois mundos.

No lado do Node, você precisará abrir um console do sistema operacional e executar npm install socket.io -g (apenas uma vez) para instalar o amplamente utilizado e merecidamente popular módulo socket.io . Após fazer isso, seus scripts poderão chamar require("socket.io") para aproveitar o incrível poder desse módulo. (Mais detalhes sobre isso em instantes.)

No lado do navegador, você precisa apontar para o socket.io.slim.js script, para que sua página web possa consumir dados via Websocket. (Não tente usar a API padrão de Websocket do navegador para isso, pois o módulo socket.io mencionado utiliza seu próprio esquema de keep-alive, que não é reconhecido pelo navegador. Para evitar conflitos, use o script cliente socket.io.slim.js. Como benefício adicional, o script inclui polyfills que garantem compatibilidade com Websocket em navegadores mais antigos.) A maneira mais fácil de obter o script cliente é baixá-lo de um servidor de borda (CDN), inserindo o seguinte trecho em sua página web:

Com esse script instalado, sua página web está pronta para se conectar aos sockets servidos pelo seu próprio servidor de socket.

SERVINDO WEBSOCKETS

Vamos falar sobre como configurar um servidor de socket em modo loopback (ou seja, em ws://localhost). É incrivelmente simples e extremamente útil para comunicação entre processos.

Você vai precisar do Node, é claro, e também do módulo socket.io (conforme descrito acima). Em seguida, basta iniciar o Node e fazê-lo executar um script como o seguinte:

Desconsiderando os comentários, estamos falando de apenas cerca de 30 linhas de código. Conceitualmente, o que acontece é que nós require('http')para que possamos configurar uma instância fictícia de servidor HTTP. Em seguida, require('socket.io').listen(server) para que o módulo socket.io possa converter as requisições HTTP recebidas em conexões Websocket.

Por padrão, as conexões Websocket habilitam comunicação full-duplex, baseada em mensagens e ponto a ponto entre as partes conectadas. No entanto, comunicação ponto a ponto não significa que as mensagens são automaticamente transmitidas para outras conexões. Para habilitar o broadcasting, registramos um listener de eventos personalizado, o on.('echo') listener na linha 58, que re-emite as mensagens "echo" recebidas para todas as conexões de socket, como uma nova mensagem do tipo 'message'. Portanto, a regra aqui é: para mensagens ponto a ponto, utilize o tipo de evento 'message'; mas para garantir que o servidor de socket repasse sua mensagem a todos os listeners, utilize o tipo de mensagem 'echo'. (Esta é uma convenção nossa, aliás, não algo imposto pelo socket.io.)

O último ponto a observar é que o código acima, por si só, não faz nada, pois trata-se de uma definição de classe. É necessário instanciar a classe em tempo de execução para utilizá-la. Mas isso é muito simples. Os comentários no início do código explicam como usar a classe. Além disso, veremos como utilizá-la nas próximas publicações do blog.

Não perca as próximas publicações desta série, pois em breve estaremos realizando transações sem contato em um gateway real — tudo pelo navegador, usando JavaScript! Fique atento!