2.3 KiB
2.3 KiB
go-gemini
go-gemini
implements the Gemini protocol
in Go.
It aims to provide an API similar to that of net/http
to make it easy to
develop Gemini clients and servers.
Examples
See examples/client
and examples/server
for an example client and server.
To run the examples:
go run -tags=example ./examples/server
Overview
A quick overview of the Gemini protocol:
- Client opens connection
- Server accepts connection
- Client and server complete a TLS handshake
- Client validates server certificate
- Client sends request
- Server sends response header
- Server sends response body (only for successful responses)
- Server closes connection
- Client handles response
The way this is implemented in this package is like so:
- Client makes a request with
NewRequest
. The client can verify server certificates in the Request options, see Recommended TLS configuration. - Server recieves the request and constructs a response.
The server calls the
Serve(*ResponseWriter, *Request)
method on theHandler
field. The handler writes the response. The server then closes the connection. - Client recieves the response as a
*Response
. The client then handles the response. The client can now verify the certificate of the server using a Trust-On-First-Use method.
Recommended TLS configuration
For clients, the recommended TLS configuration is as follows:
// Accept self-signed server certificates
req.TLSConfig.InsecureSkipVerify = true
// Manually verify server certificates, using TOFU
req.TLSConfig.VerifyPeerCertificate = func(rawCerts [][]byte, chains [][]*x509.Certificate) error {
// Verify the server certificate here
// Return an error on failure, or nil on success
return nil
}
Note that gemini.Get
does not verify server certificates.
For servers, the recommended TLS configuration is as follows:
// Specify a certificate
// To load a certificate, use `tls.LoadX509KeyPair`.
srv.TLSConfig.Certificates = append(srv.TLSConfig.Certificates, cert)
// Request client certificates
srv.TLSConfig.ClientAuth = tls.RequestClientCert