Sto cercando di migliorare la nostra postura di sicurezza e parte di ciò significa che dobbiamo evitare di utilizzare credenziali segrete quando possibile.
Sfortunatamente, il plugin OIDC richiedeva una credenziale di segreto client per raggiungere l’endpoint /userinfo e non sono riuscito a configurare il mio forum con esso abilitato.
Fortunatamente, la specifica OIDC è effettivamente definita in un modo che non richiede l’uso di token segreti.
Se ci atteniamo al id_token flow, l’IdP ci invierà tutte le informazioni necessarie per autenticare un utente senza dover contattare nuovamente l’IdP.
Questo è sicuro perché il reindirizzamento è configurato nell’IdP e non dobbiamo preoccuparci che il token bearer venga inoltrato alla destinazione sbagliata.
Ho proceduto a creare una patch per il plugin OIDC per supportare il flusso id_token e ho inviato una pull request qui:
La PR non è del tutto completa poiché necessita ancora di unit test, ma è quasi pronta e ho confermato che funziona correttamente con Azure AD (Entra ID).
Per riferimento, qui è la documentazione per il plugin OIDC:
Penso che quello che stai descrivendo qui sia il flussi “Implicit Flow” di OpenID Connect, che funziona senza alcuna comunicazione server-server e, pertanto, non necessita di un segreto condiviso. Invece, tutte le informazioni vengono trasmesse tramite i reindirizzamenti HTTP e l’ID token viene verificato crittograficamente utilizzando le chiavi pubbliche dal Discovery Document.
Va bene, e penso che sia una richiesta di funzionalità valida. Ma è un sistema molto diverso dal nostro plugin attuale, che utilizza il flusso di codice di autorizzazione. Questo flusso utilizza la comunicazione server-server con un segreto condiviso e, pertanto, non è necessaria alcuna verifica crittografica dell’id_token. Questo è più semplice per certi versi, ma più complesso per altri.
Importante: non possiamo semplicemente cambiare l’implementazione predefinita nel plugin. I siti che utilizzano il flusso di codice di autorizzazione devono continuare a utilizzarlo. IIRC molti provider di identità non supportano nemmeno l’Implicit Flow.
Quindi penso che ci siano due strade da percorrere qui:
Aggiungiamo il supporto per l’“implicit flow” nel plugin OIDC, ma rendiamolo una cosa opt-in. Penso sia improbabile che accettiamo una PR che introduca la gemma openid-connect come dipendenza di Discourse core, quindi dovrebbe essere implementata all’interno della nostra strategia attuale.
Il plugin discourse-lti (learning tools integration) potrebbe essere una fonte utile di ispirazione, perché il protocollo LTI si basa sull’implicit flow OIDC. La logica di decodifica dell’id_token è qui
o in alternativa
Costruisci l’implicit flow come un plugin completamente nuovo. In questo caso, saresti libero di fare quello che vuoi in termini di implementazione (ma dovresti anche mantenerlo tu stesso)
Vale la pena notare anche che l’“Implicit Flow” OIDC aumenta la superficie di attacco per attacchi CSRF ed esposizione di token:
Penso che possa ancora avere senso per alcune situazioni. Ma sembra che il flusso Authorization Code (predefinito di Discourse) con PKCE (opzionale in Discourse) sia il modo più consigliato per utilizzare OIDC.
Penso che possa ancora avere senso in alcune situazioni. Ma sembra che il flusso del codice di autorizzazione (il predefinito di Discourse) con PKCE (opzionale in Discourse) sia il modo più consigliato per utilizzare OIDC.
Questo è molto interessante: finora non avevo compreso appieno PKCE. Sulla base della mia lettura della documentazione di Auth0, sembra che (in determinate configurazioni) questo flusso abbia i vantaggi del flusso implicito (nessun segreto client) senza nessuno degli svantaggi.
È forse qualcosa che si può fare invece? Sembra che sia semplice come rimuovere il parametro del segreto client dall’endpoint /token.
E, in definitiva, la mia principale preoccupazione è semplicemente eliminare il requisito di un segreto client
diff --git a/plugins/discourse-openid-connect/lib/omniauth_open_id_connect.rb b/plugins/discourse-openid-connect/lib/omniauth_open_id_connect.rb
index 410a88f46dc..e74ee360aae 100644
--- a/plugins/discourse-openid-connect/lib/omniauth_open_id_connect.rb
+++ b/plugins/discourse-openid-connect/lib/omniauth_open_id_connect.rb
@@ -73,6 +73,11 @@ module OmniAuth
)
options[:client_options][:auth_scheme] = :request_body
end
+
+ # Se stiamo usando PKCE _e_ non c'è client_secret, usa lo schema di autenticazione request_body.
+ if options[:pkce] && options[:client_secret].empty?
+ options[:client_options][:auth_scheme] = :request_body
+ end
end
def request_phase
L’URI di reindirizzamento è configurato nel pannello di controllo di Azure come segue: