gemax

package
v0.3.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 27, 2023 License: MIT Imports: 23 Imported by: 2

Documentation

Overview

Package gemax provides gemini protocol implementations. Gemini specification: gemini://gemini.circumlunar.space/docs/specification.gmi

Index

Constants

View Source
const DefaultMaxConnections = 256

DefaultMaxConnections default number of maximum connections.

View Source
const MIMEGemtext = "text/gemini"

MIMEGemtext describes a MIME type for gemini text. As a subtype of the top-level media type "text", "text/gemini" inherits the "charset" parameter defined in RFC 2046. However, as noted in 3.3, the default value of "charset" is "UTF-8" for "text" content transferred via Gemini.

A single additional parameter specific to the "text/gemini" subtype is defined: the "lang" parameter. The value of "lang" denotes the natural language or language(s) in which the textual content of a "text/gemini" document is written. The presence of the "lang" parameter is optional. When the "lang" parameter is present, its interpretation is defined entirely by the client. For example, clients which use text-to-speech technology to make Gemini content accessible to visually impaired users may use the value of "lang" to improve pronunciation of content. Clients which render text to a screen may use the value of "lang" to determine whether text should be displayed left-to-right or right-to-left. Simple clients for users who only read languages written left-to-right may simply ignore the value of "lang". When the "lang" parameter is not present, no default value should be assumed and clients which require some notion of a language in order to process the content (such as text-to-speech screen readers) should rely on user-input to determine how to proceed in the absence of a "lang" parameter.

Valid values for the "lang" parameter are comma-separated lists of one or more language tags as defined in RFC4646. For example:

  • "text/gemini; lang=en" Denotes a text/gemini document written in English
  • "text/gemini; lang=fr" Denotes a text/gemini document written in French
  • "text/gemini; lang=en,fr" Denotes a text/gemini document written in a mixture of English and French
  • "text/gemini; lang=de-CH" Denotes a text/gemini document written in Swiss German
  • "text/gemini; lang=sr-Cyrl" Denotes a text/gemini document written in Serbian using the Cyrllic script
  • "text/gemini; lang=zh-Hans-CN" Denotes a text/gemini document written in Chinese using the Simplified script as used in mainland China
View Source
const MaxHeaderSize = 1024

MaxHeaderSize is used while parsing server responses.

View Source
const MaxRequestSize = int64(1024 + len("\r\n"))

MaxRequestSize is the maximum incoming request size in bytes.

Variables

View Source
var ErrBadRequest = errors.New("bad request")
View Source
var ErrHeaderTooLarge = errors.New("header is too large: max header size is " + strconv.Itoa(MaxHeaderSize))

ErrHeaderTooLarge means that server response exceeds the MaxHeaderSize limit.

View Source
var ErrInvalidResponse = errors.New("malformed server response header")

ErrInvalidResponse means that server response is badly formed.

View Source
var ErrInvalidServerName = errors.New("server domain and server TLS domain name don't match")

ErrInvalidServerName means that the server certificate doesn't match the server domain.

View Source
var (
	// ErrTooManyRedirects means that server tried through too many adresses.
	// Default limit is 10.
	// User implementations of CheckRedirect should use this error then limiting number of redirects.
	ErrTooManyRedirects = errors.New("too many redirects")
)

Functions

func NotFound

func NotFound(rw ResponseWriter, req IncomingRequest)

NotFound serves a not found error.

func ParseResponseHeader

func ParseResponseHeader(re io.ByteReader) (status.Code, string, error)

ParseResponseHeader reads gemini header in form of "<code><SP><meta><CRLF>". If provided header is longer than MaxHeaderSize, than returns ErrHeaderTooLarge. Returns ErrInvalidResponse for badly formed server responses.

func Query

func Query(query urlpkg.Values) []string

Query extracts canonical gemini query values from url query part. Values are sorted in ascending order. Expected values:

?query&key=value => [query]
?a&b=&key=value => [a, b]

func Redirect

func Redirect(rw ResponseWriter, req IncomingRequest, target string, code status.Code)

Redirect client to another page. This handler can work with relative If code is status.Success, then generates a small gemini document with a single redirect link. This mechanism can be used as redirect on other protocol pages.

Examples:

Redirect(rw, req, "gemini://other.server.com/page", status.Redirect)
Redirect(rw, req, "../root/page", status.PermanentRedirect)
Redirect(rw, req, "https://wikipedia.org", status.Success)

Types

type Client

type Client struct {
	MaxResponseSize int64
	Dial            func(ctx context.Context, host string, cfg *tls.Config) (net.Conn, error)
	// CheckRedirect specifies the policy for handling redirects.
	// If CheckRedirect is not nil, the client calls it before
	// following an Gemini redirect. The arguments req and via are
	// the upcoming request and the requests made already, oldest
	// first. If CheckRedirect returns an error, the Client's Fetch
	// method returns both the previous Response (with its Body
	// closed) and CheckRedirect's error.
	// instead of issuing the Request req.
	// As a special case, if CheckRedirect returns ErrUseLastResponse,
	// then the most recent response is returned with its body
	// unclosed, along with a nil error.
	//
	// If CheckRedirect is nil, the Client uses its default policy,
	// which is to stop after 10 consecutive requests.
	CheckRedirect func(ctx context.Context, verification *urlpkg.URL, via []RedirectedRequest) error
	// contains filtered or unexported fields
}

Client is used to fetch gemini resources. Empty client value cane be considered as initialized.

func (*Client) Fetch

func (client *Client) Fetch(ctx context.Context, url string) (*Response, error)

Fetch gemini resource.

type FileSystem

type FileSystem struct {
	// The backend file system.
	FS fs.FS

	// Will be prepended to the request pats.
	Prefix string
	// Optional text logger.
	Logf func(format string, args ...interface{})
}

FileSystem serves file systems as gemini catalogs. It will search index.gmi and index.gemini in each catalog to use it content as header of corresponding directory page.

This handler is not intended to be used as file server, it's more like a static site server.

func (*FileSystem) Serve

func (fileSystem *FileSystem) Serve(ctx context.Context, rw ResponseWriter, req IncomingRequest)

Serve provided file system as gemini catalogs.

type Handler

type Handler func(ctx context.Context, rw ResponseWriter, req IncomingRequest)

Handler describes a gemini protocol handler.

func ServeContent

func ServeContent(contentType string, content []byte) Handler

ServeContent creates a handler, which serves provided bytes as static page.

type IncomingRequest

type IncomingRequest interface {
	URL() *url.URL
	RemoteAddr() string
	// Certificates returns the TLS certificates provided by the client.
	Certificates() []*x509.Certificate
}

IncomingRequest describes a server side request object.

func ParseIncomingRequest

func ParseIncomingRequest(re io.Reader, remoteAddr string) (IncomingRequest, error)

ParseIncomingRequest constructs an IncomingRequest from bytestream and additional parameters (remote address for now).

type RedirectedRequest added in v0.1.1

type RedirectedRequest struct {
	Req      *urlpkg.URL
	Response *Response
}

RedirectedRequest contains executed gemini request data and corresponding response with closed body.

type Response

type Response struct {
	Status status.Code
	Meta   string
	// contains filtered or unexported fields
}

Response contains parsed server response.

type ResponseWriter

type ResponseWriter interface {
	WriteStatus(code status.Code, meta string)
	io.WriteCloser
}

ResponseWriter describes a server side response writer.

type Server

type Server struct {
	Addr string
	// Hosts expected by server.
	// If empty, then every host will be valid.
	Hosts       []string
	Handler     Handler
	ConnContext func(ctx context.Context, conn net.Conn) context.Context
	Logf        func(format string, args ...interface{})

	// Maximum number of simultaneous connections served by Server.
	//	0 - DefaultMaxConnections
	//	<0 - no limitation
	MaxConnections int
	// contains filtered or unexported fields
}

Server is gemini protocol server.

func (*Server) ListenAndServe

func (server *Server) ListenAndServe(ctx context.Context, tlsCfg *tls.Config) error

ListenAndServe starts a TLS gemini server at specified server. It will block until context is canceled. It respects the MaxConnections setting. It will await all running handlers to end.

func (*Server) Serve

func (server *Server) Serve(ctx context.Context, listener net.Listener) error

Serve starts server on provided listener. Provided context will be passed to handlers. Serve will await all running handlers to end.

func (*Server) Stop

func (server *Server) Stop()

Stop gracefully shuts down the server: closes all connections.

Directories

Path Synopsis
internal
bufreader
Package bufreader provides buffered reader-closer gadget.
Package bufreader provides buffered reader-closer gadget.
bufwriter
Package bufwriter provides a buffered writer gadget.
Package bufwriter provides a buffered writer gadget.
multierr
Package multierr provides utilities for error chaining.
Package multierr provides utilities for error chaining.
testaddr
Package testaddr selects free port for testing purposes.
Package testaddr selects free port for testing purposes.
tester
Package tester provies test facilities for client and servers.
Package tester provies test facilities for client and servers.
Package status provides status codes for gemini protocols.
Package status provides status codes for gemini protocols.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL