← back to the garden

MD

Como transformar o Discourse em um tracker privado de BitTorrent

Análise técnica, arquitetural, operacional e jurídica para criar um plugin de Discourse integrado a um tracker privado de BitTorrent.

  • pesquisa
  • discourse
  • bittorrent
  • tracker-privado
  • plugin
  • arquitetura
  • self-hosting

Como transformar o Discourse em um tracker privado de BitTorrent

É tecnicamente possível transformar uma comunidade Discourse na interface de um tracker privado de BitTorrent. O Discourse pode cuidar das contas, convites, grupos, catálogo, pesquisa, comentários, moderação, reputação e páginas de cada torrent. O que ele não deve fazer, numa instalação séria, é processar diretamente todo o tráfego de announce dos clientes BitTorrent: essa parte possui características de carga, protocolo e segurança diferentes das de um fórum Ruby on Rails.

O desenho recomendado é, portanto, um plugin de Discourse acompanhado por um tracker dedicado. Para o usuário, tudo parece parte do Discourse. Por baixo, o plugin é a autoridade de membros e catálogo, enquanto um serviço pequeno e especializado recebe os anúncios dos clientes, mantém os peers ativos e envia estatísticas agregadas de volta ao plugin.

Esta análise parte de um uso legítimo: distribuição privada de arquivos próprios, licenciados, em domínio público, software livre, imagens de sistemas, acervos institucionais ou outros materiais cuja circulação tenha sido autorizada. O protocolo BitTorrent é uma tecnologia neutra; a legalidade depende do conteúdo e das autorizações. A arquitetura deve nascer com política de direitos autorais, canal de denúncia e rastreabilidade administrativa.

Resumo executivo

Resposta curta: sim, é possível e a ideia é boa, desde que o Discourse não seja forçado a virar o próprio daemon de tracker.

A melhor solução é desenvolver um projeto provisoriamente chamado discourse-private-tracker, composto por duas partes:

  1. Plugin do Discourse: gerencia usuários, convites, grupos, uploads de metadados .torrent, páginas de catálogo, permissões, downloads personalizados, passkeys, moderação, relatórios e estatísticas consolidadas.
  2. Tracker sidecar: serviço independente, inicialmente apenas HTTPS, que valida passkeys e info-hashes, devolve peers, mantém sessões de swarm em memória ou Redis e publica deltas de tráfego para o Discourse.

O melhor ponto de partida para o sidecar é o Chihaya, escrito em Go. O projeto foi criado justamente para integrar BitTorrent a ambientes existentes, oferece frontends HTTP e UDP, armazenamento substituível, Redis, Prometheus e uma cadeia de middlewares anteriores e posteriores ao announce. Sua licença é BSD de duas cláusulas, favorável a adaptações. A autenticação por passkey e a contabilidade individual ainda precisariam ser implementadas como middleware próprio.

O Torrust Tracker é a segunda melhor base: moderno, ativo, escrito em Rust, com modos privado e por lista permitida, API de administração, HTTP, TLS, UDP, IPv4/IPv6 e persistência. Entretanto, sua própria lista de desenvolvimento ainda apresenta estatísticas específicas por peer e torrent como trabalho pendente. Ele resolve autorização e matchmaking melhor do que resolve a contabilidade tradicional por usuário.

Para uma prova de conceito muito pequena, bittorrent-tracker permite criar rapidamente um servidor Node.js com filtro assíncrono por info-hash e segredo. É excelente para validar a experiência, mas exigirá uma camada própria de persistência e contabilidade antes de operar como tracker privado completo.

UNIT3D já entrega praticamente todas as funções de um tracker privado, inclusive passkeys, peers, razão de compartilhamento, limites e moderação. Contudo, ele é uma aplicação Laravel completa, não uma biblioteca para Discourse. Usá-lo junto ao Discourse resultaria em dois produtos e dois modelos de usuários; adaptar seu UNIT3D-Announce exigiria desacoplar o serviço do banco e dos conceitos internos do UNIT3D.

Não foi encontrado, na busca pelo diretório oficial de plugins do Discourse, no repositório que cataloga plugins conhecidos e no GitHub, um plugin atual e mantido que transforme o Discourse em tracker privado. A ideia parece suficientemente inédita para justificar um projeto próprio.

Veredito

Pergunta Resposta
É possível? Sim. O sistema de plugins do Discourse permite backend Rails, tabelas, rotas, controladores, jobs e interface Ember.
Um componente de tema é suficiente? Não. Tema altera interface; passkeys, autorização, parsing e persistência exigem plugin de servidor.
O Discourse deve receber os announces? Somente numa prova de conceito pequena. Em produção, use um serviço dedicado.
Melhor arquitetura Plugin Discourse + Chihaya com middleware próprio + Redis + PostgreSQL.
Caminho mais rápido para um tracker completo Instalar UNIT3D separado e unificar login; não transforma verdadeiramente o Discourse.
Caminho mais simples para provar a ideia Plugin mínimo + bittorrent-tracker em Node.js, apenas HTTPS e sem razão punitiva.
Dificuldade Média para um protótipo; alta para uma comunidade confiável e resistente a fraude.
Maior risco técnico Contabilidade correta, vazamento de passkeys, abuso do endpoint e compatibilidade de clientes.
Maior risco não técnico Distribuição não autorizada e tratamento de endereços IP e históricos de uso.

Metodologia e critérios

A pesquisa examinou as especificações oficiais do BitTorrent, o código e a documentação atuais do Discourse, o modelo oficial de plugin, os catálogos conhecidos de plugins e os repositórios dos principais trackers abertos.

As alternativas foram avaliadas por: atividade de manutenção; adequação a tracker privado; autenticação; lista permitida de torrents; contabilidade individual; extensibilidade; desempenho; suporte a HTTP/HTTPS, UDP e IPv6; persistência; observabilidade; licença; acoplamento; dificuldade de integração com o Discourse; e risco operacional.

As datas de atividade dos repositórios foram verificadas em 24 de agosto de 2026. Estimativas de tempo, capacidade e custo são projeções de engenharia, não promessas dos projetos citados. O documento não substitui uma análise jurídica aplicada ao país de hospedagem, à entidade operadora e ao conteúdo distribuído.

O que significa “transformar o Discourse em tracker”

Um tracker privado moderno é a combinação de pelo menos quatro produtos:

  1. Comunidade: cadastro, convites, regras, fóruns, mensagens, denúncias e moderação.
  2. Índice: catálogo pesquisável de torrents, categorias, descrições, arquivos, tamanhos e estatísticas.
  3. Tracker de protocolo: endpoint que recebe announce dos clientes e devolve a lista de peers da mesma swarm.
  4. Contabilidade: atribuição de upload, download, tempo de seed e conclusão a uma conta.

O Discourse já é muito competente no primeiro item e oferece grande parte da fundação do segundo. O plugin acrescentaria o restante do índice e a ligação com os dois últimos. Os arquivos grandes não passam pelo Discourse nem pelo tracker: continuam sendo transferidos diretamente entre clientes BitTorrent. O fórum hospeda apenas páginas, metadados e os pequenos arquivos .torrent.

O que já pode ser reaproveitado do Discourse

  • Contas, e-mail, sessões, autenticação social, 2FA e recuperação.
  • Convites, aprovação manual e configuração de comunidade fechada.
  • Grupos para membros, uploaders, moderadores e equipe.
  • Categorias privadas com permissões separadas de ver, responder e criar.
  • Tópicos, comentários, pesquisa, tags, notificações, chat e mensagens.
  • Flags, silenciamento, suspensão, auditoria e fila de revisão.
  • Badges, níveis de confiança e histórico comunitário.
  • API REST, webhooks, jobs em Sidekiq, PostgreSQL e Redis.
  • Armazenamento externo e uploads seguros, quando configurados corretamente.
  • Extensão de backend e frontend por plugins.

A documentação de desenvolvimento confirma que o núcleo tem backend Ruby on Rails e frontend Ember e que plugins podem alterar os dois lados. O guia oficial mostra como um plugin define um Rails::Engine, controladores, rotas e módulos isolados; o esqueleto oficial já inclui diretórios para modelos, migrações, interface e testes.

O que precisa ser construído

  • Parser e validador seguro de metainfo BitTorrent.
  • Registro de torrents por info-hash.
  • Download personalizado do .torrent por usuário.
  • Geração, rotação e revogação de passkeys.
  • Serviço de announce e scrape.
  • Lista de torrents permitidos.
  • Estado de seeders, leechers e peers.
  • Contabilidade por usuário e por torrent.
  • Políticas de ratio, seed time, freeleech e download slots, caso desejadas.
  • Telas administrativas e páginas de estatísticas.
  • Integração segura entre plugin e sidecar.
  • Proteções contra falsificação, vazamento e abuso.
  • Política jurídica e de privacidade específica.

Como o protocolo funciona

A BEP 3 define a distribuição BitTorrent como a interação entre um servidor web, um arquivo de metainfo, um tracker, um seeder inicial e os clientes finais. O .torrent é um dicionário em bencode. Seu campo superior announce informa o tracker; o dicionário info descreve os arquivos e as peças.

O info_hash de BitTorrent v1 é o SHA-1 dos bytes bencoded do dicionário info. Isso produz uma regra fundamental para o plugin:

O endereço announce pode ser personalizado sem alterar a swarm, porque fica fora de info. Inserir ou mudar private=1 dentro de info, por outro lado, altera o info-hash.

Assim, o sistema pode armazenar um metainfo canônico, sem segredo, e gerar no momento do download uma cópia cuja URL seja semelhante a:

https://tracker.example/announce/PASSKEY_DO_USUARIO

O cliente passa a enviar periodicamente requisições com info_hash, peer_id, porta, bytes enviados, bytes baixados, bytes restantes e eventos como started, completed e stopped. O tracker valida a passkey e o torrent, registra o peer e devolve outros endereços da mesma swarm.

Torrent privado não significa criptografado ou anônimo

A BEP 27 define private=1. Clientes compatíveis devem anunciar apenas ao tracker privado e não usar mecanismos externos de descoberta. Isso reduz o vazamento por DHT, PEX e descoberta local, mas não criptografa o conteúdo e não oculta peers uns dos outros. Cada peer precisa conhecer o IP e a porta dos demais para transferir dados.

Clientes modificados podem desobedecer à regra. Remover private=1 altera o info-hash e cria outra swarm, mas não impede alguém que já tenha o conteúdo de redistribuí-lo. “Privado” significa acesso controlado ao tracker, não DRM.

Por que começar apenas com HTTPS

A BEP 15 reduz bastante o custo de anúncios usando UDP, mas seu campo key não é uma credencial padronizada de conta; normalmente é escolhido pelo cliente. Passkeys em caminhos HTTPS são mais compatíveis com o modelo tradicional de trackers privados, mais fáceis de revogar, registrar e proteger por proxy.

Para o MVP, a recomendação é:

  • https://tracker.example/announce/{passkey};
  • https://tracker.example/scrape/{passkey} ou scrape desativado;
  • respostas compactas de peers;
  • IPv4 e IPv6;
  • intervalo inicial entre 30 e 45 minutos, com mínimo protegido;
  • UDP e WebTorrent deixados para versões posteriores.

Arquiteturas possíveis

Opção A — Tudo dentro do Discourse

O plugin cria um controlador Rails em /tracker/announce/:passkey, consulta PostgreSQL/Redis e devolve bencode.

Vantagens: uma implantação, acesso direto aos usuários, código conceitualmente simples e ótimo para demonstrar a ideia.

Problemas: cada cliente chama o endpoint repetidamente mesmo sem navegar no fórum; a carga concorre com páginas, API e Sidekiq; respostas de tracker não combinam com middleware web comum; atualizações do Discourse podem afetar o endpoint; UDP não cabe naturalmente no Rails; e um ataque ao announce pode degradar toda a comunidade.

Veredito: aceitável somente para laboratório ou grupo muito pequeno. Não é a arquitetura a publicar como plugin geral.

Opção B — Plugin + tracker sidecar

O Discourse é a fonte de verdade para contas, catálogo e decisões administrativas. O sidecar recebe announces, usa cache local/Redis para autorizar e envia eventos agregados a uma fila.

Vantagens: isolamento de carga e falhas; liberdade para Go ou Rust; atualização independente; melhor desempenho; possibilidade de múltiplas réplicas; métricas próprias; e uma interface de integração explícita.

Problemas: dois processos, contrato entre serviços, consistência eventual e mais trabalho de implantação.

Veredito: arquitetura recomendada.

Opção C — Discourse + UNIT3D separados

UNIT3D funciona como tracker e índice; Discourse permanece como fórum. Um provedor OIDC comum ou integração de SSO mantém uma identidade aproximada nos dois sistemas.

Vantagens: funções maduras de tracker privado ficam prontas mais rapidamente. O código atual do UNIT3D já verifica passkey, grupo, cliente, torrent, intervalo mínimo, conexões e slots no controlador de announce.

Problemas: catálogo, perfis, permissões e moderação duplicados; integração visual imperfeita; sincronização de banimentos; dois bancos; e pouca vantagem real em “transformar o Discourse”.

Veredito: melhor para colocar um tracker convencional no ar, pior para concretizar esta ideia como produto distinto.

Opção D — Adaptar o UNIT3D-Announce ao plugin

O serviço UNIT3D-Announce é um tracker Rust de alto desempenho que já trabalha com passkeys e estatísticas. Poderia ser bifurcado e receber uma nova camada de repositório compatível com as tabelas do plugin.

Vantagens: lógica específica de tracker privado já existente e desempenho documentado muito superior ao controlador PHP do UNIT3D.

Problemas: forte acoplamento atual ao modelo UNIT3D, adaptação invasiva, licença AGPL e manutenção de um fork complexo.

Veredito: opção válida para uma segunda geração, após estabilizar o modelo de dados e entender as regras desejadas.

Arquitetura recomendada

Navegador
   |
   v
Discourse + discourse-private-tracker
   |-- contas, convites, grupos e 2FA
   |-- tópicos, catálogo, pesquisa e comentários
   |-- upload/validação do metainfo
   |-- download personalizado com passkey
   |-- administração, denúncias e estatísticas
   |
   +---- PostgreSQL: catálogo, usuários e totais consolidados
   +---- Sidekiq: validação, agregação, alertas e limpeza
   +---- armazenamento de objetos: metainfo canônico
   |
   +---- API interna autenticada -------------------+
                                                    |
Cliente BitTorrent                                  v
   |                                      Tracker sidecar Chihaya
   | HTTPS announce com passkey             |-- middleware de autenticação
   +---------------------------------------->|-- lista permitida de info-hashes
                                            |-- peers ativos e scrape
                                            |-- deltas de upload/download
                                            |-- limites e métricas
                                                    |
                                                    +-- Redis próprio
                                                    +-- fila de eventos
                                                    +-- Prometheus

Divisão de responsabilidades

Responsabilidade Discourse/plugin Sidecar
Cadastro, login, 2FA e convites Sim Não
Grupos e suspensão Sim Cache da decisão
Página e comentários do torrent Sim Não
Parsing e aprovação do .torrent Sim Recebe info-hash permitido
Personalização do arquivo baixado Sim Não
Validação rápida de passkey Fonte de verdade Execução em cache
Announce e resposta de peers Não Sim
Peers ativos Exibe agregados Fonte operacional
Histórico de tráfego Consolida Produz deltas
Ratio e políticas Define e aplica Faz bloqueio imediato em cache
Logs comunitários Sim Não
Métricas de protocolo Exibe resumo Prometheus

Escolha do motor de tracker

Projeto Pontos fortes Limitações para esta ideia Uso recomendado
Chihaya Go; HTTP/UDP; IPv4/IPv6; Redis; Prometheus; alta disponibilidade; middlewares; BSD-2-Clause Autenticação por conta e ratio precisam de middleware próprio; releases formais antigas exigem fixar e testar um commit atual Base recomendada para produção personalizada
Torrust Tracker Rust; ativo; TLS; API; modo privado e whitelist; SQLite/MySQL/PostgreSQL; BEP 27 Chaves são o mecanismo de autenticação, mas estatísticas detalhadas por peer/torrent ainda aparecem no roadmap; AGPL Alternativa moderna se ratio não for central ou se houver disposição para contribuir/forkar
bittorrent-tracker Node.js; API simples; HTTP/UDP/WebSocket; filtro assíncrono; eventos; MIT Estado e contabilidade de tracker privado precisam ser construídos; não é um portal completo Melhor para prova de conceito rápida
UNIT3D-Announce Rust; passkey e contabilidade maduras; desempenho; regras de tracker privado Vinculado às tabelas e regras do UNIT3D; AGPL Fork para versão avançada, não para primeiro MVP
Aquatic Rust; alto desempenho; HTTP/UDP/WebTorrent; listas de info-hash; Prometheus; Apache-2.0 Focado em tracker aberto; sem identidade e ratio prontos Grandes swarms sem contabilidade individual
opentracker C; mínimo consumo; muito simples; HTTP/UDP Deliberadamente aberto, sem persistência e pouco adequado a usuários/passkeys Não recomendado para este produto
Ocelot Modelo clássico de tracker privado e integração histórica com Gazelle Repositório original sem alterações de código desde 2015, somente IPv4 e forte acoplamento ao esquema Gazelle/MySQL Referência histórica, não base nova

Por que Chihaya vence

A arquitetura oficial do Chihaya separa frontends de protocolo, lógica e armazenamento. Uma cadeia configurável de PreHook atua antes da resposta e PostHook executa tarefas assíncronas depois dela. O repositório atual já inclui middlewares de aprovação de cliente, JWT, aprovação de torrent e intervalo variável.

