38 #include <netinet/in.h>
41 #include <sys/socket.h>
43 #include <arpa/inet.h>
51 #define G_START_HUB "GVOHub::start_hub()"
52 #define G_GET_SOCKET "GVOHub::get_socket()"
209 result.append(
"=== GVOHub ===");
316 std::string msg =
"Unable to start listening on Hub socket. Errno="+
322 struct sockaddr_in cli_addr;
323 socklen_t clilen =
sizeof(cli_addr);
329 int socket = accept(
m_socket, (
struct sockaddr *)&cli_addr, &clilen);
331 std::string msg =
"Client connection to socket not accepted.";
369 #if defined(G_CONSOLE_DUMP)
370 std::cout <<
"GVOHub::handle_request" << std::endl;
377 std::string message =
"";
386 message.append(std::string(buffer));
392 #if defined(G_SHOW_MESSAGE)
393 std::cout << std::endl;
394 std::cout <<
"GVOHub has received the following message:" << std::endl;
395 std::cout <<
"==========================================" << std::endl;
396 std::cout << message << std::endl;
401 size_t start = message.find(
"<?xml");
402 if (start != std::string::npos) {
403 xml =
GXml(message.substr(start, std::string::npos));
407 std::string method_called;
412 method_called = text->
text();
417 #if defined(G_CONSOLE_DUMP)
418 std::cout <<
"GVOHub has received the message type \"";
419 std::cout << method_called <<
"\"" << std::endl;
423 if (method_called.compare(
"samp.hub.ping") == 0) {
426 else if (method_called.compare(
"samp.hub.register") == 0) {
429 else if (method_called.compare(
"samp.hub.unregister") == 0) {
432 else if (method_called.compare(
"samp.hub.declareMetadata") == 0) {
435 else if (method_called.compare(
"samp.hub.declareSubscriptions") == 0) {
438 else if (method_called.compare(
"samp.hub.setXmlrpcCallback") == 0) {
441 else if (method_called.compare(
"samp.hub.getSubscriptions") == 0) {
444 else if (method_called.compare(
"samp.hub.getRegisteredClients") == 0) {
447 else if (method_called.compare(
"samp.hub.getSubscribedClients") == 0) {
450 else if (method_called.compare(
"samp.hub.getMetadata") == 0) {
453 else if (method_called.compare(
"samp.hub.notify") == 0) {
456 else if (method_called.compare(
"samp.hub.notifyAll") == 0) {
459 else if (method_called.compare(
"samp.hub.call") == 0) {
462 else if (method_called.compare(
"samp.hub.callAll") == 0) {
465 else if (method_called.compare(
"samp.hub.callAndWait") == 0) {
468 else if (method_called.compare(
"samp.hub.reply") == 0) {
471 else if (method_called.compare(
"samp.hub.shutdown") == 0) {
490 #if defined(G_CONSOLE_DUMP)
491 std::cout <<
"GVOHub::request_ping" << std::endl;
513 #if defined(G_CONSOLE_DUMP)
514 std::cout <<
"GVOHub::request_register" << std::endl;
519 std::string reference;
524 if (
m_clients[i].reference == reference) {
543 std::string response =
"";
546 response.append(
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
547 response.append(
"<methodResponse>\n");
548 response.append(
"<params>\n");
549 response.append(
" <param><value><struct>\n");
550 response.append(
" <member>\n");
551 response.append(
" <name>samp.private-key</name>\n");
552 response.append(
" <value>"+voclient.
private_key+
"</value>\n");
553 response.append(
" </member>\n");
554 response.append(
" <member>\n");
555 response.append(
" <name>samp.hub-id</name>\n");
556 response.append(
" <value>"+
m_hub_id+
"</value>\n");
557 response.append(
" </member>\n");
558 response.append(
" <member>\n");
559 response.append(
" <name>samp.self-id</name>\n");
560 response.append(
" <value>"+voclient.
reference+
"</value>\n");
561 response.append(
" </member>\n");
562 response.append(
" <member>\n");
563 response.append(
" <name>samp.status</name>\n");
564 response.append(
" <value>samp.ok</value>\n");
565 response.append(
" </member>\n");
566 response.append(
" <member>\n");
567 response.append(
" <name>samp.url-translator</name>\n");
568 response.append(
" <value>"+
hub_url()+
"</value>\n");
569 response.append(
" </member>\n");
570 response.append(
" </struct></value></param>\n");
571 response.append(
"</params>\n");
572 response.append(
"</methodResponse>\n");
578 for (
int i = 0; i <
m_clients.size(); ++i) {
579 for (
int j = 0; j <
m_clients[i].subscriptions.size(); ++j) {
580 if (
"samp.hub.event.register" ==
m_clients[i].subscriptions[j]) {
603 #if defined(G_CONSOLE_DUMP)
604 std::cout <<
"GVOHub::request_unregister" << std::endl;
617 for (
int k = 0; k <
m_clients.size(); ++k) {
619 for (
int j = 0; j <
m_clients[k].subscriptions.size(); ++j) {
620 if (
"samp.hub.event.unregister" ==
m_clients[k].subscriptions[j]) {
633 #if defined(G_CONSOLE_ERRORS)
635 std::cout <<
"*** ERROR: GVOHub::request_unregister: ";
637 std::cout <<
"\"" << std::endl;
657 #if defined(G_CONSOLE_DUMP)
658 std::cout <<
"GVOHub::request_declare_metadata" << std::endl;
668 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > value > struct");
684 for (
int k = 0; k <
m_clients.size(); ++k) {
686 for (
int j = 0; j <
m_clients[k].subscriptions.size(); ++j) {
687 if (
"samp.hub.event.metadata" ==
m_clients[k].subscriptions[j]) {
697 #if defined(G_CONSOLE_ERRORS)
699 std::cout <<
"*** ERROR: GVOHub::request_declare_metadata: ";
701 std::cout <<
"\"" << std::endl;
721 #if defined(G_CONSOLE_DUMP)
722 std::cout <<
"GVOHub::request_declare_subscriptions" << std::endl;
735 for (
int k = 0; k < subscriptions.size(); ++k) {
736 m_clients[i].subscriptions.push_back(subscriptions[k]);
745 #if defined(G_CONSOLE_ERRORS)
747 std::cout <<
"*** ERROR: GVOHub::request_declare_subscriptions: ";
749 std::cout <<
"\"" << std::endl;
767 const socklen_t& sock)
770 #if defined(G_CONSOLE_DUMP)
771 std::cout <<
"GVOHub::request_set_xml_rpc_callback" << std::endl;
789 #if defined(G_CONSOLE_ERRORS)
791 std::cout <<
"*** ERROR: GVOHub::request_set_xml_rpc_callback: ";
793 std::cout <<
"\"" << std::endl;
813 #if defined(G_CONSOLE_DUMP)
814 std::cout <<
"GVOHub::request_get_subscriptions" << std::endl;
821 std::string response =
"";
824 response.append(
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
825 response.append(
"<methodResponse>\n");
826 response.append(
"<params>\n");
827 response.append(
" <param><value><struct>\n");
830 if (client_name ==
"gammalib_hub") {
844 for (
int k = 0; k <
m_clients[i].subscriptions.size(); ++k) {
845 response.append(
" <member>\n");
846 response.append(
" <name>");
847 response.append(
m_clients[i].subscriptions[k]);
848 response.append(
"</name>\n");
849 response.append(
" <value></value>\n");
850 response.append(
" </member>\n");
856 #if defined(G_CONSOLE_ERRORS)
858 std::cout <<
"*** ERROR: GVOHub::request_get_subscriptions: ";
860 std::cout <<
"\"" << std::endl;
867 response.append(
" </struct></value></param>\n");
868 response.append(
"</params>\n");
869 response.append(
"</methodResponse>\n");
890 #if defined(G_CONSOLE_DUMP)
891 std::cout <<
"GVOHub::request_get_registered_clients" << std::endl;
898 std::string msg =
"";
901 msg.append(
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
902 msg.append(
"<methodResponse>\n");
903 msg.append(
"<params>\n");
904 msg.append(
" <param><value><array><data>\n");
905 msg.append(
" <value>gammalib_hub</value>\n");
908 for (
int i = 0; i <
m_clients.size(); ++i) {
910 msg.append(
" <value>");
912 msg.append(
"</value>\n");
917 msg.append(
" </data></array></value></param>\n");
918 msg.append(
"</params>\n");
919 msg.append(
"</methodResponse>\n");
940 #if defined(G_CONSOLE_DUMP)
941 std::cout <<
"GVOHub::request_get_subscribed_clients" << std::endl;
945 std::string msg =
"";
947 msg.append(
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
948 msg.append(
"<methodResponse>\n");
949 msg.append(
"<params>\n");
950 msg.append(
" <param><value><struct>\n");
951 msg.append(
" <member>\n");
952 msg.append(
" <name>c0</name>\n");
953 msg.append(
" <value><struct></struct></value>\n");
954 msg.append(
" </member>\n");
955 msg.append(
" <member>\n");
956 msg.append(
" <name>gammalib_hub</name>\n");
957 msg.append(
" <value><struct></struct></value>\n");
958 msg.append(
" </member>\n");
959 msg.append(
" </struct></value></param>\n");
960 msg.append(
"</params>\n");
961 msg.append(
"</methodResponse>");
982 #if defined(G_CONSOLE_DUMP)
983 std::cout <<
"GVOHub::request_get_metadata" << std::endl;
990 std::string response =
"";
993 response.append(
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n");
994 response.append(
"<methodResponse>\n");
995 response.append(
"<params>\n");
996 response.append(
" <param><value><struct>\n");
997 response.append(
" <member>\n");
998 response.append(
" <name>samp.status</name>\n");
999 response.append(
" <value>samp.ok</value>\n");
1000 response.append(
" </member>\n");
1003 if (client_name ==
"gammalib_hub") {
1004 response.append(
" <member>\n");
1005 response.append(
" <name>samp.name</name>\n");
1006 response.append(
" <value>gammalib_hub</value>\n");
1007 response.append(
" </member>\n");
1008 response.append(
" <member>\n");
1009 response.append(
" <name>samp.description.text</name>\n");
1010 response.append(
" <value>GammaLib VO Hub</value>\n");
1011 response.append(
" </member>\n");
1012 response.append(
" <member>\n");
1013 response.append(
" <name>samp.icon.url</name>\n");
1014 response.append(
" <value>http://a.fsdn.com/allura/p/gammalib/icon</value>\n");
1015 response.append(
" </member>\n");
1016 response.append(
" <member>\n");
1017 response.append(
" <name>samp.documentation.url</name>\n");
1018 response.append(
" <value>http://cta.irap.omp.eu/gammalib/user_manual/modules/vo.html</value>\n");
1019 response.append(
" </member>\n");
1020 response.append(
" <member>\n");
1021 response.append(
" <name>author.affiliation</name>\n");
1022 response.append(
" <value>IRAP, Toulouse, France</value>\n");
1023 response.append(
" </member>\n");
1024 response.append(
" <member>\n");
1025 response.append(
" <name>author.email</name>\n");
1026 response.append(
" <value>jurgen.knodlseder@irap.omp.eu</value>\n");
1027 response.append(
" </member>\n");
1028 response.append(
" <member>\n");
1029 response.append(
" <name>author.name</name>\n");
1030 response.append(
" <value>J. Knoedlseder, T. Louge</value>\n");
1031 response.append(
" </member>\n");
1032 response.append(
" <member>\n");
1033 response.append(
" <name>home.page</name>\n");
1034 response.append(
" <value>http://cta.irap.omp.eu/gammalib/</value>\n");
1035 response.append(
" </member>\n");
1048 response.append(
" <member>\n");
1049 response.append(
" <name>samp.name</name>\n");
1050 response.append(
" <value>"+
m_clients[i].name+
"</value>\n");
1051 response.append(
" </member>\n");
1052 response.append(
" <member>\n");
1053 response.append(
" <name>samp.description.text</name>\n");
1054 response.append(
" <value>"+
m_clients[i].description+
"</value>\n");
1055 response.append(
" </member>\n");
1056 response.append(
" <member>\n");
1057 response.append(
" <name>samp.icon.url</name>\n");
1058 response.append(
" <value>"+
m_clients[i].icon+
"</value>\n");
1059 response.append(
" </member>\n");
1060 response.append(
" <member>\n");
1061 response.append(
" <name>samp.documentation.url</name>\n");
1062 response.append(
" <value>"+
m_clients[i].documentation+
"</value>\n");
1063 response.append(
" </member>\n");
1064 response.append(
" <member>\n");
1065 response.append(
" <name>author.affiliation</name>\n");
1066 response.append(
" <value>"+
m_clients[i].affiliation+
"</value>\n");
1067 response.append(
" </member>\n");
1068 response.append(
" <member>\n");
1069 response.append(
" <name>author.email</name>\n");
1070 response.append(
" <value>"+
m_clients[i].email+
"</value>\n");
1071 response.append(
" </member>\n");
1072 response.append(
" <member>\n");
1073 response.append(
" <name>author.name</name>\n");
1074 response.append(
" <value>"+
m_clients[i].author_name+
"</value>\n");
1075 response.append(
" </member>\n");
1076 response.append(
" <member>\n");
1077 response.append(
" <name>home.page</name>\n");
1078 response.append(
" <value>"+
m_clients[i].homepage+
"</value>\n");
1079 response.append(
" </member>\n");
1084 #if defined(G_CONSOLE_ERRORS)
1086 std::cout <<
"*** ERROR: GVOHub::request_get_metadata: ";
1088 std::cout <<
"\"" << std::endl;
1095 response.append(
" </struct></value></param>\n");
1096 response.append(
"</params>\n");
1097 response.append(
"</methodResponse>\n");
1120 #if defined(G_CONSOLE_DUMP)
1121 std::cout <<
"GVOHub::request_notify_all entrance" << std::endl;
1127 #if defined(G_CONSOLE_DUMP)
1128 std::cout <<
"mtype:"+mtype << std::endl;
1135 for (
int i = 0; i <
m_clients.size(); ++i) {
1138 for (
int j = 0; j <
m_clients[i].subscriptions.size(); ++j) {
1141 if (mtype ==
m_clients[i].subscriptions[j]) {
1144 if (mtype ==
"image.load.fits") {
1149 else if (mtype ==
"table.load.votable") {
1175 #if defined(G_CONSOLE_DUMP)
1176 std::cout <<
"GVOHub::request_shutdown" << std::endl;
1200 #if defined(G_CONSOLE_DUMP)
1201 std::cout <<
"GVOHub::get_client_key" << std::endl;
1205 std::string client_key =
"";
1208 const GXmlNode* node = xml.
element(
"methodCall > params > param > value");
1212 client_key = text->
text();
1233 #if defined(G_CONSOLE_DUMP)
1234 std::cout <<
"GVOHub::get_client_index" << std::endl;
1247 for (
int i = 0; i <
m_clients.size(); ++i) {
1273 #if defined(G_CONSOLE_DUMP)
1274 std::cout <<
"GVOHub::get_client_index" << std::endl;
1281 for (
int i = 0; i <
m_clients.size(); ++i) {
1282 if (
m_clients[i].reference == reference) {
1312 const std::string& name)
const
1315 std::string value =
"";
1319 #if defined(G_CONSOLE_DUMP)
1320 std::cout <<
"GVOHub::get_response_value parsing non null node" << std::endl;
1322 int num = node->
elements(
"member");
1323 for (
int i = 0; i < num; ++i) {
1325 std::string one_name;
1326 std::string one_value;
1328 #if defined(G_CONSOLE_DUMP)
1329 std::cout <<
"GVOHub::get_response_value parsing "+one_name+
" " + one_value << std::endl;
1331 if (one_name == name) {
1338 #if defined(G_CONSOLE_DUMP)
1339 std::cout <<
"GVOHub::get_response_value parsing NULL node" << std::endl;
1356 std::vector<std::string> subscriptions;
1359 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > "
1362 int num = node->
elements(
"member");
1363 for (
int i = 0; i < num; ++i) {
1365 if (member != NULL) {
1370 subscriptions.push_back(text->
text());
1378 return subscriptions;
1394 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > "
1418 std::string url =
"";
1422 if (hub_ptr != NULL) {
1426 std::string lockurl = std::string(hub_ptr);
1427 if (lockurl.compare(0, 12,
"std-lockurl:") == 0) {
1430 url = lockurl.substr(12, std::string::npos);
1443 std::string prefix =
"";
1445 if (home_ptr != NULL) {
1446 prefix = std::string(home_ptr) +
"/";
1450 url = prefix +
".samp";
1471 FILE* fptr = fopen(lockurl.c_str(),
"w");
1477 fprintf(fptr,
"# SAMP lockfile\n");
1478 fprintf(fptr,
"# Required keys:\n");
1479 fprintf(fptr,
"samp.secret=%s\n",
m_secret.c_str());
1480 fprintf(fptr,
"samp.hub.xmlrpc.url=%s\n",
hub_url().c_str());
1481 fprintf(fptr,
"samp.profile.version=%s\n",
m_version.c_str());
1482 fprintf(fptr,
"# Info stored by hub for some private reason:\n");
1483 fprintf(fptr,
"gammalib.hubid=%s\n",
m_hub_id.c_str());
1506 std::remove(lockurl.c_str());
1526 struct sockaddr_in serv_addr;
1529 for (
int i = 0; i < 100; ++i) {
1532 std::memset(&serv_addr, 0,
sizeof(serv_addr));
1535 serv_addr.sin_family = AF_INET;
1536 serv_addr.sin_addr.s_addr = inet_addr(
m_hub_host.c_str());
1537 serv_addr.sin_port = htons(port);
1540 sock = socket(AF_INET, SOCK_STREAM, 0);
1544 std::string msg =
"Unable to create Hub socket. Errno="+
1550 if (bind(sock, (
struct sockaddr*)&serv_addr,
sizeof(serv_addr)) < 0) {
1551 if (errno == EADDRINUSE) {
1556 std::string msg =
"Unable to bind Hub socket to address "+
1590 int length = content.length();
1593 std::string prefix =
"HTTP/1.1 200 OK\n"
1594 "Connection: close\n"
1595 "Content-Type: text/xml\n"
1600 std::string post = prefix + content;
1603 #if defined(G_SHOW_MESSAGE)
1604 std::cout << std::endl;
1605 std::cout <<
"GVOHub response:" << std::endl;
1606 std::cout <<
"================" << std::endl;
1607 std::cout << post << std::endl;
1613 int length = post.length();
1614 int sent_length = send(sock, post.c_str(), length, 0);
1615 if (sent_length < length) {
1616 post = post.substr(sent_length, std::string::npos);
1640 std::string response =
"";
1643 response.append(
"<?xml version='1.0' encoding='UTF-8'?>\n");
1644 response.append(
"<methodResponse>\n");
1645 response.append(
"<params>\n");
1646 response.append(
" <param><value><struct>\n");
1647 response.append(
" <member>\n");
1648 response.append(
" <name>samp.status</name>\n");
1649 response.append(
" <value>samp.ok</value>\n");
1650 response.append(
" </member>\n");
1651 response.append(
" </struct></value></param>\n");
1652 response.append(
"</params>\n");
1653 response.append(
"</methodResponse>\n");
1674 std::string response =
"";
1677 response.append(
"<?xml version='1.0' encoding='UTF-8'?>\n");
1678 response.append(
"<methodResponse>\n");
1679 response.append(
" <params>\n");
1680 response.append(
" <param>\n");
1681 response.append(
" <value/>\n");
1682 response.append(
" </param>\n");
1683 response.append(
" </params>\n");
1684 response.append(
"</methodResponse>\n");
1703 const std::string& notification)
const
1709 std::string host =
"127.0.0.1";
1710 std::string port =
"2525";
1711 std::string path =
"xmlrpc";
1712 if (url.compare(0, 7,
"http://") == 0) {
1715 size_t stop = url.find(
":", start);
1716 size_t end = std::string::npos;
1717 if (stop != std::string::npos) {
1718 length = stop -
start;
1721 length = std::string::npos;
1723 host = url.substr(start, length);
1724 if (stop != std::string::npos) {
1726 end = url.find(
"/", stop);
1727 if (end != std::string::npos) {
1728 length = end - stop;
1731 length = std::string::npos;
1733 port = url.substr(stop, length);
1735 if (end != std::string::npos) {
1737 length = url.length() - end;
1738 path = url.substr(end, length);
1743 struct addrinfo hints;
1744 std::memset(&hints, 0,
sizeof(hints));
1745 hints.ai_family = AF_INET;
1746 hints.ai_socktype = SOCK_STREAM;
1749 struct addrinfo* servinfo;
1750 if (getaddrinfo(host.c_str(), port.c_str(), &hints, &servinfo) == 0) {
1753 for (
struct addrinfo* ptr = servinfo; ptr != NULL; ptr = ptr->ai_next) {
1756 socket = ::socket(ptr->ai_family,
1762 if (::connect(socket,
1764 ptr->ai_addrlen) == -1) {
1782 int length = notification.length();
1785 std::string prefix =
"POST /"+path+
" HTTP/1.0\n"
1786 "Connection: close\n"
1787 "User-Agent: GammaLib\n"
1788 "Content-Type: text/xml\n"
1792 std::string post = prefix + notification;
1795 #if defined(G_SHOW_MESSAGE)
1796 std::cout << std::endl;
1797 std::cout <<
"GVOHub sends following notification:" << std::endl;
1798 std::cout <<
"====================================" << std::endl;
1799 std::cout << post << std::endl;
1805 int length = post.length() + 1;
1806 int sent_length = send(socket, post.c_str(), length, 0);
1807 if (sent_length < length) {
1808 post = post.substr(sent_length, std::string::npos);
1835 const std::string& reference)
1838 std::string msg =
"";
1841 msg.append(
"<?xml version=\"1.0\"?>\n");
1842 msg.append(
"<methodCall>\n");
1843 msg.append(
"<methodName>samp.client.receiveNotification</methodName>\n");
1844 msg.append(
"<params>\n");
1845 msg.append(
" <param><value>"+client.
private_key+
"</value></param>\n");
1846 msg.append(
" <param><value>"+
m_hub_id+
"</value></param>\n");
1847 msg.append(
" <param><value><struct>\n");
1848 msg.append(
" <member>\n");
1849 msg.append(
" <name>samp.mtype</name>\n");
1850 msg.append(
" <value>samp.hub.event.register</value>\n");
1851 msg.append(
" </member>\n");
1852 msg.append(
" <member>\n");
1853 msg.append(
" <name>samp.params</name>\n");
1854 msg.append(
" <value><struct>\n");
1855 msg.append(
" <member>\n");
1856 msg.append(
" <name>id</name>\n");
1857 msg.append(
" <value>"+reference+
"</value>\n");
1858 msg.append(
" </member>\n");
1859 msg.append(
" </struct></value>\n");
1860 msg.append(
" </member>\n");
1861 msg.append(
" </struct></value></param>\n");
1862 msg.append(
"</params>\n");
1863 msg.append(
"</methodCall>\n");
1883 const std::string& reference)
1886 std::string msg =
"";
1889 msg.append(
"<?xml version=\"1.0\"?>\n");
1890 msg.append(
"<methodCall>\n");
1891 msg.append(
"<methodName>samp.client.receiveNotification</methodName>\n");
1892 msg.append(
"<params>\n");
1893 msg.append(
" <param><value>"+client.
private_key+
"</value></param>\n");
1894 msg.append(
" <param><value>"+
m_hub_id+
"</value></param>\n");
1895 msg.append(
" <param><value><struct>\n");
1896 msg.append(
" <member>\n");
1897 msg.append(
" <name>samp.mtype</name>\n");
1898 msg.append(
" <value>samp.hub.event.unregister</value>\n");
1899 msg.append(
" </member>\n");
1900 msg.append(
" <member>\n");
1901 msg.append(
" <name>samp.params</name>\n");
1902 msg.append(
" <value><struct>\n");
1903 msg.append(
" <member>\n");
1904 msg.append(
" <name>id</name>\n");
1905 msg.append(
" <value>"+reference+
"</value>\n");
1906 msg.append(
" </member>\n");
1907 msg.append(
" </struct></value>\n");
1908 msg.append(
" </member>\n");
1909 msg.append(
" </struct></value></param>\n");
1910 msg.append(
"</params>\n");
1911 msg.append(
"</methodCall>\n");
1931 const std::string& reference)
1935 for (k = 0; k <
m_clients.size(); ++k) {
1936 if (
m_clients[k].reference == reference) {
1945 std::string msg =
"";
1948 msg.append(
"<?xml version=\"1.0\"?>\n");
1949 msg.append(
"<methodCall><methodName>samp.client.receiveNotification</methodName>\n");
1950 msg.append(
"<params>\n");
1951 msg.append(
" <param><value>"+client.
private_key+
"</value></param>\n");
1952 msg.append(
" <param><value>"+
m_hub_id+
"</value></param>\n");
1953 msg.append(
" <param><value><struct>\n");
1954 msg.append(
" <member>\n");
1955 msg.append(
" <name>samp.mtype</name>\n");
1956 msg.append(
" <value>samp.hub.event.metadata</value>\n");
1957 msg.append(
" </member>\n");
1958 msg.append(
" <member>\n");
1959 msg.append(
" <name>samp.params</name>\n");
1960 msg.append(
" <value><struct>\n");
1961 msg.append(
" <member>\n");
1962 msg.append(
" <name>id</name>\n");
1963 msg.append(
" <value>"+
m_clients[k].reference+
"</value>\n");
1964 msg.append(
" </member>\n");
1965 msg.append(
" <member>\n");
1966 msg.append(
" <name>metadata</name>\n");
1967 msg.append(
" <value><struct>\n");
1968 msg.append(
" <member>\n");
1969 msg.append(
" <name>samp.name</name>\n");
1970 msg.append(
" <value>"+
m_clients[k].name+
"</value>\n");
1971 msg.append(
" </member>\n");
1972 msg.append(
" <member>\n");
1973 msg.append(
" <name>samp.description.text</name>\n");
1974 msg.append(
" <value>"+
m_clients[k].description+
"</value>\n");
1975 msg.append(
" </member>\n");
1976 msg.append(
" <member>\n");
1977 msg.append(
" <name>samp.icon.url</name>\n");
1978 msg.append(
" <value>"+
m_clients[k].icon+
"</value>\n");
1979 msg.append(
" </member>\n");
1980 msg.append(
" <member>\n");
1981 msg.append(
" <name>samp.documentation.url</name>\n");
1982 msg.append(
" <value>"+
m_clients[k].documentation+
"</value>\n");
1983 msg.append(
" </member>\n");
1984 msg.append(
" <member>\n");
1985 msg.append(
" <name>author.affiliation</name>\n");
1986 msg.append(
" <value>"+
m_clients[k].affiliation+
"</value>\n");
1987 msg.append(
" </member>\n");
1988 msg.append(
" <member>\n");
1989 msg.append(
" <name>author.name</name>\n");
1990 msg.append(
" <value>"+
m_clients[k].author_name+
"</value>\n");
1991 msg.append(
" </member>\n");
1992 msg.append(
" <member>\n");
1993 msg.append(
" <name>author.email</name>\n");
1994 msg.append(
" <value>"+
m_clients[k].email+
"</value>\n");
1995 msg.append(
" </member>\n");
1996 msg.append(
" <member>\n");
1997 msg.append(
" <name>home.page</name>\n");
1998 msg.append(
" <value>"+
m_clients[k].homepage+
"</value>\n");
1999 msg.append(
" </member>\n");
2000 msg.append(
" </struct></value>\n");
2001 msg.append(
" </member>\n");
2002 msg.append(
" </struct></value>\n");
2003 msg.append(
" </member>\n");
2004 msg.append(
" </struct></value></param>\n");
2005 msg.append(
"</params>\n");
2006 msg.append(
"</methodCall>\n");
2032 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > "
2033 "value > struct > member > value > "
2042 std::string msg =
"";
2045 msg.append(
"<?xml version=\"1.0\"?>\n");
2046 msg.append(
"<methodCall>\n");
2047 msg.append(
"<methodName>samp.client.receiveNotification</methodName>\n");
2048 msg.append(
"<params>\n");
2049 msg.append(
" <param><value>"+client.
private_key+
"</value></param>\n");
2050 msg.append(
" <param><value>"+
m_hub_id+
"</value></param>\n");
2051 msg.append(
" <param><value><struct>\n");
2052 msg.append(
" <member>\n");
2053 msg.append(
" <name>samp.mtype</name>\n");
2054 msg.append(
" <value>image.load.fits</value>\n");
2055 msg.append(
" </member>\n");
2056 msg.append(
" <member>\n");
2057 msg.append(
" <name>samp.params</name>\n");
2058 msg.append(
" <value><struct>\n");
2059 msg.append(
" <member>\n");
2060 msg.append(
" <name>name</name>\n");
2061 msg.append(
" <value>"+name+
"</value>\n");
2062 msg.append(
" </member>\n");
2063 msg.append(
" <member>\n");
2064 msg.append(
" <name>image-id</name>\n");
2065 msg.append(
" <value>"+
id+
"</value>\n");
2066 msg.append(
" </member>\n");
2067 msg.append(
" <member>\n");
2068 msg.append(
" <name>url</name>\n");
2069 msg.append(
" <value>"+url+
"</value>\n");
2070 msg.append(
" </member>\n");
2071 msg.append(
" </struct></value>\n");
2072 msg.append(
" </member>\n");
2073 msg.append(
" </struct></value></param>\n");
2074 msg.append(
"</params>\n");
2075 msg.append(
"</methodCall>\n");
2098 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > "
2099 "value > struct > member > value > "
2108 std::string msg =
"";
2111 msg.append(
"<?xml version=\"1.0\"?>\n");
2112 msg.append(
"<methodCall>\n");
2113 msg.append(
"<methodName>samp.client.receiveNotification</methodName>\n");
2114 msg.append(
"<params>\n");
2115 msg.append(
" <param><value>"+client.
private_key+
"</value></param>\n");
2116 msg.append(
" <param><value>"+
m_hub_id+
"</value></param>\n");
2117 msg.append(
" <param><value><struct>\n");
2118 msg.append(
" <member>\n");
2119 msg.append(
" <name>samp.mtype</name>\n");
2120 msg.append(
" <value>table.load.votable</value>\n");
2121 msg.append(
" </member>\n");
2122 msg.append(
" <member>\n");
2123 msg.append(
" <name>samp.params</name>\n");
2124 msg.append(
" <value><struct>\n");
2125 msg.append(
" <member>\n");
2126 msg.append(
" <name>name</name>\n");
2127 msg.append(
" <value>"+name+
"</value>\n");
2128 msg.append(
" </member>\n");
2129 msg.append(
" <member>\n");
2130 msg.append(
" <name>table-id</name>\n");
2131 msg.append(
" <value>"+
id+
"</value>\n");
2132 msg.append(
" </member>\n");
2133 msg.append(
" <member>\n");
2134 msg.append(
" <name>url</name>\n");
2135 msg.append(
" <value>"+url+
"</value>\n");
2136 msg.append(
" </member>\n");
2137 msg.append(
" </struct></value>\n");
2138 msg.append(
" </member>\n");
2139 msg.append(
" </struct></value></param>\n");
2140 msg.append(
"</params>\n");
2141 msg.append(
"</methodCall>\n");
2159 std::string
str =
"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmno"
2161 while(str.size() != length) {
2162 int pos = ((rand() % (str.size() - 1)));
2181 #if defined(G_CONSOLE_DUMP)
2182 std::cout <<
"In GVOHub::get_mtype" << std::endl;
2186 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > "
2224 std::string client_name =
"";
2227 const GXmlNode* node = xml.
element(
"methodCall > params > param[1] > value");
2231 client_name = text->
text();
Abstract XML node base class.
std::vector< std::string > get_subscriptions(const GXml &xml) const
Returns subscriptions from XML document.
void xml_get_name_value_pair(const GXmlNode *node, std::string &name, std::string &value)
Extract name / value pair from XML node.
std::string m_hub_id
Hub identifier used by the hub when it sends message itself rather than forwarding from others...
void handle_request(const socklen_t &sock)
Reads the client message and runs appropriate function.
std::string hub_url(void) const
Return Hub URL.
std::string getenv(const std::string &arg)
Return value of environment variable.
void post_samp_void(const socklen_t &sock) const
Post SAMP void massage to client.
void delete_samp_file(void) const
Delete the lockfile.
std::string print(const GChatter &chatter=NORMAL) const
Print VO hub information.
GVOHub & operator=(const GVOHub &hub)
Assignment operator.
XML class interface definition.
void free_members(void)
Delete class members.
void post_samp_ok(const socklen_t &sock) const
Post SAMP ok massage to client.
void request_declare_subscriptions(const GXml &xml, const socklen_t &sock)
Handles subscriptions declaration requests.
void request_get_subscriptions(const GXml &xml, const socklen_t &sock)
Handles subscriptions getting requests.
void notify_metadata(const client &client, const std::string &reference)
Notify client about the metadata of another client.
void request_register(const GXml &xml, const socklen_t &sock)
Handles registration requests.
GVOHub(void)
Void constructor.
int recv(int fd, char *buffer, int len, int flags, int timeout)
Checks whether a parameter has occured once.
std::string get_mtype(const GXml &xml) const
Extract mtype from XML request.
void request_get_subscribed_clients(const GXml &xml, const socklen_t &sock)
Handles subscribed client information requests.
virtual int elements(void) const
Return number of GXMLElement children of node.
std::string m_hub_path
Hub path.
void request_get_registered_clients(const GXml &xml, const socklen_t &sock)
Handles registered client information requests.
void init_members(void)
Initialise class members.
virtual ~GVOHub(void)
Destructor.
std::string random_string(const size_t &length) const
Generates random string of characters.
void start_hub(void)
Starts the SAMP hub socket and listens on it.
GXmlElement * element(const int &index)
Return pointer to child element.
std::string m_secret
Secret Hub key.
SAMP hub class interface definition.
const std::string & text(void) const
Return text.
std::vector< client > m_clients
Clients.
void notify_register(const client &client, const std::string &reference)
Notify client about another client registering at Hub.
void request_declare_metadata(const GXml &xml, const socklen_t &sock)
Handles metadata declaration requests.
std::string get_hub_lockfile(void) const
Returns SAMP Hub lockfile URL.
void start(void)
Start Hub.
std::string get_client_key(const GXml &xml) const
Extract client key from XML request.
void request_get_metadata(const GXml &xml, const socklen_t &sock)
Handles a metadata requests.
void request_notify_all(const GXml &xml, const socklen_t &sock)
Handle request to notify all clients.
GVOHub * clone(void) const
Clone object.
void post_string(const std::string &content, const socklen_t &sock) const
Post string content to client.
void request_unregister(const GXml &xml, const socklen_t &sock)
Handles unregistration requests.
std::string m_version
The version of the SAMP Standard Profile implemented by the hub.
void request_shutdown(const socklen_t &sock)
Handles Hub shutdown requests.
bool m_shutdown
Shutdown request.
std::string get_response_value(const GXmlNode *node, const std::string &name) const
Returns value for a named parameter.
virtual GXmlElement * element(const int &index)
Return pointer to GXMLElement child.
void clear(void)
Clear object.
void request_set_xml_rpc_callback(const GXml &xml, const socklen_t &sock)
Handles XML-RPC callback setting requests.
void notify_table_load(const GVOHub::client &client, const GXml &xml)
Notify client about VO table loading.
void notify_unregister(const client &client, const std::string &reference)
Notify client about another client unregistering at Hub.
void create_samp_file(void) const
Create the lockfile.
std::string get_client_name(const GXml &xml) const
Return client name from XML message.
Exception handler interface definition.
std::string m_hub_port
Hub port.
void request_ping(const socklen_t &sock)
Handles ping requests.
void copy_members(const GVOHub &client)
Copy class members.
void notify(const std::string &url, const std::string ¬ification) const
Send notification to client.
std::string get_callback_url(const GXml &xml) const
Returns callback URL of client.
virtual GXmlNode * append(const GXmlNode &node)
Append XML child node.
std::string parformat(const std::string &s, const int &indent=0)
Convert string in parameter format.
int get_socket(void)
Get Hub socket.
Abstract XML node base class interface definition.
std::string m_hub_host
Hub host.
int get_client_index(const GXml &xml) const
Extract client index in shared memory from XML request.
void notify_image_load(const client &client, const GXml &xml)
Notify client about image loading.
std::string str(const unsigned short int &value)
Convert unsigned short integer value into string.