Skip to content

Instantly share code, notes, and snippets.

@clee
Created August 20, 2013 22:10
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save clee/6288003 to your computer and use it in GitHub Desktop.
Save clee/6288003 to your computer and use it in GitHub Desktop.
tailpipe uses 'tail -f' to read a file, and spits out the result over EventSource to whoever's listening.
package main
import (
eventsource "github.com/msgehard/goEventSource"
"encoding/json"
"net/http"
"os/exec"
"flag"
"log"
// "fmt"
)
type Message struct {
Body string
}
func makeHandler(c <-chan string, quit <-chan bool) func(*eventsource.Conn) {
return func(es *eventsource.Conn) {
log.Println("Client listening.")
for {
select {
case msg := <-c:
log.Printf("length of msg is: %d", len(msg))
m := Message{msg}
j, _ := json.Marshal(m)
es.Write(string(j))
case <-quit:
log.Println("tail died!")
return
case <-es.CloseNotify():
log.Println("Client abandoned us.")
return
}
}
}
}
func main() {
flag.Parse()
filename := flag.Arg(0)
tail := exec.Command("tail", "-f", filename)
tailStdout, err := tail.StdoutPipe()
if err != nil {
log.Fatal("can't start tail. better bail!")
return
}
if err := tail.Start(); err != nil {
log.Fatal("can't start tail. gotta bail!")
return
}
b := make([]byte, 1024)
c := make(chan string)
quit := make(chan bool)
go func() {
for {
n, _ := tailStdout.Read(b)
if n > 0 {
c <- string(b[:n])
}
}
}()
http.Handle("/events", eventsource.Handler(makeHandler(c, quit)))
http.Handle("/", http.FileServer(http.Dir("/home/clee/Public/tailpipe")))
go tail.Wait()
http.ListenAndServe(":8000", nil)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment