---
term: 'Notificações Push vs. Live Queries'
seoTitle: 'Notificações Push vs. Live Queries: Qual Canal de Tempo Real Usar'
headline: 'Notificações Push vs. Live Queries: qual delas você precisa?'
slug: push-vs-live-queries
category: api-realtime
shortDefinition: 'Uma notificação push é um alerta entregue pelo sistema operacional que alcança apps fechados; uma live query transmite mudanças com o app aberto.'
relatedTerms:
  - push-notifications-apns-fcm
  - real-time-live-queries
  - websockets-real-time-sync
  - sse-vs-websockets-vs-polling
contrastsWith:
  - real-time-live-queries
aboutTerms:
  - 'Notificações Push'
  - 'Subscriptions de Live Query'
faq:
  - question: 'Qual é a diferença entre notificações push e live queries?'
    answer: 'O caminho de entrega e o estado do app que cada uma atende. Uma notificação push viaja pelo gateway de push do sistema operacional e chega ao dispositivo mesmo com o app fechado — mas carrega um payload pequeno e opaco, com garantias de melhor esforço. Uma live query é uma subscription por WebSocket que o app em execução mantém aberta: objetos completos, em tempo real, com permissões verificadas — e morta no instante em que o app morre.'
  - question: 'Live queries funcionam com o app fechado?'
    answer: 'Não, e nenhuma esperteza do lado do cliente muda isso. Uma live query é estado dentro do seu processo em execução — um WebSocket que o app mantém aberto. Quando o sistema operacional suspende ou mata o app, o socket morre junto, e as plataformas mobile suspendem apps em segundo plano de forma agressiva para poupar bateria. Alcançar um app fechado é exatamente o trabalho que o SO reserva para o próprio gateway de push.'
  - question: 'Um app de chat deve usar push ou live query?'
    answer: 'Os dois, divididos pelo estado do app. A conversa aberta se inscreve em uma live query — as mensagens aparecem na hora, com dados completos, incluindo indicadores de digitação e confirmações de leitura. Com o app fechado, o push alerta o destinatário, carregando apenas o suficiente para renderizar o banner. O toque abre o app, que se reinscreve e reconsulta para se atualizar. Todo mensageiro popular funciona assim.'
  - question: 'A entrega de notificações push é garantida?'
    answer: 'Não — a entrega é de melhor esforço por design. Os gateways do SO agrupam, limitam e descartam mensagens sob pressão de bateria, usuários desativam a permissão por completo e dispositivos ficam sem energia. Pushes silenciosos de segundo plano são limitados ainda mais que os visíveis. Trate o push como um toque no ombro para acordar alguém, nunca como contrato de transporte de dados; o app precisa reconciliar o estado consultando depois de abrir.'
  - question: 'Qual o tamanho máximo do payload de uma notificação push?'
    answer: 'Kilobytes, não dados. Os gateways do SO limitam o payload em cerca de 4 KB, e esse payload é opaco ao modelo de permissões do seu backend — o que você colocar nele fica no pipeline de notificações, fora das suas ACLs. O padrão robusto envia apenas identificadores e strings de exibição, deixando o app aberto buscar os objetos reais pela API normal, com permissões verificadas.'
  - question: 'O que é uma notificação push silenciosa?'
    answer: 'Um push sem alerta visível que pede ao SO para acordar seu app brevemente em segundo plano — em geral para pré-carregar dados e deixar a próxima abertura instantânea. É o recurso mais racionado do sistema de push: o SO limita a quantidade de wakeups por app por dia e ignora o excedente, então o push silencioso funciona como camada de otimização, nunca como canal confiável de sincronização.'
  - question: 'Preciso de push e live queries ao mesmo tempo?'
    answer: 'Se os usuários se importam com eventos que acontecem enquanto o app está fechado — mensagens, pedidos, alertas —, sim, quase inevitavelmente. Os dois canais cobrem estados disjuntos do app: a live query é dona da experiência com o app aberto, o push é dono do reengajamento a partir do estado fechado. Backends que trazem os dois embutidos deixam uma única escrita no banco se espalhar por ambos, então precisar dos dois deixa de significar construir duas vezes.'
codeLanguages: [javascript, dart, swift, kotlin]
externalAuthorities:
  - name: 'RFC 8030 — Generic Event Delivery Using HTTP Push'
    url: 'https://datatracker.ietf.org/doc/html/rfc8030'
  - name: 'Push API — MDN Web Docs'
    url: 'https://developer.mozilla.org/en-US/docs/Web/API/Push_API'
  - name: 'Push technology (Wikipedia)'
    url: 'https://en.wikipedia.org/wiki/Push_technology'
  - name: 'Live Queries — Parse Server guide'
    url: 'https://docs.parseplatform.org/parse-server/guide/#live-queries'
cta:
  title: 'Um backend, os dois canais'
  text: 'O Back4app entrega notificações push e Live Queries sobre os mesmos dados: uma escrita no banco se espalha para os gateways de push do sistema operacional e para cada WebSocket inscrito. Configure o trigger afterSave uma vez e cubra todos os estados do app.'
  linkText: 'Comece grátis'
  linkUrl: 'https://www.back4app.com/signup'
author: 'Back4app Engineering'
publishedDate: '2026-08-25'
translationKey: push-notifications-vs-live-queries
---

**Uma notificação push é um alerta entregue pelo sistema operacional que alcança apps fechados; uma live query transmite mudanças com o app aberto.** Tratá-las como rivais é o erro clássico — elas cobrem *estados disjuntos do app*, e a verdadeira pergunta de design não é "qual das duas", e sim "onde está o usuário agora?". A maioria dos apps que parecem realmente em tempo real roda as duas e roteia por essa resposta.

## Principais pontos

| Pergunta | Resposta |
| --- | --- |
| Notificações push | Entrega pelo gateway do SO (APNs, FCM) — alcança apps fechados, payload opaco de ~4 KB, melhor esforço |
| Live queries | Subscription por WebSocket — objetos completos com permissões verificadas, tempo real, app precisa estar aberto |
| A rivalidade | Falsa — atendem estados disjuntos do app e se compõem, não competem |
| A regra de roteamento | App aberto → live query · app fechado → push · toque no push → abre, reinscreve, atualiza |
| O modo de falha | Usar push como canal de dados, ou esperar que sockets sobrevivam ao processo |

## Os dois canais, em código

O padrão para o qual quase todo app de mensagens, pedidos e alertas converge:

**JavaScript:**

```javascript
// JavaScript — Back4app JS SDK: one channel per app state
// While the app is OPEN — the live query delivers the data itself
const messages = new Parse.Query('Message');
messages.equalTo('conversation', conversationId);
const sub = await messages.subscribe();
sub.on('create', (m) => appendBubble(m));   // full object, real time

// While it is CLOSED — push owns delivery: register this device
const installation = await Parse.Installation.currentInstallation();
installation.set('channels', [`user-${currentUser.id}`]);
await installation.save();
// A Cloud Code afterSave trigger sends the push to this channel —
// the OS shows the alert; the tap opens the app, which re-subscribes.
```

**Flutter:**

```dart
// Flutter / Dart — Back4app Flutter SDK: one channel per app state
// While the app is OPEN — the live query delivers the data itself
final liveQuery = LiveQuery();
final messages = QueryBuilder<ParseObject>(ParseObject('Message'))
  ..whereEqualTo('conversation', conversationId);

final sub = await liveQuery.client.subscribe(messages);
sub.on(LiveQueryEvent.create, (m) => appendBubble(m)); // full object

// While it is CLOSED — push owns delivery: register this device
final installation = await ParseInstallation.currentInstallation();
installation.set('channels', ['user-$userId']);
await installation.save();
// A Cloud Code afterSave trigger sends the push to this channel —
// the OS shows the alert; the tap opens the app, which re-subscribes.
```

**Swift:**

```swift
// iOS / Swift — Back4app Swift SDK: one channel per app state
// While the app is OPEN — the live query delivers the data itself
let messages = Message.query("conversation" == conversationId)
let subscription = messages.subscribeCallback
subscription?.handleEvent { _, event in
  if case .created(let m) = event { appendBubble(m) }  // full object
}

// While it is CLOSED — push owns delivery: register this device
var installation = Installation.current
installation?.channels = ["user-\(userId)"]
installation?.save { _ in }
// A Cloud Code afterSave trigger sends the push to this channel —
// the OS shows the alert; the tap opens the app, which re-subscribes.
```

**Kotlin:**

