Esempi completi per la REST API di Discourse

Ci sono diverse guide che coprono vari utilizzi o spiegazioni dell’API.

Questa offre esempi pratici e completi su come utilizzarla.

:warning: Tutti gli esempi di codice in questa guida non sono intesi come best practice né vanno utilizzati così come sono.
Molti controlli, la gestione degli errori e altro sono volutamente ignorati o omessi per concentrarsi esclusivamente sull’uso dell’API.

A cosa serve l’API?

La maggior parte delle tue azioni su Discourse (pubblicare, mettere like, modificare una impostazione, ecc.) viene eseguita tramite l’API effettuando richieste a un endpoint[1].

Ad esempio, quando crei un argomento su meta, viene effettuata una richiesta POST a https://meta.discourse.org/posts.json. La richiesta contiene, tra le altre cose, l’autore, il titolo, la categoria, i tag e il contenuto del tuo post.

L’utilizzo personalizzato dell’API viene solitamente effettuato per automatizzare attività e spesso in combinazione con altri servizi, come webhook, script, software di terze parti e altre API.

Per utilizzare l’API è obbligatorio disporre di credenziali API. Questo può essere fatto in pochi clic, seguendo questa guida: Create and configure an API key

Non aspettare oltre, passiamo al primo esempio di utilizzo dell’API. :technologist:

Creare un argomento mensile

In questo esempio, useremo curl e cron per creare un argomento mensile “conversazione libera” sul tuo forum. Una pratica comune nelle comunità online :slight_smile:

Creare la chiave API

Segui la guida per la creazione della chiave API. Imposta Livello utente su Utente singolo.
L’utente scelto sarà l’autore dell’argomento mensile.
Successivamente, puoi scegliere un ambito Globale o un ambito Granulare; in quest’ultimo caso, dovrà avere almeno l’accesso ArgomentiScrittura.
Annota la tua chiave API generata. :writing_hand:

Creare un comando curl

Dalla riga di comando del tuo server, esegui questo comando per verificare se funziona e se un argomento viene creato correttamente utilizzando curl e l’API REST di Discourse con la tua chiave API:

curl -X POST "https://il-tuo-discourse.com/posts.json" -H "Content-Type: application/json" -H "Api-Key: LA_TUA_CHIAVE_API" -H "Api-Username: IL_TUO_NOME_UTENTE" -d "{\"title\": \"Creazione argomento di prova con l'API\", \"raw\": \"Ecco il contenuto dell'argomento\", \"category\": ID_CATEGORIA }"

Sostituisci:

  • il-tuo-discourse.com con il dominio del tuo forum
  • LA_TUA_CHIAVE_API con la tua chiave API
  • IL_TUO_NOME_UTENTE con il nome utente scelto per la chiave API
  • ID_CATEGORIA con l’ID della categoria in cui vuoi pubblicare il tuo argomento.

Se tutto è configurato correttamente, sul tuo forum dovrebbe essere creato un nuovo argomento di prova, simile a questo:

La maggior parte del lavoro è fatta in questa fase! Ora dobbiamo modificare il titolo e il contenuto dell’argomento con qualcosa di più appropriato e impostare la ricorrenza della creazione dell’argomento.

Inizia modificando il titolo dell’argomento da:
Creazione argomento di prova con l'API
a:
Conversazione libera del mese - $(date +\%B).

Fai lo stesso per il contenuto, da:
Creazione argomento di prova con l'API
a:
Cosa hai apprezzato di più e di meno durante $(date +\%B -d 'last month')?\nSentiti libero di condividere i tuoi pensieri e fornire idee. 🙂

:information_source: Sto usando il comando Unix date per inserire il nome del mese corrente nel titolo e quello del mese precedente nel contenuto.

:information_source: \n nel contenuto crea una nuova riga.

Puoi usare la riga di comando ed eseguire la richiesta curl aggiornata. Dovrebbe aver creato un nuovo argomento sul tuo forum simile a questo:

Impostare l’evento ricorrente

Creeremo un’attività cron che eseguirà il comando curl il primo giorno di ogni mese. :calendar:

Modifica il file cron con il seguente comando:

crontab -e

Inserisci questa riga alla fine del file (modifica il contenuto della richiesta come necessario) e salva le modifiche.

