Skip to content

Instantly share code, notes, and snippets.

@dustin
Created February 9, 2012 03:57
Show Gist options
  • Save dustin/1777162 to your computer and use it in GitHub Desktop.
Save dustin/1777162 to your computer and use it in GitHub Desktop.
A web server that runs out of inetd
package main
import (
"errors"
"fmt"
"net"
"net/http"
"os"
"time"
)
type StdioListener bool
type StdioConn bool
var stategen = make(chan bool)
// Listener implementation
func (sl *StdioListener) Accept() (net.Conn, error) {
// I can only accept once, but this is called in a relatively
// tight loop. I'm driving the two states with a simple
// boolean channel. The first accept is a real connection.
// The next one blocks until that connection is done at which
// point it returns an error and the server exits.
if <-stategen {
return new(StdioConn), nil
}
return nil, errors.New("Done")
}
func (sl *StdioListener) Close() error {
return nil
}
func (sl *StdioListener) Addr() net.Addr {
return &net.IPAddr{net.IPv4(0, 0, 0, 0)}
}
// Conn impl
func (sl *StdioConn) Read(b []byte) (int, error) {
return os.Stdin.Read(b)
}
func (sl *StdioConn) Write(b []byte) (int, error) {
return os.Stdout.Write(b)
}
func (sl *StdioConn) LocalAddr() net.Addr {
return &net.IPAddr{net.IPv4(0, 0, 0, 0)}
}
func (sl *StdioConn) RemoteAddr() net.Addr {
return sl.LocalAddr()
}
func (sl *StdioConn) SetDeadline(t time.Time) error {
return nil
}
func (sl *StdioConn) SetReadDeadline(t time.Time) error {
return nil
}
func (sl *StdioConn) SetWriteDeadline(t time.Time) error {
return nil
}
func (sl *StdioConn) Close() error {
stategen <- false
return nil
}
func main() {
s := http.Server{}
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hello, %q\n", r.URL.Path)
})
// Must send this async or it deadlocks
go func() { stategen <- true }()
var sl StdioListener
s.Serve(&sl)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment