auth
auth/client.go
Add support for registering Clients. Add an API endpoint to register Clients, which was the last step necessary before the OAuth2 integration could be tried out.
1.1 --- a/client.go Wed Dec 17 22:27:44 2014 -0500 1.2 +++ b/client.go Sun Jan 04 00:07:27 2015 -0500 1.3 @@ -1,8 +1,11 @@ 1.4 package auth 1.5 1.6 import ( 1.7 + "crypto/rand" 1.8 + "encoding/hex" 1.9 "encoding/json" 1.10 "errors" 1.11 + "github.com/gorilla/mux" 1.12 "net/http" 1.13 "net/url" 1.14 "time" 1.15 @@ -313,3 +316,80 @@ 1.16 defer m.endpointLock.RUnlock() 1.17 return int64(len(m.endpoints[client.String()])), nil 1.18 } 1.19 + 1.20 +type newClientReq struct { 1.21 + Name string `json:"name"` 1.22 + Logo string `json:"logo"` 1.23 + Website string `json:"website"` 1.24 + Type string `json:"type"` 1.25 + Endpoints []string `json:"endpoints"` 1.26 +} 1.27 + 1.28 +func RegisterClientHandlers(r *mux.Router, context Context) { 1.29 + r.Handle("/clients", wrap(context, CreateClientHandler)).Methods("POST") 1.30 +} 1.31 + 1.32 +func CreateClientHandler(w http.ResponseWriter, r *http.Request, c Context) { 1.33 + username, password, ok := r.BasicAuth() 1.34 + if !ok { 1.35 + // TODO(paddy): return error 1.36 + return 1.37 + } 1.38 + profile, err := authenticate(username, password, c) 1.39 + if err != nil { 1.40 + // TODO(paddy): return error 1.41 + return 1.42 + } 1.43 + var req newClientReq 1.44 + decoder := json.NewDecoder(r.Body) 1.45 + err = decoder.Decode(&req) 1.46 + if err != nil { 1.47 + encode(w, r, http.StatusBadRequest, invalidFormatResponse) 1.48 + return 1.49 + } 1.50 + secret := make([]byte, 32) 1.51 + _, err = rand.Read(secret) 1.52 + if err != nil { 1.53 + // TODO(paddy): return error 1.54 + return 1.55 + } 1.56 + client := Client{ 1.57 + ID: uuid.NewID(), 1.58 + Secret: hex.EncodeToString(secret), 1.59 + OwnerID: profile.ID, 1.60 + Name: req.Name, 1.61 + Logo: req.Logo, 1.62 + Website: req.Website, 1.63 + Type: req.Type, 1.64 + } 1.65 + err = c.SaveClient(client) 1.66 + if err != nil { 1.67 + // TODO(paddy): return error 1.68 + return 1.69 + } 1.70 + endpoints := []Endpoint{} 1.71 + for _, u := range req.Endpoints { 1.72 + uri, err := url.Parse(u) 1.73 + if err != nil { 1.74 + // TODO(paddy): add error to response 1.75 + continue 1.76 + } 1.77 + endpoint := Endpoint{ 1.78 + ID: uuid.NewID(), 1.79 + ClientID: client.ID, 1.80 + URI: *uri, 1.81 + Added: time.Now(), 1.82 + } 1.83 + err = c.AddEndpoint(client.ID, endpoint) 1.84 + if err != nil { 1.85 + // TODO(paddy): return error 1.86 + return 1.87 + } 1.88 + endpoints = append(endpoints, endpoint) 1.89 + } 1.90 + resp := response{ 1.91 + Clients: []Client{client}, 1.92 + Endpoints: endpoints, 1.93 + } 1.94 + encode(w, r, http.StatusCreated, resp) 1.95 +}