Articolo originale: JavaScript Discord Bot Tutorial – Code a Discord Bot And Host it for Free

Questo tutorial ti mostrerà come utilizzare JavaScript e Node.js per creare il tuo bot Discord completamente nel cloud.

Non devi installare nulla sul tuo computer e non devi pagare nulla per ospitare il tuo bot.

Utilizzeremo una serie di strumenti, tra cui l'API Discord, le librerie Node.js e una piattaforma di cloud computing chiamata Repl.it .

Se preferisci codificare il tuo bot discord usando Python invece di JavaScript, leggi invece questo tutorial .

C'è anche una versione video di questo tutorial scritto. Il video è riportato di seguito e la versione scritta è dopo il video.

Come creare un account Discord Bot

Per poter lavorare con la libreria Node.js e l'API Discord, dobbiamo prima creare un account Bot su Discord.

Ecco i passaggi per creare un account Bot su Discord.

1. Assicurati di aver effettuato l'accesso al sito Web Discord .

2. Passare alla pagina dell'applicazione .

3. Fare clic sul pulsante "New Application".

image-117

4. Assegna un nome all'applicazione e fai clic su "Create".

image-118

5. Vai alla scheda "Bot" e quindi fai clic su "Add Bot". Dovrai confermare facendo clic su "Yes, do it!"

image-119

Mantieni le impostazioni predefinite per Public Bot (selezionato) e Require OAuth2 Code Grant (deselezionato).

Il tuo bot è stato creato. Il passaggio successivo consiste nel copiare il token.

image-122

Questo token è la password del tuo bot, quindi non condividerla con nessuno. Potrebbe consentire a qualcuno di accedere al tuo bot e fare ogni sorta di cose cattive.

Puoi rigenerare il token se viene condiviso accidentalmente.

Come invitare il tuo bot a unirsi a un server

Ora devi portare il tuo utente bot in un server. Per fare ciò, dovresti creare un URL di invito per esso.

Vai alla scheda "OAuth2". Quindi seleziona "bot" nella sezione "scopes".

image-123

Ora scegli le autorizzazioni che desideri per il bot. Il nostro bot utilizzerà principalmente messaggi di testo, quindi non abbiamo bisogno di molte autorizzazioni. Potresti aver bisogno di più permessi a seconda di cosa vuoi che faccia il tuo bot. Fai attenzione con l'autorizzazione "Administrator".

image-124

Dopo aver selezionato le autorizzazioni appropriate, fai clic sul pulsante "copy" sopra le autorizzazioni. Ciò copierà un URL che può essere utilizzato per aggiungere il bot a un server.

Incolla l'URL nel tuo browser, scegli un server a cui invitare il bot e fai clic su "Authorize".

Per aggiungere il bot, il tuo account necessita dell'autorizzazione "Manage Server".

Ora che hai creato l'utente bot, inizieremo a scrivere il codice JavaScript per il bot.

Come codificare un bot Discord di base con la libreria discord.js

Useremo la libreria discord.js di Node per scrivere il codice per il bot. discord.js è un wrapper API per Discord che semplifica la creazione di un bot Discord in Node.js/JavaScript.

Come creare una repl e installare discord.js

Puoi sviluppare il bot sul tuo computer locale con qualsiasi editor di codice. Tuttavia, in questo tutorial, useremo Repl.it perché renderà più semplice per chiunque seguirlo. Repl.it è un IDE online che puoi utilizzare nel tuo browser web.

Inizia andando su Repl.it . Crea un nuovo Repl e scegli "Node.js" come linguaggio. Ciò significa che il linguaggio di programmazione sarà JavaScript.

Per utilizzare la libreria discord.js, aggiungi semplicemente const Discord = require("discord.js");nella parte superiore di main.js. Questa guida è scritta per una versione precedente di discord.js, per installare questa versione esegui nel terminale (Shell) di Repl.it il seguente comando.

> npm install --save discord.js@12.5.3
image-1

Come impostare gli eventi Discord per il tuo bot

discord.js ruota attorno al concetto di eventi. Un evento è qualcosa che ascolti e a cui poi rispondi. Ad esempio, quando arriva un messaggio, riceverai un evento al riguardo a cui puoi rispondere.

Creiamo un bot che risponda a uno specifico messaggio. Il  codice per questo semplice bot è preso direttamente dalla documentazione discord.js . Aggiungeremo più funzionalità al bot in seguito.

Aggiungi questo codice a main.js. Spiegherò cosa fa tutto questo codice a breve.

const Discord = require("discord.js")
const client = new Discord.Client()

client.on("ready", () => {
  console.log(`Logged in as ${client.user.tag}!`)
})

client.on("message", msg => {
  if (msg.content === "ping") {
    msg.reply("pong");
  }
})

client.login(process.env.TOKEN)

Quando hai creato il tuo utente bot su Discord, hai ottenuto un token. Ora salveremo questo token nella tab Secrets.

image-2

In questo modo il Token rimarrà segreto. Al di fuori di repl.it useresti un file .env per dichiarare le variabili di ambiente.

Quindi, se stai sviluppando su Repl.it, includi solo informazioni private come token o chiavi tab Secrets.

Per salvare il tuo Token, scrivi TOKEN nel campo "key", e incolla il token che hai preso dalle impostazioni del bot nel campo "value", poi premi "Add new secret".

Ora esaminiamo cosa fa ogni riga nel codice del tuo bot Discord.

La prima riga importa la libreria discord.js. Successivamente, creiamo un'istanza di un Client. Questa è la connessione a Discord.

client.on() viene utilizzato per verificare la presenza di eventi . Accetta un nome di evento e quindi una funzione di callback da chiamare quando si verifica l'evento. In questo codice, l'evento  ready viene chiamato quando il bot è pronto per iniziare a essere utilizzato. Quindi, quando il server Discord ha un nuovo messaggio, viene chiamato l'evento message.

Il codice controlla se msg.content è uguale a 'ping'. In tal caso, il bot risponde al canale con 'pong'.

Ora che il bot è impostato, la riga finale esegue il bot con il token di accesso. Ottiene il token dal file .env.

Abbiamo il codice per il bot, quindi ora non ci resta che eseguirlo.

Come eseguire il bot

Ora fai clic sul pulsante Esegui in alto per eseguire il tuo bot in repl.it.

Ora vai nella tua stanza Discord e digita "ping". Il tuo bot dovrebbe restituire "pong".

image

Come migliorare il bot

Ora che abbiamo un bot di base funzionante, lo miglioreremo. Si chiama "Encourage Bot" per un motivo.

Questo bot risponderà con un messaggio di incoraggiamento ogni volta che qualcuno invia un messaggio contenente una parola triste o deprimente.

Chiunque potrà aggiungere nuovi messaggi incoraggianti nel bot e i messaggi inviati dall'utente verranno archiviati nel database Repl.it.

Il bot restituirà anche una citazione ispiratrice casuale tramite l'uso di un'API quando qualcuno digita il messaggio "$inspire" nella chat.

Inizieremo con l'aggiunta della funzione "$inspire".

Come aggiungere citazioni di ispirazione al bot

Otterremo citazioni di ispirazione da un'API chiamata zenquotes.io. Dobbiamo importare il modulo node-fetch, aggiungere una funzione getQuote() e aggiornare il nostro codice bot per chiamare la funzione.

Ecco il codice aggiornato. Dopo il codice, spiegherò le nuove parti.

const Discord = require("discord.js")
const fetch = require("node-fetch")
const client = new Discord.Client()

function getQuote() {
  return fetch("https://zenquotes.io/api/random")
    .then(res => {
      return res.json()
      })
    .then(data => {
      return data[0]["q"] + " -" + data[0]["a"]
    })
}

client.on("ready", () => {
  console.log(`Logged in as ${client.user.tag}!`)
})

client.on("message", msg => {
  if (msg.author.bot) return
    
  if (msg.content === "$inspire") {
    getQuote().then(quote => msg.channel.send(quote))
  }
})

client.login(process.env.TOKEN)

Ora dobbiamo importare il modulo  node-fetch. Questo modulo consente al nostro codice di effettuare una richiesta HTTP per ottenere dati dall'API.

La funzione getQuote() è piuttosto semplice. Innanzitutto, utilizza il modulo node-fetch per richiedere i dati dall'URL dell'API. L'API restituisce una citazione ispiratrice casuale. Questa funzione potrebbe essere facilmente riscritta per ottenere citazioni da un'API diversa, se quella corrente smette di funzionare.

Quindi la funzione converte la risposta dall'API in JSON e crea una stringa da restituire. Attraverso tentativi ed errori ho capito come ottenere la citazione dal JSON nel formato stringa che volevo. La citazione viene restituita dalla funzione come stringa.

La restante parte di aggiornamento del codice è verso la fine. Prima cercava il messaggio "ping". Ora cerca "$inspire". Invece di restituire "pong", ottiene la citazione con getQuote() e la restituisce. Usiamo msg.channel.send() per inviare il messaggio al canale. Inoltre, il codice controlla se il messaggio proviene dal bot stesso e, in tal caso, esce dalla funzione in modo che non faccia nulla.

A questo punto puoi eseguire il tuo codice e provarlo.

Come aggiungere messaggi incoraggianti al bot

Ora implementeremo la funzione in cui il bot risponde con messaggi incoraggianti quando un utente pubblica un messaggio con una parola triste.

Come aggiungere parole tristi al bot

Per prima cosa dobbiamo creare un array che contenga le parole tristi a cui risponderà il bot.

Aggiungi la seguente riga dopo aver creato la variabile client:

sadWords = ["sad", "depressed", "unhappy", "angry", "miserable"]

Sentiti libero di aggiungere più parole all'elenco.

Come aggiungere messaggi incoraggianti al bot

Ora aggiungeremo una serie di messaggi incoraggianti con cui il bot risponderà.

Aggiungi il seguente array dopo l'elenco  sadWords che hai creato:

encouragements = [
  "Cheer up!",
  "Hang in there.",
  "You are a great person / bot!"
]

Come prima, sentiti libero di aggiungere altre frasi a tua scelta all'array . Per ora sto usando solo tre elementi perché in seguito aggiungeremo la possibilità per gli utenti di aggiungere altre frasi incoraggianti da utilizzare per il bot.

Come rispondere ai messaggi

Ora dobbiamo aggiornare il nostro bot per utilizzare le due liste che abbiamo creato.

Ora aggiorneremo la funzione message per controllare tutti i messaggi per vedere se contengono una parola dall'elenco sadWords. Se viene trovata una parola triste, il bot invierà un messaggio casuale di incoraggiamento.

Ecco il codice aggiornato:

client.on("message", msg => {
  if (msg.content === "$inspire") {
    getQuote().then(quote => msg.channel.send(quote))
  }

  if (sadWords.some(word => msg.content.includes(word))) {
    const encouragement = encouragements[Math.floor(Math.random() * encouragements.length)]
    msg.reply(encouragement)
  }

})

Questo è un buon momento per testare il bot. Adesso ne sai abbastanza per creare il tuo bot. Ma in seguito imparerai come implementare funzionalità più avanzate e archiviare i dati utilizzando il database Repl.it.

Come abilitare i messaggi inviati dall'utente

Il bot è completamente funzionante, ma ora consentiamo di aggiornare il bot direttamente da Discord. Un utente dovrebbe essere in grado di aggiungere messaggi più incoraggianti che il bot può utilizzare quando rileva una parola triste.

Utilizzeremo il database integrato di Repl.it per archiviare i messaggi inviati dagli utenti. Questo database è un archivio di tipo chiave-valore integrato in ogni repl su  Repl.it.

Nella parte superiore del codice, sotto le altre istruzioni di importazione, aggiungi:

const Database = require("@replit/database")
const db = new Database()

Questo ci consentirà di utilizzare il database Repl.it. Quando esegui il codice, Repl.it dovrebbe installare automaticamente il modulo database. Se per qualche motivo non è così, potresti dover andare nella scheda Shell (non nella Console) e digitare "npm install @replit/database".

Dopo aver creato l'array  encouragements, inserire il codice seguente per aggiungere gli incoraggiamenti al database, se necessario:

db.get("encouragements").then(encouragements => {
  if (!encouragements || encouragements.length < 1) {
    db.set("encouragements", starterEncouragements)
  }  
})

Inoltre, rinomina l'array  encouragements  in starterEncouragements.

Gli utenti potranno aggiungere messaggi di incoraggiamento personalizzati che il bot può utilizzare direttamente dalla chat di Discord. Prima di aggiungere nuovi comandi per il bot, creiamo due funzioni di supporto che aggiungeranno messaggi personalizzati al database e li cancelleranno.

Aggiungi il seguente codice dopo la funzione getQuote():

function updateEncouragements(encouragingMessage) {
  db.get("encouragements").then(encouragements => {
    encouragements.push([encouragingMessage])
    db.set("encouragements", encouragements)
  })
}

function deleteEncouragment(index) {
  db.get("encouragements").then(encouragements => {
    if (encouragements.length > index) {
      encouragements.splice(index, 1)
      db.set("encouragements", encouragements)
    }
  })
}

La funzione updateEncouragements() accetta un messaggio incoraggiante come argomento.

Per prima cosa ottiene gli "incoraggiamenti" dal database. Quindi, aggiunge il nuovo incoraggiamento all'array e memorizza l'array aggiornato nel database sotto la chiave "encouragements".

La funzione deleteEncouragement() accetta un indice come argomento.

Ottiene l'elenco degli incoraggiamenti dal database archiviato nella chiave "encouragements". Se la lunghezza è maggiore dell'indice, la voce dell'elenco in quell'indice viene eliminata. Infine, l'elenco aggiornato viene nuovamente memorizzato nel database sotto il chiave "encouragements".

Ecco il codice aggiornato per la funzione message. Dopo il codice, spiegherò le nuove sezioni.

client.on("message", msg => {
  if (msg.content === "$inspire") {
    getQuote().then(quote => msg.channel.send(quote))
  }

  
  if (sadWords.some(word => msg.content.includes(word))) {
    db.get("encouragements").then(encouragements => {
      const encouragement = encouragements[Math.floor(Math.random() * encouragements.length)]
      msg.reply(encouragement)
    })
  }

  if (msg.content.startsWith("$new")) {
    encouragingMessage = msg.content.split("$new ")[1]
    updateEncouragements(encouragingMessage)
    msg.channel.send("New encouraging message added.")
  }

  if (msg.content.startsWith("$del")) {
    index = parseInt(msg.content.split("$del ")[1])
    deleteEncouragment(index)
    msg.channel.send("Encouraging message deleted.")
  }
})

La sezione delle parole tristi è stata aggiornata per utilizzare i messaggi incoraggianti dal database in modo da poter utilizzare i messaggi inviati dagli utenti.

La successiva nuova sezione di codice  viene utilizzata per aggiungere un nuovo messaggio inviato dall'utente al database. Se un messaggio Discord inizia con "$new", il testo dopo "$new" verrà utilizzato come nuovo messaggio di incoraggiamento.

Il codice msg.content.split('$new ')[1] separa il messaggio dal comando "$new" e memorizza il messaggio in una variabile. In quella riga di codice, prende nota dello spazio in '$new '. Vogliamo tutto dopo lo spazio.

Chiamiamo la funzione ausiliaria updateEncouragements con il nuovo messaggio, quindi il bot invia un messaggio alla chat discord confermando che il messaggio è stato aggiunto.

La terza nuova sezione (alla fine del codice sopra) controlla se un nuovo messaggio Discord inizia con "$del". Questo è il comando per eliminare un elemento dall'elenco "encouragements" nel database.

L'indice viene separato dal messaggio Discord che inizia con "$del". Quindi, la funzione deleteEncouragement() viene chiamata passando come parametro l'indice da eliminare. L'elenco aggiornato degli incoraggiamenti viene caricato nella variabile encouragements, quindi il bot invia un messaggio a Discord con l'elenco corrente.

Funzionalità finali del bot

Il bot dovrebbe funzionare, quindi questo è un buon momento per testarlo. Ora aggiungeremo alcune funzionalità finali.

Aggiungeremo la possibilità di ottenere un elenco di messaggi inviati dall'utente direttamente da Discord e aggiungeremo la possibilità di disattivare e attivare il bot a risponde alle parole tristi.

Ti fornirò il codice finale completo del programma e poi discuterò gli aggiornamenti sotto il codice.

const Discord = require("discord.js")
const fetch = require("node-fetch")
const Database = require("@replit/database")

const db = new Database()
const client = new Discord.Client()

const sadWords = ["sad", "depressed", "unhappy", "angry", "miserable"]

const starterEncouragements = [
  "Cheer up!",
  "Hang in there.",
  "You are a great person / bot!"
]

db.get("encouragements").then(encouragements => {
  console.log(encouragements)
  if (!encouragements || encouragements.length < 1) {
    db.set("encouragements", starterEncouragements)
  }  
})

db.get("responding").then(value => {
  if (value == null) {
    db.set("responding", true)
  }  
})

function getQuote() {
  return fetch("https://zenquotes.io/api/random")
    .then(res => {
      return res.json()
      })
    .then(data => {
      return data[0]["q"] + " -" + data[0]["a"]
    })
}

function updateEncouragements(encouragingMessage) {
  db.get("encouragements").then(encouragements => {
    encouragements.push([encouragingMessage])
    db.set("encouragements", encouragements)
  })
}

function deleteEncouragment(index) {
  db.get("encouragements").then(encouragements => {
    if (encouragements.length > index) {
      encouragements.splice(index, 1)
      db.set("encouragements", encouragements)
    }
  })
}

client.on("ready", () => {
  console.log(`Logged in as ${client.user.tag}!`)
})

client.on("message", msg => {
  if (msg.content === "$inspire") {
    getQuote().then(quote => msg.channel.send(quote))
  }

  db.get("responding").then(responding => {
    if (responding && sadWords.some(word => msg.content.includes(word))) {
      db.get("encouragements").then(encouragements => {
        const encouragement = encouragements[Math.floor(Math.random() * encouragements.length)]
        msg.reply(encouragement)
      })
    }
  })

  if (msg.content.startsWith("$new")) {
    encouragingMessage = msg.content.split("$new ")[1]
    updateEncouragements(encouragingMessage)
    msg.channel.send("New encouraging message added.")
  }

  if (msg.content.startsWith("$del")) {
    index = parseInt(msg.content.split("$del ")[1])
    deleteEncouragment(index)
    msg.channel.send("Encouraging message deleted.")
  }

  if (msg.content.startsWith("$list")) {
    db.get("encouragements").then(encouragements => {
      msg.channel.send(encouragements)
    })
  }
    
  if (msg.content.startsWith("$responding")) {
    value = msg.content.split("$responding ")[1]

    if (value.toLowerCase() == "true") {
      db.set("responding", true)
      msg.channel.send("Responding is on.")
    } else {
      db.set("responding", false)
      msg.channel.send("Responding is off.")
    }
  }
})

client.login(process.env.TOKEN)

La prima sezione aggiunta al codice è proprio sotto l'elenco starterEncouragements:

db.get("responding").then(value => {
  if (value == null) {
    db.set("responding", true)
  }  
})

Creiamo una nuova chiave nel database chiamata "responding" e la impostiamo su "true". Lo useremo per determinare se il bot deve rispondere a parole tristi o meno. Poiché il database viene salvato anche dopo che il programma si interrompe, creiamo la nuova chiave solo se non esiste già.

La successiva parte nuova del codice è nella sezione che risponde alle parole tristi che ora è  all'interno di questa istruzione if. Il bot risponderà alle parole tristi solo se db.get("responding") = true. La possibilità di aggiornare questo valore viene dopo questa successiva sezione .

Successivamente, dopo il codice per fare in modo che il bot risponda al comando "$del", c'è un nuovo codice per rispondere al comando "$list" quando viene inviato come messaggio Discord.

Il bot invia l'elenco degli incoraggiamenti come messaggio Discord.

La nuova sezione finale viene dopo. Questo codice fa sì che il bot risponda al comando "$responding". Questo comando accetta un argomento di "true" o "false". Ecco un esempio di utilizzo: "$responding true".

Il codice prima estrae l'argomento con value = msg.content.split("$responding ")[1](come prima, nota lo spazio in "$responding "). Quindi c'è un'istruzione if/else che imposta in modo appropriato la chiave di "responding" nel database e invia un messaggio di notifica a Discord. Se l'argomento è diverso da  "true", il codice lo presuppone "falso".

Il codice per il bot è completo! Ora puoi eseguire il bot e provarlo. Ma c'è un altro passo importante che discuteremo in seguito.

Come configurare il bot per l'esecuzione continua

Se esegui il tuo bot in repl.it e poi chiudi la scheda in cui è in esecuzione, il tuo bot smetterà di funzionare.

Ma ci sono due modi in cui puoi mantenere il tuo bot in esecuzione continua, anche dopo aver chiuso il tuo web bowser.

Il primo modo e il modo più semplice è iscriversi a un piano a pagamento su Repl.it. Il loro piano a pagamento più economico si chiama Hacker Plan e include cinque Repls sempre attivi.

Puoi ottenere tre mesi gratis utilizzando questo link (limitato alle prime 1000 persone): https://repl.it/claim?code=tryalwayson2103

Dopo esserti iscritto a quel piano, apri il tuo Repl e fai clic sul nome in alto. Quindi seleziona l'opzione "Always On".

image-36

C'è un altro modo per mantenere il codice in esecuzione anche gratuitamente, ma è un po' più complicato. Repl.it continuerà a eseguire un server web anche dopo la chiusura della scheda. Ma anche un server web funzionerà solo per un'ora senza alcun utilizzo.

Ecco cosa dicono i documenti di repl.it:

Una volta distribuito, il server continuerà a funzionare in background, anche dopo aver chiuso la scheda del browser. Il server rimarrà sveglio e attivo fino a un'ora dopo l'ultima richiesta, dopodiché entrerà in una fase di sospensione. Le risposte dormienti verranno svegliate non appena riceve un'altra richiesta; non è necessario eseguire nuovamente la repl. Tuttavia, se apporti modifiche al tuo server, dovrai riavviare la repl per vedere tali modifiche riflesse nella versione live.

Per mantenere il bot continuamente in esecuzione, utilizzeremo un altro servizio gratuito chiamato Uptime Robot all'indirizzo https://uptimerobot.com/ .

Uptime Robot può essere impostato per eseguire il ping del server web del bot su repl.it ogni 5 minuti. Con ping costanti, il bot non entrerà mai nella fase dormiente e continuerà ad essere attivo.

Quindi dobbiamo fare altre due cose per far funzionare continuamente il nostro bot:

  1. creare un server web in repl.it e
  2. impostare Uptime Robot per eseguire continuamente il ping del server web.

Come creare un Web Server in repl.it

Creare un server web è più semplice di quanto si possa pensare.

Per farlo, crea un nuovo file nel tuo progetto chiamato server.js.

Quindi aggiungi il seguente codice:

const express = require("express")

const server = express()

server.all("/", (req, res) => {
  res.send("Bot is running!")
})

function keepAlive() {
  server.listen(3000, () => {
    console.log("Server is ready.")
  })
}

module.exports = keepAlive

In questo codice, utilizziamo express per avviare un server web. Il server restituisce "Bot is running!" a chiunque lo visiti. Il server verrà eseguito su un thread separato dal nostro bot. Non discuteremo di tutto qui poiché il resto non è realmente rilevante per il nostro bot.

Ora abbiamo solo bisogno del bot per eseguire questo server web.

Aggiungi la riga seguente all'inizio di index.js  per importare il server.

const keepAlive = require("./server")

Per avviare il server Web quando index.jsviene eseguito, aggiungi la riga seguente come penultima riga, subito prima dell'esecuzione del bot.

keepAlive()

Quando esegui il bot su repl.it dopo aver aggiunto questo codice, si aprirà una nuova finestra del server web. C'è un URL mostrato per il server web. Copia l'URL in modo da poterlo utilizzare nella sezione successiva.

image-1

Come impostare Uptime Robot

Ora dobbiamo impostare Uptime Robot per eseguire il ping del server Web ogni cinque minuti. Ciò farà sì che il bot funzioni continuamente.

Crea un account gratuito su https://uptirobot.com/ .

Una volta effettuato l'accesso al tuo account, fai clic su "Add New Monitor".

image-21

Per il nuovo monitor, seleziona "HTTP(s)" come Tipo di monitor e chiamalo come preferisci. Quindi, incolla l'URL del tuo server web da repl.it. Infine, fai clic su "Create Monitor".

image-22

Fatto! Ora il bot funzionerà continuamente in modo che le persone possano sempre interagire con esso su Repl.it.

Conclusione

Ora sai come creare un bot Discord con JavaScript ed eseguirlo continuamente nel cloud.

Ci sono molte altre cose che la libreria discord.js può fare. Quindi, se vuoi dare a un bot Discord ancora più funzionalità, il tuo prossimo passo è controllare i documenti per discord.js.

Nota: questo tutorial si basa su una vecchia versione di discord.js, che potrebbe smettere di essere supportata in qualsiasi momento.