Essa estrutura corresponde quase exatamente ao necessário:

  • PreHook PasskeyAuth: extrai passkey, consulta cache e rejeita conta inválida.
  • PreHook TorrentApproval: rejeita info-hash não aprovado.
  • PreHook Policy: aplica banimento, limite de peers e cliente bloqueado.
  • PostHook Accounting: calcula deltas válidos e publica eventos.
  • Storage Redis: guarda peers ativos e swarms.
  • Prometheus: mede announces, erros, latência e volume.

O antigo chihaya-privtrak-middleware serve como referência conceitual para deltas por usuário e info-hash, mas declara estar em estágio inicial e não deve ser adotado sem auditoria e atualização.

Modelo do plugin Discourse

Estrutura sugerida

discourse-private-tracker/
├── plugin.rb
├── config/
│   ├── routes.rb
│   ├── settings.yml
│   └── locales/
├── lib/discourse_private_tracker/
│   ├── engine.rb
│   ├── torrent_parser.rb
│   ├── torrent_personalizer.rb
│   ├── passkey_service.rb
│   └── tracker_client.rb
├── app/
│   ├── controllers/discourse_private_tracker/
│   ├── models/discourse_private_tracker/
│   ├── serializers/
│   └── jobs/
├── db/migrate/
├── assets/javascripts/discourse/
├── stylesheets/
├── spec/
└── test/javascripts/

O plugin deve usar um Rails::Engine isolado, conforme o guia atual de estrutura e autoloading, em vez de concentrar classes em plugin.rb. A interface deve usar a API JavaScript e plugin outlets estáveis; alterações diretas de classes internas devem ser evitadas porque o próprio Discourse alerta que esse mecanismo pode quebrar com mudanças no núcleo.

Modelo de dados mínimo

Tabela Campos principais Finalidade
private_tracker_accounts user_id, passkey_digest, status, uploaded, downloaded, seed_seconds, last_announce_at Estado de tracker ligado ao usuário Discourse
private_tracker_torrents topic_id, info_hash_v1, info_hash_v2, name, size, file_count, private, status, uploader_id Catálogo técnico e ligação com tópico
private_tracker_downloads user_id, torrent_id, downloaded_at, passkey_version Auditoria de obtenção do metainfo
private_tracker_transfers user_id, torrent_id, uploaded, downloaded, seed_seconds, completed_at Totais consolidados por usuário e torrent
private_tracker_accounting_batches event_id, received_at, payload_digest, processed_at Idempotência na comunicação do sidecar
private_tracker_moderation_events ator, alvo, ação, motivo, timestamps Rotação, bloqueio, remoção e revisão
private_tracker_reports torrent, denunciante, fundamento, estado, decisão Denúncias e direitos autorais

Peers ativos não devem ser gravados em uma linha PostgreSQL a cada announce. Eles pertencem ao sidecar/Redis e expiram por TTL. PostgreSQL recebe somente totais agregados, conclusões e eventos administrativos que precisem sobreviver.

Tópico como unidade editorial

Cada torrent aprovado pode corresponder a um tópico numa categoria restrita. O primeiro post contém descrição, origem, licença, instruções e imagens; comentários funcionam normalmente. O plugin associa o topic_id ao registro técnico e injeta acima das respostas:

  • botão de baixar .torrent;
  • tamanho e número de arquivos;
  • seeders, leechers e concluídos;
  • estado de aprovação;
  • categoria e tags;
  • crédito ao uploader;
  • alerta de ausência de seed;
  • ações de denúncia para membros;
  • ações de moderação para equipe.

Para navegação em volume, uma rota própria /torrents deve oferecer filtros por categoria, atividade, tamanho, data e estado. Não convém tentar transformar a lista normal de tópicos em uma tabela de tracker por meio de alterações frágeis no frontend.

Fluxos completos

1. Entrada e autorização do membro

  1. O Discourse opera como comunidade fechada, com convite ou aprovação manual.
  2. O usuário confirma e-mail e configura 2FA conforme a política.
  3. Um job cria private_tracker_accounts com estado pending ou enabled.
  4. A passkey aleatória é produzida com CSPRNG, mostrada somente quando necessária e armazenada como digest pesquisável, nunca em texto nos logs.
  5. O sidecar recebe uma atualização assinada ou atualiza seu cache sob demanda.
  6. Suspender o usuário no Discourse revoga imediatamente o acesso no tracker.

Não use o trust_level como única autorização. Níveis de confiança mudam por atividade social; acesso ao tracker deve ser um estado explícito ou grupo administrável.

2. Envio de um torrent

  1. O uploader cria localmente o .torrent dos arquivos que já possui e pretende semear.
  2. Envia o metainfo por formulário do plugin, junto de descrição e comprovação de autorização quando aplicável.
  3. O plugin limita tamanho, lê bytes com biblioteca bencode e rejeita estruturas malformadas, profundas ou excessivas.
  4. Valida nomes, caminhos, tamanhos, número de arquivos, peças, trackers existentes e versões v1/v2.
  5. Garante private=1. Se precisar acrescentá-lo, informa que o info-hash muda e gera uma nova versão canônica.
  6. Remove announce-list, nodes e trackers externos. Web seeds só permanecem quando aprovados.
  7. Calcula o info-hash diretamente dos bytes canônicos do dicionário info.
  8. Verifica duplicidade e cria um tópico em estado de revisão.
  9. Um moderador aprova conteúdo, categoria e licença.
  10. O plugin envia o info-hash para a lista permitida do sidecar.
  11. O uploader baixa sua cópia personalizada e inicia o seed.

O parser não deve confiar em nomes de arquivos. Caminhos absolutos, .., caracteres nulos, componentes reservados e árvores v2 inválidas precisam ser rejeitados ou normalizados apenas para exibição. A BEP 52 alerta explicitamente para sanitização de . e .. e para validação canônica antes de recalcular hashes.

3. Download personalizado

  1. O membro abre o tópico e solicita o arquivo.
  2. O controller verifica login, estado da conta, permissão da categoria e política de download.
  3. Recupera o metainfo canônico.
  4. Substitui somente os campos superiores de tracker por uma URL com a passkey atual.
  5. Reencoda de forma canônica sem modificar o dicionário info.
  6. Confere novamente o info-hash antes de responder.
  7. Envia Content-Type: application/x-bittorrent, Content-Disposition: attachment e Cache-Control: private, no-store.
  8. Registra a entrega sem registrar a passkey bruta.

Esse arquivo não deve usar uma URL temporária que expire em poucas horas: o cliente precisa anunciar enquanto estiver semeando durante dias ou meses. A passkey é revogável, mas persistente até rotação.

4. Announce

  1. O cliente solicita GET /announce/{passkey} com os campos do protocolo.
  2. O proxy encaminha o IP real somente a partir de proxies confiáveis.
  3. O sidecar limita tamanho e sintaxe antes de qualquer acesso externo.
  4. O middleware transforma a passkey em digest e consulta cache.
  5. Verifica conta habilitada, info-hash permitido, intervalo mínimo, peer_id, porta e contadores.
  6. Calcula o delta em relação à sessão anterior do mesmo usuário, torrent e peer.
  7. Atualiza o peer ativo com TTL e escolhe uma amostra de peers da swarm.
  8. Responde imediatamente em bencode.
  9. Em PostHook, publica o delta de contabilidade numa fila.
  10. Um job agrega os eventos e atualiza os totais no PostgreSQL.

5. Rotação de passkey

  1. Usuário ou moderador solicita rotação por suspeita de vazamento.
  2. O plugin gera nova credencial, aumenta passkey_version e invalida a anterior.
  3. O sidecar recebe revogação de alta prioridade.
  4. Torrents antigos passam a receber failure reason sem revelar detalhes da conta.
  5. O usuário baixa novamente os metadados ou substitui o tracker no cliente.
  6. O evento fica na auditoria administrativa.

Uma opção avançada é passkey diferente por torrent ou por download. Ela reduz o impacto de vazamento, mas multiplica registros e torna a experiência de rotação mais trabalhosa. Para o MVP, uma passkey por usuário é suficiente; passkeys por torrent podem vir depois.

6. Remoção e denúncia

  1. A denúncia entra no plugin e pode ocultar preventivamente o botão de download.
  2. O moderador altera o torrent para blocked.
  3. O sidecar remove o info-hash da lista permitida.
  4. Announces passam a falhar e nenhum peer novo é apresentado.
  5. O metainfo e os registros administrativos são preservados pelo prazo da política, sem manter conteúdo que nunca esteve no servidor.
  6. A decisão, fundamento e comunicação ficam auditáveis.

Bloquear o tracker não apaga cópias já distribuídas nem impede peers que já se conhecem de continuar uma conexão existente. A ação limita novas descobertas e demonstra resposta administrativa; ela não é um mecanismo de revogação criptográfica.

Contrato entre Discourse e sidecar

O sidecar não deve consultar a API pública do Discourse em cada announce. Isso transferiria latência e carga para o fórum. Use sincronização orientada a eventos e cache local.

Comandos do plugin para o sidecar

PUT    /internal/v1/users/{user_id}
DELETE /internal/v1/users/{user_id}/passkeys/{version}
PUT    /internal/v1/torrents/{info_hash}
DELETE /internal/v1/torrents/{info_hash}
POST   /internal/v1/policies/reload
GET    /internal/v1/health

Eventos do sidecar

{
  "event_id": "01J...",
  "user_id": 42,
  "torrent_id": 913,
  "peer_fingerprint": "digest",
  "uploaded_delta": 1048576,
  "downloaded_delta": 0,
  "seed_seconds_delta": 1800,
  "event": "update",
  "observed_at": "2026-08-24T18:00:00Z"
}

Use mTLS ou HMAC com timestamp e nonce para chamadas internas. Tokens administrativos nunca devem aparecer em query strings. A API de administração fica numa rede privada, inacessível pela internet. Eventos têm IDs únicos e processamento idempotente; reenviar um lote não pode duplicar créditos.

Cache e consistência

  • Cache positivo de usuário/passkey: curto, por exemplo 5 minutos.
  • Cache negativo: muito curto, para não perpetuar erro de sincronização.
  • Banimentos e rotações: canal de invalidação imediato.
  • Info-hashes permitidos: snapshot local mais eventos incrementais.
  • Falha do Discourse: tracker continua com cache por uma janela limitada.
  • Falha da fila: eventos ficam em spool durável no sidecar.
  • Reconciliação: job diário compara totais, torrents e usuários.

Contabilidade e ratio

Os campos uploaded e downloaded são informados pelo próprio cliente. Portanto, ratio de tracker privado é uma métrica útil de incentivo, mas não uma medição criptograficamente confiável. Clientes modificados podem mentir.

Regras mínimas para reduzir fraude e erro

  • Contadores devem ser inteiros não negativos e monotônicos dentro da sessão.
  • Reinício do cliente abre uma nova sessão controlada, não um delta negativo.
  • Delta máximo deve ser compatível com tempo decorrido e um teto configurável.
  • downloaded + left deve ser plausível em relação ao tamanho, admitindo rechecks.
  • completed deve ser idempotente.
  • O mesmo peer_id em locais incompatíveis gera alerta, não banimento automático.
  • Muitas passkeys no mesmo IP não significam fraude por si só: NAT e seedboxes são comuns.
  • Mudança de IP também não é fraude por si só: conexões móveis e VPNs mudam.
  • Créditos especiais, freeleech e double upload devem ser aplicados no agregador, com versão da política registrada.
  • Correções administrativas precisam gerar lançamentos de ajuste, não edição silenciosa.

Política inicial recomendada

Não comece com banimento automático por ratio. Nas primeiras versões, exiba upload, download, tempo de seed e torrents semeados, mas use intervenções graduais:

  1. aviso;
  2. limitação de novos downloads;
  3. período de recuperação;
  4. revisão humana;
  5. suspensão somente após evidência consistente.

Um sistema pequeno ganha mais com metas de tempo de seed e pedidos de reseed do que com uma economia complexa de bônus.

