|
@@ -2,6 +2,7 @@ package controller
|
|
|
|
|
|
import (
|
|
|
"encoding/json"
|
|
|
+ "errors"
|
|
|
"fmt"
|
|
|
"net/http"
|
|
|
"strings"
|
|
@@ -40,13 +41,13 @@ func nodeHandlers(r *mux.Router) {
|
|
|
//
|
|
|
// Authenticate to make further API calls related to a network.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: successResponse
|
|
|
+// Responses:
|
|
|
+// 200: successResponse
|
|
|
func authenticate(response http.ResponseWriter, request *http.Request) {
|
|
|
|
|
|
var authRequest models.AuthParams
|
|
@@ -343,13 +344,13 @@ func authorize(nodesAllowed, networkCheck bool, authNetwork string, next http.Ha
|
|
|
//
|
|
|
// Gets all nodes associated with network including pending nodes.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeSliceResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeSliceResponse
|
|
|
func getNetworkNodes(w http.ResponseWriter, r *http.Request) {
|
|
|
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
@@ -382,13 +383,14 @@ func getNetworkNodes(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Get all nodes across all networks.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
+//
|
|
|
+// Responses:
|
|
|
+// 200: nodeSliceResponse
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeSliceResponse
|
|
|
// Not quite sure if this is necessary. Probably necessary based on front end but may want to review after iteration 1 if it's being used or not
|
|
|
func getAllNodes(w http.ResponseWriter, r *http.Request) {
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
@@ -439,13 +441,13 @@ func getUsersNodes(user models.User) ([]models.Node, error) {
|
|
|
//
|
|
|
// Get an individual node.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func getNode(w http.ResponseWriter, r *http.Request) {
|
|
|
// set header.
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
@@ -504,13 +506,13 @@ func getNode(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Create a node on a network.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeGetResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeGetResponse
|
|
|
func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
|
|
@@ -547,6 +549,12 @@ func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
return
|
|
|
}
|
|
|
|
|
|
+ if !logic.IsVersionComptatible(node.Version) {
|
|
|
+ err := errors.New("incomatible netclient version")
|
|
|
+ logic.ReturnErrorResponse(w, r, logic.FormatError(err, "badrequest"))
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
node.Network = networkName
|
|
|
|
|
|
network, err := logic.GetNetworkByNode(&node)
|
|
@@ -631,7 +639,7 @@ func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
}
|
|
|
if !updatedUserNode { // user was found but not updated, so delete node
|
|
|
logger.Log(0, "failed to add node to user", keyName)
|
|
|
- logic.DeleteNodeByID(&node, true)
|
|
|
+ logic.DeleteNode(&node, true)
|
|
|
logic.ReturnErrorResponse(w, r, logic.FormatError(err, "internal"))
|
|
|
return
|
|
|
}
|
|
@@ -645,12 +653,12 @@ func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
return
|
|
|
}
|
|
|
|
|
|
- // Create client for this node in Mq
|
|
|
+ // Create client for this host in Mq
|
|
|
event := mq.MqDynsecPayload{
|
|
|
Commands: []mq.MqDynSecCmd{
|
|
|
{ // delete if any client exists already
|
|
|
Command: mq.DeleteClientCmd,
|
|
|
- Username: node.ID,
|
|
|
+ Username: node.HostID,
|
|
|
},
|
|
|
{
|
|
|
Command: mq.CreateRoleCmd,
|
|
@@ -660,7 +668,7 @@ func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
},
|
|
|
{
|
|
|
Command: mq.CreateClientCmd,
|
|
|
- Username: node.ID,
|
|
|
+ Username: node.HostID,
|
|
|
Password: nodePassword,
|
|
|
Textname: node.Name,
|
|
|
Roles: []mq.MqDynSecRole{
|
|
@@ -700,13 +708,14 @@ func createNode(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Takes a node out of pending state.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
+//
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
// Takes node out of pending state
|
|
|
// TODO: May want to use cordon/uncordon terminology instead of "ispending".
|
|
|
func uncordonNode(w http.ResponseWriter, r *http.Request) {
|
|
@@ -733,13 +742,13 @@ func uncordonNode(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Create an egress gateway.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func createEgressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
var gateway models.EgressGatewayRequest
|
|
|
var params = mux.Vars(r)
|
|
@@ -772,13 +781,13 @@ func createEgressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Delete an egress gateway.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func deleteEgressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
var params = mux.Vars(r)
|
|
@@ -806,13 +815,13 @@ func deleteEgressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Create an ingress gateway.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func createIngressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
var params = mux.Vars(r)
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
@@ -850,13 +859,13 @@ func createIngressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Delete an ingress gateway.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func deleteIngressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
var params = mux.Vars(r)
|
|
@@ -888,13 +897,13 @@ func deleteIngressGateway(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Update an individual node.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func updateNode(w http.ResponseWriter, r *http.Request) {
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
|
|
@@ -998,13 +1007,13 @@ func updateNode(w http.ResponseWriter, r *http.Request) {
|
|
|
//
|
|
|
// Delete an individual node.
|
|
|
//
|
|
|
-// Schemes: https
|
|
|
+// Schemes: https
|
|
|
//
|
|
|
-// Security:
|
|
|
-// oauth
|
|
|
+// Security:
|
|
|
+// oauth
|
|
|
//
|
|
|
-// Responses:
|
|
|
-// 200: nodeResponse
|
|
|
+// Responses:
|
|
|
+// 200: nodeResponse
|
|
|
func deleteNode(w http.ResponseWriter, r *http.Request) {
|
|
|
// Set header
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
@@ -1013,22 +1022,11 @@ func deleteNode(w http.ResponseWriter, r *http.Request) {
|
|
|
var params = mux.Vars(r)
|
|
|
var nodeid = params["nodeid"]
|
|
|
fromNode := r.Header.Get("requestfrom") == "node"
|
|
|
- var node, err = logic.GetNodeByID(nodeid)
|
|
|
+ node, err := logic.GetNodeByID(nodeid)
|
|
|
if err != nil {
|
|
|
- if fromNode {
|
|
|
- node, err = logic.GetDeletedNodeByID(nodeid)
|
|
|
- if err != nil {
|
|
|
- logger.Log(0, r.Header.Get("user"),
|
|
|
- fmt.Sprintf("error fetching node from deleted nodes [ %s ] info: %v", nodeid, err))
|
|
|
- logic.ReturnErrorResponse(w, r, logic.FormatError(err, "badrequest"))
|
|
|
- return
|
|
|
- }
|
|
|
- } else {
|
|
|
- logger.Log(0, r.Header.Get("user"),
|
|
|
- fmt.Sprintf("error fetching node [ %s ] info: %v", nodeid, err))
|
|
|
- logic.ReturnErrorResponse(w, r, logic.FormatError(err, "badrequest"))
|
|
|
- return
|
|
|
- }
|
|
|
+ logger.Log(0, "error retrieving node to delete", err.Error())
|
|
|
+ logic.ReturnErrorResponse(w, r, logic.FormatError(err, "badrequest"))
|
|
|
+ return
|
|
|
}
|
|
|
if isServer(&node) {
|
|
|
err := fmt.Errorf("cannot delete server node")
|
|
@@ -1044,34 +1042,35 @@ func deleteNode(w http.ResponseWriter, r *http.Request) {
|
|
|
return
|
|
|
}
|
|
|
}
|
|
|
- //send update to node to be deleted before deleting on server otherwise message cannot be sent
|
|
|
- node.Action = models.NODE_DELETE
|
|
|
-
|
|
|
- err = logic.DeleteNodeByID(&node, fromNode)
|
|
|
- if err != nil {
|
|
|
- logic.ReturnErrorResponse(w, r, logic.FormatError(err, "internal"))
|
|
|
+ if err := logic.DeleteNode(&node, fromNode); err != nil {
|
|
|
+ logic.ReturnErrorResponse(w, r, logic.FormatError(fmt.Errorf("failed to delete node"), "internal"))
|
|
|
return
|
|
|
}
|
|
|
if fromNode {
|
|
|
- // deletes node related role and client
|
|
|
- event := mq.MqDynsecPayload{
|
|
|
- Commands: []mq.MqDynSecCmd{
|
|
|
- {
|
|
|
- Command: mq.DeleteClientCmd,
|
|
|
- Username: nodeid,
|
|
|
- },
|
|
|
- },
|
|
|
- }
|
|
|
-
|
|
|
- if err := mq.PublishEventToDynSecTopic(event); err != nil {
|
|
|
- logger.Log(0, fmt.Sprintf("failed to send DynSec command [%v]: %v",
|
|
|
- event.Commands, err.Error()))
|
|
|
+ //check if server should be removed from mq
|
|
|
+ found := false
|
|
|
+ // err is irrelevent
|
|
|
+ nodes, _ := logic.GetAllNodes()
|
|
|
+ for _, nodetocheck := range nodes {
|
|
|
+ if nodetocheck.HostID == node.HostID {
|
|
|
+ found = true
|
|
|
+ break
|
|
|
+ }
|
|
|
}
|
|
|
- }
|
|
|
-
|
|
|
- if servercfg.Is_EE {
|
|
|
- if err = logic.EnterpriseResetAllPeersFailovers(node.ID, node.Network); err != nil {
|
|
|
- logger.Log(0, "failed to reset failover lists during node delete for node", node.Name, node.Network)
|
|
|
+ if !found {
|
|
|
+ // deletes node related role and client
|
|
|
+ event := mq.MqDynsecPayload{
|
|
|
+ Commands: []mq.MqDynSecCmd{
|
|
|
+ {
|
|
|
+ Command: mq.DeleteClientCmd,
|
|
|
+ Username: node.HostID,
|
|
|
+ },
|
|
|
+ },
|
|
|
+ }
|
|
|
+ if err := mq.PublishEventToDynSecTopic(event); err != nil {
|
|
|
+ logger.Log(0, fmt.Sprintf("failed to send DynSec command [%v]: %v",
|
|
|
+ event.Commands, err.Error()))
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
logic.ReturnSuccessResponse(w, r, nodeid+" deleted.")
|