- Rayfish é a primeira versão de uma VPN mesh P2P entre dispositivos de usuários, sem servidores nem contas, mantendo o estado da rede como registros assinados armazenados pelos membros
- Ao eliminar o plano de controle central, a rede continua funcionando após a entrada, sem conta de empresa, operador ou servidor de coordenação que precise ficar sempre ligado
- O Iroh v1 serviu de base para o lançamento ao cuidar de conexões QUIC criptografadas, travessia de NAT, hole punching e fallback por relay quando não há caminho direto
- Atualmente oferece entrada simultânea em várias redes isoladas, entrada por código de convite ou aprovação, Magic DNS, firewall por dispositivo, provisionamento declarativo de frota, conexões 1:1 e transferência de arquivos
- Pode perder para o Tailscale em maturidade e throughput, e também não é um SDK, mas o foco está em quem precisa de uma rede privada sem parte central
O problema que o Rayfish quer resolver
- Rayfish é uma VPN mesh P2P para criar redes privadas entre dispositivos
- Funciona sem servidor intermediário nem empresa da qual você precise depender para mantê-la operando
- O usuário recebe chaves, os dispositivos se encontram por meio dessas chaves, e a rede criada pertence às pessoas que estão nela
Um design sem plano de controle central
- Muitas VPNs modernas dependem de um plano de controle operado por uma empresa
- A empresa decide os membros da rede e as políticas
- A empresa continua no fluxo mesmo enquanto os dispositivos se comunicam
- Se a empresa encerrar as operações, aumentar preços ou romper a relação com clientes, fica difícil a rede privada continuar sendo totalmente do usuário
- O Rayfish remove contas e o operador central
- O estado da rede é um registro assinado que qualquer membro pode repassar a outro membro
- Mesmo que os criadores do Rayfish desapareçam, as redes existentes continuam funcionando
Como lida com várias redes em um único dispositivo
- O Rayfish parte da premissa de que o usuário não usa apenas uma rede plana
- Um mesmo dispositivo pode pertencer ao mesmo tempo a uma rede de amigos, uma de side project e outra de trabalho
- A implementação roda por trás de um único processo e de uma única interface virtual
- Cada rede fica isolada das outras, e o usuário se torna membro pleno de todas as redes em que entrar
Um lançamento viabilizado pelo Iroh v1
- O Rayfish delega ao Iroh as partes difíceis da camada de transporte
- Conexões QUIC criptografadas entre peers
- Travessia de NAT
- Hole punching
- Fallback por relay quando não há caminho direto
- O Iroh v1 ofereceu a estabilidade necessária para que a camada de transporte não ficasse oscilando durante o desenvolvimento, tornando este lançamento possível
- O próximo desafio é refinar as ferramentas iniciais até virarem algo que possa rodar em produção sem atrito
Um spin-off da Field Technologies
- Rayfish é um projeto derivado da empresa de trading de alta frequência Field Technologies
- Ele se apoia na experiência interna de construir repetidamente descoberta de dispositivos, consenso de estado compartilhado e comunicação rápida e privada ao lidar com sistemas distribuídos
- Essa infraestrutura interna foi criada principalmente para não depender do plano de controle de outras empresas
- O Rayfish foi uma ideia cultivada por mais de 4 anos, mas sua natureza sem operador central atrasou a transformação em produto por não haver um ponto claro de cobrança
- No futuro, pode se expandir para problemas corporativos como gestão de frota e auditoria, mas esses recursos ainda não existem
Recursos disponíveis hoje
-
Estrutura ponto a ponto
- O Rayfish é ponto a ponto, não hub-and-spoke
- Todos os membros se conectam diretamente a todos os outros membros
- A associação não é um valor consultado em um servidor, mas sim um registro assinado que cada membro carrega consigo
- O coordenador que criou a rede só é necessário ao aceitar novos membros; depois da entrada, a rede funciona sem ninguém central
-
Redes fechadas e formas de entrada
- A rede é fechada por padrão
- O coordenador pode adicionar novos membros de duas formas
- Código de convite de uso único
- Aprovação em tempo real de um pedido de entrada
- Se for necessário uma rede pública, é possível abrir o acesso com
ray create --open, e nesse caso basta o room id para entrar
- Os membros que entram podem ser acessados por IPs estáveis e nomes Magic DNS amigáveis
- O hostname padrão pode ser definido com
ray up --hostname dario, e --hostname pode ser sobrescrito por rede
ray up --hostname dario
ray create --name prod
ray invite prod --hostname web
ray join <code>
-
Firewall por dispositivo
- Cada dispositivo tem seu próprio firewall e decide por conta própria o que aceitar e de quem aceitar
- O coordenador pode publicar regras de firewall recomendadas por rede
- Cada host pode aceitar as regras ou escolher a instalação automática
- É uma forma de fornecer padrões compartilhados sem um servidor central de políticas que todos sejam obrigados a seguir
-
Provisionamento de frota
- Para vários dispositivos, é possível definir e aplicar redes e regras de firewall por meio de um arquivo declarativo
- A especificação é um mapa
networks:, e sob cada rede ficam os peers e portas permitidos por host
networks:
prod:
web:
allows:
"*": "tcp:443"
db:
allows:
web: "tcp:5432"
game:
"*":
allows:
"*": "tcp:6969"
ray apply deploy.yaml --dry-run
ray apply deploy.yaml --invite-missing
- Para a frota, é possível criar chaves reutilizáveis sem emitir códigos por máquina
ray invite prod --reusable
ray join <key> --hostname web01 --auto-accept-firewall
- Revogar a chave impede apenas novas entradas, sem afetar os servidores que já entraram
- O
ray apply funciona de forma idempotente, então o arquivo de especificação permanece como estado de referência da frota
-
Conexões 1:1 e transferência de arquivos
- Quando não for necessário criar uma rede separada,
ray connect cria uma conexão 1:1 baseada em contact ID
ray contact id
ray connect <their-contact-id>
ray connections approve <id>
- Após a aprovação, uma rede privada de 2 peers é criada automaticamente
- Magic DNS, firewall e recursos de mesh funcionam da mesma forma, e em
ray status isso aparece como [direct]
- O contact ID pode ser rotacionado, e as conexões já existentes continuam funcionando
- Como já existe um caminho autenticado e criptografado entre os membros, é possível enviar arquivos sem serviço adicional
ray send ./build.tar.gz web01
ray files accept 1
Diferenças em relação ao Tailscale
- Tailscale e Rayfish oferecem IPs estáveis, Magic DNS, travessia de NAT e plano de dados P2P
- A maior diferença é onde fica o controle
- O Tailscale usa um plano de controle como o servidor de coordenação do Tailscale ou o Headscale self-hosted
- O Rayfish não tem plano de controle central; o estado da rede fica em registros assinados propagados via P2P
- O plano de dados também é diferente
- O Tailscale usa WireGuard rodando no kernel
- O Rayfish usa datagramas Iroh/QUIC em espaço de usuário
- Em velocidade, o Tailscale costuma levar vantagem
- Como o WireGuard roda no kernel, a diferença pode ficar evidente em links rápidos e transferências grandes
- O Rayfish troca um pouco de throughput bruto por uma arquitetura sem parte central
- O Rayfish usa um par de chaves no disco como identidade, e não conta ou SSO
- O Rayfish é novo e focado no mínimo viável; o Tailscale é mais maduro e tem um conjunto mais amplo de recursos
Diferenças em relação ao Yggdrasil
- O Yggdrasil oferece uma rede IPv6 criptografada de ponta a ponta sem autoridade central
- A diferença aparece na etapa final que o usuário precisa operar diretamente
- O Yggdrasil fornece uma única rede global com endereços IPv6
- O Rayfish fornece redes privadas separadas, criadas pelo usuário e com entrada controlada por ele
- O Rayfish inclui facilidades como códigos de convite, nomes DNS amigáveis, firewall por rede e prompts de aprovação de entrada
- O Yggdrasil é adequado para engenheiros com conhecimento de redes, enquanto o Rayfish também mira quem quer montar facilmente uma rede privada para poucas pessoas
O que dá e o que não dá para construir
- O Rayfish não é uma biblioteca, e sim uma ferramenta pronta
- Não pode ser embutido dentro de uma aplicação como um SDK
- Ele é adequado para cenários em que dispositivos com Rayfish instalado precisam se comunicar de forma privada
- Servidores P2P de jogos acessados por amigos por nome
- APIs internas não expostas à internet pública
- Destinos de backup
- Apps de chat ou chamada entre membros da rede
- Um banco de dados compartilhado entre duas equipes que não devem se enxergar mutuamente
- As aplicações podem acessar peers por
name.network.ray
- Pessoas externas sem Rayfish instalado não conseguem acessar a rede, e não há gateway para terceiros
Exemplos de configuração real
-
Quando dois departamentos compartilham um banco de dados
- Mantendo
payments e analytics como redes separadas, os dois departamentos não conseguem se ver
- Apenas a máquina do banco de dados entra nas duas redes
- Em cada rede, configura-se um firewall recomendado para abrir apenas as portas necessárias
networks:
payments:
db:
allows:
"*": "tcp:8123,tcp:9000"
analytics:
db:
allows:
"*": "tcp:8123,tcp:9000"
- Cada equipe acessa por
db.payments.ray ou db.analytics.ray
- As duas redes não sabem da existência uma da outra, e o controle de acesso é montado com separação de rede e host compartilhado, sem auditoria central de ACL
-
Servidor de Minecraft para amigos
- Ao criar uma rede fechada e convidar os amigos, eles podem se conectar por nome sem IP, port forwarding nem DNS dinâmico
ray create --name mc
ray invite mc
- Os clientes se conectam a
mc-host.mc.ray:25565
-
Grupo fechado em que todos abrem portas
- Se todos os membros precisarem abrir a porta TCP 6969, o administrador pode sugerir a regra uma vez
ray firewall suggest mc --subject '*' --allow '*:tcp:6969'
- Cada membro revisa a regra sugerida e a aceita ou rejeita
ray firewall pending mc
ray firewall accept mc
- Sugestões de firewall não são regras obrigatórias, e o membro pode recusá-las se não quiser
Segurança e endereçamento
- Os endereços IP não são atribuídos por um servidor; eles são derivados da identidade criptográfica de cada peer
- Conflitos de endereço são extremamente raros, mas se acontecerem, o coordenador coloca o segundo peer no próximo slot livre
- Todos os peers convergem de forma determinística para a mesma atribuição de endereços sem um alocador central
- O Rayfish estrutura a segurança em dois elementos, em vez de uma ACL central
- Segmentação, em que só peers da mesma rede conseguem se comunicar
- Firewall por rede em cada dispositivo
- Para isolar
prod e dev, basta criá-las como duas redes distintas
- Hosts que pertencem a várias redes carregam seu próprio firewall em cada uma delas
É preciso abrir servidor e portas?
- Não é necessário hospedar um servidor de controle separado
- O coordenador que criou a rede pode ficar offline depois que todos os membros tiverem entrado
- O Iroh cuida da travessia de NAT e do hole punching, e usa fallback por relay criptografado quando um caminho direto é impossível
- Se você controla o roteador e quer um caminho direto garantido para uma máquina específica, pode encaminhar a porta UDP fixa do Rayfish, mas isso é opcional
Próximos passos e quando não faz sentido
- Hoje ele é oferecido como ferramenta de linha de comando para desktop e servidores
- O próximo trabalho é expandir para dispositivos que os usuários realmente carregam consigo
- Cliente Android
- Cliente iOS
- Aplicativo de desktop de verdade
- Ao mesmo tempo, o projeto está fortalecendo os recursos existentes para que possam ser usados em produção sem atrito
- Se Tailscale, VPN corporativa ou uma mesh WireGuard montada manualmente já funcionam bem para você, há pouco motivo para migrar para Rayfish
- O Rayfish é mais novo, tem menos recursos, e muitas coisas já são oferecidas com mais polimento pelas ferramentas existentes
- O que o Rayfish elimina é uma coisa
- Contas
- Uma empresa capaz de interromper a rede
- Um servidor de controle que precisa ficar sempre ligado
- Um banco de dados de políticas operado por terceiros
Como começar
- A instalação começa com um comando de uma linha
curl -fsSL https://rayfish.xyz/install.sh | sh
- A criação da primeira rede e o processo de convite continuam na documentação
1 comentários
Comentários no Lobste.rs
Gosto muito do fato de o Rayfish partir, desde o início, do pressuposto de lidar com mais de uma rede ao mesmo tempo.
No Tailscale, isso não parece ser uma prioridade, então pode ser uma vantagem bem grande.
A parte sobre ter surgido como spin-off de uma empresa de trading de alta frequência foi inesperada, e dizer que o Tailscale vence em velocidade porque “o plano de dados do WireGuard roda no kernel” está errado. O Tailscale não usa WireGuard no kernel, mas as pessoas continuam tendo essa impressão.
Ele disse que “as ideias, o produto e a escrita são meus”, mas é uma pena haver um
CLAUDE.mdno repositório. Dito isso, olhando o resumo de contribuições, o clod tem 1.017++ / 383-- linhas, enquanto o autor tem 104.786++ / 47.064-- linhas, então a maior parte do código não parece ter sido feita de qualquer jeito por IA. Ainda assim, não sei se valia a pena deixar esse tipo de vestígio no repositório por causa de 1/100 do trabalho.Até agora, eu via o Iroh sendo usado principalmente de formas bonitinhas, mas não muito úteis; este pode ser justamente o app que faltava.
Isso também não parece ser uma prioridade no Tailscale.
O produto em si parece realmente muito legal, e a única coisa que me impede de trocar minha malha Tailscale é a ausência de um cliente Android.
Dito isso, o texto parece ter sido escrito pelo menos em parte por IA, o que me incomodou um pouco.
E parece que eles também distribuem um build APK de debug na tag nightly: https://github.com/rayfish/rayfish/…
Eu também vi este texto há 5 minutos, então não sei, além desses links, se ele realmente funciona.
A comparação com o Yggdrasil é fraca e também erra nos fatos. A testnet do Yggdrasil é operada como uma rede global, mas isso é apenas um resultado conveniente da topologia do Yggdrasil.
Ele pode aceitar dinamicamente qualquer conexão entre dois conjuntos separados de chaves, e a única diferença entre duas redes Yggdrasil separadas e uma grande rede é se elas estão trocando mensagens entre si. Qualquer pessoa pode criar uma rede Yggdrasil privada.
As chaves são criptograficamente impossíveis de adivinhar, mas eu não diria que isso chega a significar serviços ocultos. Os nomes de domínio são arbitrários, mas muita gente também aponta o DNS global para o espaço de endereços do Yggdrasil.
Se a perspectiva é “se você só quer uma rede para três amigos e um servidor de jogo, há muita coisa para montar no Yggdrasil”, então é até surpreendente não haver comparação com o tinc, que é quase o padrão para três amigos e um servidor de jogo.
A explicação é que não há o conceito de criar uma rede privada separada e admitir pessoas, nem recursos de conveniência como códigos de convite, nomes DNS amigáveis, firewall por rede e prompt de aprovação quando alguém tenta entrar. Para um engenheiro de redes, isso pode não ser um problema.
Outro ponto ausente na comparação com o Yggdrasil é que o Rayfish aproveita o NAT hole punching do Iroh, permitindo que dois peers se comuniquem mesmo que nenhum dos lados esteja acessível publicamente.