Segurança

Ameaças prioritárias

Ameaça Consequência Controle principal
Vazamento de passkey Terceiro anuncia e atribui tráfego à vítima rotação imediata, digest no banco, logs redigidos, HTTPS
.torrent malformado consumo de CPU/memória, parser crash ou caminhos perigosos limites rígidos, parser canônico, fuzzing, processamento isolado
Announce flood indisponibilidade do tracker ou fórum sidecar isolado, rate limits por token/IP, intervalos e proteção de borda
Falsificação de contadores ratio e reputação incorretos deltas monotônicos, limites plausíveis, alertas e revisão
Enumeração de swarms exposição de catálogo e atividade info-hash whitelist, scrape autenticado, sem full scrape público
Usuário suspenso ainda ativo acesso após banimento invalidação push e TTL curto
Proxy mal configurado IPs falsos nos logs e peers confiar apenas em endereços explícitos do proxy
Logs contendo segredos comprometimento em backup ou observabilidade filtro de URL, nunca registrar caminho completo do announce
CSRF em administração alteração de política controles nativos do Discourse, POST autenticado e permissões Guardian
SSRF por web seed servidor acessa destinos internos não buscar URLs do torrent; allowlist se houver verificação externa
XSS em nomes de arquivos ataque à interface do catálogo escapar toda saída; nomes são bytes não confiáveis
Plugin quebrado após atualização perda de acesso ou exposição CI contra versões suportadas e staging antes de atualizar Discourse

Passkeys

  • Gere pelo menos 32 bytes aleatórios e represente em base64url ou hexadecimal.
  • Não derive do ID do usuário, e-mail ou senha.
  • Armazene HMAC-SHA-256(chave_do_servidor, passkey) para permitir busca sem guardar o segredo bruto.
  • Separe a chave HMAC dos bancos e backups.
  • Nunca mostre a passkey em HTML reutilizável, analytics, referer ou logs.
  • O endpoint de download insere a credencial diretamente no arquivo.
  • Permita rotação por usuário e por moderador.
  • Apague a passkey de mensagens de erro e páginas de suporte.
  • Configure Nginx, CDN e APM para registrar /announce/[REDACTED].

Uploads seguros

O código atual do Discourse possui uploads seguros ligados ao contexto de posts privados e pode produzir URLs assinadas em armazenamento externo. A configuração exige armazenamento S3 antes de habilitar secure_uploads, conforme as validações do próprio projeto. Para esta aplicação há duas escolhas válidas:

  1. Usar uploads seguros do Discourse para o metainfo canônico, garantindo que o tópico esteja numa categoria restrita.
  2. Usar um bucket privado exclusivo do plugin e servir o arquivo somente pelo controller personalizado.

A segunda opção torna a personalização e o controle de cache mais explícitos. Em nenhuma delas o objeto canônico deve conter passkey.

Privacidade inerente ao BitTorrent

Membros de uma swarm recebem IP e porta de outros membros. O operador também associa conta, passkey, info-hash, IP, cliente, tempo e contadores. Isso forma um conjunto sensível do ponto de vista de privacidade operacional, mesmo quando o conteúdo é legítimo.

O produto deve explicar claramente:

  • quais dados são coletados;
  • para que são usados;
  • por quanto tempo ficam;
  • quem da equipe pode vê-los;
  • que outros peers verão o IP durante a transferência;
  • como solicitar acesso, correção e eliminação quando aplicável;
  • quais dados precisam ser preservados por obrigação ou defesa de direitos.

Aspectos jurídicos no Brasil

Direitos autorais

A Lei nº 9.610/1998 reserva ao titular formas de reprodução, distribuição e disponibilização de obras. Ser um grupo fechado ou exigir convite não transforma automaticamente uma cópia não autorizada em uso permitido.

Uma operação defensável deve aceitar somente:

  • material criado pelo uploader;
  • software e mídia sob licença que permita redistribuição;
  • domínio público verificado;
  • conteúdo institucional com autorização documentada;
  • backups e datasets cuja circulação entre membros esteja permitida.

O formulário de envio deve exigir declaração de origem e base de autorização. Categorias de maior risco podem exigir prova documental antes da publicação. Deve haver termos, política de retirada, canal de contato e registro das decisões.

Registros e responsabilidade do provedor

O Marco Civil da Internet, Lei nº 12.965/2014, contém regras sobre sigilo, disponibilização de registros e guarda de registros de acesso para determinados provedores de aplicações constituídos como pessoa jurídica, em atividade organizada, profissional e com fins econômicos. A incidência concreta e os prazos aplicáveis dependem da natureza da operação; devem ser definidos com assessoria jurídica antes do lançamento.

Não confunda retenção obrigatória de registros com autorização para guardar tudo indefinidamente. Logs técnicos, eventos de moderação e contabilidade devem ter finalidades e prazos diferentes.

LGPD

A LGPD, Lei nº 13.709/2018, exige finalidade, necessidade, segurança, transparência e direitos dos titulares. Neste sistema, IP deixa de ser um identificador técnico isolado porque está diretamente associado à conta, ao histórico e à atividade.

A ANPD publica guia e checklist de segurança para agentes de pequeno porte. A página atual de comunicação de incidentes explica que incidentes confirmados envolvendo dados pessoais e capazes de causar risco ou dano relevante podem exigir comunicação à ANPD e aos titulares.

Antes de operar:

  • faça inventário de dados e bases legais;
  • documente retenção;
  • limite acesso administrativo;
  • proteja backups;
  • estabeleça canal para titulares;
  • prepare resposta a incidentes;
  • avalie um RIPD se escala, monitoramento ou risco justificarem;
  • obtenha revisão jurídica específica.

Infraestrutura recomendada

Ambiente pequeno

VPS 1: Discourse oficial em contêiner
  PostgreSQL + Redis + Sidekiq + plugin

VPS 2: tracker sidecar
  Chihaya customizado + Redis + Prometheus

Armazenamento:
  bucket S3 compatível privado para metainfo e backups

Seed inicial:
  qBittorrent ou Transmission em servidor separado

É possível começar numa única máquina com contêineres separados, mas separar o tracker reduz o impacto de flood e facilita escalar. O domínio também deve ser separado, por exemplo forum.exemplo.org e tracker.exemplo.org.

Componentes

Componente Escolha inicial Motivo
Comunidade Discourse self-hosted plugin de servidor exige controle da instalação
Tracker Chihaya com middleware próprio desenho extensível e licença permissiva
Catálogo tabelas do plugin + tópicos une metadados estruturados e discussão
Banco durável PostgreSQL do Discourse integra usuários e catálogo
Estado efêmero Redis separado do tracker peers e cache não disputam com o fórum
Fila Redis Streams, NATS JetStream ou HTTP em lotes com spool entrega de eventos e retentativa
Objetos S3 compatível privado metainfo canônico, backup e URLs controladas
Proxy Nginx ou HAProxy TLS, IP real, limites e logs redigidos
Métricas Prometheus + Grafana saúde do tracker e capacidade
Logs Loki ou equivalente, com redaction investigação sem expor passkeys
Seeder qBittorrent/Transmission isolado disponibilidade inicial do conteúdo autorizado

Não compartilhe automaticamente o Redis do Discourse com o tracker. Use instância, ACL ou pelo menos credenciais, namespace e limites separados. O tracker deve poder falhar sem corromper sessões e filas do fórum.

Etapas de desenvolvimento

Fase 0 — Prova técnica, 3 a 7 dias

  • Subir Discourse de desenvolvimento.
  • Criar plugin pelo esqueleto oficial.
  • Associar um registro de torrent a um tópico.
  • Aceitar um .torrent de teste autorizado.
  • Personalizar apenas o campo announce.
  • Executar um tracker local simples.
  • Transferir um pequeno arquivo entre dois clientes.
  • Confirmar que DHT e PEX ficam desativados.

Saída: prova de que metainfo, passkey e experiência no tópico funcionam.

Fase 1 — Protótipo funcional, 2 a 4 semanas

  • Contas de tracker ligadas a usuários.
  • Passkey por usuário e rotação.
  • Upload, parsing e aprovação manual.
  • Catálogo /torrents básico.
  • Download personalizado.
  • Sidecar HTTPS com lista permitida.
  • Seeders/leechers na página.
  • Suspensão sincronizada.
  • Logs redigidos e testes principais.

Decisão importante: nesta fase, contabilize atividade para observação, mas não aplique punição automática por ratio.

Fase 2 — MVP confiável, 6 a 10 semanas adicionais

  • Chihaya e middlewares próprios.
  • Fila durável e eventos idempotentes.
  • Contabilidade por usuário/torrent.
  • Seed time, reseed e políticas graduais.
  • Painel administrativo.
  • Denúncias e retirada.
  • Métricas, alertas e backups.
  • Fuzz tests para bencode.
  • Testes com qBittorrent, Transmission, Deluge, rTorrent e libtorrent.
  • Staging para atualizações do Discourse.

Fase 3 — Produção ampliada, 2 a 4 meses adicionais

  • IPv6 completo.
  • Réplicas do tracker e Redis HA.
  • Passkey por torrent opcional.
  • Clientes permitidos ou observados.
  • Freeleech, bônus e slots, apenas se a comunidade realmente precisar.
  • API documentada para automação.
  • Exportação e exclusão de dados.
  • Auditoria externa de segurança.
  • Procedimentos jurídicos e de incidentes testados.

As durações são estimativas para uma pessoa experiente em Rails/Discourse e Go. Quem estiver aprendendo as duas plataformas deve multiplicar os prazos. A complexidade principal não é desenhar a tela; é manter autorização e contabilidade corretas sob concorrência, falhas e clientes não confiáveis.

Testes indispensáveis

Plugin

  • Migrações em instalação nova e atualização.
  • Permissões para anônimo, membro, uploader, moderador e administrador.
  • Download negado após suspensão.
  • Passkey nunca presente em serializer, log ou HTML.
  • Info-hash igual antes e depois da personalização do announce.
  • Upload duplicado e torrent bloqueado.
  • Tópico movido entre categorias com permissões diferentes.
  • Remoção, restauração e retenção de metainfo.
  • Compatibilidade com versão estável e tests-passed do Discourse.

Parser

  • Bencode truncado, chaves fora de ordem e inteiros inválidos.
  • Estruturas profundamente aninhadas.
  • Milhões de arquivos declarados em objeto pequeno.
  • Tamanhos negativos, overflow e somas inconsistentes.
  • Caminhos absolutos, .., caracteres nulos e Unicode problemático.
  • v1, v2 e híbrido.
  • private=0, ausente e duplicado.
  • Múltiplos trackers, DHT nodes e web seeds.
  • Round-trip preservando exatamente o dicionário info.

Tracker

  • Passkey válida, inválida, revogada e rotacionada.
  • Torrent permitido, pendente e bloqueado.
  • started, atualização, completed, stopped e timeout.
  • Dois peers atrás do mesmo NAT.
  • IPv4 e IPv6.
  • Contadores reiniciados após crash do cliente.
  • Reenvio do mesmo lote sem duplicar créditos.
  • Fórum indisponível e fila indisponível.
  • Flood, announce antes do intervalo e payload excessivo.
  • Nenhuma passkey em métricas ou logs.

Teste de ponta a ponta

  1. Criar arquivo aleatório autorizado.
  2. Gerar torrent privado.
  3. Publicar e aprovar.
  4. Baixar como usuário A e iniciar seed.
  5. Baixar como usuário B e concluir transferência.
  6. Conferir peers e contadores.
  7. Rotacionar passkey de B e observar falha controlada.
  8. Baixar novamente e recuperar acesso.
  9. Bloquear torrent e confirmar que novos announces falham.
  10. Restaurar a partir de backup em ambiente limpo.

Critérios de aceitação do MVP

