Ricette di biscotti SameSite

Chrome, Firefox, Edge e altri ancora modificheranno il loro comportamento predefinito in linea con la proposta IETF, Incrementally Better Cookies per:

  • I cookie senza un attributo SameSite verranno trattati come SameSite=Lax, il che significa che il comportamento predefinito prevederà la limitazione dei cookie ai contesti proprietari solo.
  • I cookie per l'utilizzo tra siti devono specificare SameSite=None; Secure per consentire l'inclusione nel contesto di terze parti.

Questa funzionalità è il comportamento predefinito dalla versione stabile di Chrome 84 in poi. Se non lo hai già fatto, devi aggiornare gli attributi dei cookie di terze parti in modo che non vengano bloccati in futuro.

Supporto cross-browser

Consulta la sezione Compatibilità del browser nella pagina MDN Set-Cookie.

Casi d'uso dei cookie cross-site o di terze parti

Esistono diversi casi d'uso e pattern comuni in cui i cookie devono essere inviati in un contesto di terze parti. Se fornisci o dipendi da uno di questi casi d'uso, assicurati che tu o il provider stiate aggiornando i cookie per garantire che il servizio continui a funzionare correttamente.

Contenuti all'interno di un <iframe>

I contenuti di un altro sito visualizzato in un <iframe> sono inseriti in un contesto di terze parti. Ecco alcuni casi d'uso standard:

  • Contenuti incorporati condivisi da altri siti, ad esempio video, mappe, esempi di codice e post social.
  • Widget di servizi esterni, ad esempio funzionalità di pagamento, calendari, prenotazione e prenotazione.
  • Widget come pulsanti social o servizi antifrode che creano <iframes> meno evidenti.

I cookie possono essere utilizzati qui, tra le altre cose, per mantenere lo stato della sessione, memorizzare preferenze generali, attivare statistiche o personalizzare i contenuti per gli utenti che dispongono di account esistenti.

Diagramma di una finestra del browser in cui l&#39;URL dei contenuti incorporati non corrisponde all&#39;URL della pagina.
Se i contenuti incorporati non provengono dallo stesso sito del contesto di navigazione di primo livello, si tratta di contenuti di terze parti.

Inoltre, poiché il web è intrinsecamente componibile, gli elementi <iframes> vengono utilizzati per incorporare contenuti che vengono visualizzati anche in un contesto proprietario o di primo livello. Tutti i cookie utilizzati dal sito saranno considerati cookie di terze parti quando il sito viene visualizzato all'interno del frame. Se stai creando siti che vuoi incorporare facilmente da altri utenti pur facendo affidamento sui cookie per funzionare, dovrai anche assicurarti che siano contrassegnati per l'utilizzo tra siti oppure di poter eseguire tranquillamente il fallback senza utilizzarli.

Richieste "non sicure" tra i siti

Anche se la parola "non sicuro" può sembrare un po' preoccupante, si riferisce a qualsiasi richiesta intesa a cambiare stato. Sul web sono principalmente richieste POST. I cookie contrassegnati come SameSite=Lax verranno inviati durante navigazioni di primo livello sicure, ad esempio facendo clic su un link per passare a un altro sito. Tuttavia, qualcosa come un invio <form> tramite POST a un sito diverso non includerà i cookie.

Diagramma di una richiesta che si sposta da una pagina all&#39;altra.
Se la richiesta in arrivo utilizza un metodo "sicuro", i cookie verranno inviati.

Questo pattern viene utilizzato per i siti che possono reindirizzare l'utente a un servizio remoto per eseguire alcune operazioni prima di tornare, ad esempio reindirizzare l'utente a un provider di identità di terze parti. Prima che l'utente lasci il sito, viene impostato un cookie contenente un token monouso con l'aspettativa che questo token possa essere controllato nella richiesta restituita per mitigare gli attacchi di falsificazione di richieste incrociate su siti (CSRF). Se la richiesta di ritorno avviene tramite POST, sarà necessario contrassegnare i cookie come SameSite=None; Secure.

Risorse remote

Qualsiasi risorsa remota su una pagina potrebbe fare affidamento sui cookie da inviare con una richiesta, dai tag <img>, dai tag <script> e così via. I casi d'uso più comuni includono i pixel di monitoraggio e la personalizzazione dei contenuti.

Questo vale anche per le richieste avviate da JavaScript da fetch o XMLHttpRequest. Se fetch() viene chiamato con l'opzione credentials: 'include', significa che è possibile che i cookie siano previsti per quelle richieste. Per XMLHttpRequest devi cercare le istanze della proprietà withCredentials impostata su true. Questo è un buon indicatore del fatto che i cookie potrebbero essere previsti per queste richieste. Questi cookie dovranno essere contrassegnati in modo appropriato per essere inclusi nelle richieste cross-site.

Contenuti all'interno di una WebView

Un componente WebView in un'app specifica della piattaforma è basato su un browser e dovrai verificare se si applicano le stesse restrizioni o problemi. In Android, se la WebView è basata su Chrome, le nuove impostazioni predefinite non verranno applicate immediatamente a Chrome 84. Tuttavia, l'intento è quello di applicarli in futuro, per cui dovresti comunque testare e prepararti per questo. Inoltre, Android consente alle sue app specifiche della piattaforma di impostare i cookie direttamente tramite l'API CookieManager. Come per i cookie impostati tramite intestazioni o JavaScript, valuta la possibilità di includere SameSite=None; Secure se sono destinati all'utilizzo tra siti.

