diff options
author | Martin Schanzenbach <mschanzenbach@posteo.de> | 2015-03-26 18:22:20 +0000 |
---|---|---|
committer | Martin Schanzenbach <mschanzenbach@posteo.de> | 2015-03-26 18:22:20 +0000 |
commit | ddbe636f3a013cde33ce94ecb9435bfd39f6355f (patch) | |
tree | 40a4ac88070e677ffd434b01a36978cb33ac063f /src/gns/plugin_rest_gns.c | |
parent | 45d2452b677a6432ca076a9010ebeccd610d80c5 (diff) | |
download | gnunet-ddbe636f3a013cde33ce94ecb9435bfd39f6355f.tar.gz gnunet-ddbe636f3a013cde33ce94ecb9435bfd39f6355f.zip |
-gns rest
Diffstat (limited to 'src/gns/plugin_rest_gns.c')
-rw-r--r-- | src/gns/plugin_rest_gns.c | 194 |
1 files changed, 66 insertions, 128 deletions
diff --git a/src/gns/plugin_rest_gns.c b/src/gns/plugin_rest_gns.c index 60ccb23c0..1859a76e1 100644 --- a/src/gns/plugin_rest_gns.c +++ b/src/gns/plugin_rest_gns.c | |||
@@ -31,17 +31,21 @@ | |||
31 | #include <gnunet_gnsrecord_lib.h> | 31 | #include <gnunet_gnsrecord_lib.h> |
32 | #include <gnunet_namestore_service.h> | 32 | #include <gnunet_namestore_service.h> |
33 | #include <gnunet_gns_service.h> | 33 | #include <gnunet_gns_service.h> |
34 | #include <gnunet_rest_lib.h> | ||
34 | #include <jansson.h> | 35 | #include <jansson.h> |
35 | 36 | ||
36 | #define API_NAMESPACE "/gns" | 37 | #define API_NAMESPACE "/gns" |
37 | 38 | ||
38 | #define GNUNET_REST_JSON_ATTR_ID "id" | ||
39 | 39 | ||
40 | #define GNUNET_REST_JSON_ATTR_TYPE "type" | 40 | #define GNUNET_REST_JSONAPI_GNS_RECORD_TYPE "type" |
41 | 41 | ||
42 | #define GNUNET_GNS_JSON_RECORD_TYPE "rtype" | 42 | #define GNUNET_REST_JSONAPI_GNS_RECORD "records" |
43 | 43 | ||
44 | #define GNUNET_REST_JSON_ATTR_DATA "data" | 44 | #define GNUNET_REST_JSONAPI_GNS_EGO "ego" |
45 | |||
46 | #define GNUNET_REST_JSONAPI_GNS_PKEY "pkey" | ||
47 | |||
48 | #define GNUNET_REST_JSONAPI_GNS_OPTIONS "options" | ||
45 | 49 | ||
46 | /** | 50 | /** |
47 | * @brief struct returned by the initialization function of the plugin | 51 | * @brief struct returned by the initialization function of the plugin |
@@ -118,12 +122,12 @@ struct LookupHandle | |||
118 | 122 | ||
119 | /** | 123 | /** |
120 | * The Pkey to use | 124 | * The Pkey to use |
121 | * In stirng representation from JSON | 125 | * In string representation from JSON |
122 | */ | 126 | */ |
123 | const char *pkey_str; | 127 | const char *pkey_str; |
124 | 128 | ||
125 | /** | 129 | /** |
126 | * The record type to look up | 130 | * The record type |
127 | */ | 131 | */ |
128 | int type; | 132 | int type; |
129 | 133 | ||
@@ -200,28 +204,6 @@ cleanup_handle (struct LookupHandle *handle) | |||
200 | 204 | ||
201 | 205 | ||
202 | /** | 206 | /** |
203 | * Create s JSON Response for MHD | ||
204 | * TODO move to lib | ||
205 | * @param data the JSON to return (can be NULL) | ||
206 | * @return a MHD_Response handle | ||
207 | */ | ||
208 | struct MHD_Response* | ||
209 | create_json_response (const char *data) | ||
210 | { | ||
211 | size_t len; | ||
212 | if (NULL == data) | ||
213 | len = 0; | ||
214 | else | ||
215 | len = strlen (data); | ||
216 | struct MHD_Response *resp = MHD_create_response_from_buffer (len, | ||
217 | (void*)data, | ||
218 | MHD_RESPMEM_MUST_COPY); | ||
219 | MHD_add_response_header (resp,MHD_HTTP_HEADER_CONTENT_TYPE,"application/json"); | ||
220 | return resp; | ||
221 | } | ||
222 | |||
223 | |||
224 | /** | ||
225 | * Task run on shutdown. Cleans up everything. | 207 | * Task run on shutdown. Cleans up everything. |
226 | * | 208 | * |
227 | * @param cls unused | 209 | * @param cls unused |
@@ -232,7 +214,7 @@ do_error (void *cls, | |||
232 | const struct GNUNET_SCHEDULER_TaskContext *tc) | 214 | const struct GNUNET_SCHEDULER_TaskContext *tc) |
233 | { | 215 | { |
234 | struct LookupHandle *handle = cls; | 216 | struct LookupHandle *handle = cls; |
235 | struct MHD_Response *resp = create_json_response (NULL); | 217 | struct MHD_Response *resp = GNUNET_REST_create_json_response (NULL); |
236 | handle->proc (handle->proc_cls, resp, GNUNET_SYSERR); | 218 | handle->proc (handle->proc_cls, resp, GNUNET_SYSERR); |
237 | cleanup_handle (handle); | 219 | cleanup_handle (handle); |
238 | } | 220 | } |
@@ -300,39 +282,35 @@ process_lookup_result (void *cls, uint32_t rd_count, | |||
300 | { | 282 | { |
301 | struct LookupHandle *handle = cls; | 283 | struct LookupHandle *handle = cls; |
302 | struct MHD_Response *resp; | 284 | struct MHD_Response *resp; |
285 | struct JsonApiObject *json_object; | ||
286 | struct JsonApiResource *json_resource; | ||
303 | uint32_t i; | 287 | uint32_t i; |
304 | char *result; | 288 | char *result; |
305 | json_t *result_root; | ||
306 | json_t *result_data; | ||
307 | json_t *result_array; | 289 | json_t *result_array; |
308 | json_t *record_obj; | 290 | json_t *record_obj; |
309 | 291 | ||
310 | result_root = json_object(); | ||
311 | result_array = json_array(); | 292 | result_array = json_array(); |
312 | result_data = json_object(); | 293 | json_object = GNUNET_REST_jsonapi_object_new (); |
313 | json_object_set_new (result_root, GNUNET_REST_JSON_ATTR_ID, json_string (handle->name)); | 294 | json_resource = GNUNET_REST_jsonapi_resource_new (GNUNET_REST_JSONAPI_GNS_RECORD, handle->name); |
314 | json_object_set (result_root, | ||
315 | GNUNET_REST_JSON_ATTR_TYPE, | ||
316 | json_string (GNUNET_GNS_JSON_RECORD_TYPE)); | ||
317 | handle->lookup_request = NULL; | 295 | handle->lookup_request = NULL; |
318 | for (i=0; i<rd_count; i++) | 296 | for (i=0; i<rd_count; i++) |
319 | { | 297 | { |
320 | if ( (rd[i].record_type != handle->type) && | 298 | if ( (rd[i].record_type != handle->type) && |
321 | (GNUNET_GNSRECORD_TYPE_ANY != handle->type) ) | 299 | (GNUNET_GNSRECORD_TYPE_ANY != handle->type) ) |
322 | continue; | 300 | continue; |
323 | |||
324 | record_obj = gnsrecord_to_json (&(rd[i])); | 301 | record_obj = gnsrecord_to_json (&(rd[i])); |
325 | json_array_append (result_array, record_obj); | 302 | json_array_append (result_array, record_obj); |
326 | json_decref (record_obj); | 303 | json_decref (record_obj); |
327 | } | 304 | } |
328 | json_object_set (result_root, GNUNET_REST_JSON_ATTR_DATA, result_data); | 305 | GNUNET_REST_jsonapi_resource_add_attr (json_resource, |
329 | json_decref (result_data); | 306 | GNUNET_REST_JSONAPI_GNS_RECORD, |
330 | json_object_set (result_data, "query_result", result_array); | 307 | result_array); |
331 | json_decref (result_array); | 308 | GNUNET_REST_jsonapi_object_resource_add (json_object, json_resource); |
332 | result = json_dumps (result_root, JSON_COMPACT); | 309 | GNUNET_REST_jsonapi_data_serialize (json_object, &result); |
333 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Result %s\n", result); | 310 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Result %s\n", result); |
334 | json_decref (result_root); | 311 | json_decref (result_array); |
335 | resp = create_json_response (result); | 312 | GNUNET_REST_jsonapi_object_delete (json_object); |
313 | resp = GNUNET_REST_create_json_response (result); | ||
336 | handle->proc (handle->proc_cls, resp, MHD_HTTP_OK); | 314 | handle->proc (handle->proc_cls, resp, MHD_HTTP_OK); |
337 | GNUNET_free (result); | 315 | GNUNET_free (result); |
338 | cleanup_handle (handle); | 316 | cleanup_handle (handle); |
@@ -505,7 +483,6 @@ int | |||
505 | parse_url (const char *url, struct LookupHandle *handle) | 483 | parse_url (const char *url, struct LookupHandle *handle) |
506 | { | 484 | { |
507 | char *name; | 485 | char *name; |
508 | char *type; | ||
509 | char tmp_url[strlen(url)+1]; | 486 | char tmp_url[strlen(url)+1]; |
510 | char *tok; | 487 | char *tok; |
511 | 488 | ||
@@ -521,75 +498,9 @@ parse_url (const char *url, struct LookupHandle *handle) | |||
521 | name); | 498 | name); |
522 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 499 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
523 | "Got name: %s\n", handle->name); | 500 | "Got name: %s\n", handle->name); |
524 | type = strtok (NULL, "/"); | ||
525 | if (NULL == type) | ||
526 | { | ||
527 | handle->type = GNUNET_GNSRECORD_TYPE_ANY; | ||
528 | return GNUNET_OK; | ||
529 | } | ||
530 | handle->type = GNUNET_GNSRECORD_typename_to_number (type); | ||
531 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
532 | "Got type: %s\n", type); | ||
533 | return GNUNET_OK; | ||
534 | } | ||
535 | |||
536 | /** | ||
537 | * Parse json from REST request | ||
538 | * TODO 1. this leaks 2. Rework JSON API. This is confusing | ||
539 | * | ||
540 | * @param data REST data | ||
541 | * @param data_size data size | ||
542 | * @param handle Handle to populate | ||
543 | * @return GNUNET_SYSERR on error | ||
544 | */ | ||
545 | int | ||
546 | parse_json (const char *data, size_t data_size, struct LookupHandle *handle) | ||
547 | { | ||
548 | json_error_t error; | ||
549 | json_t *pkey_json; | ||
550 | json_t *ego_json; | ||
551 | json_t *options_json; | ||
552 | |||
553 | char term_data[data_size+1]; | ||
554 | term_data[data_size] = '\0'; | ||
555 | |||
556 | memcpy (term_data, data, data_size); | ||
557 | |||
558 | handle->json_root = json_loads (term_data, 0, &error); | ||
559 | |||
560 | if (NULL == handle->json_root) | ||
561 | { | ||
562 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, error.text); | ||
563 | return GNUNET_SYSERR; | ||
564 | } | ||
565 | |||
566 | if(!json_is_object(handle->json_root)) | ||
567 | { | ||
568 | return GNUNET_SYSERR; | ||
569 | } | ||
570 | |||
571 | ego_json = json_object_get (handle->json_root, "ego"); | ||
572 | |||
573 | if(json_is_string(ego_json)) | ||
574 | { | ||
575 | handle->ego_str = json_string_value (ego_json); | ||
576 | } | ||
577 | |||
578 | pkey_json = json_object_get (handle->json_root, "pkey"); | ||
579 | if(json_is_string(pkey_json)) | ||
580 | { | ||
581 | handle->pkey_str = json_string_value (pkey_json); | ||
582 | } | ||
583 | |||
584 | options_json = json_object_get (handle->json_root, "options"); | ||
585 | if(json_is_integer (options_json)) | ||
586 | { | ||
587 | handle->options = json_integer_value (options_json); | ||
588 | } | ||
589 | return GNUNET_OK; | 501 | return GNUNET_OK; |
590 | } | 502 | } |
591 | 503 | ||
592 | |||
593 | /** | 504 | /** |
594 | * Function processing the REST call | 505 | * Function processing the REST call |
595 | * | 506 | * |
@@ -607,8 +518,9 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
607 | void *proc_cls) | 518 | void *proc_cls) |
608 | { | 519 | { |
609 | struct LookupHandle *handle = GNUNET_new (struct LookupHandle); | 520 | struct LookupHandle *handle = GNUNET_new (struct LookupHandle); |
610 | handle->timeout = GNUNET_TIME_UNIT_FOREVER_REL; | 521 | struct GNUNET_HashCode key; |
611 | 522 | ||
523 | handle->timeout = GNUNET_TIME_UNIT_FOREVER_REL; | ||
612 | //parse name and type from url | 524 | //parse name and type from url |
613 | if (GNUNET_OK != parse_url (conndata_handle->url, handle)) | 525 | if (GNUNET_OK != parse_url (conndata_handle->url, handle)) |
614 | { | 526 | { |
@@ -616,18 +528,8 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
616 | GNUNET_SCHEDULER_add_now (&do_error, handle); | 528 | GNUNET_SCHEDULER_add_now (&do_error, handle); |
617 | return; | 529 | return; |
618 | } | 530 | } |
619 | |||
620 | handle->proc_cls = proc_cls; | 531 | handle->proc_cls = proc_cls; |
621 | handle->proc = proc; | 532 | handle->proc = proc; |
622 | if (0 < conndata_handle->data_size) | ||
623 | { | ||
624 | if (GNUNET_OK != parse_json (conndata_handle->data, conndata_handle->data_size, handle)) | ||
625 | { | ||
626 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error parsing json...\n"); | ||
627 | GNUNET_SCHEDULER_add_now (&do_error, handle); | ||
628 | return; | ||
629 | } | ||
630 | } | ||
631 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 533 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
632 | "Connecting...\n"); | 534 | "Connecting...\n"); |
633 | handle->gns = GNUNET_GNS_connect (cfg); | 535 | handle->gns = GNUNET_GNS_connect (cfg); |
@@ -636,7 +538,6 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
636 | &do_error, handle); | 538 | &do_error, handle); |
637 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 539 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
638 | "Connected\n"); | 540 | "Connected\n"); |
639 | |||
640 | if (NULL == handle->gns) | 541 | if (NULL == handle->gns) |
641 | { | 542 | { |
642 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | 543 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
@@ -644,9 +545,40 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
644 | GNUNET_SCHEDULER_add_now (&do_error, handle); | 545 | GNUNET_SCHEDULER_add_now (&do_error, handle); |
645 | return; | 546 | return; |
646 | } | 547 | } |
548 | GNUNET_CRYPTO_hash (GNUNET_REST_JSONAPI_GNS_OPTIONS, | ||
549 | strlen (GNUNET_REST_JSONAPI_GNS_OPTIONS), | ||
550 | &key); | ||
551 | handle->options = GNUNET_GNS_LO_DEFAULT; | ||
552 | if ( GNUNET_YES == | ||
553 | GNUNET_CONTAINER_multihashmap_contains (conndata_handle->url_param_map, | ||
554 | &key) ) | ||
555 | { | ||
556 | handle->options = GNUNET_GNS_LO_DEFAULT;//TODO(char*) GNUNET_CONTAINER_multihashmap_get (conndata_handle->url_param_map, | ||
557 | //&key); | ||
558 | } | ||
559 | GNUNET_CRYPTO_hash (GNUNET_REST_JSONAPI_GNS_RECORD_TYPE, | ||
560 | strlen (GNUNET_REST_JSONAPI_GNS_RECORD_TYPE), | ||
561 | &key); | ||
562 | if ( GNUNET_YES == | ||
563 | GNUNET_CONTAINER_multihashmap_contains (conndata_handle->url_param_map, | ||
564 | &key) ) | ||
565 | { | ||
566 | handle->type = GNUNET_GNSRECORD_typename_to_number | ||
567 | (GNUNET_CONTAINER_multihashmap_get (conndata_handle->url_param_map, | ||
568 | &key)); | ||
569 | } | ||
570 | else | ||
571 | handle->type = GNUNET_GNSRECORD_TYPE_ANY; | ||
647 | 572 | ||
648 | if (NULL != handle->pkey_str) | 573 | GNUNET_CRYPTO_hash (GNUNET_REST_JSONAPI_GNS_PKEY, |
574 | strlen (GNUNET_REST_JSONAPI_GNS_PKEY), | ||
575 | &key); | ||
576 | if ( GNUNET_YES == | ||
577 | GNUNET_CONTAINER_multihashmap_contains (conndata_handle->url_param_map, | ||
578 | &key) ) | ||
649 | { | 579 | { |
580 | handle->pkey_str = GNUNET_CONTAINER_multihashmap_get (conndata_handle->url_param_map, | ||
581 | &key); | ||
650 | if (GNUNET_OK != | 582 | if (GNUNET_OK != |
651 | GNUNET_CRYPTO_ecdsa_public_key_from_string (handle->pkey_str, | 583 | GNUNET_CRYPTO_ecdsa_public_key_from_string (handle->pkey_str, |
652 | strlen(handle->pkey_str), | 584 | strlen(handle->pkey_str), |
@@ -656,10 +588,17 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
656 | return; | 588 | return; |
657 | } | 589 | } |
658 | lookup_with_public_key (handle); | 590 | lookup_with_public_key (handle); |
659 | 591 | return; | |
660 | } | 592 | } |
661 | if (NULL != handle->ego_str) | 593 | GNUNET_CRYPTO_hash (GNUNET_REST_JSONAPI_GNS_EGO, |
594 | strlen (GNUNET_REST_JSONAPI_GNS_EGO), | ||
595 | &key); | ||
596 | if ( GNUNET_YES == | ||
597 | GNUNET_CONTAINER_multihashmap_contains (conndata_handle->url_param_map, | ||
598 | &key) ) | ||
662 | { | 599 | { |
600 | handle->ego_str = GNUNET_CONTAINER_multihashmap_get (conndata_handle->url_param_map, | ||
601 | &key); | ||
663 | handle->el = GNUNET_IDENTITY_ego_lookup (cfg, | 602 | handle->el = GNUNET_IDENTITY_ego_lookup (cfg, |
664 | handle->ego_str, | 603 | handle->ego_str, |
665 | &identity_zone_cb, | 604 | &identity_zone_cb, |
@@ -671,7 +610,6 @@ rest_gns_process_request(struct RestConnectionDataHandle *conndata_handle, | |||
671 | (0 == strcmp (".zkey", | 610 | (0 == strcmp (".zkey", |
672 | &handle->name[strlen (handle->name) - 4])) ) | 611 | &handle->name[strlen (handle->name) - 4])) ) |
673 | { | 612 | { |
674 | /* no zone required, use 'anonymous' zone */ | ||
675 | GNUNET_CRYPTO_ecdsa_key_get_public | 613 | GNUNET_CRYPTO_ecdsa_key_get_public |
676 | (GNUNET_CRYPTO_ecdsa_key_get_anonymous (), | 614 | (GNUNET_CRYPTO_ecdsa_key_get_anonymous (), |
677 | &(handle->pkey)); | 615 | &(handle->pkey)); |