```kotlin
// Android / Kotlin — Back4app Android SDK: one channel per app state
// While the app is OPEN — the live query delivers the data itself
val client = ParseLiveQueryClient.Factory.getClient()
val messages = ParseQuery.getQuery<ParseObject>("Message")
messages.whereEqualTo("conversation", conversationId)

val sub = client.subscribe(messages)
sub.handleEvent(SubscriptionHandling.Event.CREATE) { _, m ->
    appendBubble(m)                                  // full object
}

// While it is CLOSED — push owns delivery: register this device
val installation = ParseInstallation.getCurrentInstallation()
installation.put("channels", listOf("user-$userId"))
installation.saveInBackground()
// A Cloud Code afterSave trigger sends the push to this channel.
```

Repare no que cada metade resolve: a subscription entrega *dados* — objetos inteiros, eventos tipados, em tempo real. O registro da instalação garante *atenção* — o direito de interromper o usuário depois, por um pipeline que seu app não controla.

## Duas entregas, dois donos

Os caminhos dificilmente seriam mais diferentes, e cada propriedade da tabela comparativa decorre de quem é dono do último quilômetro.

Uma **notificação push** sai do seu backend como uma requisição a um gateway operado pelo sistema operacional — os gateways de push do iOS e do Android (APNs, FCM), ou um serviço de push do navegador falando [RFC 8030](https://datatracker.ietf.org/doc/html/rfc8030) na web. O gateway é dono da entrega: guarda mensagens para dispositivos offline, agrupa e limita sob pressão de bateria e acorda seu app ou renderiza o banner. Esse poder emprestado é o ponto inteiro — *só* o SO consegue alcançar um processo que não está rodando — e também a restrição inteira: payloads limitados a cerca de 4 KB, entrega de melhor esforço, wakeups silenciosos racionados por dia e um payload fora do modelo de permissões do seu backend.

Uma **live query** nunca sai do seu perímetro de confiança: o app mantém um [WebSocket](/glossary/pt/websockets/) com o servidor de subscriptions do backend, que compara cada escrita no banco com a consulta inscrita e faz push de eventos tipados — create, update, enter, leave, delete — com [ACLs aplicadas por assinante](/glossary/pt/live-queries-tempo-real/). Objetos completos, latência de tempo real, sem teto de payload digno de menção. A dependência é brutal em troca: a subscription é estado dentro do seu processo e, quando o SO suspende o app — o que as plataformas mobile fazem de forma agressiva —, o socket, e o canal, acabam.

```mermaid
flowchart TB
  accTitle: Roteando entrega em tempo real pelo estado do app
  accDescr: Uma escrita no banco dispara a lógica do backend. Se o app do destinatário estiver aberto, uma live query envia o objeto completo por WebSocket. Se o app estiver fechado, o backend envia um payload pequeno pelo gateway de push do sistema operacional, que exibe uma notificação; ao tocá-la, o app abre, se reinscreve e se atualiza consultando.
  W["Escrita no banco<br/>(mensagem, pedido, alerta)"] --> T["Trigger no backend<br/>(afterSave)"]
  T -->|"app aberto"| LQ["Push via live query<br/>objeto completo · WebSocket"]
  T -->|"app fechado"| GW["Gateway de push do SO<br/>(APNs, FCM)"]
  GW --> N["Banner de notificação<br/>payload de ~4 KB"]
  N -->|"toque"| O["App abre →<br/>reinscrição + consulta de atualização"]
  LQ --> UI["Tela atualiza no lugar"]
  O --> UI
```

## Notificações push vs. live queries

| | Notificações push | Subscriptions de live query |
| --- | --- | --- |
| Alcança um app fechado | **Sim — o poder que a define** | Não — a subscription morre com o processo |
| Payload | ~4 KB, opaco às suas ACLs | Objetos completos, com permissões verificadas por assinante |
| Garantia de entrega | Melhor esforço; agrupável, limitável, descartável | Confiável enquanto conectado; precisa de atualização após lacunas |
| Latência | Ordem de segundos, depende do gateway | Tempo real (~RTT) |
| Dono do transporte | O SO e seu gateway | A frota de WebSockets do seu backend |
| Consentimento do usuário | Prompt de permissão; o usuário pode revogar | Nenhum — são os dados do próprio app |
| Custo do mau uso | Fadiga de notificação, desinstalações | Carga de bateria e de sockets se houver inscrições demais |
| Feito para | Atenção e reengajamento | Dados e estado dentro do app |

As linhas se compõem com clareza porque os dois canais respondem a perguntas diferentes: o push responde *"como eu alcanço o usuário?"*, as live queries respondem *"como a tela continua verdadeira?"* — e é por isso que a [comparação no nível de transporte](/glossary/pt/sse-vs-websockets-vs-polling/) entre SSE, WebSockets e polling vive inteiramente dentro da segunda pergunta.

## A costura: onde os apps realmente quebram

Os bugs moram na emenda entre os canais. Um usuário toca em um push sobre uma mensagem que *também* foi entregue por live query antes de o app ser suspenso — deduplique por ID do objeto, não por canal. Chega um push sobre dados que o usuário já não pode acessar — busque pela API normal ao abrir e deixe as ACLs responderem, nunca confie no payload. O app ficou fechado três dias — o app reaberto não consegue recuperar a lacuna a partir do push (notificações não são um diário), então a costura é sempre *reinscrever e depois reexecutar a consulta base* para reconstruir a verdade, mantendo o [registro do token de push](/glossary/pt/notificacoes-push/) atualizado em segundo plano. Projete a costura uma vez e os dois canais viram tédio — que é o objetivo.

## Casos de uso comuns

- **Chat e mensageria** — a live query renderiza a conversa aberta; o push carrega o "nova mensagem" pelo estado fechado. O app canônico de dois canais.
- **Rastreamento de pedidos e entregas** — a tela de acompanhamento aberta se inscreve; mudanças para "entregue" com o app fechado chegam como push.
- **Alertas operacionais** — consoles de plantão se inscrevem para o painel de parede; o caminho do pager é push, porque ninguém deixa o app aberto às 3 da manhã.
- **Leilões e lançamentos** — movimento de preço ao vivo dentro do app; ser superado enquanto está fora é push, com deep link de volta para a tela ao vivo.
- **Engajamento social** — curtidas e respostas chegam como push de reengajamento; o feed aberto fica ao vivo via subscription.

## Qual canal você deveria usar? Matriz de decisão

| Sua situação | Use |
| --- | --- |
| A tela está aberta e precisa se manter atual | Live query |
| O evento acontece com o app fechado e o usuário precisa saber | Notificação push |
| O payload é sensível ou restrito por permissão | Live query — ou push só com identificadores, buscando ao abrir |
| Você precisa de entrega garantida e ordenada de dados | Nenhum dos dois sozinho — atualização por consulta ao abrir, canais como aceleradores |
| Atualizar um badge ou contador dentro do app em tempo real | Live query |
| Reengajar usuários que não abrem o app há dias | Push — é o único canal capaz disso |
| Quiosque ou painel de parede que nunca dorme | Só live query; push não acrescenta nada |

## Limitações e trade-offs

- **Push não é canal de dados.** Teto de payload, roteamento opaco fora das suas ACLs e agrupamento o tornam estruturalmente errado para carregar estado — envie ponteiros, busque a verdade ao abrir.
- **Entrega de push é probabilidade, não promessa.** Otimizadores de bateria, permissões revogadas e throttling de gateway descartam mensagens em silêncio; tudo que não pode ser perdido precisa de um caminho de reconciliação por consulta.
- **Live queries param na fronteira do processo.** Nenhum socket sobrevive à suspensão; tratar uma subscription como canal sempre ligado é a premissa falsa por trás da maioria dos bugs de "perdemos eventos".
- **Os dois canais cobram do cliente.** Subscriptions amplas demais queimam bateria e correspondência no servidor; push afoito queima boa vontade — a desinstalação é o rate limiting do usuário.
- **A costura é responsabilidade sua.** Deduplicação, consultas de atualização e renovação de token são lógica de aplicação; nenhum dos canais entrega isso de graça.

## Push e live queries no Back4app

O Back4app é uma plataforma open-source de Backend as a Service (BaaS) que combina banco de dados gerenciado, APIs REST e GraphQL geradas automaticamente, autenticação, armazenamento de arquivos e funções serverless com Cloud Code. Os dois canais vêm embutidos e compartilham um único caminho de escrita: um trigger `afterSave` no Cloud Code, na mesma escrita de banco, pode enviar o push — pelas integrações da plataforma com os gateways, com segmentação por dispositivo e por canal — enquanto o [Live Query](/glossary/pt/live-queries-tempo-real/) espalha o objeto completo para cada cliente inscrito e autorizado, automaticamente. O diagrama de roteamento acima colapsa em um trigger e uma chamada de subscribe, e a lógica da costura — consultas de atualização, registro de token pela classe Installation — roda pelos mesmos SDKs mostrados nas abas de código.
