| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346 | package serverimport (	"fmt"	"context"	"log"	"strings"	"strconv"	"net"	"time"	"io"        "golang.zx2c4.com/wireguard/wgctrl/wgtypes"	"github.com/gravitl/netmaker/netclient/config"        "github.com/gravitl/netmaker/netclient/auth"        "github.com/gravitl/netmaker/netclient/local"        nodepb "github.com/gravitl/netmaker/grpc"        "google.golang.org/grpc"	"google.golang.org/grpc/metadata"	//homedir "github.com/mitchellh/go-homedir")func GetNode(network string) nodepb.Node {        modcfg, err := config.ReadConfig(network)        if err != nil {                log.Fatalf("Error: %v", err)        }	nodecfg := modcfg.Node	var node nodepb.Node	node.Name = nodecfg.Name	node.Interface = nodecfg.Interface	node.Nodenetwork = nodecfg.Network	node.Localaddress = nodecfg.LocalAddress	node.Address = nodecfg.WGAddress	node.Address6 = nodecfg.WGAddress6	node.Listenport = nodecfg.Port	node.Keepalive = nodecfg.KeepAlive	node.Postup = nodecfg.PostUp	node.Postdown = nodecfg.PostDown	node.Publickey = nodecfg.PublicKey	node.Macaddress = nodecfg.MacAddress	node.Endpoint = nodecfg.Endpoint	node.Password = nodecfg.Password	if nodecfg.DNS == "on" {		node.Dnsoff = false	} else {		node.Dnsoff = true	}        if nodecfg.IsDualStack == "yes" {                node.Isdualstack = true        } else {                node.Isdualstack = false        }        if nodecfg.IsIngressGateway == "yes" {                node.Isingressgateway= true        } else {                node.Isingressgateway = false        }        return node}func RemoveNetwork(network string) error {        //need to  implement checkin on server side        cfg, err := config.ReadConfig(network)        if err != nil {                return err        }	servercfg := cfg.Server        node := cfg.Node	fmt.Println("Deleting remote node with MAC: " + node.MacAddress)        var wcclient nodepb.NodeServiceClient        var requestOpts grpc.DialOption        requestOpts = grpc.WithInsecure()        conn, err := grpc.Dial(servercfg.GRPCAddress, requestOpts)	if err != nil {                log.Printf("Unable to establish client connection to " + servercfg.GRPCAddress + ": %v", err)		//return err        }else {        wcclient = nodepb.NewNodeServiceClient(conn)        ctx := context.Background()        ctx, err = auth.SetJWT(wcclient, network)        if err != nil {                //return err                log.Printf("Failed to authenticate: %v", err)        } else {        var header metadata.MD        _, err = wcclient.DeleteNode(                ctx,                &nodepb.DeleteNodeReq{                        Macaddress: node.MacAddress,                        NetworkName: node.Network,                },                grpc.Header(&header),        )        if err != nil {		log.Printf("Encountered error deleting node: %v", err)		fmt.Println(err)        } else {		fmt.Println("Deleted node " + node.MacAddress)	}	}	}	err = local.WipeLocal(network)	if err != nil {                log.Printf("Unable to wipe local config: %v", err)	}	if cfg.Daemon != "off" {		err =  local.RemoveSystemDServices(network)	}	return err}func GetPeers(macaddress string, network string, server string, dualstack bool, isIngressGateway bool) ([]wgtypes.PeerConfig, bool, []string, error) {        //need to  implement checkin on server side        hasGateway := false        var gateways []string        var peers []wgtypes.PeerConfig        var wcclient nodepb.NodeServiceClient        cfg, err := config.ReadConfig(network)        if err != nil {                log.Fatalf("Issue retrieving config for network: " + network +  ". Please investigate: %v", err)        }        nodecfg := cfg.Node        keepalive := nodecfg.KeepAlive        keepalivedur, err := time.ParseDuration(strconv.FormatInt(int64(keepalive), 10) + "s")        if err != nil {                log.Fatalf("Issue with format of keepalive value. Please update netconfig: %v", err)        }        requestOpts := grpc.WithInsecure()        conn, err := grpc.Dial(server, requestOpts)        if err != nil {                log.Fatalf("Unable to establish client connection to localhost:50051: %v", err)        }        // Instantiate the BlogServiceClient with our client connection to the server        wcclient = nodepb.NewNodeServiceClient(conn)        req := &nodepb.GetPeersReq{                Macaddress: macaddress,                Network: network,        }        ctx := context.Background()        ctx, err = auth.SetJWT(wcclient, network)        if err != nil {                fmt.Println("Failed to authenticate.")                return peers, hasGateway, gateways, err        }        var header metadata.MD        stream, err := wcclient.GetPeers(ctx, req, grpc.Header(&header))        if err != nil {                fmt.Println("Error retrieving peers")                fmt.Println(err)                return nil, hasGateway, gateways, err        }        for {                res, err := stream.Recv()                // If end of stream, break the loop                if err == io.EOF {                        break                }                // if err, return an error                if err != nil {                        if strings.Contains(err.Error(), "mongo: no documents in result") {                                continue                        } else {                        fmt.Println("ERROR ENCOUNTERED WITH RESPONSE")                        fmt.Println(res)                        return peers, hasGateway, gateways, err                        }                }                pubkey, err := wgtypes.ParseKey(res.Peers.Publickey)                if err != nil {                        fmt.Println("error parsing key")                        return peers, hasGateway, gateways, err                }                if nodecfg.PublicKey == res.Peers.Publickey {                        continue                }                if nodecfg.Endpoint == res.Peers.Endpoint {                        continue                }                var peer wgtypes.PeerConfig                var peeraddr = net.IPNet{                        IP: net.ParseIP(res.Peers.Address),                        Mask: net.CIDRMask(32, 32),                }                var allowedips []net.IPNet                allowedips = append(allowedips, peeraddr)                if res.Peers.Isegressgateway {                        hasGateway = true                        gateways = append(gateways,res.Peers.Egressgatewayrange)                        _, ipnet, err := net.ParseCIDR(res.Peers.Egressgatewayrange)                        if err != nil {                                fmt.Println("ERROR ENCOUNTERED SETTING GATEWAY")                                fmt.Println("NOT SETTING GATEWAY")                                fmt.Println(err)                        } else {                                fmt.Println("    Gateway Range: "  + res.Peers.Egressgatewayrange)                                allowedips = append(allowedips, *ipnet)                        }                }                if res.Peers.Address6 != "" && dualstack {                        var addr6 = net.IPNet{                                IP: net.ParseIP(res.Peers.Address6),                                Mask: net.CIDRMask(128, 128),                        }                        allowedips = append(allowedips, addr6)                }                if keepalive != 0 {                peer = wgtypes.PeerConfig{                        PublicKey: pubkey,                        PersistentKeepaliveInterval: &keepalivedur,                        Endpoint: &net.UDPAddr{                                IP:   net.ParseIP(res.Peers.Endpoint),                                Port: int(res.Peers.Listenport),                        },                        ReplaceAllowedIPs: true,                        AllowedIPs: allowedips,                        }                } else {                peer = wgtypes.PeerConfig{                        PublicKey: pubkey,                        Endpoint: &net.UDPAddr{                                IP:   net.ParseIP(res.Peers.Endpoint),                                Port: int(res.Peers.Listenport),                        },                        ReplaceAllowedIPs: true,                        AllowedIPs: allowedips,                        }                }                peers = append(peers, peer)        }        if isIngressGateway {                extPeers, err := GetExtPeers(macaddress, network, server, dualstack)                if err == nil {                        peers = append(peers, extPeers...)                } else {                        fmt.Println("ERROR RETRIEVING EXTERNAL PEERS")                        fmt.Println(err)                }        }        return peers, hasGateway, gateways, err}func GetExtPeers(macaddress string, network string, server string, dualstack bool) ([]wgtypes.PeerConfig, error) {        var peers []wgtypes.PeerConfig        var wcclient nodepb.NodeServiceClient        cfg, err := config.ReadConfig(network)        if err != nil {                log.Fatalf("Issue retrieving config for network: " + network +  ". Please investigate: %v", err)        }        nodecfg := cfg.Node        requestOpts := grpc.WithInsecure()        conn, err := grpc.Dial(server, requestOpts)        if err != nil {                log.Fatalf("Unable to establish client connection to localhost:50051: %v", err)        }        // Instantiate the BlogServiceClient with our client connection to the server        wcclient = nodepb.NewNodeServiceClient(conn)        req := &nodepb.GetExtPeersReq{                Macaddress: macaddress,                Network: network,        }        ctx := context.Background()        ctx, err = auth.SetJWT(wcclient, network)        if err != nil {                fmt.Println("Failed to authenticate.")                return peers, err        }        var header metadata.MD        stream, err := wcclient.GetExtPeers(ctx, req, grpc.Header(&header))        if err != nil {                fmt.Println("Error retrieving peers")                fmt.Println(err)                return nil, err        }        for {                res, err := stream.Recv()                // If end of stream, break the loop                if err == io.EOF {                        break                }                // if err, return an error                if err != nil {                        if strings.Contains(err.Error(), "mongo: no documents in result") {                                continue                        } else {                        fmt.Println("ERROR ENCOUNTERED WITH RESPONSE")                        fmt.Println(res)                        return peers, err                        }                }                pubkey, err := wgtypes.ParseKey(res.Extpeers.Publickey)                if err != nil {                        fmt.Println("error parsing key")                        return peers, err                }                if nodecfg.PublicKey == res.Extpeers.Publickey {                        continue                }                var peer wgtypes.PeerConfig                var peeraddr = net.IPNet{                        IP: net.ParseIP(res.Extpeers.Address),                        Mask: net.CIDRMask(32, 32),                }                var allowedips []net.IPNet                allowedips = append(allowedips, peeraddr)		if res.Extpeers.Address6 != "" && dualstack {                        var addr6 = net.IPNet{                                IP: net.ParseIP(res.Extpeers.Address6),                                Mask: net.CIDRMask(128, 128),                        }                        allowedips = append(allowedips, addr6)                }                peer = wgtypes.PeerConfig{                        PublicKey: pubkey,                        ReplaceAllowedIPs: true,                        AllowedIPs: allowedips,                        }                peers = append(peers, peer)        }        return peers, err}
 |