FreeToGenerate.com

Ejecuta el algoritmo que el estándar HTML especifica de verdad, incluidos los casos que el RFC dejó abiertos y los que ninguna tabla de referencia recoge. No se sube nada.

Una cabecera por línea. El estándar dice que un valor separado por comas y varias cabeceras independientes dan el mismo resultado, así que aquí sirven las dos formas.

Prueba uno:

El documento que envía la cabecera.

Uno por línea, del más interno al más externo: la página que incrusta la tuya, luego la que incrusta a esa, hasta la pestaña. Déjalo vacío si nadie la enmarca.

Si una política aplicada incluye una directiva frame-ancestors, X-Frame-Options se ignora por completo, antes incluso de leer su valor.

Qué hace un navegador conforme

El navegador se niega a mostrarla

El valor es SAMEORIGIN y hay un antecesor de otro origen. La comprobación recorre la cadena entera, así que basta con un marco ajeno en cualquier punto.

Valores tras separar
sameorigin
Primer antecesor de otro origen
https://widgets.partner.test

Todos los casos que el estándar recoge

Estos son los valores para los que el estándar HTML publica respuestas resueltas, incluidos los no conformes. Los veredictos los calcula esta página, no están copiados, y se evalúan contra un padre del mismo origen.

Valor de la cabeceraVálidoResultado
DENYUn solo valorEl navegador se niega a mostrarla
SAMEORIGINLa página puede incrustarse
INVALIDNoLa página puede incrustarse
ALLOWALLNoLa página puede incrustarse
ALLOW-FROM=https://example.com/NoLa página puede incrustarse
SAMEORIGIN, SAMEORIGINVarios valoresNoLa página puede incrustarse
SAMEORIGIN, DENYNoEl navegador se niega a mostrarla
SAMEORIGIN,NoEl navegador se niega a mostrarla
SAMEORIGIN, ALLOWALLNoEl navegador se niega a mostrarla
SAMEORIGIN, INVALIDNoEl navegador se niega a mostrarla
ALLOWALL, INVALIDNoEl navegador se niega a mostrarla
ALLOWALL,NoEl navegador se niega a mostrarla
INVALID, INVALIDNoLa página puede incrustarse

Todo funciona en tu navegador. No se sube nada, y al recargar la página se olvida lo que escribiste.

También disponible en: English · Português · Français · العربية

X-Frame-Options: qué hace realmente la cabecera hoy

Pega tu cabecera y los marcos que rodean la página, y comprueba qué paso del estándar decide.

¿Qué es X-Frame-Options?

X-Frame-Options es una cabecera de respuesta que indica al navegador si tu página puede mostrarse dentro del marco de otra persona. Existe para frenar el clickjacking: un atacante incrusta tu página real, la vuelve invisible y consigue que la víctima pulse un botón que no ve. Solo dos valores significan algo: DENY rechaza cualquier marco y SAMEORIGIN lo permite únicamente desde tu propio origen.

La cabecera es más antigua que el proceso que suele producir los estándares web. Los navegadores la implementaron hacia 2009, y la descripción que todo el mundo cita, el RFC 7034, se escribió cuatro años después para documentar lo que ya estaba construido. Ese RFC está marcado como Informational y lo dice de sí mismo en sus primeras líneas: no es una especificación de la vía de estándares de internet.

Es decir, el documento al que enlaza la mayoría de las páginas ya no es el que gobierna el comportamiento. El estándar HTML es el que ahora contiene el modelo de procesamiento y afirma sin rodeos que su definición sustituye a la del RFC. La gramática que da es más corta, el algoritmo es más preciso y resuelve varias cuestiones que el RFC dejó abiertas de forma explícita.

Cómo usarla

  1. Introduce tu cabecera. Una por línea si la respuesta envía más de una. Un valor separado por comas y varias cabeceras independientes son equivalentes según la norma, así que ambas formas dan aquí la misma respuesta.
  2. Describe los marcos que rodean la página. Indica el origen del documento que envía la cabecera y después los orígenes que lo enmarcan, del más interno al más externo, hasta la pestaña. Importa más de lo que parece: la comprobación recorre la cadena entera.
  3. Añade una Content-Security-Policy si la envías. Si una política aplicada incluye frame-ancestors, X-Frame-Options se ignora del todo. Marca la casilla de Report-Only para ver la diferencia, que es mayor de lo que casi nadie espera.

Los casos que ninguna tabla recoge