O produto só deve ser chamado de tracker privado funcional quando:

  • nenhum torrent não aprovado consegue anunciar;
  • nenhum membro suspenso continua autenticando após a janela definida;
  • .torrent baixado por um usuário não contém a passkey de outro;
  • personalizar o announce não muda o info-hash;
  • passkeys não aparecem em logs, analytics ou erros;
  • eventos reenviados não duplicam tráfego;
  • o tracker continua respondendo durante indisponibilidade curta do fórum;
  • a falha do tracker não derruba o Discourse;
  • anônimos não veem catálogo, arquivos ou estatísticas;
  • a equipe consegue bloquear torrent e conta rapidamente;
  • backup e restauração foram ensaiados;
  • política de conteúdo, privacidade e denúncia está publicada.

Custos e capacidade

Para uma comunidade pequena, o custo de infraestrutura tende a ser modesto porque o tracker não transporta os arquivos; ele troca mensagens pequenas de descoberta. O tráfego pesado ocorre entre peers e no seeder inicial.

Uma implantação inicial pode operar com:

  • Discourse em configuração compatível com suas exigências oficiais;
  • sidecar com 1 a 2 vCPU e 1 a 2 GB de RAM;
  • Redis pequeno para peers;
  • armazenamento de objetos quase irrelevante em volume, pois .torrent é pequeno;
  • monitoramento e backups.

Esses números são estimativas, não requisitos garantidos. Capacidade depende de usuários simultâneos, intervalo de announce, número de torrents e política de retenção. Faça teste de carga com a distribuição esperada, não apenas benchmark de requisições vazias.

O verdadeiro custo está no desenvolvimento, atualizações do Discourse, moderação, segurança e gestão jurídica. Um tracker tecnicamente leve pode ser operacionalmente exigente.

O que não construir no começo

  • UDP autenticado.
  • Aplicativo móvel próprio.
  • Streaming no navegador.
  • Integrações com debrid.
  • DHT privado customizado.
  • Sistema de moedas e loja de bônus.
  • Convites negociáveis.
  • Ranks automáticos complexos.
  • Scraper de terceiros.
  • Metadados automáticos para todas as mídias.
  • IA moderando direitos autorais.
  • Cliente BitTorrent próprio.
  • Alterações profundas no núcleo do Discourse.

Esses itens aumentam superfície de abuso e manutenção sem provar o valor central: comunidade Discourse, publicação controlada e distribuição P2P privada.

Alternativa pragmática sem desenvolver tudo

Se o objetivo principal for operar um tracker convencional rapidamente, instale UNIT3D e mantenha o Discourse como comunidade externa. Use um provedor de identidade comum, links cruzados e criação automática de tópicos para torrents aprovados. É menos elegante, mas reduz muito o trabalho inicial.

Se o objetivo for realmente criar um produto novo e potencialmente publicável para outras comunidades Discourse, construa o plugin + sidecar. Esse projeto tem uma proposta clara: transformar tópicos privados em distribuições P2P autorizadas sem substituir a comunidade por um frontend clássico de tracker.

Recomendações práticas

Escolha recomendada

  1. Nomeie provisoriamente o projeto discourse-private-tracker.
  2. Faça o plugin ser a autoridade de usuário, catálogo e política.
  3. Use Chihaya com middleware próprio como sidecar de produção.
  4. Comece apenas com announce HTTPS e torrents v1 privados.
  5. Use tópicos como páginas editoriais e uma rota /torrents para filtros.
  6. Gere o .torrent personalizado no download; nunca armazene passkeys nos objetos.
  7. Mantenha peers em Redis e totais consolidados em PostgreSQL.
  8. Sincronize bloqueios imediatamente e demais dados por eventos idempotentes.
  9. Não puna ratio automaticamente no MVP.
  10. Restrinja o projeto a conteúdo autorizado e implemente retirada antes do lançamento.

Primeira especificação de produto

O primeiro lançamento precisa de apenas seis telas:

  1. catálogo de torrents;
  2. página do torrent integrada ao tópico;
  3. formulário de envio;
  4. fila de aprovação;
  5. painel pessoal com atividade e rotação de passkey;
  6. painel administrativo de usuários, torrents e saúde do tracker.

Primeira decisão de engenharia

Antes de escrever toda a interface, construa um experimento vertical:

tópico privado -> upload canônico -> aprovação -> download personalizado
-> qBittorrent A -> announce -> qBittorrent B -> transferência -> estatística no tópico

Se esse percurso funcionar com dois clientes reais, passkey rotacionável e bloqueio imediato, a ideia está tecnicamente provada. Só então vale investir em ratio, badges e automações.

Conclusão

Transformar o Discourse em um tracker privado é possível e pode resultar num produto interessante. O Discourse resolve justamente a parte que muitos softwares de tracker tratam de maneira secundária: comunidade, conversação, identidade, confiança e moderação. O protocolo BitTorrent acrescenta uma forma eficiente de distribuir arquivos sem transformar o servidor web num repositório de grandes downloads.

A implementação correta não coloca o announce dentro do fórum. Ela cria um plugin de integração profundo e um tracker sidecar especializado. Entre as bases pesquisadas, Chihaya oferece o melhor encaixe arquitetural; Torrust é a alternativa moderna; bittorrent-tracker é o caminho de protótipo; e UNIT3D é a referência para funções e regras, mas não deve ser fundido ao Discourse no primeiro momento.

O projeto é de dificuldade média para demonstrar e alta para operar com segurança. Um protótipo legítimo pode surgir em poucas semanas. Um tracker público para terceiros, com contabilidade confiável, políticas, privacidade, atualização contínua e resistência a abuso, é um produto de meses. Ainda assim, a ideia é tecnicamente coerente, relativamente original e vale um protótipo vertical.

Fontes consultadas


Nota sobre atualidade

Pesquisa concluída em 24 de agosto de 2026. Discourse, Chihaya, Torrust, UNIT3D e suas APIs evoluem continuamente. Confirme versões, licenças, compatibilidade e documentação oficial antes de iniciar a implementação. Aspectos jurídicos exigem avaliação profissional aplicada ao conteúdo, à operação e à jurisdição escolhida.