0 0 1 * * curl -X POST "https://il-tuo-discourse.com/posts.json" -H "Content-Type: application/json" -H "Api-Key: LA_TUA_CHIAVE_API" -H "Api-Username: IL_TUO_NOME_UTENTE" -d "{\"title\": \"Conversazione libera del mese - $(date +\%B)\", \"raw\": \"Cosa hai apprezzato di più e di meno durante $(date +\%B -d 'last month')?\nSentiti libero di condividere i tuoi pensieri e fornire idee. 🙂\", \"category\": 4 }"

:information_source: La parte 0 0 1 * * definisce l’intervallo con cui verrà eseguita il comando. Puoi saperne di più sulla sintassi qui: https://crontab.guru

È fatto! Il tuo server creerà ora un nuovo argomento “conversazione libera” il primo giorno di ogni mese, utilizzando l’API REST di Discourse, una richiesta curl e un’attività cron. :partying_face:

Cambiare automaticamente lo schema colori di un tema

Facciamo in modo che il nostro tema predefinito utilizzi uno schema colori che corrisponda alla stagione corrente :snowflake: :hibiscus: :sunny: :fallen_leaf:

Useremo Ruby per gestire i controlli sui mesi e un’attività cron per eseguire lo script.

Potremmo usare molti altri metodi oltre a Ruby e cron, ma questa guida mira anche a mostrare come utilizzare l’API con vari strumenti.

Preparare il tema e gli schemi colori

Scegli il tema a cui vuoi cambiare lo schema colori e ottieni il suo ID. Troverai l’ID nell’URL del tema. Ad esempio, l’ID di questo tema è 1:

Crea 4 palette colori e annota anche i loro ID.
Qui, l’ID della palette Autunnale è 17:

Creare lo script

Installa Ruby sul tuo server.

Crea un file seasons.rb. Per questo esempio, considererò che si trovi in ~/scripts/.

Inserisci il seguente contenuto in questo file. Effettueremo una richiesta PUT al nostro endpoint del tema e invieremo un payload contenente l’ID dello schema colori:

require 'net/http'
require 'json'
require 'date'

current_month = Date.today.month
color_scheme_id = case current_month
                  when 1..3 then 18 # Inverno
                  when 4..6 then 15 # Primavera
                  when 7..9 then 16 # Estate
                  else           17 # Autunno
                  end

uri = URI('https://il-tuo-discourse.com/admin/themes/ID_TEMA.json')
http = Net::HTTP.new(uri.host, uri.port)
http.use_ssl = true

request = Net::HTTP::Put.new(uri, {
  'Api-Key' => 'LA_TUA_CHIAVE_API',
  'Api-Username' => 'IL_TUO_NOME_UTENTE',
  'Content-Type' => 'application/json'
})

request.body = JSON.generate({
  "theme" => {
    "color_scheme_id" => color_scheme_id
  }
})

response = http.request(request)

Sostituisci:

  • il-tuo-discourse.com con il dominio del tuo forum
  • LA_TUA_CHIAVE_API con la tua chiave API
  • IL_TUO_NOME_UTENTE con il nome utente scelto per la chiave API
  • ID_TEMA con l’ID del tuo tema. Puoi trovarlo alla fine dell’URL della pagina delle impostazioni del tema.
    Ad esempio, in https://il-tuo-discourse.com/admin/customize/themes/38, l’ID del tema è 38.

Proviamo manualmente lo script.
Prima, imposta uno schema colori non stagionale nell’interfaccia di Discourse, se non è già così.

Poi, esegui lo script con il seguente comando:

ruby ~/scripts/seasons.rb

Aggiorna il browser. Lo schema colori utilizzato dal tuo tema dovrebbe essere cambiato. :slight_smile:

L’ultima cosa da fare è creare il job cron che eseguirà questo script il primo giorno del mese in corrispondenza di ogni cambio di stagione.

Dai un’occhiata al primo esempio se non ricordi come creare un’attività cron.

0 0 1 1,4,7,10 * ruby ~/scripts/seasons.rb

È fatto! Il tuo forum indosserà ora nuovi colori all’inizio di ogni nuova stagione! :sunny: :partying_face:

Ricevere una richiesta web su un server web e utilizzare i suoi dati per aggiornare un argomento di Discourse

Questo è più complesso! :technologist:

Il nostro strumento sarà PHP, il che significa che assumeremo di avere un server web funzionante da qualche parte con PHP installato.

In questo esempio, riceveremo un payload webhook di Ko-Fi (un servizio di donazioni) su una pagina PHP, che utilizzerà quindi i dati ricevuti per utilizzare l’API di Discourse e aggiornare il titolo e il contenuto di un argomento.

Più specificamente, aggiornerà il titolo dell’argomento con l’importo e la data della donazione, e aggiungerà una nuova riga alla tabella che elenca le donazioni precedenti (addirittura farà saltare automaticamente l’argomento :shushing_face:):

Ogni volta che un utente effettua una donazione, Ko-Fi[2] invierà una richiesta al nostro script PHP.

Configurare Ko-Fi

Ho impostato la configurazione sulla pagina webhooks di Ko-Fi aggiungendo semplicemente l’URL del mio file PHP e annotando il token di verifica nascosto nella sezione Avanzate.

Su una singola donazione, Ko-Fi invierà un payload come questo al nostro script PHP:

data = {
  "verification_token": "d8546b84-c698-4df5-9811-39d35813e2ff",
  "message_id": "a499df4c-7bbb-4061-b4a6-8b9d969da689",
  "timestamp": "2023-10-19T13:35:06Z",
  "type": "Donation",
  "is_public": true,
  "from_name": "Jo Example",
  "message": "Buona fortuna con l'integrazione!",
  "amount": "3.00",
  "url": "https://ko-fi.com/Home/CoffeeShop?txid=00000000-1111-2222-3333-444444444444",
  "email": "jo.example@example.com",
  "currency": "USD",
  "is_subscription_payment": false,
  "is_first_subscription_payment": false,
  "kofi_transaction_id": "00000000-1111-2222-3333-444444444444",
  "shop_items": null,
  "tier_name": null,
  "shipping": null
}

Riceveremo questo payload, quindi estraiamo le due informazioni di cui abbiamo bisogno:

  • L’importo (3.00), che arrotonderemo a un numero intero.

  • L’timestamp (2023-10-19T13:35:06Z), che formatteremo in una data più leggibile.

Ricevere il payload di Ko-Fi

Innanzitutto, mettiamo il seguente codice nella nostra pagina PHP per ricevere la richiesta da Ko-Fi, assicurandoci di aver ricevuto una richiesta POST e che il valore del token corrisponda a quello fornito nella pagina webhooks di Ko-Fi. Formattiamo anche l’importo e la data come detto prima.

if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    $jsonData = json_decode($_POST['data'], true);

    if ($jsonData['verification_token'] === 'IL_TUO_TOKEN_DI_VERIFICA') {
        $amount = floor(floatval($jsonData['amount']));
        $date = (new DateTime($jsonData['timestamp']))->format('d/m/Y');
    }
}

Sostituisci:

  • IL_TUO_TOKEN_DI_VERIFICA con il token fornito da Ko-Fi

Aggiornare il titolo dell’argomento

Il passaggio successivo è aggiornare il titolo del nostro argomento. Useremo curl nel nostro script PHP per effettuare una richiesta PUT al corretto endpoint.

        $putData = json_encode(['title' => '🥳 Nuova donazione: ' . $amount . '€ il ' . $date]);
        $ch = curl_init('https://il-tuo-discourse.com/t/test-nuovo-argomento/ID_ARGOMENTO');
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'PUT');
        curl_setopt($ch, CURLOPT_POSTFIELDS, $putData);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_HTTPHEADER, [
            'Content-Type: application/json',
            'Content-Length: ' . strlen($putData),
            'Api-Key: LA_TUA_CHIAVE_API',
            'Api-Username: IL_TUO_NOME_UTENTE'
        ]);
        curl_exec($ch);

Sostituisci:

  • il-tuo-discourse.com con il dominio del tuo forum
  • ID_ARGOMENTO con l’ID corretto dell’argomento
  • LA_TUA_CHIAVE_API con la tua chiave API
  • IL_TUO_NOME_UTENTE con il nome utente scelto per la chiave API

Aggiornare il contenuto del post

Per poter aggiungere nuovo contenuto al primo post dell’argomento, dobbiamo prima recuperarne il contenuto attuale con una richiesta GET.

        $ch_get = curl_init('https://il-tuo-discourse.com/posts/ID_POST.json');
        curl_setopt($ch_get, CURLOPT_RETURNTRANSFER, true);
        $currentContent = json_decode(curl_exec($ch_get), true)['raw'];

Sostituisci:

  • ID_POST con l’ID corretto del post[3]

Infine, dobbiamo aggiornare il contenuto del post aggiungendo una nuova riga alla tabella con l’importo e la data. Lo faremo con una richiesta PUT.

        $updatedContent = $currentContent . "\n| " . $amount . "€ | " . $date . " |";
        $putPostData = json_encode(['post' => ['raw' => $updatedContent]]);
        $ch_put = curl_init('https://il-tuo-discourse.com/posts/ID_POST');
        curl_setopt($ch_put, CURLOPT_CUSTOMREQUEST, 'PUT');
        curl_setopt($ch_put, CURLOPT_POSTFIELDS, $putPostData);
        curl_setopt($ch_put, CURLOPT_HTTPHEADER, [
            'Content-Type: application/json',
            'Content-Length: ' . strlen($putPostData),
            'Api-Key: LA_TUA_CHIAVE_API',
            'Api-Username: IL_TUO_NOME_UTENTE'
        ]);
        curl_exec($ch_put);

Sostituisci:

  • il-tuo-discourse.com con il dominio del tuo forum
  • ID_POST con l’ID corretto del post
  • LA_TUA_CHIAVE_API con la tua chiave API
  • IL_TUO_NOME_UTENTE con il nome utente scelto per la chiave API

Il codice finale appare così:

<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    $jsonData = json_decode($_POST['data'], true);

    if ($jsonData['verification_token'] === 'IL_TUO_TOKEN_DI_VERIFICA') {
        $amount = floor(floatval($jsonData['amount']));
        $date = (new DateTime($jsonData['timestamp']))->format('d/m/Y');

        $putData = json_encode(['title' => '🥳 Nuova donazione: ' . $amount . '€ il ' . $date]);
        $ch = curl_init('https://il-tuo-discourse.com/t/test-nuovo-argomento/ID_ARGOMENTO');
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'PUT');
        curl_setopt($ch, CURLOPT_POSTFIELDS, $putData);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_HTTPHEADER, [
            'Content-Type: application/json',
            'Content-Length: ' . strlen($putData),
            'Api-Key: LA_TUA_CHIAVE_API',
            'Api-Username: IL_TUO_NOME_UTENTE'
        ]);
        curl_exec($ch);

        $ch_get = curl_init('https://il-tuo-discourse.com/posts/ID_POST.json');
        curl_setopt($ch_get, CURLOPT_RETURNTRANSFER, true);
        $currentContent = json_decode(curl_exec($ch_get), true)['raw'];

        $updatedContent = $currentContent . "\n| " . $amount . "€ | " . $date . " |";
        $putPostData = json_encode(['post' => ['raw' => $updatedContent]]);
        $ch_put = curl_init('https://il-tuo-discourse.com/posts/ID_POST');
        curl_setopt($ch_put, CURLOPT_CUSTOMREQUEST, 'PUT');
        curl_setopt($ch_put, CURLOPT_POSTFIELDS, $putPostData);
        curl_setopt($ch_put, CURLOPT_HTTPHEADER, [
            'Content-Type: application/json',
            'Content-Length: ' . strlen($putPostData),
            'Api-Key: LA_TUA_CHIAVE_API',
            'Api-Username: IL_TUO_NOME_UTENTE'
        ]);
        curl_exec($ch_put);

        curl_close($ch);
        curl_close($ch_get);
        curl_close($ch_put);
    } else {
        http_response_code(403);
        echo "Token di verifica non valido.";
    }
} else {
    http_response_code(405);
    echo "Sono consentite solo richieste POST.";
}
?>

Ripeto ancora una volta l’avvertimento all’inizio di questa guida :stuck_out_tongue:

:warning: Tutti gli esempi di codice in questa guida non sono intesi come best practice né vanno utilizzati così come sono.
Molti controlli, la gestione degli errori e altro sono volutamente ignorati o omessi per concentrarsi esclusivamente sull’uso dell’API.

Ora possiamo attivare una richiesta di prova da Ko-Fi e vedere come aggiorna il nostro argomento, sia il titolo che il contenuto. :slight_smile:

È tutto!
Hai un argomento che verrà aggiornato e fatto saltare ogni volta che qualcuno effettua una donazione su Ko-Fi! :partying_face:


:information_source: Questo argomento è un wiki. Sentiti libero di correggere eventuali errori che vedi e di discutere su come migliorare questa guida.


  1. Un URL specifico, in questo contesto. Ad esempio, https://il-tuo-discourse.com/posts.json ↩︎

  2. Un po’ di informazioni sulla loro API: https://help.ko-fi.com/hc/en-us/articles/360004162298-Does-Ko-fi-Have-an-API-or-Webhook- ↩︎

  3. L’ID del post può essere trovato nel codice HTML. È un elemento <article> con il seguente attributo: data-post-id="ID_POST" ↩︎

10 Mi Piace

Questo è fantastico @Canapin e molto necessario, penso. Stavo cercando qualcosa del genere un po’ di tempo fa. Grazie! :slight_smile:

3 Mi Piace

Come specifico un sottotema?
Se ho jBASE con un sottotema di AutoDoc, devo unire i due in un argomento con un delimitatore (jBASE>AutoDoc) o esiste un tag di categoria?

L’ho capito. Quando sei sulla pagina della categoria o sottocategoria, l’URL mostra il # invece del nome della categoria. Poiché le sottocategorie hanno i propri numeri, non devi combinare nulla.

Come sostituisco un articolo con informazioni aggiornate?

Attualmente, ricevo
{“action”:“create_post”,“errors”:[“Title has already been used”]}
invece di un aggiornamento riuscito.

Non c’è un’azione diversa per aggiornare i post?

Questo è il testo della risposta. La richiesta curl non specifica un’azione.

curl -X POST “http://LOCATION.local/posts.json” -H “Content-Type:
application/json” -H “Api-Key: APIKEY” -H “Api-Username: BOB” -d "{"title": "PL AUTO.DOC.FUN SCS
-TEST Autodoc","raw": " …

E se si utilizza l’endpoint per aggiornare un argomento?

O forse per aggiornare un post:

Non l’avevo visto. Ben notato. Ci proverò. Grazie.

Aggiornamento: mi manca ancora qualcosa. Sembra che l’unica differenza sia l’aggiunta di un edit_reason. Ci ho provato e non ha fatto differenza.

Ecco l’intero curl:

curl -X POST “http://localhost.local/posts.json” -H “Content-Type:
application/json” -H “Api-Key: API KEY” -H “Api-Username: BOB” -d “{"title": "Title of the Article","raw": "The quick brown fox jumped over the lazy dog.2023-12-26.","edit_reason": "auto","category": 66}”

% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
100 1927 0 65 100 1862 1177 33729 --:–:-- --:–:-- --:–:-- 34481

{“action”:“create_post”,“errors”:[“Title has already been used”]}

1 Mi Piace

Per aggiornare un argomento o un post, dovresti usare il metodo PUT!

Come ha sottolineato Firepup, se desideri aggiornare il contenuto di un post, puoi utilizzare la seguente API: Discourse API Docs

Il problema è che PUT richiede l’ID# e io non li ho.
Quando invio un POST per un nuovo argomento, raccolgo il # ma quel numero non sembra funzionare.
Quando uso un browser per visualizzare un argomento, mostra un # diverso ma quel numero non sembra funzionare.

Ad esempio: ho generato un argomento e l’evento POST restituisce {“id”:3244,…}
L’URL per accedervi dice …test-pl-auto-doc-fun/2803

Quindi, invio questo PUT:
curl -X PUT “http://LOCATION.local/posts.json/3244” -H “Content-Type: application/json” -H “Api-Key: KEY” -H “Api-Username: system” -d
“{"title": "Autodoc SCS-TEST PL AUTO.DOC.FUN","raw": "…","edit_reason": "auto","category": 66}”

E ricevo indietro l’HTML per la Pagina non trovata.

Dovrebbe essere /posts/3244.json.

L’id che ottieni da quella richiesta POST è l’ID del post (del primo post); è univoco tra tutti i post.

Entrambi i video nella guida sembrano restituire un 404.

1 Mi Piace

L’API può essere utilizzata per chiamare l’AI Helper?

Non credo, perché docs.discourse.org non lo menziona. Potrei sbagliarmi, però.

Perché l’AI helper dovrebbe essere utilizzato tramite API :thinking:

per costruire un bot collegato al mio sito web che sia collegato al mio forum con sette anni di conoscenza al suo interno per rispondere alle domande.
o per costruire un bot in grado di rispondere alle email che sia collegato al mio forum con sette anni di conoscenza al suo interno per rispondere alle domande.

Allora probabilmente ai-bot è più quello che stai cercando. ai-helper è quello che aiuta durante la lettura e la scrittura dei post.

Come dice la nota, non si tratta di un elenco completo.

Nota: Per qualsiasi endpoint non elencato, puoi seguire la guida reverse engineer the Discourse API per capire come utilizzare un endpoint API.

2 Mi Piace

Puoi fare tutto ciò che puoi fare dall’UX tramite l’API. Ingegnerizza al contrario l’API di Discourse

Le cose vengono aggiunte e modificate nell’API continuamente. Trovo più facile vedere sempre cosa sta succedendo nel browser.

5 Mi Piace

ottima idea grazie!