Formattare un feed RSS con CSS: cosa funziona ancora in Chrome

Un foglio CSS collegato a un feed continua a funzionare in Chrome dopo la rimozione di XSLT, a patto che il server invii il feed come application/xml o text/xml. Se invece arriva come application/rss+xml, lo stesso feed appare come testo semplice e il CSS viene ignorato. Lo abbiamo verificato in Chromium 156 e su un sito di prova con WordPress; la configurazione richiede tre passaggi.

Si può formattare un feed RSS con CSS senza XSLT?

Sì, se il server invia il feed con il tipo di contenuto giusto. L’annuncio di Chrome su XSLT precisa che l’istruzione di elaborazione <?xml-stylesheet ... ?> resta supportata per i fogli CSS, indicati con type="text/css". Sparisce solo XSLT, con Chrome 158, il 17 novembre 2026.

Il cambiamento interessa chi pubblica un feed che oggi usa un foglio XSL. Chrome osserva che molti feed RSS e Atom usano XSLT per essere leggibili quando li si apre direttamente nel browser. Dal 17 novembre questi feed perdono la loro impaginazione in Chrome. Un foglio CSS è l’alternativa più leggera: nessuna trasformazione, solo regole sull’aspetto di ogni elemento.

Il vincolo sul tipo di contenuto nasce dal modo in cui Chrome gestisce i tipi di media dei feed. Un feed inviato come application/rss+xml o application/atom+xml si apre in Chrome come testo semplice, a cui non si applica alcun foglio di stile, né CSS né XSL. La nostra guida sui feed RSS mostrati come testo spiega questo comportamento e cosa può fare chi legge il feed.

Per formattare un feed RSS con CSS servono quindi due cose: la riga del foglio di stile nel feed e un server che lo invii come application/xml o text/xml. Se oggi il feed formattato con XSL si vede correttamente in Chrome, il server invia già uno di questi tipi, e basta cambiare la riga del foglio di stile.

Con quale tipo di contenuto Chrome applica il CSS a un feed?

Con application/xml o text/xml. Il 14 ottobre 2026 abbiamo aperto in Chromium 156 due piccoli feed, uno Atom e uno RSS, serviti da un server locale. In entrambi, subito dopo la dichiarazione XML, c’era questa riga:

<?xml-stylesheet type="text/css" href="/feed.css"?>

Il foglio di prova mostrava ogni elemento title in rosso, a 28 pixel, e nascondeva tutti gli altri, così da poter controllare il risultato nello stile calcolato. Ogni caso è stato provato due volte: con la funzione XSLT di Chromium attiva e poi disattivata, come sarà in Chrome 158. I risultati sono stati identici.

Feed Tipo inviato dal server Cosa ha mostrato Chromium
Atom application/xml CSS applicato: titoli in rosso
Atom text/xml CSS applicato
RSS application/xml CSS applicato
RSS text/xml CSS applicato
Atom application/atom+xml Testo semplice del feed, CSS ignorato
RSS application/rss+xml Testo semplice del feed, CSS ignorato

Quando il feed appariva come testo semplice, la pagina mostrava il codice sorgente così come era stato inviato, con un carattere a spaziatura fissa, riga del foglio di stile compresa. Nei casi formattati, Chrome non mostrava alcun messaggio sopra il contenuto. Gli elementi nascosti, come id e updated, sparivano dalla pagina ma restavano nel documento.

Senza la riga del foglio di stile, lo stesso feed RSS inviato come application/xml è comparso nella vista ad albero di Chrome, sotto il messaggio «no style information» (nessuna informazione di stile), che spieghiamo nella guida su come aprire un file XML in Chrome. Con XSLT disattivato, per un feed collegato a un foglio XSL Chrome mostra un altro messaggio: «This document cannot be formatted as intended» (il documento non può essere formattato come previsto).

Come si collega un foglio CSS a un feed?

In tre passaggi.

1. Aggiungere l’istruzione di elaborazione. È definita nella raccomandazione del W3C «Associating Style Sheets with XML documents» e va inserita nel prologo, cioè subito dopo <?xml version="1.0"?> e prima dell’elemento radice, <rss> o <feed>. Lo pseudo-attributo href è obbligatorio. Gli altri sono facoltativi: type, title, media, charset e alternate. Ecco un feed RSS completo con la riga del foglio di stile:

