Saltar para o conteúdo
ADITUS-Queue

A sala de espera virtual empresarial

ADITUS-Queue é uma sala de espera virtual autónoma que protege qualquer site, API ou serviço online contra picos de tráfego. Integra-se perfeitamente na plataforma de tickets ADITUS — e é implementado de forma igualmente independente na frente de qualquer aplicação web. Os visitantes são mantidos numa sala de espera alojada e admitidos estritamente por ordem de chegada, a uma taxa configurada por minuto. A integração varia desde um único link de gateway ou tag de script sem infraestrutura por parte do operador, passando pela aplicação no proxy reverso ou CDN, até à API REST simples.

Novo: taxa de admissão autorregulada. A fila lê um exame de saúde da sua loja e ajusta a taxa por conta própria – mais visitantes quando a loja tem espaço, alívio imediato quando está sob pressão.

Apesar da profundidade: a configuração demora minutos, não dias. Um link publicado ou uma etiqueta de script — sem infraestrutura, sem implementação, sem alterações de código da sua parte.

Início rápido: em direto em menos de 2 minutos

Proteja a sua aplicação em menos de 2 minutos: copie a tag do script para o seu head ou publique o link da gateway. Sem alterações na infraestrutura do seu servidor. Só quando pretende o máximo controlo é que ativa os recursos avançados opcionais – tudo o resto nesta página é exatamente isso: profundidade opcional para mais tarde.

503
Clássicorígido e sobrecarregado – todos os visitantes chegam à loja ao mesmo tempo
Sala de esperaA verificação do estado regula a taxa
ADITUS-Queuedinâmico e protegido — admissão exatamente ao ritmo que a loja pode suportar
  1. 1

    Crie uma sala de espera

    Na consola de administração ADITUS: nome, morada da loja, taxa de admissão por minuto. Os padrões sensatos cobrem todo o resto.

  2. 2

    Copiar uma linha

    Publique o link do gateway pronto em vez do link da loja – ou cole a etiqueta de script preparada na página da loja, exatamente como um snippet analítico.

  3. 3

    Concluído — a fila está montada

    Abaixo da taxa de admissão, os visitantes nunca veem a sala de espera. Só quando ocorre um pico é que entra a fila – alojada, dimensionada e operada por nós.

Cresce consigo: três níveis de proteção

O poder da fila é um caminho de atualização, não um requisito. O nível 1 cobre sozinho a grande maioria dos casos de utilização.

Nível 1: Proteção baseLink de gateway ou tag de script. Pronto imediatamente, sem infraestrutura — suficiente para a maioria dos casos padrão.Pronto para usar agora
Nível 2: Proteção avançadaA taxa de admissão auto-regulada através do exame de saúde da loja – a fila opera o mostrador para si.Opcional
Nível 3: Proteção à prova de balaProteção de edge através de verificação JWT offline em Nginx, Caddy ou CDN — para equipas DevOps.Opcional — para equipas DevOps

Integração: duas opções

Qual a opção que se enquadra depende de uma questão: o link da loja publicada pode ser alterado? Se sim, o link da gateway é a melhor escolha – o tráfego nunca chega à loja antes da admissão. Se o URL da loja publicada for fixo, a tag script protege a loja sem qualquer alteração na sua publicação. Para além destes dois, a verificação pode ser aplicada no proxy reverso ou CDN (abaixo), conduzida diretamente pela API REST ou verificada em qualquer linguagem de back-end com uma biblioteca JWT – Node.js, PHP, Java,.NET, Python, Go.

Gateway-LinkScript-TagProxy reverso/CDNREST-APIVerificação no back-end (JWT, qualquer linguagem)

Opção A: a ligação do gateway (recomendada)

Cada sala de espera fornece o seu próprio URL de entrada. É publicado em todos os locais onde o link da loja apareceria – newsletter, site, redes sociais. A fila recebe o pedido e decide do lado do servidor num único passo: abaixo da taxa de admissão o visitante é encaminhado diretamente para o endereço da loja configurada e não se apercebe da fila; ultrapassada a tarifa, o visitante chega à sala de espera e é automaticamente encaminhado quando chega a sua vez. A loja em si não recebe tráfego antes da admissão – os pedidos são absorvidos antes de chegarem à infraestrutura da loja.

newsletter.html
<!-- Der veröffentlichte Shop-Link zeigt auf die Queue statt auf den Shop: -->
<a href="https://developers.aditus.com/queue/<slug>/enter">Tickets kaufen</a>

Para esta opção, o endereço de destino da loja (Ziel-URL) deve ser configurado para a fila — é o endereço para onde os visitantes admitidos são encaminhados. Os visitantes admitidos chegam à loja com um token de admissão assinado no URL – um JWT HS256 padrão que a loja pode opcionalmente verificar offline no seu próprio back-end utilizando o segredo partilhado.A estrutura, os claims e um exemplo de backend estão documentados abaixo. Nota: o gateway protege o ponto de entrada publicado; os visitantes que conhecem diretamente o URL da loja podem ainda ignorá-lo. Se isto for importante, combine o link do gateway com a etiqueta do script ou verifique o token no backend da loja.

Opção B: a etiqueta de script

Quando o link da loja publicado não pode ser alterado, a integração é uma única etiqueta de script. É entregue juntamente com as páginas da loja – da mesma forma que um snippet analítico é entregue – e deve estar presente em todas as páginas que a sala de espera deve proteger. Recomenda-se a colocação no <head> com o atributo defer; a posição exata não é crítica.

shop.html
<!-- Auf jeder zu schützenden Shop-Seite im <head>: -->
<script src="https://developers.aditus.com/queue/<slug>/embed.js" defer></script>

A etiqueta exata para uma sala de espera específica – com o slug correto já introduzido – está disponível na consola de administração do ADITUS por fila. O script realiza três verificações em cada carregamento de página:

  1. 1

    Visitante possui um passe válido

    Nada acontece. O passe é guardado durante a sessão do navegador e o visitante utiliza a loja sem interrupções.

  2. 2

    Visitante regressa da sala de espera

    O token de admissão no URL é verificado no servidor (subscrição, atribuição de fila, expiração). Se for válido, será armazenado um passe de sessão e o token será removido da barra de endereço. Os tokens inválidos ou expirados enviam o visitante de volta para a sala de espera.

  3. 3

    Visitante não tem passe

    Se não estiver ninguém à espera, o visitante é admitido silenciosamente em segundo plano e permanece na página – a sala de espera nunca é mostrada. Só quando a taxa de admissão configurada for ultrapassada e houver formação de fila é que o visitante é redirecionado para a sala de espera; a página atual é passada como um URL de retorno validado, pelo que, após a admissão, o visitante acede exatamente à página originalmente solicitada.

