Xiang Li 12 years ago
parent
commit
ef59a03fbb
11 changed files with 234 additions and 261 deletions
  1. 12 15
      command.go
  2. 10 19
      handlers.go
  3. 70 79
      raftd.go
  4. 29 31
      store/store.go
  5. 13 16
      store/store_test.go
  6. 4 5
      store/watcher.go
  7. 1 1
      store/watcher_test.go
  8. 17 12
      trans_handler.go
  9. 6 6
      web/conn.go
  10. 40 40
      web/hub.go
  11. 32 37
      web/web.go

+ 12 - 15
command.go

@@ -1,4 +1,5 @@
 package main
 package main
+
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
 //
 //
 // Commands
 // Commands
@@ -6,11 +7,11 @@ package main
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
 
 
 import (
 import (
+	"encoding/json"
 	"github.com/benbjohnson/go-raft"
 	"github.com/benbjohnson/go-raft"
 	"github.com/xiangli-cmu/raft-etcd/store"
 	"github.com/xiangli-cmu/raft-etcd/store"
-	"encoding/json"
 	"time"
 	"time"
-	)
+)
 
 
 // A command represents an action to be taken on the replicated state machine.
 // A command represents an action to be taken on the replicated state machine.
 type Command interface {
 type Command interface {
@@ -20,8 +21,8 @@ type Command interface {
 
 
 // Set command
 // Set command
 type SetCommand struct {
 type SetCommand struct {
-	Key string `json:"key"`
-	Value string `json:"value"`
+	Key        string    `json:"key"`
+	Value      string    `json:"value"`
 	ExpireTime time.Time `json:"expireTime"`
 	ExpireTime time.Time `json:"expireTime"`
 }
 }
 
 
@@ -40,7 +41,6 @@ func (c *SetCommand) GeneratePath() string {
 	return "set/" + c.Key
 	return "set/" + c.Key
 }
 }
 
 
-
 // Get command
 // Get command
 type GetCommand struct {
 type GetCommand struct {
 	Key string `json:"key"`
 	Key string `json:"key"`
@@ -52,12 +52,12 @@ func (c *GetCommand) CommandName() string {
 }
 }
 
 
 // Set the value of key to value
 // Set the value of key to value
-func (c *GetCommand) Apply(server *raft.Server) ([]byte, error){
+func (c *GetCommand) Apply(server *raft.Server) ([]byte, error) {
 	res := store.Get(c.Key)
 	res := store.Get(c.Key)
 	return json.Marshal(res)
 	return json.Marshal(res)
 }
 }
 
 
-func (c *GetCommand) GeneratePath() string{
+func (c *GetCommand) GeneratePath() string {
 	return "get/" + c.Key
 	return "get/" + c.Key
 }
 }
 
 
@@ -71,8 +71,8 @@ func (c *DeleteCommand) CommandName() string {
 	return "delete"
 	return "delete"
 }
 }
 
 
-// Delete the key 
-func (c *DeleteCommand) Apply(server *raft.Server) ([]byte, error){
+// Delete the key
+func (c *DeleteCommand) Apply(server *raft.Server) ([]byte, error) {
 	return store.Delete(c.Key)
 	return store.Delete(c.Key)
 }
 }
 
 
@@ -86,14 +86,14 @@ func (c *WatchCommand) CommandName() string {
 	return "watch"
 	return "watch"
 }
 }
 
 
-func (c *WatchCommand) Apply(server *raft.Server) ([]byte, error){
+func (c *WatchCommand) Apply(server *raft.Server) ([]byte, error) {
 	ch := make(chan store.Response)
 	ch := make(chan store.Response)
 
 
 	// add to the watchers list
 	// add to the watchers list
-	store.AddWatcher(c.Key, ch)	
+	store.AddWatcher(c.Key, ch)
 
 
 	// wait for the notification for any changing
 	// wait for the notification for any changing
-	res := <- ch
+	res := <-ch
 
 
 	return json.Marshal(res)
 	return json.Marshal(res)
 }
 }
@@ -112,6 +112,3 @@ func (c *JoinCommand) Apply(server *raft.Server) ([]byte, error) {
 	// no result will be returned
 	// no result will be returned
 	return nil, err
 	return nil, err
 }
 }
-
-
-

+ 10 - 19
handlers.go

@@ -1,17 +1,16 @@
 package main
 package main
 
 
 import (
 import (
+	"encoding/json"
 	"github.com/benbjohnson/go-raft"
 	"github.com/benbjohnson/go-raft"
 	"net/http"
 	"net/http"
-	"encoding/json"
 	//"fmt"
 	//"fmt"
 	"io/ioutil"
 	"io/ioutil"
 	//"bytes"
 	//"bytes"
-	"time"
-	"strings"
 	"strconv"
 	"strconv"
-	)
-
+	"strings"
+	"time"
+)
 
 
 //--------------------------------------
 //--------------------------------------
 // HTTP Handlers
 // HTTP Handlers
@@ -73,9 +72,8 @@ func SnapshotHttpHandler(w http.ResponseWriter, req *http.Request) {
 	w.WriteHeader(http.StatusInternalServerError)
 	w.WriteHeader(http.StatusInternalServerError)
 }
 }
 
 
-
 func JoinHttpHandler(w http.ResponseWriter, req *http.Request) {
 func JoinHttpHandler(w http.ResponseWriter, req *http.Request) {
-	
+
 	command := &JoinCommand{}
 	command := &JoinCommand{}
 
 
 	if err := decodeJsonRequest(req, command); err == nil {
 	if err := decodeJsonRequest(req, command); err == nil {
@@ -87,7 +85,6 @@ func JoinHttpHandler(w http.ResponseWriter, req *http.Request) {
 	}
 	}
 }
 }
 
 
-
 func SetHttpHandler(w http.ResponseWriter, req *http.Request) {
 func SetHttpHandler(w http.ResponseWriter, req *http.Request) {
 	key := req.URL.Path[len("/set/"):]
 	key := req.URL.Path[len("/set/"):]
 
 
@@ -96,7 +93,7 @@ func SetHttpHandler(w http.ResponseWriter, req *http.Request) {
 	if err != nil {
 	if err != nil {
 		warn("raftd: Unable to read: %v", err)
 		warn("raftd: Unable to read: %v", err)
 		w.WriteHeader(http.StatusInternalServerError)
 		w.WriteHeader(http.StatusInternalServerError)
-		return 
+		return
 	}
 	}
 
 
 	debug("[recv] POST http://%v/set/%s [%s]", server.Name(), key, content)
 	debug("[recv] POST http://%v/set/%s [%s]", server.Name(), key, content)
@@ -112,11 +109,11 @@ func SetHttpHandler(w http.ResponseWriter, req *http.Request) {
 		if err != nil {
 		if err != nil {
 			warn("raftd: Bad duration: %v", err)
 			warn("raftd: Bad duration: %v", err)
 			w.WriteHeader(http.StatusInternalServerError)
 			w.WriteHeader(http.StatusInternalServerError)
-			return 
+			return
 		}
 		}
 		command.ExpireTime = time.Now().Add(time.Second * (time.Duration)(duration))
 		command.ExpireTime = time.Now().Add(time.Second * (time.Duration)(duration))
 	} else {
 	} else {
-		command.ExpireTime = time.Unix(0,0)
+		command.ExpireTime = time.Unix(0, 0)
 	}
 	}
 
 
 	excute(command, &w)
 	excute(command, &w)
@@ -134,7 +131,6 @@ func DeleteHttpHandler(w http.ResponseWriter, req *http.Request) {
 	excute(command, &w)
 	excute(command, &w)
 }
 }
 
 
-
 func excute(c Command, w *http.ResponseWriter) {
 func excute(c Command, w *http.ResponseWriter) {
 	if server.State() == "leader" {
 	if server.State() == "leader" {
 		if body, err := server.Do(c); err != nil {
 		if body, err := server.Do(c); err != nil {
@@ -152,11 +148,11 @@ func excute(c Command, w *http.ResponseWriter) {
 		(*w).Write([]byte(server.Leader()))
 		(*w).Write([]byte(server.Leader()))
 		return
 		return
 	}
 	}
-	
+
 	(*w).WriteHeader(http.StatusInternalServerError)
 	(*w).WriteHeader(http.StatusInternalServerError)
 
 
 	return
 	return
-} 
+}
 
 
 func MasterHttpHandler(w http.ResponseWriter, req *http.Request) {
 func MasterHttpHandler(w http.ResponseWriter, req *http.Request) {
 	w.WriteHeader(http.StatusOK)
 	w.WriteHeader(http.StatusOK)
@@ -202,8 +198,3 @@ func WatchHttpHandler(w http.ResponseWriter, req *http.Request) {
 	}
 	}
 
 
 }
 }
-
-
-
-
-

+ 70 - 79
raftd.go

@@ -2,23 +2,23 @@ package main
 
 
 import (
 import (
 	"bytes"
 	"bytes"
+	"crypto/tls"
+	"crypto/x509"
 	"encoding/json"
 	"encoding/json"
 	"encoding/pem"
 	"encoding/pem"
 	"flag"
 	"flag"
 	"fmt"
 	"fmt"
 	"github.com/benbjohnson/go-raft"
 	"github.com/benbjohnson/go-raft"
-	"log"
+	"github.com/xiangli-cmu/raft-etcd/store"
+	"github.com/xiangli-cmu/raft-etcd/web"
 	"io"
 	"io"
 	"io/ioutil"
 	"io/ioutil"
+	"log"
 	"net/http"
 	"net/http"
-	"strings"
 	"os"
 	"os"
-	"time"
 	"strconv"
 	"strconv"
-	"crypto/tls"
-	"crypto/x509"
-	"github.com/xiangli-cmu/raft-etcd/web"
-	"github.com/xiangli-cmu/raft-etcd/store"
+	"strings"
+	"time"
 )
 )
 
 
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
@@ -27,7 +27,6 @@ import (
 //
 //
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
 
 
-
 var verbose bool
 var verbose bool
 var leaderHost string
 var leaderHost string
 var address string
 var address string
@@ -45,15 +44,16 @@ func init() {
 	flag.StringVar(&certFile, "cert", "", "the cert file of the server")
 	flag.StringVar(&certFile, "cert", "", "the cert file of the server")
 	flag.StringVar(&keyFile, "key", "", "the key file of the server")
 	flag.StringVar(&keyFile, "key", "", "the key file of the server")
 }
 }
+
 // CONSTANTS
 // CONSTANTS
-const (	
+const (
 	HTTP = iota
 	HTTP = iota
 	HTTPS
 	HTTPS
 	HTTPSANDVERIFY
 	HTTPSANDVERIFY
 )
 )
 
 
 const (
 const (
-	ELECTIONTIMTOUT = 3 * time.Second
+	ELECTIONTIMTOUT  = 3 * time.Second
 	HEARTBEATTIMEOUT = 1 * time.Second
 	HEARTBEATTIMEOUT = 1 * time.Second
 )
 )
 
 
@@ -65,7 +65,7 @@ const (
 
 
 type Info struct {
 type Info struct {
 	Host string `json:"host"`
 	Host string `json:"host"`
-	Port int `json:"port"`
+	Port int    `json:"port"`
 }
 }
 
 
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
@@ -79,7 +79,6 @@ var logger *log.Logger
 
 
 var storeMsg chan string
 var storeMsg chan string
 
 
-
 //------------------------------------------------------------------------------
 //------------------------------------------------------------------------------
 //
 //
 // Functions
 // Functions
@@ -100,7 +99,7 @@ func main() {
 	raft.RegisterCommand(&SetCommand{})
 	raft.RegisterCommand(&SetCommand{})
 	raft.RegisterCommand(&GetCommand{})
 	raft.RegisterCommand(&GetCommand{})
 	raft.RegisterCommand(&DeleteCommand{})
 	raft.RegisterCommand(&DeleteCommand{})
-	
+
 	// Use the present working directory if a directory was not passed in.
 	// Use the present working directory if a directory was not passed in.
 	var path string
 	var path string
 	if flag.NArg() == 0 {
 	if flag.NArg() == 0 {
@@ -118,7 +117,7 @@ func main() {
 	name := fmt.Sprintf("%s:%d", info.Host, info.Port)
 	name := fmt.Sprintf("%s:%d", info.Host, info.Port)
 
 
 	fmt.Printf("Name: %s\n\n", name)
 	fmt.Printf("Name: %s\n\n", name)
-	
+
 	// secrity type
 	// secrity type
 	st := securityType()
 	st := securityType()
 
 
@@ -126,7 +125,7 @@ func main() {
 		panic("ERROR type")
 		panic("ERROR type")
 	}
 	}
 
 
-    t := createTranHandler(st)
+	t := createTranHandler(st)
 
 
 	// Setup new raft server.
 	// Setup new raft server.
 	s := store.GetStore()
 	s := store.GetStore()
@@ -159,7 +158,7 @@ func main() {
 			server.Do(command)
 			server.Do(command)
 			debug("%s start as a leader", server.Name())
 			debug("%s start as a leader", server.Name())
 
 
-		// start as a fellower in a existing cluster
+			// start as a fellower in a existing cluster
 		} else {
 		} else {
 			server.StartElectionTimeout()
 			server.StartElectionTimeout()
 			server.StartFollower()
 			server.StartFollower()
@@ -171,7 +170,7 @@ func main() {
 			fmt.Println("success join")
 			fmt.Println("success join")
 		}
 		}
 
 
-	// rejoin the previous cluster
+		// rejoin the previous cluster
 	} else {
 	} else {
 		server.StartElectionTimeout()
 		server.StartElectionTimeout()
 		server.StartFollower()
 		server.StartFollower()
@@ -181,15 +180,14 @@ func main() {
 	// open the snapshot
 	// open the snapshot
 	go server.Snapshot()
 	go server.Snapshot()
 
 
+	if webPort != -1 {
+		// start web
+		s.SetMessager(&storeMsg)
+		go webHelper()
+		go web.Start(server, webPort)
+	}
 
 
-    if webPort != -1 {
-    	// start web
-    	s.SetMessager(&storeMsg)
-    	go webHelper()
-    	go web.Start(server, webPort)
-    } 
-
-    startTransport(info.Port, st)
+	startTransport(info.Port, st)
 
 
 }
 }
 
 
@@ -216,12 +214,12 @@ func createTranHandler(st int) transHandler {
 		}
 		}
 
 
 		tr := &http.Transport{
 		tr := &http.Transport{
-			TLSClientConfig:   &tls.Config{
-				Certificates: []tls.Certificate{tlsCert},
+			TLSClientConfig: &tls.Config{
+				Certificates:       []tls.Certificate{tlsCert},
 				InsecureSkipVerify: true,
 				InsecureSkipVerify: true,
-				},
-				DisableCompression: true,
-			}
+			},
+			DisableCompression: true,
+		}
 
 
 		t.client = &http.Client{Transport: tr}
 		t.client = &http.Client{Transport: tr}
 		return t
 		return t
@@ -231,36 +229,35 @@ func createTranHandler(st int) transHandler {
 	return transHandler{}
 	return transHandler{}
 }
 }
 
 
-func startTransport(port int, st int) {	
+func startTransport(port int, st int) {
 
 
 	// internal commands
 	// internal commands
-    http.HandleFunc("/join", JoinHttpHandler)
-    http.HandleFunc("/vote", VoteHttpHandler)
-    http.HandleFunc("/log", GetLogHttpHandler)
-    http.HandleFunc("/log/append", AppendEntriesHttpHandler)
-    http.HandleFunc("/snapshot", SnapshotHttpHandler)
-
-    // external commands
-    http.HandleFunc("/set/", SetHttpHandler)
-    http.HandleFunc("/get/", GetHttpHandler)
-    http.HandleFunc("/delete/", DeleteHttpHandler)
-    http.HandleFunc("/watch/", WatchHttpHandler)
-    http.HandleFunc("/master", MasterHttpHandler)
+	http.HandleFunc("/join", JoinHttpHandler)
+	http.HandleFunc("/vote", VoteHttpHandler)
+	http.HandleFunc("/log", GetLogHttpHandler)
+	http.HandleFunc("/log/append", AppendEntriesHttpHandler)
+	http.HandleFunc("/snapshot", SnapshotHttpHandler)
+
+	// external commands
+	http.HandleFunc("/set/", SetHttpHandler)
+	http.HandleFunc("/get/", GetHttpHandler)
+	http.HandleFunc("/delete/", DeleteHttpHandler)
+	http.HandleFunc("/watch/", WatchHttpHandler)
+	http.HandleFunc("/master", MasterHttpHandler)
 
 
-    switch st {
+	switch st {
 
 
-    case HTTP:
-    	log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d", port), nil))
+	case HTTP:
+		log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d", port), nil))
 
 
-    case HTTPS:
-    	http.ListenAndServeTLS(fmt.Sprintf(":%d", port), certFile, keyFile, nil)
+	case HTTPS:
+		http.ListenAndServeTLS(fmt.Sprintf(":%d", port), certFile, keyFile, nil)
 
 
-    case HTTPSANDVERIFY:
-    	pemByte, _ := ioutil.ReadFile(CAFile)
+	case HTTPSANDVERIFY:
+		pemByte, _ := ioutil.ReadFile(CAFile)
 
 
 		block, pemByte := pem.Decode(pemByte)
 		block, pemByte := pem.Decode(pemByte)
 
 
-
 		cert, err := x509.ParseCertificate(block.Bytes)
 		cert, err := x509.ParseCertificate(block.Bytes)
 
 
 		if err != nil {
 		if err != nil {
@@ -274,16 +271,16 @@ func startTransport(port int, st int) {
 		server := &http.Server{
 		server := &http.Server{
 			TLSConfig: &tls.Config{
 			TLSConfig: &tls.Config{
 				ClientAuth: tls.RequireAndVerifyClientCert,
 				ClientAuth: tls.RequireAndVerifyClientCert,
-				ClientCAs: certPool,
-				},
-			Addr:fmt.Sprintf(":%d", port),
+				ClientCAs:  certPool,
+			},
+			Addr: fmt.Sprintf(":%d", port),
 		}
 		}
 		err = server.ListenAndServeTLS(certFile, keyFile)
 		err = server.ListenAndServeTLS(certFile, keyFile)
 
 
 		if err != nil {
 		if err != nil {
 			log.Fatal(err)
 			log.Fatal(err)
 		}
 		}
-    }
+	}
 
 
 }
 }
 
 
@@ -291,8 +288,8 @@ func startTransport(port int, st int) {
 // Config
 // Config
 //--------------------------------------
 //--------------------------------------
 
 
-func securityType() int{
-	if keyFile == "" && certFile == "" && CAFile == ""{
+func securityType() int {
+	if keyFile == "" && certFile == "" && CAFile == "" {
 
 
 		return HTTP
 		return HTTP
 
 
@@ -310,7 +307,6 @@ func securityType() int{
 	return -1
 	return -1
 }
 }
 
 
-
 func getInfo(path string) *Info {
 func getInfo(path string) *Info {
 	info := &Info{}
 	info := &Info{}
 
 
@@ -325,10 +321,10 @@ func getInfo(path string) *Info {
 			}
 			}
 		}
 		}
 		file.Close()
 		file.Close()
-	
-	// Otherwise ask user for info and write it to file.
+
+		// Otherwise ask user for info and write it to file.
 	} else {
 	} else {
-		
+
 		if address == "" {
 		if address == "" {
 			fatal("Please give the address of the local machine")
 			fatal("Please give the address of the local machine")
 		}
 		}
@@ -341,9 +337,9 @@ func getInfo(path string) *Info {
 
 
 		info.Host = input[0]
 		info.Host = input[0]
 		info.Host = strings.TrimSpace(info.Host)
 		info.Host = strings.TrimSpace(info.Host)
-		
+
 		info.Port, err = strconv.Atoi(input[1])
 		info.Port, err = strconv.Atoi(input[1])
-		
+
 		if err != nil {
 		if err != nil {
 			fatal("Wrong port %s", address)
 			fatal("Wrong port %s", address)
 		}
 		}
@@ -355,11 +351,10 @@ func getInfo(path string) *Info {
 			fatal("Unable to write info to file: %v", err)
 			fatal("Unable to write info to file: %v", err)
 		}
 		}
 	}
 	}
-	
+
 	return info
 	return info
 }
 }
 
 
-
 //--------------------------------------
 //--------------------------------------
 // Handlers
 // Handlers
 //--------------------------------------
 //--------------------------------------
@@ -367,15 +362,14 @@ func getInfo(path string) *Info {
 // Send join requests to the leader.
 // Send join requests to the leader.
 func Join(s *raft.Server, serverName string) error {
 func Join(s *raft.Server, serverName string) error {
 	var b bytes.Buffer
 	var b bytes.Buffer
-	
+
 	command := &JoinCommand{}
 	command := &JoinCommand{}
 	command.Name = s.Name()
 	command.Name = s.Name()
 
 
 	json.NewEncoder(&b).Encode(command)
 	json.NewEncoder(&b).Encode(command)
-	
 
 
 	// t must be ok
 	// t must be ok
-	t,_ := server.Transporter().(transHandler)
+	t, _ := server.Transporter().(transHandler)
 	debug("Send Join Request to %s", serverName)
 	debug("Send Join Request to %s", serverName)
 	resp, err := Post(&t, fmt.Sprintf("%s/join", serverName), &b)
 	resp, err := Post(&t, fmt.Sprintf("%s/join", serverName), &b)
 
 
@@ -399,6 +393,7 @@ func Join(s *raft.Server, serverName string) error {
 	}
 	}
 	return fmt.Errorf("Unable to join: %v", err)
 	return fmt.Errorf("Unable to join: %v", err)
 }
 }
+
 //--------------------------------------
 //--------------------------------------
 // Web Helper
 // Web Helper
 //--------------------------------------
 //--------------------------------------
@@ -410,7 +405,6 @@ func webHelper() {
 	}
 	}
 }
 }
 
 
-
 //--------------------------------------
 //--------------------------------------
 // HTTP Utilities
 // HTTP Utilities
 //--------------------------------------
 //--------------------------------------
@@ -434,13 +428,13 @@ func encodeJsonResponse(w http.ResponseWriter, status int, data interface{}) {
 	}
 	}
 }
 }
 
 
-func Post(t *transHandler, path string, body io.Reader) (*http.Response, error){
+func Post(t *transHandler, path string, body io.Reader) (*http.Response, error) {
 
 
 	if t.client != nil {
 	if t.client != nil {
-		resp, err := t.client.Post("https://" + path, "application/json", body)
+		resp, err := t.client.Post("https://"+path, "application/json", body)
 		return resp, err
 		return resp, err
 	} else {
 	} else {
-		resp, err := http.Post("http://" + path, "application/json", body)
+		resp, err := http.Post("http://"+path, "application/json", body)
 		return resp, err
 		return resp, err
 	}
 	}
 }
 }
@@ -461,22 +455,19 @@ func Get(t *transHandler, path string) (*http.Response, error) {
 
 
 func debug(msg string, v ...interface{}) {
 func debug(msg string, v ...interface{}) {
 	if verbose {
 	if verbose {
-		logger.Printf("DEBUG " + msg + "\n", v...)
+		logger.Printf("DEBUG "+msg+"\n", v...)
 	}
 	}
 }
 }
 
 
 func info(msg string, v ...interface{}) {
 func info(msg string, v ...interface{}) {
-	logger.Printf("INFO  " + msg + "\n", v...)
+	logger.Printf("INFO  "+msg+"\n", v...)
 }
 }
 
 
 func warn(msg string, v ...interface{}) {
 func warn(msg string, v ...interface{}) {
-	logger.Printf("Alpaca Server: WARN  " + msg + "\n", v...)
+	logger.Printf("Alpaca Server: WARN  "+msg+"\n", v...)
 }
 }
 
 
 func fatal(msg string, v ...interface{}) {
 func fatal(msg string, v ...interface{}) {
-	logger.Printf("FATAL " + msg + "\n", v...)
+	logger.Printf("FATAL "+msg+"\n", v...)
 	os.Exit(1)
 	os.Exit(1)
 }
 }
-
-
-

+ 29 - 31
store/store.go

@@ -1,11 +1,11 @@
 package store
 package store
 
 
 import (
 import (
-	"path"
 	"encoding/json"
 	"encoding/json"
-	"time"
 	"fmt"
 	"fmt"
-	)
+	"path"
+	"time"
+)
 
 
 // global store
 // global store
 var s *Store
 var s *Store
@@ -13,26 +13,24 @@ var s *Store
 // CONSTANTS
 // CONSTANTS
 const (
 const (
 	ERROR = -1 + iota
 	ERROR = -1 + iota
-	SET 
+	SET
 	DELETE
 	DELETE
 	GET
 	GET
 )
 )
 
 
-
-var PERMANENT = time.Unix(0,0)
+var PERMANENT = time.Unix(0, 0)
 
 
 type Store struct {
 type Store struct {
 	// use the build-in hash map as the key-value store structure
 	// use the build-in hash map as the key-value store structure
-	Nodes map[string]Node  `json:"nodes"`
+	Nodes map[string]Node `json:"nodes"`
 
 
 	// the string channel to send messages to the outside world
 	// the string channel to send messages to the outside world
 	// now we use it to send changes to the hub of the web service
 	// now we use it to send changes to the hub of the web service
 	messager *chan string
 	messager *chan string
 }
 }
 
 
-
 type Node struct {
 type Node struct {
-	Value string	`json:"value"`
+	Value string `json:"value"`
 
 
 	// if the node is a permanent one the ExprieTime will be Unix(0,0)
 	// if the node is a permanent one the ExprieTime will be Unix(0,0)
 	// Otherwise after the expireTime, the node will be deleted
 	// Otherwise after the expireTime, the node will be deleted
@@ -43,14 +41,14 @@ type Node struct {
 }
 }
 
 
 type Response struct {
 type Response struct {
-	Action	 int    `json:"action"`
+	Action   int    `json:"action"`
 	Key      string `json:"key"`
 	Key      string `json:"key"`
 	OldValue string `json:"oldValue"`
 	OldValue string `json:"oldValue"`
 	NewValue string `json:"newValue"`
 	NewValue string `json:"newValue"`
 
 
 	// if the key existed before the action, this field should be true
 	// if the key existed before the action, this field should be true
 	// if the key did not exist before the action, this field should be false
 	// if the key did not exist before the action, this field should be false
-	Exist 	 bool `json:"exist"`
+	Exist bool `json:"exist"`
 
 
 	Expiration time.Time `json:"expiration"`
 	Expiration time.Time `json:"expiration"`
 }
 }
@@ -61,7 +59,7 @@ func init() {
 }
 }
 
 
 // make a new stroe
 // make a new stroe
-func createStore() *Store{
+func createStore() *Store {
 	s := new(Store)
 	s := new(Store)
 	s.Nodes = make(map[string]Node)
 	s.Nodes = make(map[string]Node)
 	return s
 	return s
@@ -73,11 +71,11 @@ func GetStore() *Store {
 }
 }
 
 
 // set the messager of the store
 // set the messager of the store
-func (s *Store)SetMessager(messager *chan string) {
+func (s *Store) SetMessager(messager *chan string) {
 	s.messager = messager
 	s.messager = messager
-}	
+}
 
 
-// set the key to value, return the old value if the key exists 
+// set the key to value, return the old value if the key exists
 func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 
 
 	key = path.Clean(key)
 	key = path.Clean(key)
@@ -97,11 +95,11 @@ func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 	node, ok := s.Nodes[key]
 	node, ok := s.Nodes[key]
 
 
 	if ok {
 	if ok {
-		// if node is not permanent before 
+		// if node is not permanent before
 		// update its expireTime
 		// update its expireTime
 		if !node.ExpireTime.Equal(PERMANENT) {
 		if !node.ExpireTime.Equal(PERMANENT) {
 
 
-				node.update <- expireTime
+			node.update <- expireTime
 
 
 		} else {
 		} else {
 			// if we want the permanent node to have expire time
 			// if we want the permanent node to have expire time
@@ -115,7 +113,7 @@ func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 		// update the information of the node
 		// update the information of the node
 		node.ExpireTime = expireTime
 		node.ExpireTime = expireTime
 		node.Value = value
 		node.Value = value
-		
+
 		resp := Response{SET, key, node.Value, value, true, expireTime}
 		resp := Response{SET, key, node.Value, value, true, expireTime}
 
 
 		msg, err := json.Marshal(resp)
 		msg, err := json.Marshal(resp)
@@ -123,14 +121,14 @@ func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 		notify(resp)
 		notify(resp)
 
 
 		// send to the messager
 		// send to the messager
-		if (s.messager != nil && err == nil) {
+		if s.messager != nil && err == nil {
 
 
 			*s.messager <- string(msg)
 			*s.messager <- string(msg)
-		} 
+		}
 
 
 		return msg, err
 		return msg, err
 
 
-	// add new node
+		// add new node
 	} else {
 	} else {
 
 
 		update := make(chan time.Time)
 		update := make(chan time.Time)
@@ -149,10 +147,10 @@ func Set(key string, value string, expireTime time.Time) ([]byte, error) {
 		notify(resp)
 		notify(resp)
 
 
 		// notify the web interface
 		// notify the web interface
-		if (s.messager != nil && err == nil) {
+		if s.messager != nil && err == nil {
 
 
 			*s.messager <- string(msg)
 			*s.messager <- string(msg)
-		} 
+		}
 
 
 		return msg, err
 		return msg, err
 	}
 	}
@@ -180,10 +178,10 @@ func expire(key string, update chan time.Time, expireTime time.Time) {
 				notify(resp)
 				notify(resp)
 
 
 				// notify the messager
 				// notify the messager
-				if (s.messager != nil && err == nil) {
+				if s.messager != nil && err == nil {
 
 
 					*s.messager <- string(msg)
 					*s.messager <- string(msg)
-				} 
+				}
 
 
 				return
 				return
 
 
@@ -191,7 +189,7 @@ func expire(key string, update chan time.Time, expireTime time.Time) {
 
 
 		case updateTime := <-update:
 		case updateTime := <-update:
 			//update duration
 			//update duration
-			// if the node become a permanent one, the go routine is 
+			// if the node become a permanent one, the go routine is
 			// not needed
 			// not needed
 			if updateTime.Equal(PERMANENT) {
 			if updateTime.Equal(PERMANENT) {
 				return
 				return
@@ -242,10 +240,10 @@ func Delete(key string) ([]byte, error) {
 		notify(resp)
 		notify(resp)
 
 
 		// notify the messager
 		// notify the messager
-		if (s.messager != nil && err == nil) {
+		if s.messager != nil && err == nil {
 
 
 			*s.messager <- string(msg)
 			*s.messager <- string(msg)
-		} 
+		}
 
 
 		return msg, err
 		return msg, err
 
 
@@ -256,7 +254,7 @@ func Delete(key string) ([]byte, error) {
 }
 }
 
 
 // save the current state of the storage system
 // save the current state of the storage system
-func (s *Store)Save() ([]byte, error) {
+func (s *Store) Save() ([]byte, error) {
 	b, err := json.Marshal(s)
 	b, err := json.Marshal(s)
 	if err != nil {
 	if err != nil {
 		fmt.Println(err)
 		fmt.Println(err)
@@ -266,7 +264,7 @@ func (s *Store)Save() ([]byte, error) {
 }
 }
 
 
 // recovery the state of the stroage system from a previous state
 // recovery the state of the stroage system from a previous state
-func (s *Store)Recovery(state []byte) error {
+func (s *Store) Recovery(state []byte) error {
 	err := json.Unmarshal(state, s)
 	err := json.Unmarshal(state, s)
 
 
 	// clean the expired nodes
 	// clean the expired nodes
@@ -277,7 +275,7 @@ func (s *Store)Recovery(state []byte) error {
 
 
 // clean all expired keys
 // clean all expired keys
 func clean() {
 func clean() {
-	for key, node := range s.Nodes{
+	for key, node := range s.Nodes {
 
 
 		if node.ExpireTime.Equal(PERMANENT) {
 		if node.ExpireTime.Equal(PERMANENT) {
 			continue
 			continue

+ 13 - 16
store/store_test.go

@@ -1,9 +1,9 @@
 package store
 package store
 
 
 import (
 import (
+	"fmt"
 	"testing"
 	"testing"
 	"time"
 	"time"
-	"fmt"
 )
 )
 
 
 func TestStoreGet(t *testing.T) {
 func TestStoreGet(t *testing.T) {
@@ -53,7 +53,6 @@ func TestStoreGet(t *testing.T) {
 // 		t.Fatalf("Get expired value")
 // 		t.Fatalf("Get expired value")
 // 	}
 // 	}
 
 
-
 // 	s.Delete("foo")
 // 	s.Delete("foo")
 
 
 // }
 // }
@@ -63,8 +62,8 @@ func TestExpire(t *testing.T) {
 	fmt.Println("TEST EXPIRE")
 	fmt.Println("TEST EXPIRE")
 
 
 	// test expire
 	// test expire
-	Set("foo", "bar", time.Now().Add(time.Second * 1))
-	time.Sleep(2*time.Second)
+	Set("foo", "bar", time.Now().Add(time.Second*1))
+	time.Sleep(2 * time.Second)
 
 
 	res := Get("foo")
 	res := Get("foo")
 
 
@@ -73,7 +72,7 @@ func TestExpire(t *testing.T) {
 	}
 	}
 
 
 	//test change expire time
 	//test change expire time
-	Set("foo", "bar", time.Now().Add(time.Second * 10))
+	Set("foo", "bar", time.Now().Add(time.Second*10))
 
 
 	res = Get("foo")
 	res = Get("foo")
 
 
@@ -81,7 +80,7 @@ func TestExpire(t *testing.T) {
 		t.Fatalf("Cannot get Value")
 		t.Fatalf("Cannot get Value")
 	}
 	}
 
 
-	Set("foo", "barbar", time.Now().Add(time.Second * 1))
+	Set("foo", "barbar", time.Now().Add(time.Second*1))
 
 
 	time.Sleep(2 * time.Second)
 	time.Sleep(2 * time.Second)
 
 
@@ -91,13 +90,12 @@ func TestExpire(t *testing.T) {
 		t.Fatalf("Got expired value")
 		t.Fatalf("Got expired value")
 	}
 	}
 
 
-
 	// test change expire to stable
 	// test change expire to stable
-	Set("foo", "bar", time.Now().Add(time.Second * 1))
+	Set("foo", "bar", time.Now().Add(time.Second*1))
 
 
-	Set("foo", "bar", time.Unix(0,0))
+	Set("foo", "bar", time.Unix(0, 0))
 
 
-	time.Sleep(2*time.Second)
+	time.Sleep(2 * time.Second)
 
 
 	res = s.Get("foo")
 	res = s.Get("foo")
 
 
@@ -105,22 +103,21 @@ func TestExpire(t *testing.T) {
 		t.Fatalf("Cannot get Value")
 		t.Fatalf("Cannot get Value")
 	}
 	}
 
 
-	// test stable to expire 
-	s.Set("foo", "bar", time.Now().Add(time.Second * 1))
-	time.Sleep(2*time.Second)
+	// test stable to expire
+	s.Set("foo", "bar", time.Now().Add(time.Second*1))
+	time.Sleep(2 * time.Second)
 	res = s.Get("foo")
 	res = s.Get("foo")
 
 
 	if res.Exist {
 	if res.Exist {
 		t.Fatalf("Got expired value")
 		t.Fatalf("Got expired value")
 	}
 	}
 
 
-	// test set older node 
-	s.Set("foo", "bar", time.Now().Add(-time.Second * 1))
+	// test set older node
+	s.Set("foo", "bar", time.Now().Add(-time.Second*1))
 	res = s.Get("foo")
 	res = s.Get("foo")
 
 
 	if res.Exist {
 	if res.Exist {
 		t.Fatalf("Got expired value")
 		t.Fatalf("Got expired value")
 	}
 	}
 
 
-
 }
 }

+ 4 - 5
store/watcher.go

@@ -3,9 +3,9 @@ package store
 import (
 import (
 	"path"
 	"path"
 	"strings"
 	"strings"
-	//"fmt"
-	)
 
 
+//"fmt"
+)
 
 
 type Watchers struct {
 type Watchers struct {
 	chanMap map[string][]chan Response
 	chanMap map[string][]chan Response
@@ -14,7 +14,6 @@ type Watchers struct {
 // global watcher
 // global watcher
 var w *Watchers
 var w *Watchers
 
 
-
 // init the global watcher
 // init the global watcher
 func init() {
 func init() {
 	w = createWatcher()
 	w = createWatcher()
@@ -66,7 +65,7 @@ func notify(resp Response) error {
 			for _, c := range chans {
 			for _, c := range chans {
 				c <- resp
 				c <- resp
 			}
 			}
-			
+
 			// we have notified all the watchers at this path
 			// we have notified all the watchers at this path
 			// delete the map
 			// delete the map
 			delete(w.chanMap, currPath)
 			delete(w.chanMap, currPath)
@@ -75,4 +74,4 @@ func notify(resp Response) error {
 	}
 	}
 
 
 	return nil
 	return nil
-}
+}

+ 1 - 1
store/watcher_test.go

@@ -1,8 +1,8 @@
 package store
 package store
 
 
 import (
 import (
-	"testing"
 	"fmt"
 	"fmt"
+	"testing"
 	"time"
 	"time"
 )
 )
 
 

+ 17 - 12
trans_handler.go

@@ -1,16 +1,16 @@
 package main
 package main
 
 
-import(
-	"encoding/json"
-	"github.com/benbjohnson/go-raft"
+import (
 	"bytes"
 	"bytes"
-	"net/http"
+	"encoding/json"
 	"fmt"
 	"fmt"
+	"github.com/benbjohnson/go-raft"
 	"io"
 	"io"
+	"net/http"
 )
 )
 
 
 type transHandler struct {
 type transHandler struct {
-	name string
+	name   string
 	client *http.Client
 	client *http.Client
 }
 }
 
 
@@ -19,7 +19,9 @@ func (t transHandler) SendAppendEntriesRequest(server *raft.Server, peer *raft.P
 	var aersp *raft.AppendEntriesResponse
 	var aersp *raft.AppendEntriesResponse
 	var b bytes.Buffer
 	var b bytes.Buffer
 	json.NewEncoder(&b).Encode(req)
 	json.NewEncoder(&b).Encode(req)
-	
+
+	debug("Send LogEntries to %s ", peer.Name())
+
 	resp, err := Post(&t, fmt.Sprintf("%s/log/append", peer.Name()), &b)
 	resp, err := Post(&t, fmt.Sprintf("%s/log/append", peer.Name()), &b)
 
 
 	if resp != nil {
 	if resp != nil {
@@ -28,7 +30,7 @@ func (t transHandler) SendAppendEntriesRequest(server *raft.Server, peer *raft.P
 		if err = json.NewDecoder(resp.Body).Decode(&aersp); err == nil || err == io.EOF {
 		if err = json.NewDecoder(resp.Body).Decode(&aersp); err == nil || err == io.EOF {
 			return aersp, nil
 			return aersp, nil
 		}
 		}
-		
+
 	}
 	}
 	return aersp, fmt.Errorf("raftd: Unable to append entries: %v", err)
 	return aersp, fmt.Errorf("raftd: Unable to append entries: %v", err)
 }
 }
@@ -39,6 +41,8 @@ func (t transHandler) SendVoteRequest(server *raft.Server, peer *raft.Peer, req
 	var b bytes.Buffer
 	var b bytes.Buffer
 	json.NewEncoder(&b).Encode(req)
 	json.NewEncoder(&b).Encode(req)
 
 
+	debug("Send Vote to %s", peer.Name())
+
 	resp, err := Post(&t, fmt.Sprintf("%s/vote", peer.Name()), &b)
 	resp, err := Post(&t, fmt.Sprintf("%s/vote", peer.Name()), &b)
 
 
 	if resp != nil {
 	if resp != nil {
@@ -47,9 +51,9 @@ func (t transHandler) SendVoteRequest(server *raft.Server, peer *raft.Peer, req
 		if err = json.NewDecoder(resp.Body).Decode(&rvrsp); err == nil || err == io.EOF {
 		if err = json.NewDecoder(resp.Body).Decode(&rvrsp); err == nil || err == io.EOF {
 			return rvrsp, nil
 			return rvrsp, nil
 		}
 		}
-		
+
 	}
 	}
-	return rvrsp, fmt.Errorf("raftd: Unable to request vote: %v", err)
+	return rvrsp, fmt.Errorf("Unable to request vote: %v", err)
 }
 }
 
 
 // Sends SnapshotRequest RPCs to a peer when the server is the candidate.
 // Sends SnapshotRequest RPCs to a peer when the server is the candidate.
@@ -58,7 +62,8 @@ func (t transHandler) SendSnapshotRequest(server *raft.Server, peer *raft.Peer,
 	var b bytes.Buffer
 	var b bytes.Buffer
 	json.NewEncoder(&b).Encode(req)
 	json.NewEncoder(&b).Encode(req)
 
 
-	debug("[send] POST %s/snapshot [%d %d]", peer.Name(), req.LastTerm, req.LastIndex)
+	debug("Send Snapshot to %s [Last Term: %d, LastIndex %d]", peer.Name(),
+		req.LastTerm, req.LastIndex)
 
 
 	resp, err := Post(&t, fmt.Sprintf("%s/snapshot", peer.Name()), &b)
 	resp, err := Post(&t, fmt.Sprintf("%s/snapshot", peer.Name()), &b)
 
 
@@ -70,5 +75,5 @@ func (t transHandler) SendSnapshotRequest(server *raft.Server, peer *raft.Peer,
 			return aersp, nil
 			return aersp, nil
 		}
 		}
 	}
 	}
-	return aersp, fmt.Errorf("raftd: Unable to send snapshot: %v", err)
-}
+	return aersp, fmt.Errorf("Unable to send snapshot: %v", err)
+}

+ 6 - 6
web/conn.go

@@ -1,17 +1,17 @@
 package web
 package web
- 
+
 import (
 import (
 	"code.google.com/p/go.net/websocket"
 	"code.google.com/p/go.net/websocket"
 )
 )
- 
+
 type connection struct {
 type connection struct {
 	// The websocket connection.
 	// The websocket connection.
 	ws *websocket.Conn
 	ws *websocket.Conn
- 
+
 	// Buffered channel of outbound messages.
 	// Buffered channel of outbound messages.
 	send chan string
 	send chan string
 }
 }
- 
+
 func (c *connection) writer() {
 func (c *connection) writer() {
 	for message := range c.send {
 	for message := range c.send {
 		err := websocket.Message.Send(c.ws, message)
 		err := websocket.Message.Send(c.ws, message)
@@ -21,10 +21,10 @@ func (c *connection) writer() {
 	}
 	}
 	c.ws.Close()
 	c.ws.Close()
 }
 }
- 
+
 func wsHandler(ws *websocket.Conn) {
 func wsHandler(ws *websocket.Conn) {
 	c := &connection{send: make(chan string, 256), ws: ws}
 	c := &connection{send: make(chan string, 256), ws: ws}
 	h.register <- c
 	h.register <- c
 	defer func() { h.unregister <- c }()
 	defer func() { h.unregister <- c }()
 	c.writer()
 	c.writer()
-}
+}

+ 40 - 40
web/hub.go

@@ -1,61 +1,61 @@
 package web
 package web
 
 
 type hub struct {
 type hub struct {
-    // status
-    open    bool
+	// status
+	open bool
 
 
-    // Registered connections.
-    connections map[*connection]bool
+	// Registered connections.
+	connections map[*connection]bool
 
 
-    // Inbound messages from the connections.
-    broadcast chan string
+	// Inbound messages from the connections.
+	broadcast chan string
 
 
-    // Register requests from the connections.
-    register chan *connection
+	// Register requests from the connections.
+	register chan *connection
 
 
-    // Unregister requests from connections.
-    unregister chan *connection
+	// Unregister requests from connections.
+	unregister chan *connection
 }
 }
 
 
 var h = hub{
 var h = hub{
-    open:   false,
-    broadcast:   make(chan string),
-    register:    make(chan *connection),
-    unregister:  make(chan *connection),
-    connections: make(map[*connection]bool),
+	open:        false,
+	broadcast:   make(chan string),
+	register:    make(chan *connection),
+	unregister:  make(chan *connection),
+	connections: make(map[*connection]bool),
 }
 }
 
 
-func Hub() *hub{
-    return &h
+func Hub() *hub {
+	return &h
 }
 }
 
 
 func HubOpen() bool {
 func HubOpen() bool {
-    return h.open
+	return h.open
 }
 }
 
 
 func (h *hub) run() {
 func (h *hub) run() {
-    h.open = true
-    for {
-        select {
-        case c := <-h.register:
-            h.connections[c] = true
-        case c := <-h.unregister:
-            delete(h.connections, c)
-            close(c.send)
-        case m := <-h.broadcast:
-            for c := range h.connections {
-                select {
-                case c.send <- m:
-                default:
-                    delete(h.connections, c)
-                    close(c.send)
-                    go c.ws.Close()
-                }
-            }
-        }
-    }
+	h.open = true
+	for {
+		select {
+		case c := <-h.register:
+			h.connections[c] = true
+		case c := <-h.unregister:
+			delete(h.connections, c)
+			close(c.send)
+		case m := <-h.broadcast:
+			for c := range h.connections {
+				select {
+				case c.send <- m:
+				default:
+					delete(h.connections, c)
+					close(c.send)
+					go c.ws.Close()
+				}
+			}
+		}
+	}
 }
 }
 
 
 func (h *hub) Send(msg string) {
 func (h *hub) Send(msg string) {
-    h.broadcast <- msg
-}
+	h.broadcast <- msg
+}

+ 32 - 37
web/web.go

@@ -1,42 +1,41 @@
 package web
 package web
 
 
 import (
 import (
-    "fmt"
-    "net/http"
-    "github.com/xiangli-cmu/raft-etcd/store"
-    "github.com/benbjohnson/go-raft"
-    "time"
-    "code.google.com/p/go.net/websocket"
-    "html/template"
+	"code.google.com/p/go.net/websocket"
+	"fmt"
+	"github.com/benbjohnson/go-raft"
+	"github.com/xiangli-cmu/raft-etcd/store"
+	"html/template"
+	"net/http"
+	"time"
 )
 )
 
 
 var s *raft.Server
 var s *raft.Server
 
 
 type MainPage struct {
 type MainPage struct {
-    Leader string
-    Address string
+	Leader  string
+	Address string
 }
 }
 
 
 func handler(w http.ResponseWriter, r *http.Request) {
 func handler(w http.ResponseWriter, r *http.Request) {
-    fmt.Fprintf(w, "Leader:\n%s\n", s.Leader())
-    fmt.Fprintf(w, "Peers:\n")
+	fmt.Fprintf(w, "Leader:\n%s\n", s.Leader())
+	fmt.Fprintf(w, "Peers:\n")
 
 
-    for peerName, _ := range s.Peers() {
-        fmt.Fprintf(w, "%s\n", peerName)
-    }
+	for peerName, _ := range s.Peers() {
+		fmt.Fprintf(w, "%s\n", peerName)
+	}
 
 
+	fmt.Fprintf(w, "Data\n")
 
 
-    fmt.Fprintf(w, "Data\n")
+	s := store.GetStore()
 
 
-    s := store.GetStore()
-
-    for key, node := range s.Nodes {
-        if node.ExpireTime.Equal(time.Unix(0,0)) {
-            fmt.Fprintf(w, "%s %s\n", key, node.Value)
-        } else {
-            fmt.Fprintf(w, "%s %s %s\n", key, node.Value, node.ExpireTime)
-        }
-    }
+	for key, node := range s.Nodes {
+		if node.ExpireTime.Equal(time.Unix(0, 0)) {
+			fmt.Fprintf(w, "%s %s\n", key, node.Value)
+		} else {
+			fmt.Fprintf(w, "%s %s %s\n", key, node.Value, node.ExpireTime)
+		}
+	}
 
 
 }
 }
 
 
@@ -44,24 +43,20 @@ var mainTempl = template.Must(template.ParseFiles("home.html"))
 
 
 func mainHandler(c http.ResponseWriter, req *http.Request) {
 func mainHandler(c http.ResponseWriter, req *http.Request) {
 
 
-    p := &MainPage{Leader: s.Leader(),
-        Address: s.Name(),}
+	p := &MainPage{Leader: s.Leader(),
+		Address: s.Name()}
 
 
-    mainTempl.Execute(c, p)
+	mainTempl.Execute(c, p)
 }
 }
 
 
-
 func Start(server *raft.Server, port int) {
 func Start(server *raft.Server, port int) {
 	s = server
 	s = server
 
 
-    go h.run()
-    http.HandleFunc("/", mainHandler)
-    http.Handle("/ws", websocket.Handler(wsHandler))
+	go h.run()
+	http.HandleFunc("/", mainHandler)
+	http.Handle("/ws", websocket.Handler(wsHandler))
 
 
-    //http.HandleFunc("/", handler)
-    fmt.Println("web listening at port ", port)
-    http.ListenAndServe(fmt.Sprintf(":%v", port), nil)
+	//http.HandleFunc("/", handler)
+	fmt.Println("web listening at port ", port)
+	http.ListenAndServe(fmt.Sprintf(":%v", port), nil)
 }
 }
-
-
-