Incorporando conteúdo externo com iframe

Entenda como usar o iframe para embutir mapas do Google, vídeos do YouTube e outros conteúdos externos na sua página.

Algumas das funcionalidades mais comuns de sites modernos dependem de uma única tag: o mapa do Google embaixo do endereço de uma empresa, o vídeo do YouTube incorporado em um artigo, o formulário de pagamento do Stripe em uma loja virtual, o widget de comentários de uma rede social. Todos eles usam a tag <iframe>.

O <iframe> — inline frame — é uma janela aberta dentro da sua página que carrega e exibe outro documento HTML completo.


Anatomia básica do iframe

<iframe
  src="https://exemplo.com"
  width="600"
  height="400"
  title="Descrição do conteúdo incorporado"
>
</iframe>
Atributo Propósito
src URL do documento a ser incorporado
width Largura em pixels ou porcentagem
height Altura em pixels
title Descrição acessível do conteúdo — obrigatório

Diferente da <img>, o <iframe> tem abertura e fechamento — e o conteúdo entre as tags é o texto de fallback para navegadores muito antigos:

<iframe src="https://exemplo.com" title="Exemplo">
  Seu navegador não suporta iframes.
  <a href="https://exemplo.com">Acessar o conteúdo</a>
</iframe>

O atributo title: obrigatório para acessibilidade

O atributo title é essencial em todo <iframe>. Leitores de tela anunciam o título do iframe antes de entrar em seu conteúdo — sem ele, o usuário não sabe o que encontrará dentro:

<!-- ❌ Sem title — o leitor de tela anuncia apenas "frame" -->
<iframe src="https://maps.google.com/..."></iframe>

<!-- ✅ Com title — o leitor de tela anuncia o conteúdo -->
<iframe
  src="https://maps.google.com/..."
  title="Mapa com a localização da nossa loja"
></iframe>

Casos de uso comuns

Incorporando um vídeo do YouTube

O YouTube gera automaticamente o código de incorporação para qualquer vídeo. O resultado é um iframe com configurações já definidas:

<iframe
  width="560"
  height="315"
  src="https://www.youtube.com/embed/dQw4w9WgXcQ"
  title="Rick Astley — Never Gonna Give You Up (videoclipe oficial)"
  frameborder="0"
  allow="accelerometer; autoplay; clipboard-write;
         encrypted-media; gyroscope; picture-in-picture"
  allowfullscreen
>
</iframe>

💡 O URL de incorporação do YouTube usa o formato youtube.com/embed/ID-DO-VIDEO — diferente da URL de visualização normal youtube.com/watch?v=ID-DO-VIDEO.


Incorporando um mapa do Google Maps

O Google Maps também oferece código de incorporação:

<iframe
  src="https://www.google.com/maps/embed?pb=..."
  width="600"
  height="450"
  style="border: 0"
  allowfullscreen
  loading="lazy"
  referrerpolicy="no-referrer-when-downgrade"
  title="Mapa com a localização da sede da empresa"
>
</iframe>

Incorporando um formulário externo

<iframe
  src="https://forms.google.com/..."
  width="640"
  height="800"
  frameborder="0"
  title="Formulário de inscrição no evento"
>
</iframe>

Incorporando um documento PDF

<iframe
  src="manual-usuario.pdf"
  width="100%"
  height="600"
  title="Manual do usuário em PDF"
>
  <p>
    Seu navegador não suporta exibição de PDF.
    <a href="manual-usuario.pdf" download>
      Baixar o manual (PDF)
    </a>.
  </p>
</iframe>

Atributos de comportamento e aparência

frameborder

<!-- Valores: 0 (sem borda) ou 1 (com borda) -->
<iframe src="..." frameborder="0"></iframe>

O frameborder foi deprecado no HTML5 — a forma correta de remover a borda é via CSS:

iframe {
  border: none;
}

allowfullscreen

<iframe
  src="https://www.youtube.com/embed/..."
  allowfullscreen
  title="Vídeo demonstrativo"
>
</iframe>

Atributo booleano que permite ao conteúdo do iframe entrar em modo de tela cheia — necessário para players de vídeo.


loading: carregamento preguiçoso

<!-- lazy: carrega apenas quando entra na área visível -->
<iframe
  src="https://www.google.com/maps/embed?pb=..."
  loading="lazy"
  title="Mapa de localização"
>
</iframe>

<!-- eager: carrega imediatamente (padrão) -->
<iframe
  src="https://exemplo.com"
  loading="eager"
  title="Conteúdo prioritário"
>
</iframe>

loading="lazy" é especialmente recomendado para iframes abaixo da área visível inicial da página — como mapas no rodapé — pois evita carregar conteúdo que o usuário pode nunca ver.


referrerpolicy: controle de privacidade

<iframe
  src="https://exemplo.com"
  referrerpolicy="no-referrer-when-downgrade"
  title="Conteúdo externo"
>
</iframe>

Define quais informações de referência são enviadas ao servidor do iframe. Os valores mais usados:

Valor Comportamento
no-referrer Não envia informação de origem
no-referrer-when-downgrade Padrão — envia em HTTPS, omite em HTTP
strict-origin-when-cross-origin Mais restritivo — recomendado

Segurança: o atributo sandbox

O atributo sandbox é um dos mais importantes do <iframe> — ele restringe as capacidades do conteúdo incorporado, protegendo sua página de comportamentos maliciosos:

<!-- Sandbox máximo: bloqueia tudo -->
<iframe
  src="https://externo.com"
  sandbox
  title="Conteúdo externo em sandbox"
>
</iframe>

Quando sandbox está presente sem valor, o iframe fica com todas as restrições ativas:

  • Sem JavaScript
  • Sem formulários
  • Sem pop-ups
  • Sem navegação da página pai
  • Sem plugins
  • Sem acesso à câmera ou microfone
  • Sem armazenamento local

Para liberar permissões específicas, use os valores:

<iframe
  src="https://externo.com"
  sandbox="allow-scripts allow-forms"
  title="Formulário externo seguro"
>
</iframe>
Permissão O que libera
allow-scripts Execução de JavaScript
allow-forms Envio de formulários
allow-popups Abertura de pop-ups e novas abas
allow-same-origin Acesso ao mesmo domínio de origem
allow-top-navigation Navegação da página pai
allow-fullscreen Modo de tela cheia
allow-downloads Download de arquivos
<!-- Iframe de vídeo com permissões necessárias -->
<iframe
  src="https://www.youtube.com/embed/..."
  sandbox="allow-scripts allow-same-origin allow-fullscreen"
  allowfullscreen
  title="Vídeo do YouTube"
>
</iframe>

<!-- Iframe de mapa com carregamento lazy -->
<iframe
  src="https://www.google.com/maps/embed?pb=..."
  sandbox="allow-scripts allow-same-origin"
  loading="lazy"
  title="Mapa de localização da loja"
>
</iframe>

⚠️ Evite usar sandbox="allow-same-origin allow-scripts" juntos sem necessidade real — essa combinação pode permitir que o iframe escape do sandbox ao acessar o contexto de origem.


O risco do clickjacking

Clickjacking é um ataque onde um site malicioso incorpora sua página em um iframe invisível e posiciona botões falsos sobre ela — fazendo o usuário clicar em elementos da sua página sem saber:

Site malicioso:
┌─────────────────────────────────┐
│  [Botão falso: "Ganhe um prêmio!"]  │
│                                 │
│   [SEU SITE invisível em iframe]│
│    ← o usuário clica aqui sem   │
│       saber que é seu site      │
└─────────────────────────────────┘

Proteção contra clickjacking

A proteção é feita no servidor com o cabeçalho HTTP X-Frame-Options ou com a diretiva frame-ancestors do Content Security Policy:

# No servidor: impede que qualquer site incorpore sua página
X-Frame-Options: DENY

# Permite incorporação apenas no próprio domínio
X-Frame-Options: SAMEORIGIN

# CSP moderno — mais flexível
Content-Security-Policy: frame-ancestors 'self'

💡 Proteger sua própria página contra clickjacking é responsabilidade do servidor — não do HTML. Como desenvolvedor front-end, é importante conhecer o conceito para comunicar a necessidade à equipe de back-end ou DevOps.


Problemas de performance com iframes

Cada <iframe> carrega um documento HTML completo — com seus próprios recursos, scripts e estilos. Isso tem implicações de performance:

<!-- ❌ Múltiplos iframes carregados juntos -->
<iframe src="mapa.com" ...></iframe>
<iframe src="video.com" ...></iframe>
<iframe src="widget.com" ...></iframe>
<iframe src="chat.com" ...></iframe>

<!-- ✅ Com loading lazy para os não-críticos -->
<iframe src="mapa.com"   loading="lazy"  ...></iframe>
<iframe src="video.com"  loading="lazy"  ...></iframe>
<iframe src="widget.com" loading="lazy"  ...></iframe>
<iframe src="chat.com"   loading="eager" ...></iframe>

Boas práticas de performance com iframes:

  • Use loading="lazy" em iframes abaixo da área inicial
  • Evite múltiplos iframes na mesma página
  • Prefira APIs nativas quando disponíveis — como a API do Google Maps em JavaScript — em vez de iframes, para maior controle e performance
  • Considere carregar o iframe apenas após interação do usuário para conteúdos pesados

Exemplo completo: página de contato

<section id="contato">
  <h2>Fale Conosco</h2>

  <div>
    <!-- Formulário de contato via Google Forms -->
    <iframe
      src="https://docs.google.com/forms/d/e/.../viewform?embedded=true"
      width="640"
      height="600"
      title="Formulário de contato"
      loading="lazy"
      sandbox="allow-scripts allow-forms allow-same-origin"
    >
      <p>
        Não foi possível carregar o formulário.
        <a href="mailto:contato@empresa.com">
          Envie um e-mail diretamente.
        </a>
      </p>
    </iframe>
  </div>

  <div>
    <!-- Mapa da localização -->
    <iframe
      src="https://www.google.com/maps/embed?pb=..."
      width="600"
      height="450"
      style="border: 0"
      loading="lazy"
      referrerpolicy="no-referrer-when-downgrade"
      title="Mapa com a localização da nossa sede em São Paulo"
      sandbox="allow-scripts allow-same-origin"
    >
    </iframe>
  </div>

</section>

Resumindo

Atributo Tipo Propósito
src Valor URL do documento incorporado
title Valor Descrição acessível — sempre obrigatório
width / height Valor Dimensões do frame
allowfullscreen Booleano Permite tela cheia
loading Valor Controla o carregamento (lazy / eager)
sandbox Valor ou booleano Restringe permissões do conteúdo
referrerpolicy Valor Controla informações de origem enviadas

Regras de ouro:

  • Sempre inclua o atributo title com descrição útil
  • Use sandbox em iframes de fontes não confiáveis
  • Use loading="lazy" em iframes abaixo da dobra
  • Remova bordas com CSS — não com frameborder="0"
  • Forneça fallback acessível entre as tags
  • Evite múltiplos iframes pesados na mesma página