Come implementare SameSite oggi stesso

Per i cookie in cui sono necessari solo in un contesto proprietario, idealmente dovresti contrassegnarli come SameSite=Lax o SameSite=Strict, a seconda delle tue esigenze. Puoi anche scegliere di non fare nulla e consentire al browser di applicare l'impostazione predefinita, ma ciò comporta il rischio di comportamenti incoerenti tra i browser e potenziali avvisi della console per ciascun cookie.

Set-Cookie: first_party_var=value; SameSite=Lax

Per i cookie necessari in un contesto di terze parti, dovrai assicurarti che siano contrassegnati come SameSite=None; Secure. Tieni presente che sono necessari entrambi gli attributi insieme. Se specifichi semplicemente None senza Secure, il cookie verrà rifiutato. Tuttavia, esistono alcune differenze incompatibili tra loro nelle implementazioni dei browser, pertanto potresti dover utilizzare alcune delle strategie di mitigazione descritte nella sezione Gestione di client incompatibili di seguito.

Set-Cookie: third_party_var=value; SameSite=None; Secure

Gestione di client incompatibili

Poiché queste modifiche per includere None e aggiornare il comportamento predefinito sono ancora relativamente nuove, esistono incongruenze tra i browser su come vengono gestite queste modifiche. Puoi fare riferimento alla pagina degli aggiornamenti su chromium.org per i problemi attualmente noti, ma non è possibile indicare se l'elenco sia esaustivo. Sebbene ciò non sia l'ideale, esistono soluzioni alternative che puoi utilizzare durante questa fase di transizione. Tuttavia, la regola generale è considerare i client incompatibili come il caso speciale. Non creare un'eccezione per i browser che implementano le regole più recenti.

La prima opzione consiste nell'impostare i cookie nuovo e vecchio:

Set-cookie: 3pcookie=value; SameSite=None; Secure
Set-cookie: 3pcookie-legacy=value; Secure

I browser che implementano il comportamento più recente imposteranno il cookie con il valore SameSite, mentre altri browser potrebbero ignorarlo o impostarlo in modo errato. Tuttavia, gli stessi browser imposteranno il cookie 3pcookie-legacy. Durante l'elaborazione dei cookie inclusi, il sito deve prima verificare la presenza del nuovo cookie di stile e, se non lo trova, poi utilizzare il cookie precedente.

L'esempio seguente mostra come eseguire questa operazione in Node.js, utilizzando il framework Express e il suo middleware cookie-parser.

const express = require('express');
const cp = require('cookie-parser');
const app = express();
app.use(cp());

app.get('/set', (req, res) => {
  // Set the new style cookie
  res.cookie('3pcookie', 'value', { sameSite: 'none', secure: true });
  // And set the same value in the legacy cookie
  res.cookie('3pcookie-legacy', 'value', { secure: true });
  res.end();
});

app.get('/', (req, res) => {
  let cookieVal = null;

  if (req.cookies['3pcookie']) {
    // check the new style cookie first
    cookieVal = req.cookies['3pcookie'];
  } else if (req.cookies['3pcookie-legacy']) {
    // otherwise fall back to the legacy cookie
    cookieVal = req.cookies['3pcookie-legacy'];
  }

  res.end();
});

app.listen(process.env.PORT);

Lo svantaggio è che ciò comporta l'impostazione di cookie ridondanti per coprire tutti i browser e richiede di apportare modifiche sia al momento dell'impostazione che durante la lettura dei cookie. Tuttavia, questo approccio dovrebbe riguardare tutti i browser indipendentemente dal loro comportamento e garantire che i cookie di terze parti continuino a funzionare come prima.

In alternativa, quando invii l'intestazione Set-Cookie, puoi scegliere di rilevare il client tramite la stringa dello user agent. Fai riferimento all'elenco dei client incompatibili e utilizza una libreria appropriata per la tua piattaforma, ad esempio la libreria ua-parser-js su Node.js. Ti consigliamo di trovare una libreria per gestire il rilevamento dello user agent, dato che probabilmente non vorrai scrivere personalmente le espressioni regolari.

Il vantaggio di questo approccio è che richiede solo una modifica al momento dell'impostazione del cookie. Tuttavia, l'avviso necessario è che lo sniffing dello user agent è intrinsecamente fragile e potrebbe non catturare tutti gli utenti interessati.

Supporto per SameSite=None in linguaggi, librerie e framework

La maggior parte delle lingue e delle librerie supporta l'attributo SameSite per i cookie, tuttavia l'aggiunta di SameSite=None è ancora relativamente nuova, il che significa che al momento potresti dover aggirare alcuni comportamenti standard. Questi dati sono documentati nel repository di esempi di SameSite su GitHub.

Richiesta di aiuto

I cookie sono sparsi dappertutto ed è raro che un sito ne abbia controllato completamente la posizione in cui sono impostati e utilizzati, soprattutto dopo aver combinato casi d'uso tra siti. Quando si verifica un problema, potrebbe essere la prima volta che qualcuno lo rileva, quindi non esitare a contattarci: