
Compartilhar:
Um professor de inglês que se tornou um engenheiro de software empático. Um otimista curioso, apaixonado por criar conteúdo acessível e ajudar desenvolvedores a aprimorar suas habilidades.
Descubra o seu Índice de Positividade no Twitter com o React
Tempo de leitura: 16 minutos
Em 2019, propus a mim mesma o desafio de espalhar positividade e gentileza no meu dia a dia.
Mas logo percebi que essa meta parecia um pouco vaga e bastante indefinida. Embora tivesse boas intenções, achei difícil avaliar seu sucesso ou impacto.
Então, durante alguns meses, refleti sobre como poderia medir minha meta e tive a sorte de descobrir que a API de Análise de Texto oferece uma maneira de acompanhar meu compromisso com a positividade!
A equipe do Azure disponibilizou seus algoritmos de aprendizado de máquina como código aberto, o que significa que posso analisar a pontuação de sentimento de qualquer texto em uma escala numérica de 0 a 1 (sendo 0 negativo e 1 positivo).
Isso significa que posso avaliar a forma como me expresso e verificar se realmente tenho espalhado gentileza e positividade, especialmente nas minhas postagens nas redes sociais!
Então, pensei em criar um aplicativo em React que utilize a API do Twitter para buscar meu tweet mais recente e analisar seu sentimento, para depois usar Messages API da Nexmo para enviar um relatório para mim mesmo!
Dá uma olhada:
Pré-requisitos
Para seguir este tutorial, você precisará de um Account na Vonage. Você pode se cadastrar agora para grátis , caso ainda não tenha um Account.
Além disso, você também precisará de:
a Desenvolvedores do Twitter Account
a API Rapid Account
Como descobrir sua pontuação de positividade no Twitter com o React
Você vai realizar as seguintes tarefas para criar seu aplicativo:
Criar um servidor de back-end com o Express
Crie um aplicativo front-end com React
Crie um componente React para receber um nome de usuário do Twitter
Recuperar o tweet mais recente com a API do Twitter
Calcular a pontuação de sentimento com a API do Microsoft Azure
Envie esse relatório para o seu celular usando a Messages API da Nexmo
Este tutorial vai guiá-lo pelo processo desde o início. No entanto, se você quiser ver o código final, pode clonar o repositório Git deste projeto.
Criar um servidor de back-end com o Express
Para começar, no diretório raiz deste projeto, execute:
Isso cria um package.json arquivo, permitindo que você comece a instalação com apenas algumas dependências.
Para fazer isso, execute:
Para que você possa executar seu servidor e seu cliente usando um único comando npm run dev, abra seu package.json arquivo e altere os scripts para que fiquem assim:
// package.json
"scripts": {
"start": "node server.js",
"server": "nodemon server.js",
"client": "npm start --prefix client",
"dev": "concurrently \"npm run server\" \"npm run client\""
},Em seguida, crie mais três arquivos na raiz do seu diretório:.env, server.js e private.key:
Preencha seu .env arquivo com as credenciais do Nexmo e do Twitter. Deve ficar assim:
# .env
# Nexmo's credentials
API_KEY=*****
API_SECRET=*********
APPLICATION_ID=**********
NEXMO_NUMBER=***********
# Twitter's credentials
CONSUMER_KEY=*******
CONSUMER_SECRET=*******
ACCESS_TOKEN_KEY=**************
ACCESS_TOKEN_SECRET=*************Para inserir a chave e o segredo da API, acesse a página da Nexmo página “Introdução” do seu Painel de Controle. E você pode obter o ID da aplicação e a chave privada na seção página “Criar um aplicativo” .
Ao criar o aplicativo, você tem a opção de vinculá-lo ao seu número de telefone da Nexmo. Certifique-se de copiar e colar esse número de telefone e inseri-lo no seu .env arquivo como NEXMO_NUMBER.
Certifique-se também de gerar um par de chaves pública/privada. Colei a chave diretamente no private.key arquivo.
Para preencher as chaves de consumidor e de acesso, bem como os segredos, crie um aplicativo no Twitter e gere as chaves e os tokens.
Agora, no seu server.js arquivo, vamos inicializar nosso aplicativo Express e incluir alguns pré-requisitos:
// server.js
const dotenv = require('dotenv');
const express = require('express');
const bodyParser = require('body-parser');
const Nexmo = require('nexmo');
const Twitter = require('twitter');
dotenv.config();
const app = express();
app.use(bodyParser.json());
const port = 5000;
app.listen(port, () => console.log(`server started on port ${port}`));
Adicione também as diferentes credenciais necessárias para utilizar as APIs do Nexmo e do Twitter:
// server.js continued:
// Nexmo credentials
const nexmo = new Nexmo({
apiKey: process.env.API_KEY,
apiSecret: process.env.API_SECRET,
applicationId: process.env.APPLICATION_ID,
privateKey: './private.key'
}, {debug: true});
// Twitter credentials
const client = new Twitter({
consumer_key: process.env.CONSUMER_KEY,
consumer_secret: process.env.CONSUMER_SECRET,
access_token_key: process.env.ACCESS_TOKEN_KEY,
access_token_secret: process.env.ACCESS_TOKEN_SECRET
});No final deste server.js arquivo, adicione as duas assinaturas dos endpoints aos quais voltaremos daqui a pouco para escrever:
// server.js continued:
app.post('/userName', function(req, res) {});
app.post('/sendSMS', function(req, res) {}); Crie um aplicativo front-end com React
Em seguida, ainda na raiz do seu diretório, crie seu aplicativo React executando o seguinte comando:
Eu dei o nome de client , mas fique à vontade para dar o nome que quiser. Depois que o aplicativo React estiver criado, acesse-o e inicie-o para verificar se tudo funcionou corretamente durante o processo de instalação:
Para que você possa executar ambas as portas simultaneamente, no arquivo client/package.json arquivo, adicione:
// package.json
"proxy": "http://localhost:5000",Ao executar o create-react-app fornece uma série de códigos padrão. Dentro da src/ pasta há um App.js arquivo. Nesse arquivo, adicionei uma chamada a um <TwitterName /> componente que vamos desenvolver a seguir.
Meu App.js arquivo tem a seguinte aparência:
// client/src/App.js
import React from 'react';
import TwitterName from './components/twitterName';
class App extends React.Component {
render() {
return (
<div>
<TwitterName />
</div>
);
}
}
export default App;A seguir, vamos criar uma components pasta dentro de src/:
Nessa pasta, crie três arquivos:
Criar um componente para receber um nome de usuário do Twitter
Dentro de twitterName.js junto com meu código padrão, vamos criar duas funções senduserName() e getTweet():
// client/src/components/twitterName.js
import React from 'react';
import SentimentCalculate from './sentimentCalculate';
class TwitterName extends React.Component {
constructor(props) {
super(props);
this.state = {
userName: '',
tweetContent: '',
};
}
senduserName();
getTweet();
render();
}
export default TwitterName;Adicione ao render() adicionar um <input /> para receber e armazenar o nome de usuário do Twitter como estado fornecido pelo usuário.
// client/src/components/twitterName.js
render() {
return (
<div>
<label>
Enter a Twitter Handle and find the most recent tweet:
<input
placeholder="twitter name"
type="text"
value={this.state.userName}
onChange={(e) => this.setState({ userName: e.target.value})}
/>
</label>
<button onClick={this.senduserName}>
find most recent tweet
</button>
</div>
)
}
O senduserName() é chamada assim que o usuário digita seu nome de usuário e clica no find most recent tweet botão. Essa função envia informações para o server.js back-end e tem a seguinte aparência:
//client/src/components/ twitterName.js
senduserName = (event) => {
event.preventDefault();
fetch('/userName', {
method: 'post',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({userName: this.state.userName})
})
this.getTweet()
}
Essa função, então, chama a getTweet() função que tem a seguinte aparência:
// client/src/components/twitterName.js
getTweet = (event) => {
fetch('/twitter')
.then(res => res.json())
.then(tweetContent => this.setState({tweetContent}, () => console.log('tweet fetched: ', tweetContent)))
}
Essa função recebe os dados do servidor e, em seguida, exibe o tweet mais recente em nossa página do React.
A única coisa que resta fazer nesta página agora é chamar o próximo componente, <SentimentCalculate /> e, portanto, na parte inferior do render() adicionamos isso e passamos o estado (tweetContent e userName) para esse componente:
// client/src/components/twitterName.js
render() {
return (
<div>
<input
placeholder="twitter name"
type="text"
value={this.state.userName}
onChange={(e) => this.setState({ userName: e.target.value})}
/>
<button onClick={this.senduserName}>
find most recent tweet
</button>
<SentimentCalculate tweetContent={this.state.tweetContent} userName={this.state.userName} />
</div>
)
} Recuperar o tweet mais recente com a API do Twitter
Vamos voltar ao server.js arquivo na raiz do nosso projeto e preencher a app.post('/userName'); função:
//server.js
// Receive input and call Twitter API
app.post('/userName', function(req, res) {
userName = req.body.userName;
app.get('/twitter', (req, res) => {
// read most recent tweet
var username = {screen_name: userName };
client.get('statuses/user_timeline', username, function(error, tweets, response) {
if (!error) {
console.log(`most recent tweet: `, tweets[0].text);
res.json(tweets[0].text)
}
});
});
});
Aqui, o userName é passado pelo cliente e, em seguida, enviado para a API do Twitter. O tweet mais recente é então enviado de volta ao cliente para ser exibido em nosso código React.
Calcule a pontuação de sentimento com a API do Microsoft Azure
Vamos expandir nosso sentimentCalculate.js arquivo agora com duas funções diferentes calculateSentiment() e showTweet():
//client/src/components/sentimentCalculate.js
import React from 'react';
import unirest from 'unirest';
import PhoneNumber from './phoneNumber';
require('dotenv').config()
class SentimentCalculate extends React.Component {
constructor(props) {
super(props);
this.state = {
tweetContent: props.tweetContent,
userName: props.userName,
score: ''
};
}
calculateSentiment();
showTweet();
render();
}
export default SentimentCalculate;Observe que estou inicializando o estado e carregando no tweetContent e userName como props do <TwitterName /> componente.
A showTweet() função será bem simples e exibirá o tweet, caso ele exista. Ela também mostrará um botão para chamar a calculateSentiment() função:
//client/src/components/sentimentCalculate.js
showTweet() {
if (this.props.tweetContent) {
return (
<div>
{this.props.tweetContent}
<button onClick={this.calculateSentiment}>
Calculate sentiment score
</button>
</div>
)
}
}
Essa calculateSentiment() função ficará assim:
//client/src/components/sentimentCalculate.js
calculateSentiment = (event) => {
console.log("calculating sentiment for: ", this.props.tweetContent)
event.preventDefault();
unirest.post("https://microsoft-azure-text-analytics-v1.p.rapidapi.com/sentiment")
.header("X-RapidAPI-Host", "microsoft-azure-text-analytics-v1.p.rapidapi.com")
.header("X-RapidAPI-Key", process.env.REACT_APP_RAPIDAPI_KEY)
.header("Content-Type", "application/json")
.send({"documents":[{"language":"en","id":"string","text":this.props.tweetContent}]})
.end((result) => {
const newScore = result.body.documents[0].score
console.log("The score is:", newScore)
this.setState({ score: newScore })
});
}
Essa função chama o Text Analytics do Microsoft Azure por meio da Rapid API. Gosto de usar a Rapid API, pois ela me permite conectar-me a várias APIs diferentes com um único login.
Guardo a chave em um .env arquivo na client pasta. Portanto, certifique-se de criar um novo .env arquivo para proteger suas credenciais também:
A calculateSentiment() função envia o tweetContent para a API e retorna uma pontuação.
Adicione à render() função um local para exibir esse novo estado:
//client/src/components/sentimentCalculate.js
render() {
return (
<div>
{this.showTweet()}
{this.state.score && `Tweet's sentiment score: ${this.state.score}`}
<PhoneNumber score={this.state.score} tweetContent={this.props.tweetContent} userName={this.props.userName} />
</div>
)
}Observe que, abaixo da partitura, o componente final se chama: <PhoneNumber />. Certifique-se também de passar o estado por meio de props para esse componente.
Envie seu Relatório de Sentimento de SMS com a Messages API da Nexmo
Vamos criar nosso phoneNumber.js arquivo agora com as funções sendSMS(), renderPhoneInput(), e renderSendButton() para implementar a funcionalidade de envio de nossa mensagem SMS por meio da Messages API do Nexmo:
//client/src/components/phoneNumber.js
import React from 'react';
class PhoneNumber extends React.Component {
constructor(props) {
super(props);
this.state = {
score: props.score,
tweetContent: props.tweetContent,
userName: props.userName,
number: ''
};
this.sendSMS = this.sendSMS.bind(this);
}
sendSMS();
renderPhoneInput();
renderSendButton();
render() {
return (
<div>
{this.renderPhoneInput()}
{this.renderSendButton()}
</div>
)
}
}
export default PhoneNumber;O primeiro método chamado é renderPhoneInput(). Vamos desenvolvê-lo agora:
//client/src/components/phoneNumber.js
renderPhoneInput() {
if (this.props.score) {
return (
<div>
Phone number:
<input
placeholder="18005554444"
type="tel"
value={this.state.number}
onChange={(e) => this.setState({ number: e.target.value})}
/>
</div>
);
}
}
Se o componente tiver recebido uma pontuação do componente anterior, esta função exibirá um campo de entrada para que o usuário forneça seu número de telefone, a fim de enviar o relatório de análise de sentimento. Assim que o usuário fornecer um número válido, a renderSendButton() função será ativada:
//client/src/components/phoneNumber.js
renderSendButton() {
if (this.state.number && this.state.number.match(/\d/g).length===11) {
return (
<div>
<button onClick={this.sendSMS}>
Send the tweet’s score to my phone
</button>
</div>
);
}
}
Esse botão, então, chama a função final, sendSMS(), que tem a seguinte aparência:
//client/src/components/phoneNumber.js
sendSMS() {
fetch('/sendSMS', {
method: 'post',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({
number: this.state.number,
score: this.props.score,
tweetContent: this.props.tweetContent,
userName: this.props.userName
})
})
.then(res => {
alert('Your text was successfully sent!')
})
.catch(function(error){ console.log(error)});
}
Essa função envia todas as informações que coletamos do usuário para o servidor. E, por fim, avisa o usuário assim que a função for concluída com sucesso.
Nosso último passo é voltar para o server.js e escrever a app.post('/sendSMS') função:
//server.js
// send SMS via Nexmo
app.post('/sendSMS', (req, res) => {
res.send(req.body);
let score = req.body.score;
let scoreSign = '';
// analyze the sentiment and assign emoji
if (score > '.5') {
scoreSign = '✅'
} else if (score == '.5') {
scoreSign = '😐'
} else {
scoreSign = '👿'
}
// Nexmo Messages API
nexmo.channel.send(
{ type: 'sms', number: req.body.number }, // To
{ type: 'sms', number: process.env.NEXMO_NUMBER }, // From
{
content: {
type: 'text',
text: `${req.body.userName}'s most recent tweet was: \"\ ${req.body.tweetContent}\"\ and the sentiment score is: ${scoreSign}`,
}
},
(err, data) => {
if (err) {
console.log(err);
} else {
console.log(data);
}
}
);
});
Há uma pequena lógica na parte superior para fazer uma análise de sentimento com base na pontuação. Você pode, sem dúvida, removê-la caso prefira enviar o número exato em vez de emojis.
Em seguida, o relatório é enviado por SMS do seu número Nexmo para o número que o usuário tiver fornecido.
Execute seu aplicativo
Veja a seguir como é a estrutura do meu aplicativo final:
Structure of folders and files
O passo final é testar o código e ver como tudo funciona! Volte ao diretório raiz e execute o comando que iniciará o servidor e o cliente simultaneamente:
Ao acessar localhost:3000 exibirá nosso componente React que solicita ao usuário um nome de usuário do Twitter.
O tweet mais recente desse usuário será então recuperado e exibido na página.
Clique no calculate the sentiment botão para chamar a API do Microsoft Azure Text Analytics e exibir a pontuação do tweet.
Digite seu número de telefone pessoal e o relatório por SMS será enviado a você por meio da Messages API da Nexmo.
🎉Pronto!🎉 Você criou com sucesso um aplicativo React para analisar o sentimento das suas postagens no Twitter, capaz de enviar um relatório por SMS para qualquer pessoa!
Próximos passos
Se isso despertou seu interesse em explorar mais as mensagens e a análise de sentimentos, aqui estão algumas ideias do que você pode tentar a seguir:
A Dispatch API da Nexmo permite que você redirecione sua mensagem de acordo com o status de entrega. Experimente essa funcionalidade e tente enviar seu relatório de sentimentos também para o Viber ou o WhatsApp!
Experimente o recurso do Twitter
/streaminge considere enviar um relatório sempre que um nome de usuário publicar um tuíte.