Spin up ENS-powered tunnels that route users to your app without touching DNS.
This project is a comprehensive toolkit designed to connect a web service running on any machine directly to a human-readable .eth domain name from the Ethereum Name Service (ENS). It effectively allows users to self-host services and make them accessible via the blockchain without relying on centralized DNS providers, SSL certificate authorities, or services like Cloudflare. The system is composed of several distinct but interconnected parts that work together to create a seamless experience. The core idea is that a browser extension resolves a .eth address by looking up a text record on the Ethereum blockchain. The end-to-end flow begins with the browser extension. When a user navigates to a URL like myservice.domain.eth, the extension intercepts it. It queries the ENS blockchain on the Sepolia testnet to find a specific text record named url associated with that domain. This record contains the URL of the project's proxy server, including a unique tunnel ID, for example, https://proxy.example.com/tunnel123. The extension then redirects the browser to this proxy URL. The proxy server, a Go application, receives this HTTP request. It extracts the tunnel ID from the URL and looks up which tunnel client is associated with it. This client is another Go application that the service owner runs on their own machine, where their actual web application is hosted. The client maintains a constant, secure WebSocket connection to the proxy server. Upon receiving the request, the proxy server forwards all its details - method, headers, and body - over this WebSocket to the correct client. The proxy client then makes an equivalent HTTP request to the local service (e.g., a server running on localhost:3000). Once the local service responds, the client sends this response back up the WebSocket to the proxy server, which in turn delivers it to the user's browser, completing the cycle.
This project, ENS Tunnels, is a comprehensive toolkit designed to simplify publishing web services through the Ethereum Name Service (ENS). It provides an end-to-end solution for connecting a .eth domain to a locally running service, bypassing traditional DNS and certificate authorities.
Core Technologies The project is a monorepo composed of five key components, each built with specific technologies suited for its role:
frontend (React, Vite): A clean, one-click user interface for interacting with the backend. Built with React and Vite, it provides a simple form for users to request a subdomain. After the backend provisions the tunnel, the frontend displays the necessary credentials for the user to connect their local service.
proxy-server (Go): A high-performance reverse proxy written in Go. It serves two main purposes:
It maintains a persistent registry of all active tunnels and their authentication keys. It listens for incoming WebSocket connections from the proxy-client and forwards HTTP traffic from the public internet to the corresponding client, effectively "tunneling" the traffic to the user's local service.
4.proxy-client (Go): A lightweight command-line client, also written in Go. A developer runs this client on the same machine as their web service (e.g., a local web server running on localhost:3000). The client establishes a persistent WebSocket connection to the proxy-server using the credentials obtained from the frontend, securely exposing the local port to the internet through the tunnel.
How It's Pieced Together
The architecture is designed to create a "zero-trust provisioning" flow that automates a process that would otherwise involve 15-20 manual steps.
Setup: An operator (the project owner) funds a wallet on the Sepolia testnet, owns a parent ENS name (like my-project.eth), and runs the backend and proxy-server.
Request: A developer visits the frontend and requests a subdomain, for example, my-demo.
Provisioning: The frontend calls the backend API. The backend then performs three key actions: It creates the my-demo.my-project.eth subdomain on-chain. It sets the tunnel text record to point to the proxy server's address (e.g., tunnel=https://proxy.my-project.com/tunnel-id-123). It tells the proxy-server to expect a connection for tunnel-id-123 with a specific secret key.
Connection: The developer receives the tunnel-id-123 and the secret key. They run the proxy-client on their local machine, passing in the credentials and the local port they want to expose (e.g., go run main.go --port 3000 --id tunnel-id-123 --key ...).
Resolution: An end-user (or the developer) with the ens-extension installed navigates to http://my-demo.my-project.eth. The extension queries the ENS blockchain for the tunnel record, finds the proxy URL, and redirects the browser. The proxy-server then routes the request through the WebSocket to the proxy-client, and the user sees the content from the local server.

