mirror of
https://github.com/zerotier/ZeroTierOne.git
synced 2025-06-06 12:33:44 +02:00
Basic control plane queries working.
This commit is contained in:
parent
b888e033c0
commit
a2605561af
4 changed files with 97 additions and 24 deletions
|
@ -373,7 +373,7 @@ ZT1_PeerList *Node::peers() const
|
||||||
ZT1_VirtualNetworkConfig *Node::networkConfig(uint64_t nwid) const
|
ZT1_VirtualNetworkConfig *Node::networkConfig(uint64_t nwid) const
|
||||||
{
|
{
|
||||||
Mutex::Lock _l(_networks_m);
|
Mutex::Lock _l(_networks_m);
|
||||||
std::map< uint64_t,SharedPtr<Network> >::iterator nw(_networks.find(nwid));
|
std::map< uint64_t,SharedPtr<Network> >::const_iterator nw(_networks.find(nwid));
|
||||||
if (nw != _networks.end()) {
|
if (nw != _networks.end()) {
|
||||||
ZT1_VirtualNetworkConfig *nc = (ZT1_VirtualNetworkConfig *)::malloc(sizeof(ZT1_VirtualNetworkConfig));
|
ZT1_VirtualNetworkConfig *nc = (ZT1_VirtualNetworkConfig *)::malloc(sizeof(ZT1_VirtualNetworkConfig));
|
||||||
nw->second->externalConfig(nc);
|
nw->second->externalConfig(nc);
|
||||||
|
|
|
@ -99,7 +99,7 @@ public:
|
||||||
ZT1_ResultCode leave(uint64_t nwid);
|
ZT1_ResultCode leave(uint64_t nwid);
|
||||||
ZT1_ResultCode multicastSubscribe(uint64_t nwid,uint64_t multicastGroup,unsigned long multicastAdi);
|
ZT1_ResultCode multicastSubscribe(uint64_t nwid,uint64_t multicastGroup,unsigned long multicastAdi);
|
||||||
ZT1_ResultCode multicastUnsubscribe(uint64_t nwid,uint64_t multicastGroup,unsigned long multicastAdi);
|
ZT1_ResultCode multicastUnsubscribe(uint64_t nwid,uint64_t multicastGroup,unsigned long multicastAdi);
|
||||||
uint64_t address(ZT1_Node *node) const;
|
uint64_t address() const;
|
||||||
void status(ZT1_NodeStatus *status) const;
|
void status(ZT1_NodeStatus *status) const;
|
||||||
ZT1_PeerList *peers() const;
|
ZT1_PeerList *peers() const;
|
||||||
ZT1_VirtualNetworkConfig *networkConfig(uint64_t nwid) const;
|
ZT1_VirtualNetworkConfig *networkConfig(uint64_t nwid) const;
|
||||||
|
|
|
@ -51,7 +51,7 @@ static std::string _jsonEscape(const char *s)
|
||||||
case '"': buf.append("\\\""); break;
|
case '"': buf.append("\\\""); break;
|
||||||
case '\\': buf.append("\\\\"); break;
|
case '\\': buf.append("\\\\"); break;
|
||||||
case '/': buf.append("\\/"); break;
|
case '/': buf.append("\\/"); break;
|
||||||
default: buf.push_back(*s); break;
|
default: buf.push_back(*p); break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return buf;
|
return buf;
|
||||||
|
@ -92,6 +92,22 @@ static std::string _jsonEnumerate(const struct sockaddr_storage *ss,unsigned int
|
||||||
buf.push_back(']');
|
buf.push_back(']');
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
static std::string _jsonEnumerate(const ZT1_PeerPhysicalPath *pp,unsigned int count)
|
||||||
|
{
|
||||||
|
char tmp[1024];
|
||||||
|
std::string buf;
|
||||||
|
buf.push_back('[');
|
||||||
|
for(unsigned int i=0;i<count;++i) {
|
||||||
|
if (i > 0)
|
||||||
|
buf.push_back(',');
|
||||||
|
buf.append("{\"address\":\"");
|
||||||
|
buf.append(_jsonEscape(reinterpret_cast<const InetAddress *>(&(pp[i].address))->toString()));
|
||||||
|
Utils::snprintf(tmp,sizeof(tmp),"\",\"lastSend\":%llu,\"lastReceive\":%llu,\"fixed\":%s}",pp[i].lastSend,pp[i].lastReceive,(pp[i].fixed == 0) ? "falase" : "true");
|
||||||
|
buf.append(tmp);
|
||||||
|
}
|
||||||
|
buf.push_back(']');
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
static void _jsonAppend(std::string &buf,const ZT1_VirtualNetworkConfig *nc)
|
static void _jsonAppend(std::string &buf,const ZT1_VirtualNetworkConfig *nc)
|
||||||
{
|
{
|
||||||
char json[65536];
|
char json[65536];
|
||||||
|
@ -141,6 +157,33 @@ static void _jsonAppend(std::string &buf,const ZT1_VirtualNetworkConfig *nc)
|
||||||
}
|
}
|
||||||
static void _jsonAppend(std::string &buf,const ZT1_Peer *peer)
|
static void _jsonAppend(std::string &buf,const ZT1_Peer *peer)
|
||||||
{
|
{
|
||||||
|
char json[65536];
|
||||||
|
const char *prole = "";
|
||||||
|
switch(peer->role) {
|
||||||
|
case ZT1_PEER_ROLE_LEAF: prole = "LEAF"; break;
|
||||||
|
case ZT1_PEER_ROLE_HUB: prole = "HUB"; break;
|
||||||
|
case ZT1_PEER_ROLE_SUPERNODE: prole = "SUPERNODE"; break;
|
||||||
|
}
|
||||||
|
Utils::snprintf(json,sizeof(json),
|
||||||
|
"{"
|
||||||
|
"\"address\": \"%.10llx\","
|
||||||
|
"\"versionMajor\": %d,"
|
||||||
|
"\"versionMinor\": %d,"
|
||||||
|
"\"versionRev\": %d,"
|
||||||
|
"\"version\": \"%d.%d.%d\","
|
||||||
|
"\"latency\": %u,"
|
||||||
|
"\"role\": \"%s\","
|
||||||
|
"\"paths\": %s"
|
||||||
|
"}",
|
||||||
|
peer->address,
|
||||||
|
peer->versionMajor,
|
||||||
|
peer->versionMinor,
|
||||||
|
peer->versionRev,
|
||||||
|
peer->versionMajor,peer->versionMinor,peer->versionRev,
|
||||||
|
peer->latency,
|
||||||
|
prole,
|
||||||
|
_jsonEnumerate(peer->paths,peer->pathCount).c_str());
|
||||||
|
buf.append(json);
|
||||||
}
|
}
|
||||||
|
|
||||||
ControlPlane::ControlPlane(Node *n,const std::set<std::string> atoks) :
|
ControlPlane::ControlPlane(Node *n,const std::set<std::string> atoks) :
|
||||||
|
@ -192,6 +235,7 @@ unsigned int ControlPlane::handleRequest(
|
||||||
if (ps[0] == "index") {
|
if (ps[0] == "index") {
|
||||||
responseContentType = "text/html";
|
responseContentType = "text/html";
|
||||||
responseBody = "<html><body>Hello World!</body></html>";
|
responseBody = "<html><body>Hello World!</body></html>";
|
||||||
|
scode = 200;
|
||||||
} else if (ps[0] == "status") {
|
} else if (ps[0] == "status") {
|
||||||
responseContentType = "application/json";
|
responseContentType = "application/json";
|
||||||
ZT1_NodeStatus status;
|
ZT1_NodeStatus status;
|
||||||
|
@ -203,7 +247,7 @@ unsigned int ControlPlane::handleRequest(
|
||||||
"\"online\":%s,"
|
"\"online\":%s,"
|
||||||
"\"versionMajor\":%d,"
|
"\"versionMajor\":%d,"
|
||||||
"\"versionMinor\":%d,"
|
"\"versionMinor\":%d,"
|
||||||
"\"versionRevision\":%d,"
|
"\"versionRev\":%d,"
|
||||||
"\"version\":\"%d.%d.%d\""
|
"\"version\":\"%d.%d.%d\""
|
||||||
"}",
|
"}",
|
||||||
status.address,
|
status.address,
|
||||||
|
@ -214,9 +258,11 @@ unsigned int ControlPlane::handleRequest(
|
||||||
ZEROTIER_ONE_VERSION_REVISION,
|
ZEROTIER_ONE_VERSION_REVISION,
|
||||||
ZEROTIER_ONE_VERSION_MAJOR,ZEROTIER_ONE_VERSION_MINOR,ZEROTIER_ONE_VERSION_REVISION);
|
ZEROTIER_ONE_VERSION_MAJOR,ZEROTIER_ONE_VERSION_MINOR,ZEROTIER_ONE_VERSION_REVISION);
|
||||||
responseBody = json;
|
responseBody = json;
|
||||||
|
scode = 200;
|
||||||
} else if (ps[0] == "config") {
|
} else if (ps[0] == "config") {
|
||||||
responseContentType = "application/json";
|
responseContentType = "application/json";
|
||||||
responseBody = "{}"; // TODO
|
responseBody = "{}"; // TODO
|
||||||
|
scode = 200;
|
||||||
} else if (ps[0] == "network") {
|
} else if (ps[0] == "network") {
|
||||||
ZT1_VirtualNetworkList *nws = _node->networks();
|
ZT1_VirtualNetworkList *nws = _node->networks();
|
||||||
if (nws) {
|
if (nws) {
|
||||||
|
@ -230,27 +276,53 @@ unsigned int ControlPlane::handleRequest(
|
||||||
_jsonAppend(responseBody,&(nws->networks[i]));
|
_jsonAppend(responseBody,&(nws->networks[i]));
|
||||||
}
|
}
|
||||||
responseBody.push_back(']');
|
responseBody.push_back(']');
|
||||||
|
scode = 200;
|
||||||
} else if (ps.size() == 2) {
|
} else if (ps.size() == 2) {
|
||||||
// Return a single network by ID or 404 if not found
|
// Return a single network by ID or 404 if not found
|
||||||
uint64_t wantnw = Utils::hexStrToU64(ps[1].c_str());
|
uint64_t wantnw = Utils::hexStrToU64(ps[1].c_str());
|
||||||
bool got = false;
|
|
||||||
for(unsigned long i=0;i<nws->networkCount;++i) {
|
for(unsigned long i=0;i<nws->networkCount;++i) {
|
||||||
if (nws->networks[i].nwid == wantnw) {
|
if (nws->networks[i].nwid == wantnw) {
|
||||||
got = true;
|
|
||||||
responseContentType = "application/json";
|
responseContentType = "application/json";
|
||||||
_jsonAppend(responseBody,&(nws->networks[i]));
|
_jsonAppend(responseBody,&(nws->networks[i]));
|
||||||
|
scode = 200;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!got)
|
} // else 404
|
||||||
scode = 404;
|
|
||||||
} else {
|
|
||||||
// Not sure what they want here, 404
|
|
||||||
scode = 404;
|
|
||||||
}
|
|
||||||
_node->freeQueryResult((void *)nws);
|
_node->freeQueryResult((void *)nws);
|
||||||
} else scode = 500;
|
} else {
|
||||||
|
scode = 500;
|
||||||
|
}
|
||||||
} else if (ps[0] == "peer") {
|
} else if (ps[0] == "peer") {
|
||||||
|
ZT1_PeerList *pl = _node->peers();
|
||||||
|
if (pl) {
|
||||||
|
if (ps.size() == 1) {
|
||||||
|
// Return [array] of all peers
|
||||||
|
responseContentType = "application/json";
|
||||||
|
responseBody = "[";
|
||||||
|
for(unsigned long i=0;i<pl->peerCount;++i) {
|
||||||
|
if (i > 0)
|
||||||
|
responseBody.push_back(',');
|
||||||
|
_jsonAppend(responseBody,&(pl->peers[i]));
|
||||||
|
}
|
||||||
|
responseBody.push_back(']');
|
||||||
|
scode = 200;
|
||||||
|
} else if (ps.size() == 2) {
|
||||||
|
// Return a single peer by ID or 404 if not found
|
||||||
|
uint64_t wantp = Utils::hexStrToU64(ps[1].c_str());
|
||||||
|
for(unsigned long i=0;i<pl->peerCount;++i) {
|
||||||
|
if (pl->peers[i].address == wantp) {
|
||||||
|
responseContentType = "application/json";
|
||||||
|
_jsonAppend(responseBody,&(pl->peers[i]));
|
||||||
|
scode = 200;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} // else 404
|
||||||
|
_node->freeQueryResult((void *)pl);
|
||||||
|
} else {
|
||||||
|
scode = 500;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} else if ((httpMethod == HTTP_POST)||(httpMethod == HTTP_PUT)) { // PUT is weird in REST but we'll take it anyway
|
} else if ((httpMethod == HTTP_POST)||(httpMethod == HTTP_PUT)) { // PUT is weird in REST but we'll take it anyway
|
||||||
} else if (httpMethod == HTTP_DELETE) {
|
} else if (httpMethod == HTTP_DELETE) {
|
||||||
|
|
|
@ -31,6 +31,7 @@
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
#include <set>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
|
@ -188,7 +189,7 @@ public:
|
||||||
if (_master)
|
if (_master)
|
||||||
_node->setNetconfMaster((void *)_master);
|
_node->setNetconfMaster((void *)_master);
|
||||||
|
|
||||||
_controlPlane = new ControlPlane(_node);
|
_controlPlane = new ControlPlane(_node,std::set<std::string>());
|
||||||
|
|
||||||
_nextBackgroundTaskDeadline = 0;
|
_nextBackgroundTaskDeadline = 0;
|
||||||
for(;;) {
|
for(;;) {
|
||||||
|
@ -453,7 +454,7 @@ public:
|
||||||
std::string contentType("text/plain"); // default if not changed in handleRequest()
|
std::string contentType("text/plain"); // default if not changed in handleRequest()
|
||||||
unsigned int scode = 404;
|
unsigned int scode = 404;
|
||||||
|
|
||||||
if ((htc->from == InetAddress::LO4)||(htc->from == InetAddress::LO6)) {
|
if ((htc->from.ipsEqual(InetAddress::LO4))||(htc->from.ipsEqual(InetAddress::LO6))) {
|
||||||
try {
|
try {
|
||||||
if (_controlPlane)
|
if (_controlPlane)
|
||||||
scode = _controlPlane->handleRequest(htc->parser.method,htc->url,htc->headers,htc->body,data,contentType);
|
scode = _controlPlane->handleRequest(htc->parser.method,htc->url,htc->headers,htc->body,data,contentType);
|
||||||
|
@ -467,15 +468,15 @@ public:
|
||||||
|
|
||||||
const char *scodestr;
|
const char *scodestr;
|
||||||
switch(scode) {
|
switch(scode) {
|
||||||
case 200: scodestr = "OK";
|
case 200: scodestr = "OK"; break;
|
||||||
case 400: scodestr = "Bad Request";
|
case 400: scodestr = "Bad Request"; break;
|
||||||
case 401: scodestr = "Unauthorized";
|
case 401: scodestr = "Unauthorized"; break;
|
||||||
case 403: scodestr = "Forbidden";
|
case 403: scodestr = "Forbidden"; break;
|
||||||
case 404: scodestr = "Not Found";
|
case 404: scodestr = "Not Found"; break;
|
||||||
case 500: scodestr = "Internal Server Error";
|
case 500: scodestr = "Internal Server Error"; break;
|
||||||
case 501: scodestr = "Not Implemented";
|
case 501: scodestr = "Not Implemented"; break;
|
||||||
case 503: scodestr = "Service Unavailable";
|
case 503: scodestr = "Service Unavailable"; break;
|
||||||
default: scodestr = "Error";
|
default: scodestr = "Error"; break;
|
||||||
}
|
}
|
||||||
|
|
||||||
Utils::snprintf(tmpn,sizeof(tmpn),"HTTP/1.1 %.3u %s\r\nCache-Control: no-cache\r\nPragma: no-cache\r\n",scode,scodestr);
|
Utils::snprintf(tmpn,sizeof(tmpn),"HTTP/1.1 %.3u %s\r\nCache-Control: no-cache\r\nPragma: no-cache\r\n",scode,scodestr);
|
||||||
|
|
Loading…
Add table
Reference in a new issue