go-bgp

a collection of golang BGP tools to monitor, archive and serve
git clone git://git.2f30.org/go-bgp
Log | Files | Refs | README

api.go (2252B)


      1 package archive
      2 
      3 import (
      4 	"errors"
      5 	"fmt"
      6 	"log"
      7 	"net/http"
      8 	"net/url"
      9 )
     10 
     11 const (
     12 	GET    = "GET"
     13 	PUT    = "PUT"
     14 	POST   = "POST"
     15 	DELETE = "DELETE"
     16 )
     17 
     18 var (
     19 	errbadreq  = errors.New("malformed request")
     20 	errbaddate = errors.New("dates should be in a YYYYMMDDHHMM format and start should be earlier than end")
     21 	errempty   = errors.New("archive empty")
     22 	errdate    = errors.New("no such date in archive")
     23 	errbadtype = errors.New(fmt.Sprintf("Supported file types:%v", ftypestrings[1:ftypesize-1]))
     24 )
     25 
     26 type Resource interface {
     27 	Get(url.Values) (int, chan reply)
     28 	Put(url.Values) (int, chan reply)
     29 	Post(url.Values) (int, chan reply)
     30 	Delete(url.Values) (int, chan reply)
     31 }
     32 
     33 type (
     34 	GetNotAllowed    struct{}
     35 	PutNotAllowed    struct{}
     36 	PostNotAllowed   struct{}
     37 	DeleteNotAllowed struct{}
     38 )
     39 
     40 func (GetNotAllowed) Get(vals url.Values) (int, chan reply) {
     41 	return 405, nil
     42 }
     43 
     44 func (PutNotAllowed) Put(vals url.Values) (int, chan reply) {
     45 	return 405, nil
     46 }
     47 func (PostNotAllowed) Post(vals url.Values) (int, chan reply) {
     48 	return 405, nil
     49 }
     50 func (DeleteNotAllowed) Delete(vals url.Values) (int, chan reply) {
     51 	return 405, nil
     52 }
     53 
     54 type API struct{}
     55 
     56 func (api *API) requestHandlerFunc(resource Resource) http.HandlerFunc {
     57 	return func(rw http.ResponseWriter, req *http.Request) {
     58 		var (
     59 			datac chan reply
     60 			code  int
     61 		)
     62 		req.ParseForm()
     63 		method := req.Method
     64 		vals := req.Form
     65 		switch method {
     66 		case GET:
     67 			code, datac = resource.Get(vals)
     68 		case PUT:
     69 			code, datac = resource.Put(vals)
     70 		case POST:
     71 			code, datac = resource.Post(vals)
     72 		case DELETE:
     73 			code, datac = resource.Delete(vals)
     74 		}
     75 		rw.WriteHeader(code)
     76 		if datac != nil { // we got a proper channel to get datafrom
     77 			//go func(dc <-chan reply) { // fire a goroutine that will end upon the chan getting closed
     78 			for r := range datac {
     79 				if r.err == nil {
     80 					rw.Write(r.data)
     81 				} else {
     82 					log.Printf("Error in received from data channel:%s\n", r.err)
     83 					rw.Write([]byte(fmt.Sprintf("%s\n", r.err)))
     84 				}
     85 			}
     86 			//}(datac)
     87 		}
     88 	}
     89 }
     90 
     91 func (api *API) AddResource(resource Resource, path string) {
     92 	http.HandleFunc(path, api.requestHandlerFunc(resource))
     93 }
     94 
     95 func (api *API) Start(port int) {
     96 	portstr := fmt.Sprintf(":%d", port)
     97 	http.ListenAndServe(portstr, nil)
     98 }