<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/css" href="/feed.css"?>
<rss version="2.0">
  <channel>
    <title>Blog di esempio</title>
    <link>https://example.com/</link>
    <description>Ultimi articoli</description>
    <item>
      <title>Primo articolo</title>
      <link>https://example.com/primo/</link>
    </item>
  </channel>
</rss>

2. Scrivere il CSS. Secondo MDN, il valore iniziale della proprietà display è inline. Un feed non ha stili HTML predefiniti: senza regole specifiche, tutti gli elementi si susseguono su una sola riga. Per prima cosa conviene trasformare i contenitori in blocchi:

rss, channel, item, feed, entry { display: block; }
title { display: block; font-size: 1.4em; margin: 1em 0 0.3em; }
link, guid, id, updated, pubDate { display: none; }

Abbiamo provato anche questo foglio su un feed RSS: i titoli sono comparsi a 1,4 volte la dimensione di base e i link sono stati nascosti. In RSS sia il canale sia ogni voce (item) hanno un proprio elemento title. Per formattarli in modo diverso si usano channel > title e item > title, oppure feed > title e entry > title in Atom. Un semplice selettore title vale anche per i titoli di un feed Atom, i cui elementi appartengono allo spazio dei nomi di Atom. La specifica Selectors del W3C stabilisce infatti che, se il foglio CSS non dichiara uno spazio dei nomi predefinito, un selettore di tipo corrisponde a elementi di qualsiasi spazio dei nomi.

3. Inviare il tipo di contenuto giusto. L’elenco dei tipi MIME comuni di MDN raccomanda application/xml per l’XML e osserva che a volte si usa ancora text/xml: meglio quindi application/xml. Il servizio di validazione dei feed del W3C segnalerà che questo tipo non è abbastanza specifico perché ogni programma riconosca un feed. Quando non si può usare un tipo più preciso, chiede che <rss o <feed compaia nei primi 512 byte: un feed che inizia con le due righe viste sopra rispetta questa condizione.

In WordPress le due modifiche richiedono solo due hook. La funzione feed_content_type() restituisce application/rss+xml per RSS e application/atom+xml per Atom, a meno che un filtro non cambi questo valore; l’azione rss_tag_pre, invece, viene eseguita tra la dichiarazione XML e l’elemento radice. Questo codice, salvato come file PHP in wp-content/mu-plugins/, la cartella dei plugin «must-use», ha funzionato su un sito di prova con WordPress 7.1.3:

<?php
// Invia i feed RSS e Atom come application/xml, così Chrome applica un foglio CSS.
add_filter( 'feed_content_type', function ( $content_type, $type ) {
	return in_array( $type, array( 'rss2', 'atom' ), true ) ? 'application/xml' : $content_type;
}, 10, 2 );

// Stampa la riga del foglio di stile tra la dichiarazione XML e l'elemento radice.
add_action( 'rss_tag_pre', function () {
	echo '<?xml-stylesheet type="text/css" href="/feed.css"?>' . "\n";
} );

Con nginx, per un feed statico, si svuota la tabella dei tipi per quell’indirizzo e si imposta un tipo predefinito, come nell’esempio della documentazione per la direttiva types:

location = /feed.xml {
    types        { }
    default_type application/xml;
}

Nella nostra prova, con questo blocco nginx 1.27 ha inviato /feed.xml come application/xml, mentre gli altri file .xml hanno mantenuto il tipo predefinito di nginx, text/xml.

Per vedere cosa invia il server, aprire il feed in Chrome, avviare i DevTools (strumenti per sviluppatori), ricaricare la pagina e selezionare la richiesta del feed nel pannello Network (Rete). Nella scheda Headers (Intestazioni), content-type compare sotto Response Headers (intestazioni della risposta). Dal terminale, curl -s -o /dev/null -D - https://example.com/feed/ mostra le stesse intestazioni di risposta.

I feed dei podcast seguono le stesse regole: sono file RSS, quindi è il tipo di contenuto a decidere se Chrome applica il CSS o mostra il testo semplice.

Il link per il rilevamento automatico del feed, nelle pagine HTML, resta com’è: l’RSS Advisory Board richiede type="application/rss+xml" in quell’elemento link. Quell’attributo sta nella pagina HTML, mentre l’intestazione Content-Type del feed dipende solo dal server che lo invia.

Cosa non può fare il CSS in un feed RSS?

Il CSS cambia l’aspetto degli elementi, non la loro natura. Ne derivano tre limiti.

L’elemento link di ogni voce resta testo: il CSS non lo rende cliccabile, quindi chi legge non può aprire l’articolo con un clic.

Anche l’HTML dentro una description resta testo. Nella nostra prova i tag sono comparsi come testo, per esempio <p> e <b>, sia con l’HTML codificato con escape sia con quello in una sezione CDATA. Conviene nascondere la descrizione o tenerla in testo semplice.

Il CSS, infine, non tocca i dati: una data resta nel formato del feed, e le voci non si possono ordinare per data o per titolo.

Per avere una vera pagina con link cliccabili serve HTML, quindi un foglio XSL invece del CSS. Per i feed che mantengono il loro XSL, l’annuncio di Chrome suggerisce di aggiungere una riga che carica lo script xslt-polyfill, precisando che non dovrebbe impedire ai lettori di feed di analizzare l’XML. Il polyfill applica solo un foglio XSL già collegato al feed, e anche qui conta il tipo di contenuto. Nella nostra prova con XSLT disattivato, lo script inserito nel feed è stato eseguito quando il feed era inviato come application/xml, mai come application/rss+xml, perché in quel caso Chrome lo mostrava come testo semplice. L’altra strada è generare l’HTML separatamente e pubblicarlo a un altro indirizzo, lasciando il feed in XML. I nostri esempi di XSLT sul server mostrano come fare.

Per confrontare la versione CSS con la vecchia impaginazione XSL, si può aprire il feed in un visualizzatore XML che applica XSL. XMLNest, disponibile nel Chrome Web Store, applica i fogli XSL (versione 1.0) come faceva Chrome e apre i feed RSS e Atom in una vista di lettura.

Fonti

  1. Chrome for Developers: Removing XSLT for a more secure browser (verificata il 14 ottobre 2026)
  2. W3C: Associating Style Sheets with XML documents 1.0 (Second Edition) (verificata il 14 ottobre 2026)
  3. W3C: Selectors Level 3, selettori di tipo e spazi dei nomi (verificata il 14 ottobre 2026)
  4. MDN: display (verificata il 14 ottobre 2026)
  5. MDN: Tipi MIME comuni (verificata il 14 ottobre 2026)
  6. W3C Feed Validation Service: tipo di media non abbastanza specifico (verificata il 14 ottobre 2026)
  7. WordPress Developer Resources: feed_content_type() (verificata il 14 ottobre 2026)
  8. WordPress Developer Resources: rss_tag_pre (verificata il 14 ottobre 2026)
  9. WordPress Developer Resources: Must Use Plugins (verificata il 14 ottobre 2026)
  10. Documentazione di nginx: modulo ngx_http_core_module, direttiva types (verificata il 14 ottobre 2026)
  11. Chrome for Developers: Network features reference (verificata il 14 ottobre 2026)
  12. RSS Advisory Board: RSS Autodiscovery (verificata il 14 ottobre 2026)
  13. XSLT Polyfill, README di mfreed7/xslt_polyfill su GitHub (verificata il 14 ottobre 2026)
  14. Test di XMLNest : Testato da XMLNest in Chromium 156.0.8078.4 il 14 ottobre 2026, con la funzione XSLT attiva e poi disattivata: un feed Atom e un feed RSS collegati a un foglio CSS con <?xml-stylesheet type="text/css"?> sono stati formattati quando venivano serviti come application/xml o text/xml; serviti come application/atom+xml o application/rss+xml, sono apparsi come testo semplice, senza alcun foglio di stile. Il foglio pubblicato in questo articolo si è applicato a un feed RSS; l'HTML di una description, con escape o in una sezione CDATA, ha mostrato i tag come testo; il feed RSS senza riga del foglio di stile ha mostrato l'albero XML di Chrome; con la funzione XSLT disattivata, un feed collegato a un foglio XSL ha mostrato «This document cannot be formatted as intended», e un elemento script dello spazio dei nomi XHTML inserito nel feed è stato eseguito quando il feed era inviato come application/xml, non come application/rss+xml. Su un sito di prova con WordPress 7.1.3, creato a partire dall'immagine Docker ufficiale, il codice di questo articolo ha inviato /feed/ e /feed/atom/ come application/xml con la riga del foglio di stile, e Chromium ha applicato il CSS; nginx 1.27 ha inviato /feed.xml come application/xml con il blocco location di questo articolo, e gli altri file .xml come text/xml (verificata il 14 ottobre 2026)