Falha ao abrir

Se o serviço de fila estiver inacessível ou a fila não existir, o script não fará nada e a loja permanecerá totalmente utilizável. Uma interrupção na sala de espera nunca bloqueia a loja.

Sem redirecionamentos abertos

Os URLs de retorno são validados no lado do servidor nos domínios configurados para a fila. A sala de espera apenas encaminha para páginas da loja registada.

Endurecimento: impondo admissão no proxy de borda

Atualização opcional — para equipas DevOpsNão é necessário para a configuração acima

Ambas as opções acima referidas protegem o ponto de entrada publicado. Se a loja estiver inacessível sem admissão, mesmo para os visitantes que conhecem o seu URL diretamente, o cheque passa para a frente da loja – para o proxy reverso ou CDN que termina o seu tráfego. A lógica é sempre a mesma três passos: obter o token do parâmetro URL aditus_queue_token quando o visitante regressa da sala de espera e armazená-lo como um cookie; em cada pedido, verifique o token do cookie como um JWT HS256 padrão com o segredo partilhado (emissor aditus-queue, audiência do slug da fila, expiração); sem um token válido, redirecione para a sala de espera em https://developers.aditus.com/queue/ <slug>. A verificação está offline — o proxy nunca chama a fila e não acrescenta latência. Os esboços seguintes mostram o padrão para quatro ambientes comuns; adapte-os à sua configuração.

NginxMódulo njs — verificação diretamente no proxy, sem serviço extra.Trecho incluído
CaddyPlugin jwtauth — configuração pura, sem uma única linha de código.Trecho incluído
CloudflareTrabalhador no limite — aplicado em todo o mundo antes de o tráfego chegar à loja.Trecho incluído
AWS CloudFrontLambda@Edge — a verificação é executada na rede global da AWS.Trecho incluído
Padrão HS256 JWTVerificação offline – sem retorno de chamadaZero latência adicionadaFunciona com qualquer proxy reverso
Nginx (njs)
# Skizze: Nginx mit njs (js_import) — prüft den Zugriffs-Token als HS256-JWT
# direkt am Proxy, ohne Rückruf an die Queue. An die eigene Umgebung anpassen.

# nginx.conf:
#   env ADITUS_QUEUE_SECRET;
#   js_import queue from /etc/nginx/queue.js;
#   server {
#     location /       { js_content queue.gate; }
#     location @shop   { proxy_pass http://shop_backend; }
#   }

// /etc/nginx/queue.js:
const crypto = require('crypto');
const SLUG = '<slug>';
const SECRET = process.env.ADITUS_QUEUE_SECRET; // Shared Secret der Queue

function claims(token) {
  const p = token.split('.');
  if (p.length !== 3) return null;
  const sig = crypto.createHmac('sha256', SECRET)
    .update(p[0] + '.' + p[1]).digest('base64url');
  if (sig !== p[2]) return null;
  const c = JSON.parse(Buffer.from(p[1], 'base64url'));
  const ok = c.iss === 'aditus-queue' && c.aud === SLUG && c.exp > Date.now() / 1000;
  return ok ? c : null;
}

function gate(r) {
  const fromUrl = r.args.aditus_queue_token;
  const m = (r.headersIn.Cookie || '').match(/(?:^|;\s*)aditus_queue=([^;]+)/);
  const token = fromUrl || (m && m[1]);
  if (!token || !claims(token)) {
    // Kein gültiger Token -> zurück in den Warteraum
    r.return(302, 'https://developers.aditus.com/queue/' + SLUG);
    return;
  }
  if (fromUrl) {
    // Token aus der Rücksprung-URL in ein Sitzungs-Cookie übernehmen
    r.headersOut['Set-Cookie'] =
      'aditus_queue=' + fromUrl + '; Path=/; Secure; HttpOnly; Max-Age=600';
  }
  r.internalRedirect('@shop');
}

export default { gate };
Caddyfile
# Skizze: Caddy mit dem jwtauth-Plugin (github.com/ggicci/caddy-jwt).
# Token kommt beim Rücksprung als ?aditus_queue_token=… oder danach als Cookie;
# jwtauth prüft beide Quellen. An die eigene Umgebung anpassen.
shop.example.com {
  route {
    jwtauth {
      sign_key {env.ADITUS_QUEUE_SECRET}
      sign_alg HS256
      from_query aditus_queue_token
      from_cookies aditus_queue
      issuer_whitelist aditus-queue
      audience_whitelist <slug>
      user_claims qnr
    }
    # Token aus der URL einmalig in ein Cookie übernehmen
    @rueckkehr query aditus_queue_token=*
    header @rueckkehr Set-Cookie "aditus_queue={http.request.uri.query.aditus_queue_token}; Path=/; Secure; HttpOnly; Max-Age=600"
    reverse_proxy shop_backend:8080
  }
  # Ohne gültigen Token: zurück in den Warteraum
  handle_errors {
    @unauth expression {http.error.status_code} == 401
    redir @unauth https://developers.aditus.com/queue/<slug> 302
  }
}
Cloudflare Worker
// Skizze: Cloudflare Worker vor dem Shop — prüft den HS256-JWT offline per
// WebCrypto. Secret als Worker-Secret ADITUS_QUEUE_SECRET hinterlegen.
const SLUG = "<slug>";
const ROOM = "https://developers.aditus.com/queue/" + SLUG;

export default {
  async fetch(req, env) {
    const url = new URL(req.url);
    const fromUrl = url.searchParams.get("aditus_queue_token");
    const m = (req.headers.get("Cookie") || "").match(/(?:^|;\s*)aditus_queue=([^;]+)/);
    const token = fromUrl || (m && m[1]);
    if (!token || !(await valid(token, env.ADITUS_QUEUE_SECRET))) {
      return Response.redirect(ROOM, 302); // zurück in den Warteraum
    }
    if (fromUrl) {
      // Token in ein Cookie übernehmen und die URL bereinigen
      url.searchParams.delete("aditus_queue_token");
      return new Response(null, {
        status: 302,
        headers: {
          Location: url.toString(),
          "Set-Cookie": "aditus_queue=" + token +
            "; Path=/; Secure; HttpOnly; Max-Age=600",
        },
      });
    }
    return fetch(req); // gültiger Pass -> durch zum Shop
  },
};

async function valid(token, secret) {
  const p = token.split(".");
  if (p.length !== 3) return false;
  const key = await crypto.subtle.importKey(
    "raw", new TextEncoder().encode(secret),
    { name: "HMAC", hash: "SHA-256" }, false, ["verify"],
  );
  const ok = await crypto.subtle.verify(
    "HMAC", key, b64url(p[2]),
    new TextEncoder().encode(p[0] + "." + p[1]),
  );
  if (!ok) return false;
  const c = JSON.parse(new TextDecoder().decode(b64url(p[1])));
  return c.iss === "aditus-queue" && c.aud === SLUG && c.exp > Date.now() / 1000;
}

function b64url(v) {
  return Uint8Array.from(
    atob(v.replace(/-/g, "+").replace(/_/g, "/")),
    (ch) => ch.charCodeAt(0),
  );
}
AWS CloudFront (Lambda@Edge)
// Skizze: AWS CloudFront mit Lambda@Edge (Viewer-Request, Node.js).
// Gleiches Muster: Token aus ?aditus_queue_token oder Cookie, HS256 offline
// prüfen, ohne gültigen Token in den Warteraum umleiten.
// Hinweis: Lambda@Edge hat keine Umgebungsvariablen — das Secret z. B. beim
// Deployment einbetten oder aus SSM/Secrets Manager cachen.
'use strict';
const crypto = require('crypto');
const SLUG = '<slug>';
const ROOM = 'https://developers.aditus.com/queue/' + SLUG;
const SECRET = '<ADITUS_QUEUE_SECRET>';

exports.handler = async (event) => {
  const req = event.Records[0].cf.request;
  const qs = new URLSearchParams(req.querystring || '');
  const fromUrl = qs.get('aditus_queue_token');
  const cookie = (req.headers.cookie || []).map((h) => h.value).join('; ');
  const m = cookie.match(/(?:^|;\s*)aditus_queue=([^;]+)/);
  const token = fromUrl || (m && m[1]);

  if (!token || !valid(token)) {
    return redirect(ROOM); // zurück in den Warteraum
  }
  if (fromUrl) {
    // Token in ein Cookie übernehmen und die URL bereinigen
    qs.delete('aditus_queue_token');
    const clean = req.uri + (qs.toString() ? '?' + qs.toString() : '');
    return redirect(clean, {
      'set-cookie': [{ key: 'Set-Cookie', value:
        'aditus_queue=' + token + '; Path=/; Secure; HttpOnly; Max-Age=600' }],
    });
  }
  return req; // gültiger Pass -> durch zum Shop (Origin)
};

function valid(token) {
  const p = token.split('.');
  if (p.length !== 3) return false;
  const sig = crypto.createHmac('sha256', SECRET)
    .update(p[0] + '.' + p[1]).digest();
  const got = Buffer.from(p[2], 'base64url');
  if (got.length !== sig.length || !crypto.timingSafeEqual(sig, got)) {
    return false;
  }
  const c = JSON.parse(Buffer.from(p[1], 'base64url'));
  return c.iss === 'aditus-queue' && c.aud === SLUG && c.exp > Date.now() / 1000;
}

function redirect(location, extraHeaders) {
  return {
    status: '302',
    headers: Object.assign(
      { location: [{ key: 'Location', value: location }] },
      extraHeaders || {},
    ),
  };
}

Nota: com a aplicação de limites em vigor, cada visitante precisa de um token – incluindo aqueles que, de outra forma, passariam silenciosamente abaixo da taxa de admissão. Publique o link do gateway (opção A) ao lado ou deixe o proxy redirecionar os visitantes sem token para a sala de espera, que emite um token imediatamente enquanto ninguém está à espera.

Configuração: o que a ADITUS precisa de si

A sala de espera é configurada pela ADITUS. Para a configuração, forneça o seguinte:

Imagem (opcional)

Uma imagem de cabeçalho para a página da sala de espera, por exemplo. o visual principal do evento. Formato paisagem, pelo menos 920 × 380 pixels (exibido até 460 px de largura, cortado até uma altura máxima de 190 px), JPG ou PNG, entregue como um URL HTTPS publicamente acessível ou como um ficheiro para ADITUS.

Texto (opcional)

Uma mensagem curta apresentada abaixo do título da sala de espera, p. uma nota sobre a venda ou espera prevista. Texto simples, as quebras de linha são preservadas; comprimento recomendado até cerca de 300 caracteres. O texto é apresentado exatamente como fornecido – se atender visitantes internacionais, forneça-o no idioma adequado ou bilingue.

Cor de destaque (opcional)