Lo interesante ocurre cuando una respuesta lleva más de un valor, algo habitual en la práctica porque un proxy o un framework añade una cabecera que la aplicación ya había puesto. El estándar publica una tabla de respuestas resueltas para exactamente esos casos, y los resultados no son los que uno imaginaría. SAMEORIGIN junto a un valor inválido bloquea la página. Dos valores inválidos la permiten. La regla es deliberada: una cabecera con un valor con sentido y otro confuso parece la mala configuración de algo que intentaba funcionar, así que se bloquea a propósito, mientras que una cabecera del todo ilegible se trata como si nunca se hubiera enviado.

Basta una coma final para desencadenarlo. Separar por comas convierte SAMEORIGIN, en dos valores, el segundo vacío, y eso cuenta como un segundo valor distinto, de modo que la página queda bloqueada. Enviar SAMEORIGIN en una cabecera y un X-Frame-Options vacío en otra produce lo mismo, exactamente por la misma razón.

ALLOWALL es el superviviente más extraño. No aparece por ninguna parte en el RFC 7034 (nunca formó parte de la gramática documentada de la cabecera) y sin embargo el estándar lo nombra, únicamente para que la regla de valores múltiples pueda atraparlo. Por sí solo no hace absolutamente nada, y una página que envía solo ALLOWALL es tan incrustable como una que no envía cabecera alguna.

ALLOW-FROM es el que todavía se copia de los tutoriales. Está en la gramática del RFC, y el estándar HTML dice con todas las letras que no debe implementarse. Una página que confíe en él para autorizar a un socio concreto está autorizando a todo el mundo, en silencio, porque un valor que la gramática no admite se trata como si no hubiera cabecera.

La pregunta que el RFC dejó abierta

SAMEORIGIN suena inequívoco y no lo es. Piensa en una página enmarcada por el widget de un socio, cuando ese widget está a su vez enmarcado por tu propio sitio en el nivel superior. ¿El origen que se compara es el de la página que enmarca directamente, el del documento de nivel superior de la pestaña, o el de todos los documentos intermedios? El RFC 7034 admite las tres lecturas en su propio texto, al señalar que los criterios pueden no evaluarse de forma unánime y enumerar cada posibilidad.

El estándar HTML lo zanja: la comprobación sube por la cadena completa de antecesores, y basta un solo documento de otro origen en cualquier punto para bloquear la página. Así que el ejemplo anterior se rechaza, aunque la página de nivel superior sea tuya. Esa es la más estricta de las tres lecturas, y es la que implementa la herramienta de arriba, razón por la cual el ejemplo por defecto parece que debería permitirse y no se permite.

La otra regla que conviene conocer es que una directiva CSP frame-ancestors no se limita a tener prioridad: elimina X-Frame-Options de la ecuación por completo. El algoritmo busca la directiva antes de mirar siquiera el valor de la cabecera, de modo que una página que envía DENY junto a cualquier política con frame-ancestors se rige solo por la política. Pero esto vale únicamente para una política aplicada. Una cabecera Content-Security-Policy-Report-Only se omite, porque el algoritmo solo considera las políticas cuya disposición es de aplicación, así que pasar frame-ancestors a Report-Only mientras haces pruebas devuelve el control, sin avisar, a una cabecera en la que quizá ya habías dejado de pensar.

Lo que esto no puede decirte

Te dice lo que debe hacer un navegador conforme, no lo que hace un navegador concreto. La distinción es real: la razón misma de que el RFC admita una ambigüedad es que las implementaciones diferían, y un navegador puede arrastrar comportamientos antiguos durante años. Nada de esto se ha medido contra un navegador real, y el apéndice de compatibilidad de un documento de 2013 no es prueba de nada sobre hoy.

Tampoco puede ver la página por la que preguntas. Los orígenes los aportas tú, así que la respuesta vale lo que valga la cadena que hayas descrito, y la cadena es precisamente la parte fácil de equivocar, porque una página puede estar enmarcada por algo que tú no pusiste ahí. Si quieres la respuesta real de una página real, las herramientas de desarrollo del navegador te dirán cuándo se rechazó un marco, y por qué.

Por último, X-Frame-Options es la mitad más antigua de una pareja. Todo lo que expresas con ella puedes expresarlo con una directiva CSP frame-ancestors, que además cubre los casos que la cabecera no alcanza: permitir un origen concreto, permitir varios o comparar por esquema. La cabecera sigue mereciendo la pena para clientes antiguos, y ambas conviven sin problema, pero un despliegue nuevo debería apoyarse en la política antes que en la cabecera.

¿Por qué es gratis?

Ejecutar un algoritmo de una especificación es aritmética sobre unas cuantas cadenas de texto, y ocurre en tu navegador. No hay servidor de por medio, así que no hay nada que facturar ni cuenta que crear.

No se sube nada. La cabecera y los orígenes que escribes no salen de la pestaña.