github.com/swiftstack/ProxyFS@v0.0.0-20210203235616-4017c267d62f/jrpcfs/test/client_test.c (about)

     1  // Copyright (c) 2015-2021, NVIDIA CORPORATION.
     2  // SPDX-License-Identifier: Apache-2.0
     3  
     4  #include <stdio.h>
     5  #include <stdlib.h>
     6  #include <unistd.h>
     7  #include <string.h>
     8  #include <sys/types.h>
     9  #include <sys/socket.h>
    10  #include <netinet/in.h>
    11  #include <netdb.h>
    12  #include <json-c/json.h>
    13  
    14  void error(const char *msg)
    15  {
    16      perror(msg);
    17      //exit(0);
    18  }
    19  
    20  static int sockfd = 0;
    21  static int portno = 12345;
    22  static char* hostname = "localhost";
    23  
    24  int sock_open() {
    25      struct sockaddr_in serv_addr;
    26      struct hostent *server;
    27  
    28      sockfd = socket(AF_INET, SOCK_STREAM, 0);
    29      if (sockfd < 0) {
    30          error("ERROR opening socket");
    31  		return -1;
    32  	}
    33      //printf("socket %s:%d opened successfully.\n",hostname,portno);
    34      server = gethostbyname(hostname);
    35      if (server == NULL) {
    36          printf("ERROR, no such host\n");
    37  		return -1;
    38      }
    39      //printf("got server for hostname %s.\n",hostname);
    40      bzero((char *) &serv_addr, sizeof(serv_addr));
    41      serv_addr.sin_family = AF_INET;
    42      bcopy((char *)server->h_addr, (char *)&serv_addr.sin_addr.s_addr, server->h_length);
    43      serv_addr.sin_port = htons(portno);
    44  
    45      if (connect(sockfd,(struct sockaddr *) &serv_addr,sizeof(serv_addr)) < 0) {
    46          //printf("ERROR connecting");
    47          error("ERROR connecting");
    48  		return -1;
    49  	}
    50  
    51  	return 0;
    52  }
    53  
    54  int sock_close() {
    55      close(sockfd);
    56  
    57  	return 0;
    58  }
    59  
    60  int sock_read(char* buf) {
    61      int n = read(sockfd,buf,255);
    62      if (n < 0) {
    63          error("ERROR reading from socket");
    64  		return -1;
    65  	}
    66  	return 0;
    67  }
    68  
    69  int sock_write(const char* buf) {
    70      int n = write(sockfd,buf,strlen(buf));
    71      if (n < 0) {
    72          error("ERROR writing to socket");
    73  		return -1;
    74  	}
    75  	return 0;
    76  }
    77  
    78  /*printing the value corresponding to boolean, double, integer and strings*/
    79  void print_json_object(struct json_object *jobj, const char *msg) {
    80  	printf("\n%s: \n", msg);
    81  	printf("---\n%s\n---\n", json_object_to_json_string(jobj));
    82  }
    83  
    84  struct json_object * find_something(struct json_object *jobj, const char *key) {
    85  	struct json_object *tmp;
    86  
    87  	json_object_object_get_ex(jobj, key, &tmp);
    88  
    89  	return tmp;
    90  }
    91  
    92  int get_jrpc_id(json_object* jobj)
    93  {
    94      json_object* obj = find_something(jobj, "id");
    95  
    96      enum json_type type = json_object_get_type(obj);
    97  	if (type != json_type_int) {
    98  		printf("Error, id field is not an int (type=%d)!\n",type);
    99  		return -1;
   100  	}
   101  
   102  	return json_object_get_int(obj);
   103  }
   104  
   105  int get_jrpc_error(json_object* jobj)
   106  {
   107      json_object* obj = NULL;
   108  	if (json_object_object_get_ex(jobj, "error", &obj)) {
   109  	    // key was found, as it should be
   110          enum json_type type = json_object_get_type(obj);
   111  		if (type == json_type_string) {
   112  			// Found an error
   113              printf("Error value: %s\n", json_object_get_string(obj));
   114  			return -1;
   115  		}
   116  	} else {
   117  		printf("Error field not found in response!\n");
   118  	}
   119  
   120  	return 0;
   121  }
   122  
   123  json_object* get_jrpc_result(json_object* jobj)
   124  {
   125      return find_something(jobj, "result");
   126  }
   127  
   128  uint64_t get_jrpc_mount_id(json_object* jobj)
   129  {
   130      json_object* obj = NULL;
   131  	// MountID is inside the result object
   132      json_object* robj = get_jrpc_result(jobj);
   133  	if (!json_object_object_get_ex(robj, "MountID", &obj)) {
   134  	    // key was not found
   135  		printf("MountID field not found in response!\n");
   136  	    return 0;
   137  	}
   138  
   139  	return json_object_get_int64(obj);
   140  }
   141  
   142  json_object* build_jrpc_request(int id, char* method)
   143  {
   144  	// Create a new JSON object to populate and return
   145  	json_object* jobj = json_object_new_object();
   146  
   147  	// Add the top-level key-value pairs
   148  	json_object_object_add(jobj, "id", json_object_new_int(id));
   149  	json_object_object_add(jobj, "method", json_object_new_string(method));
   150  	json_object_object_add(jobj, "jsonrpc", json_object_new_string("2.0"));
   151  
   152  	// Create the params array, consisting of key-value pairs
   153  	json_object* pobj = json_object_new_array();
   154  	json_object* tmp  = json_object_new_object();
   155  	json_object_object_add(tmp, "VolumeName", json_object_new_string("CommonVolume"));
   156  	json_object_object_add(tmp, "MountOptions", json_object_new_int(0));
   157  	json_object_object_add(tmp, "AuthUser", json_object_new_string("balajirao"));
   158  	json_object_array_add(pobj,tmp);
   159  
   160  	// Add the params array to the top-level object
   161  	json_object_object_add(jobj,"params",pobj);
   162  
   163  	return jobj;
   164  }
   165  
   166  
   167  int main(int argc, char *argv[])
   168  {
   169      char buffer[256];
   170  	int id = 1;
   171  
   172  	// Open socket
   173      //printf("Opening socket.\n");
   174  	if (sock_open() < 0) {
   175  		goto done;
   176  	}
   177  
   178  	// Build our request header
   179      json_object* myobj = build_jrpc_request(id, "Server.RpcMount");
   180  
   181  	// Send something
   182  	const char* writeBuf = json_object_to_json_string_ext(myobj, JSON_C_TO_STRING_PLAIN);
   183      printf("Sending data: %s\n",writeBuf);
   184  	if (sock_write(writeBuf) < 0) {
   185          printf("Error writing to socket.\n");
   186  		goto sock_close_and_done;
   187  	}
   188  
   189  	// Read response
   190      //printf("Reading from socket.\n");
   191      bzero(buffer,256);
   192  	if (sock_read(buffer) < 0) {
   193          printf("Error reading from socket.\n");
   194  		goto sock_close_and_done;
   195  	}
   196      //printf("Read %s\n",buffer);
   197  	json_object* jobj = json_tokener_parse(buffer);
   198  	//printf("response:\n---\n%s\n---\n", json_object_to_json_string_ext(jobj, JSON_C_TO_STRING_SPACED | JSON_C_TO_STRING_PRETTY));
   199  
   200  	// Get id from response
   201      int rsp_id = get_jrpc_id(jobj);
   202      if (rsp_id != id) {
   203          printf("Error, expected id=%d, received id=%d", id, rsp_id);
   204  	} else {
   205  	   // printf("Response id = %d\n",rsp_id);
   206  	}
   207  
   208  	// Was there an error?
   209      if (get_jrpc_error(jobj) != 0) {
   210  	    printf("Error was set in response.\n");
   211  	}
   212  
   213  	// Try to find the mount ID
   214      printf("Returned MountID: %lld\n", get_jrpc_mount_id(jobj));
   215  
   216  sock_close_and_done:
   217  	// Close socket
   218      //printf("Closing socket.\n");
   219  	sock_close();
   220  
   221  done:
   222      return 0;
   223  }