Abbiamo creato un badge di bronzo, Users Helping Users, per le persone che cercano di aiutare altri utenti. Questo viene assegnato manualmente (per poter distinguere tra tentativi di essere d’aiuto e “anch’io”).
Per ogni 5 badge di bronzo, vogliamo assegnare un badge d’argento, Invaluable.
L’SQL che ho trovato individua i due utenti giusti, ma solo una volta ciascuno:
SELECT user_id, current_timestamp AS granted_at
FROM user_badges
WHERE badge_id = 110 -- Users Helping Users
AND (:backfill OR user_id IN (:user_ids))
GROUP BY user_id
HAVING COUNT(*) >= 5
Mi manca qualche magia nel mio SQL, o il moltiplicatore avviene al di fuori dell’SQL?
Inoltre, non mi è chiaro come avvenga il calcolo in modo che i miei due utenti non ricevano nuovi badge ogni giorno (questo verrà eseguito con un trigger notturno) anche se non hanno ricevuto 5 nuovi badge di bronzo.
Esiste una guida a questo che la mia ricerca non ha trovato?
Ok, una ricerca più approfondita mi ha portato a una traccia che mi ha condotto a la guida
La questione del riempimento dei dati è ancora un po’ confusa, ma ho deciso di (ovviamente!) provare questo sulla nostra istanza di test. Suppongo che il riempimento dei dati venga eseguito durante la notte, quindi ne saprò di più domani.
A meno che tu non selezioni “Può essere concesso più volte”, non dovrebbe essere assegnato più di una volta, anche se si qualificano per la seconda (o più) volta.
Ok, ho riletto il tuo post più attentamente e penso di aver capito meglio cosa stai cercando di ottenere.
Sulla base dell’SQL attuale, a quegli utenti verrà assegnato il badge d’argento solo una volta, anche se permetti che venga concesso più volte:
Ho creato i badge pertinenti sul mio sito di test (incluso il permesso di concederli più volte)
Ho assegnato 5 badge di bronzo ed eseguito il processo in background per assegnare il badge (badge d’argento assegnato con successo )
Ho quindi eseguito nuovamente il processo BadgeGrant e non è stato assegnato loro un secondo badge d’argento
Ho quindi aumentato i loro badge di bronzo a 11 ed eseguito nuovamente il processo di assegnazione dei badge
Questa è una buona domanda a cui non so rispondere immediatamente.
Sto pensando provvisoriamente a qualcosa che utilizzi RANK, ma potrei star tirando a indovinare…
Prototipo approssimativo...
WITH badge_count AS (
SELECT
user_id,
granted_at,
RANK() OVER (PARTITION BY user_id ORDER BY granted_at ASC) AS rank
FROM user_badges
WHERE badge_id = 110
)
SELECT user_id, granted_at
FROM badge_count
WHERE rank IN (5,10,15,20,25,30,35,40,45,50)
Ok, un secondo tentativo usando ROW_NUMBER invece:
WITH badge_count AS (
SELECT
user_id,
granted_at,
ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY granted_at ASC) AS row
FROM user_badges
WHERE badge_id = 110
)
SELECT user_id, granted_at
FROM badge_count
WHERE row % 5 = 0
Tuttavia, dopo ulteriori test, questo funziona correttamente nell’anteprima ma non viene concesso più volte quando viene eseguito il processo effettivo di badge grant. Non sono molto sicuro del perché.
Mi sono confuso. Prenderò una tazza di tè e mi riorganizzerò.
Beh… ho dato al mio utente altri 4 bronzi ieri per vedere se l’esecuzione notturna avrebbe almeno aggiunto il nuovo badge che aveva appena “guadagnato”. (Ho pensato che se avessi dovuto recuperare il resto manualmente, avrei potuto.) Ma nemmeno quello ha funzionato.
Non posso aiutarti con la query, ma ti suggerisco di chiedere aiuto al bot Discourse AI: seleziona l’icona del bot in alto → GPT-4 → SQL Helper.
L’ho trovato molto utile nel creare query per Data Explorer semplicemente dicendogli di cosa ho bisogno e immagino che possa aiutare con le query per i badge.
Non tutti ce l’hanno, Toni Farai ingelosire la gente. (anche se @ganncamp ce l’ha, quindi è un’opzione)
Ma… sono abbastanza sicuro che la mia query sia valida. Seleziona quelle giuste nell’anteprima, ma non ne assegna più di una quando si utilizza il trigger ‘Aggiorna giornalmente’.
Ne ho impostata un’altra quasi identica per testarla basata su un badge per ‘ogni 5 post in un argomento specifico’ utilizzando il trigger ‘quando un utente crea o modifica un post’ - e quella funziona perfettamente. Sto indagando su quale possa essere la differenza…
Ecco l’SQL per quel badge di test da confrontare se qualcuno riesce a individuare qualcosa:
WITH post_count AS (
SELECT
user_id,
id,
created_at,
ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY created_at ASC) AS row
FROM posts
WHERE topic_id = 864
)
SELECT user_id, created_at granted_at, id post_id
FROM post_count
WHERE row % 5 = 0
AND (:backfill OR id IN (:post_ids))
Dopo un po’ di esplorazione e consultazione, sembra che il conceditore automatico di badge assegnerà più badge solo se sono basati su post specifici. Quindi questi tipi assegneranno solo il primo badge (l’anteprima è fuorviante ).
Penso che in casi simili i badge “escalating” possano funzionare bene (come quelli Solved). Quindi un argento per 30 e un oro per 100, per esempio, se questa potesse essere un’alternativa valida?
Quindi… anche se i badge di bronzo vengono assegnati in base ai post… non conta, vero?
Non lo so. Non credo di capire la domanda.
Immagino che il suggerimento non sia di trovare 5 badge, ma 5 post in cui è stato assegnato un badge? Posso farlo. L’ho già fatto più o meno nel mio report “trova nuovi post a cui assegnare badge”.
Hmmm. Penso di capire dove vuoi arrivare. Ci riprovo…
@ganncamp - Penso che potremmo avere un po’ di successo…
Basandomi sul fatto che il Bronze Badge A viene assegnato tramite il post wrench o dando una motivazione nella pagina /admin/users/{user_id}/{username}/badges:
Allora penso che questo sia effettivamente possibile.
WITH badge_count AS (
SELECT
user_id,
granted_at,
post_id,
ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY granted_at DESC) AS row
FROM user_badges
WHERE badge_id = 110
AND post_id IS NOT NULL
)
SELECT user_id, granted_at, post_id
FROM badge_count
WHERE row % 5 = 0
AND (:backfill OR post_id IN (:post_ids))
(Aggiungere AND post_id IS NOT NULL lo protegge nel caso in cui qualcuno ne riceva uno senza motivazione, altrimenti si rompe)
L’ho appena provato e ho accelerato attivando il job di background GrantBadge e il mio utente di test ha finalmente ricevuto il pieno riconoscimento che merita.
Beh… quando il processo è stato eseguito durante la notte,
il mio utente con 6 bronzi ha ottenuto 1 argento
il mio utente con 13 bronzi ha ottenuto… 1 argento
Questa parte del tutorial mi ha fatto pensare che un processo di backfill separato ed esplicito non fosse necessario
Dato che ogni giorno viene eseguito un backfill completo, devi tenerne conto e includere la gestione del parametro :backfill.
Per gli utenti che hanno già guadagnato più di 1 argento, come posso farli assegnare? Devo farlo manualmente?
Il backfill è il processo giornaliero. Il trigger ‘Update Daily’ è essenzialmente solo questo, mentre gli altri trigger sono molto più ‘al momento’ (ad esempio, se un badge utilizzasse ‘quando un utente crea o modifica un post’, non avrebbe bisogno di aspettare la notte per essere assegnato).
Puoi allegare uno screenshot del tuo badge in modo che io possa vedere cosa potrebbe essere diverso?
Avevo ipotizzato che il job venisse eseguito nelle ore piccole del (mio) mattino.
Infatti, originariamente avevo concesso a questo utente badge senza motivi, quindi ieri li ho revocati tutti, ho recuperato i post suoi e li ho riassegnati. Il job è stato eseguito nel bel mezzo della mia assegnazione.
Questo è sul mio sito di staging, a proposito.
Suppongo che il secondo badge verrà concesso tra qualche ora, ma vorrei vedere più badge concessi contemporaneamente. Succederà se revocherò l’argento? Gli verranno concessi 2 nuovi argenti tra… 2 ore?