Uma cor de marca em formato hexadecimal (por exemplo, #0a63c9). Colore a barra de progresso e o indicador em direto da página da sala de espera; sem indicação, é utilizada a cor predefinida da ADITUS. Juntamente com o grafismo e o texto, a sala de espera adota a identidade visual do organizador.

Domínios da loja

Os domínios das páginas nas quais o script será executado (por exemplo, shop.example.com). Definem quais os URLs de retorno que a sala de espera aceita.

Nome de visualização, URL de destino, taxa

O título da sala de espera (por exemplo, o nome do evento), o URL de destino para os visitantes admitidos (necessário para o link do gateway – é o endereço da loja para onde o gateway encaminha) e a taxa de admissão em visitantes por minuto. A taxa é o limite de rendimento: desde que cheguem menos visitantes do que a taxa permite, todos passam sem sala de espera. Pode ser ajustado a qualquer momento enquanto a fila estiver a ser executada.

Atualizado automaticamente (a cada poucos segundos)

1

Número de espera — atribuído uma vez quando a página é aberta e mantido durante toda a espera, mesmo durante uma recarga.

2

Posição e número admitido — quantos números estão à frente e até que número está aberta a admissão no momento. O número de admitidos cresce continuamente com a taxa de admissão.

3

Barra de progresso — visualiza o quanto avançou a admissão em direção ao próprio número do visitante.

4

Espera estimada — calculado a partir da posição atual e da taxa de admissão; encurta à medida que a admissão avança. Uma vez admitido o número do visitante, a página encaminha para a loja automaticamente – sem necessidade de interação.

Configurado uma vez (estático)

A

Imagem do cabeçalho — opcional, por exemplo, a imagem principal do evento.

B

Nome de exibição — o título da sala de espera, por exemplo, o nome do evento.

C

Mensagem — texto opcional abaixo do título, apresentado exatamente como fornecido.

Esquema da página da sala de espera: os marcadores corais são valores ativos que são atualizados automaticamente, os marcadores cinzentos são configurados uma vez.
A sala de espera alojada com imagem de cabeçalho e mensagem: número de espera, posição, número admitido e espera estimada é automaticamente atualizada.

A própria página da sala de espera é bilingue (alemão/inglês). O idioma é selecionado automaticamente a partir das definições do navegador do visitante; não é necessária qualquer configuração.

Operações: o painel em direto

Durante a venda, a ADITUS monitoriza cada sala de espera num painel em direto: os medidores mostram a contagem de espera atual, a entrada de novos visitantes em relação à taxa de admissão, a própria taxa de admissão (com o seu teto configurado quando a taxa autorregulada está ativada) e a espera estimada para os recém-chegados. Um gráfico de duas séries acompanha a contagem de espera em relação ao fluxo de entrada ao longo do tempo, e as instâncias de fila que servem o tráfego reportam a sua própria carga – CPU, memória e taxa de pedidos. A taxa de admissão pode ser ajustada a qualquer momento enquanto a fila estiver em curso – por exemplo, quando a loja mostrar espaço livre.

O painel em direto na consola de administração ADITUS, atualizado a cada 3 segundos durante a venda.

Operações: testes de carga e estado do serviço

A fila não é apenas considerada à prova de carga – é testada regularmente. Na consola de administração do ADITUS, os testes de carga disparam pedidos reais numa sala de espera de teste dedicada no sistema de produção (as salas de espera produtivas nunca são tocadas). Um teste simula o percurso do visitante – entrada e pesquisa de estado – a uma taxa e duração configuráveis. Os medidores em direto mostram a taxa de pedido alcançada, a latência mediana e p95 e a taxa de erro; um gráfico por segundo acompanha o rendimento em relação à latência e cada execução é mantida num histórico para que os resultados permaneçam comparáveis ​​ao longo do tempo. Os testes também são executados numa programação recorrente, e uma execução programada com um desempenho claramente inferior ao das execuções comparáveis ​​anteriores é sinalizada automaticamente.

Um teste de carga na fila de produção: KPIs em tempo real, gráfico a segundo, as instâncias de fila ativas durante o teste e o histórico de execuções anteriores.

Para monitorização externa, o serviço de fila de espera expõe uma verificação de saúde pública em /queue/healthz. Responde sem autenticação e sem tocar na base de dados — um simples sinal de disponibilidade para monitorização do tempo de atividade. Durante um teste de carga, a consola de administração mostra adicionalmente as instâncias de fila auto-reportadas com CPU, memória, atraso do ciclo de eventos e taxa de pedidos; sob carga, a plataforma inicia instâncias adicionais automaticamente e o teste torna isso visível.

Operações: a taxa de admissão auto-regulada

Atualização opcional – uma taxa fixa funciona bem

A taxa de admissão é o único botão que decide tudo durante uma promoção - e até agora alguém tinha de estar atento. Não mais: a fila pode regular a própria tarifa, de acordo com as condições reais da loja protegida. O resultado é uma sala de espera que vende tão rapidamente quanto a loja consegue lidar em segurança – a qualquer momento, sem que ninguém toque no botão.

Taxa de transferência total, risco zero

Embora a loja esteja saudável, a taxa sobe em pequenos passos e o espaço não utilizado transforma-se em vendas. No momento em que a oficina mostra tensão, a taxa cai drasticamente – deliberadamente assimétrica: o alívio é instantâneo, a carga regressa com cuidado.

À prova de falhas por design

Uma verificação de integridade inacessível nunca abre mais as portas: a taxa congela primeiro e depois cai para o mínimo configurado. A loja está protegida precisamente quando ninguém está a ver.

As suas regras, totalmente transparentes

Define o que significa integridade – tempo de resposta, carga da CPU, qualquer métrica que a sua loja reporte. Cada ajuste automático é registado e visível no painel em direto, com a regra que o acionou.

Em vez de ajustar manualmente a taxa de admissão, uma sala de espera pode regulá-la automaticamente a partir de um exame de saúde da loja protegida. O ADITUS pesquisa um URL de integridade da loja num intervalo configurável e avalia o tempo de resposta e, opcionalmente, os campos numéricos da resposta JSON em relação às regras definidas pelo operador (por exemplo: tempo de resposta abaixo de 500 ms, carga de CPU abaixo de 0,8). Embora a loja esteja saudável, a taxa aumenta lentamente em pequenos passos; assim que uma regra é violada, é rapidamente reduzida numa percentagem – deliberadamente assimétrica, de modo a que a oficina seja aliviada imediatamente, mas a carga regresse com cuidado. A taxa está sempre dentro de um mínimo e máximo configurados.

Se o endpoint de integridade não responder, o sistema falhará de forma segura: a taxa é congelada primeiro e, após várias falhas consecutivas, cai para o mínimo configurado — uma verificação de integridade inacessível nunca abre mais as portas. Cada ajuste automático é registado e visível no painel em direto e, antes que a automatização possa ser ativada, o endpoint tem de passar por um teste único na consola de administração.

O endpoint de integridade do lado da loja permanece trivial: um URL HTTPS, acessível sem autenticação, respondendo 2xx. Um corpo JSON é opcional – quaisquer campos numéricos (os objetos aninhados são nivelados em caminhos de pontos) tornam-se métricas que as regras podem referenciar:

Exemplo de resposta da verificação do estado da loja
{
  "status": "ok",
  "responseBudgetMs": 500,
  "metrics": {
    "cpuLoad": 0.42,
    "dbPoolWaiting": 0,
    "openCheckouts": 118
  }
}

// Nutzbare Messwerte (Punktpfade):
//   responseBudgetMs, metrics.cpuLoad, metrics.dbPoolWaiting, metrics.openCheckouts
// Dazu immer verfügbar: die gemessene Antwortzeit (ms).

Operações: proteção contra bots com comprovativo de trabalho

Para vendas com elevada procura, uma sala de espera pode exigir também um comprovativo de trabalho antes de atribuir um número de espera. O navegador resolve então, em segundo plano, um pequeno desafio criptográfico, invisível para o visitante e concluído em muito menos de um segundo em dispositivos comuns, com a dificuldade por defeito. Para uma rede de bots, a situação é diferente: cada entrada exige o mesmo trabalho computacional, pelo que obter milhares de números passa a ter um custo proporcional. A proteção está desativada por defeito e é ativada por sala de espera na consola de administração ADITUS; a dificuldade pode ser ajustada entre 8 e 24 bits (15 por defeito — cada bit adicional duplica o trabalho). A página alojada da sala de espera resolve o desafio automaticamente; a integração da loja não sofre alterações.

Uma consequência deliberada: enquanto a proteção estiver ativa, a passagem direta e discreta abaixo da taxa de admissão fica desativada — todos os visitantes passam pela sala de espera, pois é aí que o comprovativo de trabalho é realizado. Quanto ao âmbito, o comprovativo de trabalho protege a atribuição de números de espera contra entradas em massa. É uma medida contra compradores automatizados, não uma defesa completa contra bots; quando necessário, combine-a com medidas na própria loja, como limites de compra.

Apenas as integrações personalizadas que chamam diretamente a API da fila têm de resolver o desafio. O fluxo é o seguinte: obter um desafio, encontrar um nonce cujo hash SHA-256 do desafio e do nonce comece pelo número exigido de bits a zero e enviar ambos no pedido de entrada. Os desafios são assinados e permanecem válidos durante cinco minutos; a reutilização é também impedida em cada instância:

Fluxo de comprovativo de trabalho para integrações personalizadas
// 1. Challenge holen (nur relevant, wenn PoW für die Queue aktiv ist)
GET https://developers.aditus.com/queue/<slug>/pow
// -> { queue, enabled: true, challenge, bits, expiresInSeconds: 300,
//      algorithm: "sha256" }

// 2. Nonce suchen: SHA-256(challenge + "." + nonce) muss mit <bits>
//    Null-Bits beginnen. Im Browser per WebCrypto — bei der
//    Standard-Schwierigkeit deutlich unter einer Sekunde.

// 3. Beitritt mit Lösung
POST https://developers.aditus.com/queue/<slug>/join
{ "pow": { "challenge": "…", "nonce": "…" } }

// Ohne oder mit ungültiger Lösung antwortet /join mit
// 428 Precondition Required — und liefert im Fehlerkörper direkt eine
// frische Challenge mit, sodass kein zweiter Abruf nötig ist.

Operações: aberturas programadas com sorteio justo

Para vendas anunciadas, uma sala de espera pode ter um horário de funcionamento fixo. Os visitantes que chegam cedo entram numa pré-fila: a página da sala de espera mostra uma contagem decrescente para a inauguração, ainda ninguém entrou. À hora de abertura, ocorre a etapa crucial: a ordem de admissão entre todos os que aguardam até então é sorteada de forma bastante aleatória. Chegar três horas mais cedo não traz, portanto, qualquer vantagem em relação a chegar três minutos mais cedo; maratonas de atualização e separadores de browser acampados perdem o sentido. Todos os que aderirem após a abertura serão colocados atrás do grupo sorteado pela ordem normal de chegada.

O sorteio é uma permutação matemática sobre os números em espera emitidos antes da abertura – cada número fica exatamente uma posição, nenhum é perdido, nenhum aparece duas vezes e a atribuição não é previsível a partir da ordem de adesão. Alterar o horário de abertura na consola admin rearma o sorteio; nada muda na integração da loja ou na API.

Operações: deteção de abandono

Nem toda a gente que sorteia um número de espera fica. Os separadores fechados e os browsers abandonados deixam normalmente lacunas: a janela de admissão passa por números que já não pertencem a ninguém e o rendimento real cai abaixo da taxa configurada. Com a deteção de abandono ativada, a página alojada da sala de espera reporta a sua presença num piscar de olhos regular. Se um número permanecer silencioso durante mais tempo do que o período de carência configurado (60 a 3.600 segundos, padrão 180), será considerado abandonado – e a janela de admissão avança exatamente nessa quantidade mais rapidamente, de modo a que os lugares vagos vão para os visitantes que ainda estão à espera.

A deteção é deliberadamente indulgente: um visitante que regressa cujo número foi contabilizado como abandonado, mas já se encontra dentro da janela de admissão, é admitido normalmente – o batimento cardíaco apenas acelera, nunca revoga uma admissão. As integrações personalizadas que constroem a sua própria página de espera enviam o mesmo sinal através de POST /queue/ <slug> /heartbeat (corpo JSON com o número de espera, recomendado a cada 60 segundos).

Operações: códigos de acesso VIP

Imprensa, parceiros, contingentes de adeptos: alguns visitantes nunca deveriam ver uma sala de espera. Para estes, podem ser criados códigos de bypass por sala de espera na consola de administração do ADITUS – cada um com um rótulo, um limite de utilização opcional e uma data de validade opcional, e cada um pode ser desativado ou eliminado a qualquer momento. Um código é partilhado como um simples link: /queue/ <slug> /enter?code=… redireciona diretamente para a loja com um token de admissão válido, passando por toda a fila. As integrações personalizadas podem resgatar códigos através de POST /queue/ <slug> /bypass e receber o token como JSON.

Duas propriedades de segurança deliberadas: um código inválido na ligação da gateway passa silenciosamente para o caminho normal – as pessoas de fora não conseguem dizer se alguma vez existiu um código. E a rota JSON responde de forma idêntica para códigos inválidos, expirados, esgotados e desativados, pelo que não existe oráculo para adivinhar códigos. As admissões de bypass são marcadas como tal no token e não consomem vagas de admissão regulares.

Detalhes técnicos

As secções seguintes não são necessárias para a integração — a etiqueta de script acima está completa. Documentam como funciona o sistema para avaliação técnica e para lojas que desejam verificar a admissão no seu próprio backend.

Como funciona a admissão

Cada visitante recebe um número de espera sequencial por um único incremento atómico da base de dados. A admissão avança continuamente: o número atualmente admitido é calculado como base + taxa × minutos decorridos. A pesquisa de estado é de leitura apenas e não afeta a base de dados por pedido. Não há estado por visitante no servidor, nem cron job nem cronómetro — o próprio serviço de fila não se pode tornar um estrangulamento sob carga. A pausa na fila impede tanto a admissão como a emissão de novos números; as alterações das taxas entram em vigor continuamente e o número admitido nunca diminui.

Justiça: estritamente primeiro a chegar, primeiro a ser servido

A admissão é estritamente por ordem de chegada (FCFS): o incremento atómico fixa a posição de cada visitante no momento da adesão, e as posições nunca mudam posteriormente. Não há deliberadamente nenhuma lotaria, nenhuma randomização e nenhuma faixa de prioridade – sob escassez, a ordem de chegada é a única ordem que os visitantes aceitam como justa, e é a única que não pode ser manipulada. O salto na fila é tecnicamente excluído em dois níveis: o número de espera só aumenta e a verificação de admissão compara o número do visitante com o número atualmente admitido no servidor – o token de admissão só é emitido quando a verificação é aprovada, assinada com o segredo da fila. Um visitante não pode reivindicar uma posição melhor e um token forjado falha a verificação de assinatura. Os operadores que necessitam de fluxos separados — digamos, uma sala de espera por evento ou por venda — gerem várias salas de espera independentes, cada uma com o seu próprio slug, segredo, taxa e configuração.

Arquitetura sob carga: números medidos

O objetivo do design segue diretamente da lógica de admissão acima: como o número admitido é derivado do tempo decorrido e a verificação do estado não indica qualquer estado por visitante, quase todo o tráfego de visitantes é uma computação sem estado. Qualquer instância pode responder a qualquer pedido, as instâncias não partilham nada para além da base de dados e a plataforma adiciona automaticamente instâncias sob carga. A gravação única da base de dados por visitante — o incremento atómico na junção — é o único ponto de serialização e acontece exatamente uma vez por visitante, e não por sondagem. Os números abaixo provêm do executor de teste de carga integrado descrito acima, executado contra uma sala de espera de teste dedicada no sistema de produção: dois workers geradores solicitam duas instâncias de fila, sendo o débito e a taxa de erro retirados dos recibos assinados do serviço de fila. O perfil mix combina a adesão e a pesquisa de estado na proporção do percurso real do visitante:

CorrerResultado
status · 1.000 req/s · 120 s · 2 instânciasLatência p95 72,1 ms · taxa de erro 0 % · set. 2026, 999,2 req/s atingidos
status · 1.000 req/s · 120 s · 2 instânciasLatência p95 6,6 ms · taxa de erro 0 % · ago. 2026, 939,4 req/s atingidos (limitado pelo gerador)
mix · 500 req/s · 60 s · 2 instânciasLatência p95 1.488 ms · taxa de erro 0 % · set. 2026, 497,2 req/s atingidos, 0 × 429; p95 inclui o pico de arranque

Todas as execuções utilizaram o percurso do código de produção e terminaram sem um único erro HTTP, de transporte ou de limite de taxa. Duas instâncias sustentam mil pedidos de estado por segundo durante dois minutos – mais de dez mil visitantes em espera a consultar no seu intervalo adaptativo – e o perfil mix confirma que quinhentos pedidos por segundo, adesões incluídas, passam sem serem travados pelos orçamentos de pedidos por IP. O topo da tabela é limitado pelo gerador de carga, não pela fila: o p95 do lado da fila manteve-se em milissegundos de um dígito até o gerador funcionar no máximo. Este dimensionamento não é uma caixa negra: cada instância em execução reporta continuamente com métricas em tempo real – CPU, memória, taxa de transferência de pedidos – visíveis a qualquer momento na consola de administração do ADITUS, pelo que é transparente quantas instâncias estão à venda e quanto espaço resta. Os testes de carga programados verificam novamente estes números continuamente em relação ao sistema de produção, e uma execução que fica claramente atrás dos seus antecessores é automaticamente sinalizada.

Endpoints

Dez endpoints, sem autenticação para visitantes, CORS restrito aos domínios configurados por fila. A página alojada da sala de espera utiliza exatamente esta API – também pode ser direcionada diretamente para uma experiência de espera totalmente personalizada.

EndpointO que faz
GET /queue/<slug>Página alojada da sala de espera: pede um número, consulta o estado e encaminha automaticamente o visitante assim que este é admitido.
POST /queue/<slug>/joinAtribui um número de espera (a única operação de escrita no percurso do visitante). Devolve 423 enquanto a fila está em pausa.
GET /queue/<slug>/status?number=NConsulta o estado de admissão de um número — apenas de leitura e com o cabeçalho Retry-After. Devolve 404 para números que nunca foram atribuídos.
POST /queue/<slug>/tokenTroca um número admitido por um JWT HS256 assinado. Devolve 425 enquanto o número ainda não tiver sido admitido e 404 para números que nunca foram atribuídos.
GET /queue/<slug>/enterPonto de entrada do gateway: é publicado em vez do URL da loja. Enquanto houver capacidade, encaminha diretamente para o URL de destino configurado (com um token de admissão); caso contrário, redireciona para a sala de espera. Requer um URL de destino configurado. Aceita ?code=… para códigos de acesso VIP: um código válido evita totalmente a fila; um código inválido segue o percurso normal sem revelar qualquer informação.
GET /queue/<slug>/embed.jsScript de integração do lado da loja: deixa os visitantes entrar sem interrupções enquanto ninguém estiver à espera; assim que se formar uma fila, encaminha os visitantes sem um passe válido para a sala de espera e devolve-os exatamente à página de origem.
GET /queue/<slug>/verify?token=…Verificação de token do lado do servidor utilizada pelo script de integração: valida a assinatura, o destinatário e a validade de um token de admissão.
GET /queue/<slug>/infoInformação pública da fila: estado de atividade, número atualmente admitido e quantidade de pessoas em espera.
POST /queue/<slug>/heartbeatSinal de presença para a deteção opcional de abandono: a página da sala de espera comunica que um número continua presente. É aceite sem produzir efeitos enquanto a deteção estiver desativada.
POST /queue/<slug>/bypassUtiliza um código de acesso VIP através de JSON: devolve um token de admissão e o URL de destino. Os códigos inválidos, caducados, esgotados ou desativados devolvem todos o mesmo 404, sem fornecer pistas que permitam adivinhar códigos.
GET /queue/<slug>/powDesafio de comprovativo de trabalho para a proteção opcional contra bots: devolve enabled: false enquanto a proteção estiver desativada; caso contrário, devolve um desafio assinado cuja solução é exigida por /join.
GET /queue/healthzVerificação pública do estado do serviço para monitorização da disponibilidade: responde sem autenticação e sem aceder à base de dados. É deliberadamente excluída das métricas da instância, para que os pedidos de monitorização nunca distorçam a visão do tráfego.

1.º Solicite um número de espera

join.ts
// Wartenummer anfordern (einziger Schreibzugriff im Besucherpfad).
const res = await fetch("https://developers.aditus.com/queue/<slug>/join", {
  method: "POST",
});
const ticket: {
  queue: string;              // Queue-Slug
  name: string;               // Anzeigename des Warteraums
  number: number;             // vergebene Wartenummer
  serving: number;            // bis zu dieser Nummer wird weitergeleitet
  ahead: number;              // Anzahl Nummern vor dieser
  admitted: boolean;          // true -> sofort weiter zu /token
  estimatedWaitSeconds: number;
  retryAfterSeconds: number;  // empfohlenes Polling-Intervall
} = await res.json();
// 423 Locked -> der Warteraum ist pausiert (keine Weiterleitung, keine neuen Nummern).

2.º Pesquise o estado

status.ts
// Statusabfrage — rein lesend, beliebig oft wiederholbar.
// Der Server sendet zusätzlich einen Retry-After-Header.
const res = await fetch(
  "https://developers.aditus.com/queue/<slug>/status?number=" + ticket.number,
);
const status: {
  queue: string;
  name: string;
  active: boolean;            // false -> Weiterleitung pausiert
  number: number;
  serving: number;
  ahead: number;
  admitted: boolean;
  estimatedWaitSeconds: number;
  retryAfterSeconds: number;
} = await res.json();

if (status.admitted) {
  // -> Token abholen und zum Shop weiterleiten
}

3.º Obtenha o token de admissão

token.ts
// Sobald admitted=true: Zugriffs-Token abholen.
const res = await fetch("https://developers.aditus.com/queue/<slug>/token", {
  method: "POST",
  headers: { "Content-Type": "application/json" },
  body: JSON.stringify({ number: ticket.number }),
});
// 425 Too Early -> die Nummer ist noch nicht zur Weiterleitung freigegeben.
const grant: {
  queue: string;
  number: number;
  token: string;              // signierter HS256-JWT
  tokenType: "JWT";
  expiresInSeconds: number;   // Standard: 600 s
  targetUrl: string | null;   // konfiguriertes Weiterleitungsziel
} = await res.json();

// Weiterleitung übernimmt die gehostete Warteraum-Seite automatisch:
// targetUrl + "?aditus_queue_token=" + grant.token

Opcional: verificando o token no seu back-end

A integração da tag script é completa por si só. As lojas que controlam o seu back-end também podem verificar o token de admissão: é um JWT HS256 padrão, verificado offline com o segredo partilhado – sem retorno de chamada para a fila, sem latência extra. O segredo é gerado quando a fila é criada, mostrado exatamente uma vez e pode ser alternado a qualquer momento. Reivindicações: iss é sempre aditus-queue, aud é o slug da fila, qnr é o número de espera admitido, exp limita a validade (padrão 10 minutos). Nota: a passagem silenciosa sob a taxa de admissão não produz um token – um back-end que exija estritamente um token deve enviar os visitantes sem ele para a sala de espera, que depois emite um token imediatamente quando ninguém está à espera.

verify.ts
// ZIELSYSTEM (dein Shop / deine Seite): Token prüfen — Standard-JWT (HS256).
// Das Secret erhältst du einmalig von ADITUS beim Einrichten des Warteraums.
import jwt from "jsonwebtoken";

const payload = jwt.verify(token, process.env.ADITUS_QUEUE_SECRET!, {
  algorithms: ["HS256"],
  issuer: "aditus-queue",     // iss ist immer aditus-queue
  audience: "<slug>",         // aud ist der Queue-Slug deines Warteraums
}) as { qnr: number; iat: number; exp: number };

// payload.qnr = die weitergeleitete Wartenummer.
// Gültiger Token -> Besucher passieren lassen (z. B. Cookie setzen).
// Fehlender/ungültiger Token -> zurück in den Warteraum:
//   https://developers.aditus.com/queue/<slug>

Segurança num só lugar

Os mecanismos de segurança estão descritos onde pertencem no fluxo acima; esta secção os recolhe. Tokens assinados: os tokens de admissão são JWTs HS256, assinados com um segredo por fila que é mostrado exatamente uma vez e pode ser alternado a qualquer momento; a ligação de público (slug de fila) e uma expiração curta (padrão 10 minutos) limitam o valor de um token capturado. Proteção de bot: a verificação opcional de prova de trabalho torna a adesão em massa de bot farms proporcionalmente dispendiosa; os desafios são assinados pelo HMAC e expiram ao fim de cinco minutos; uma proteção de melhor esforço por instância também suprime a reutilização de um desafio gasto – o verdadeiro gerador de custos é o próprio trabalho de hash. Redireccionamentos: Os URLs de retorno são validados no lado do servidor em relação aos domínios configurados por fila — a sala de espera nunca se torna um redireccionamento aberto. Superfície API: os endpoints dos visitantes não transportam qualquer credencial, o CORS é restrito por fila, o acesso do administrador utiliza chaves API que estão ligadas a uma única sala de espera, armazenadas apenas como hashes, não podem gerir outras chaves e deixar um rasto de auditoria. Picos de tráfego: a arquitetura stateless absorve a carga por design — qualquer instância responde a qualquer pedido e a plataforma escala as instâncias automaticamente; a filtragem DDoS ao nível da rede é fornecida pela plataforma de alojamento na parte frontal do serviço.

Modos de falha: o que acontece quando algo se parte

Uma sala de espera está diante da receita – o seu comportamento de fracasso é tão importante como o seu caminho feliz.

  • Serviço de fila inacessível (variante script-tag): o script falha a abertura – a loja permanece totalmente utilizável. Uma interrupção na sala de espera nunca bloqueia a loja.
  • Serviço de fila inacessível (variante gateway): pausa de novas entradas; os visitantes já admitidos estão na loja e mantêm-se inalterados.
  • Perda de uma única instância: nenhum visitante se apercebe. Nenhum estado por visitante reside em nenhuma instância – cada instância responde a todos os pedidos, a base de dados partilhada é o único componente com estado.
  • Atualização do browser: o número de espera é mantido na sessão do browser — uma recarga volta à mesma posição, o lugar na fila nunca é perdido.
  • O visitante limpa os cookies ou o armazenamento do browser: a posição não é deliberadamente recuperável — o visitante sorteia um novo número no final da linha. Qualquer outra coisa abriria caminho para fraudes de posição.
  • Sala de espera em pausa: paragem de entrada e admissão com sinal claro (HTTP 423) e mensagem explicativa na sala de espera — sem erros silenciosos.
  • A verificação de integridade da loja falha (taxa automática): a taxa congela primeiro e depois desce para o mínimo configurado – uma verificação de integridade inacessível nunca abre mais as portas.

Como se compara com os produtos dedicados para salas de espera

O ADITUS-Queue aborda os mesmos problemas técnicos que os produtos dedicados de sala de espera virtual empresarial. A tabela mapeia as capacidades pelas quais estes produtos são medidos de acordo com a forma como o ADITUS-Queue os cobre – incluindo uma omissão deliberada.

CapacidadeNa fila ADITUS
JustiçaFCFS estrito via incremento atómico; o salto de fila é tecnicamente excluído.
Fail-openCom a integração script-tag, uma interrupção na sala de espera nunca bloqueia a aplicação protegida; os visitantes já admitidos não são afetados em todas as variantes.
Aplicação na periferiaVerificação de tokens offline em Nginx, Caddy, Cloudflare, CloudFront – zero latência adicionada.
Proteção contra botsComprovativo de trabalho opcional por fila, invisível para os navegadores reais.
Desempenho comprovadoNúmeros medidos publicados, verificados continuamente por testes de carga programados na produção.
Admissão adaptativaTaxa autorregulada impulsionada pela verificação de integridade da própria aplicação protegida.
API-firstCada recurso de visitante e administrador é um endpoint REST documentado.
Filas prioritárias/VIPDeliberadamente não oferecido – a ordem de chegada estrita é a promessa de justiça. Audiências separadas funcionam como salas de espera separadas.

Administração via chave API

Tudo o que a consola de administração ADITUS permite fazer numa sala de espera — ajustar a taxa de admissão, pausar ou alterar a configuração — também pode ser automatizado. O acesso utiliza uma chave de API com o prefixo qak_, enviada como Bearer token; cada chave é criada para uma única sala de espera e só pode ler ou alterar essa sala. As chaves são criadas e revogadas na consola de administração, apresentadas uma única vez e armazenadas apenas sob a forma de hash. Um caso de utilização típico é um runbook de início de vendas: uma tarefa agendada aumenta a taxa de admissão imediatamente antes da abertura, um script pausa a fila em caso de emergência e a monitorização lê a configuração atual. Aplicam-se três salvaguardas: uma chave nunca acede a outras salas de espera nem a funções administrativas globais (testes de carga, agendamentos ou instâncias), sendo esses pedidos rejeitados no servidor; a gestão das próprias chaves não é possível com uma destas chaves, pelo que uma chave exposta nunca pode criar nem listar outras; e todas as alterações efetuadas com uma chave são registadas no registo de auditoria com o nome da chave e da respetiva sala de espera.

Exemplos com curl
# Konfiguration des zugeordneten Warteraums lesen. Jeder Key ist an genau
# einen Warteraum gebunden — die Liste enthält daher höchstens diesen einen
# Eintrag; andere Warteräume und globale Verwaltungsfunktionen sind mit
# einem Key nicht erreichbar.
curl -H "Authorization: Bearer qak_…" \
  https://developers.aditus.com/api/admin/queue/sites

# Weiterleitungsrate im laufenden Betrieb anheben: Lesen -> Feld ändern -> Schreiben.
# PATCH erwartet die vollständige Konfiguration (ohne slug); unbekannte
# Felder wie id oder Zeitstempel werden serverseitig ignoriert.
KEY="qak_…"; BASE="https://developers.aditus.com/api/admin/queue"
SITE=$(curl -s -H "Authorization: Bearer $KEY" "$BASE/sites" \
  | jq '.sites[0]')
echo "$SITE" | jq '.ratePerMinute = 300' | curl -s -X PATCH \
  -H "Authorization: Bearer $KEY" -H "Content-Type: application/json" \
  -d @- "$BASE/sites/$(echo "$SITE" | jq -r .id)"

# Zugeordneten Warteraum pausieren (keine Weiterleitung, keine neuen Nummern):
# active = false
echo "$SITE" | jq '.active = false' | curl -s -X PATCH \
  -H "Authorization: Bearer $KEY" -H "Content-Type: application/json" \
  -d @- "$BASE/sites/$(echo "$SITE" | jq -r .id)"
Agendado através do GitHub Actions
# .github/workflows/onsale.yml — Weiterleitungsrate zum Vorverkaufsstart anheben.
# Den API-Key als Repository-Secret ADITUS_QUEUE_API_KEY hinterlegen. Der Key
# ist an den Warteraum des Vorverkaufs gebunden — mehr kann er nicht.
name: Weiterleitungsrate zum On-Sale anheben
on:
  schedule:
    - cron: "55 8 14 3 *"   # 14. März, 08:55 UTC — kurz vor dem On-Sale
  workflow_dispatch: {}

jobs:
  raise-rate:
    runs-on: ubuntu-latest
    steps:
      - name: Rate auf 300/min anheben
        env:
          KEY: ${{ secrets.ADITUS_QUEUE_API_KEY }}
        run: |
          BASE="https://developers.aditus.com/api/admin/queue"
          # Der Key sieht nur seinen gebundenen Warteraum — .sites[0] genügt.
          SITE=$(curl -sf -H "Authorization: Bearer $KEY" "$BASE/sites" \
            | jq '.sites[0]')
          echo "$SITE" | jq '.ratePerMinute = 300' \
            | curl -sf -X PATCH \
              -H "Authorization: Bearer $KEY" \
              -H "Content-Type: application/json" \
              -d @- "$BASE/sites/$(echo "$SITE" | jq -r .id)"