1
0
mirror of https://github.com/falk-werner/webfuse synced 2024-10-27 20:34:10 +00:00

use json_writer to write json data

This commit is contained in:
Falk Werner 2020-07-13 22:41:19 +02:00
parent 09c5195c0c
commit 547cd0d7a6
21 changed files with 298 additions and 139 deletions

View File

@ -77,7 +77,7 @@ wf_impl_client_protocol_receive(
static bool static bool
wf_impl_client_protocol_send( wf_impl_client_protocol_send(
json_t * request, struct wf_message * message,
void * user_data) void * user_data)
{ {
bool result = false; bool result = false;
@ -85,13 +85,13 @@ wf_impl_client_protocol_send(
if (NULL != protocol->wsi) if (NULL != protocol->wsi)
{ {
struct wf_message * message = wf_impl_message_create(request); wf_impl_slist_append(&protocol->messages, &message->item);
if (NULL != message) lws_callback_on_writable(protocol->wsi);
{ result = true;
wf_impl_slist_append(&protocol->messages, &message->item); }
lws_callback_on_writable(protocol->wsi); else
result = true; {
} wf_impl_message_dispose(message);
} }
return result; return result;
@ -330,14 +330,13 @@ wf_impl_client_protocol_authenticate(
wf_impl_credentials_init_default(&creds); wf_impl_credentials_init_default(&creds);
protocol->callback(protocol->user_data, WF_CLIENT_AUTHENTICATE_GET_CREDENTIALS, &creds); protocol->callback(protocol->user_data, WF_CLIENT_AUTHENTICATE_GET_CREDENTIALS, &creds);
json_incref(creds.data);
wf_impl_jsonrpc_proxy_invoke( wf_impl_jsonrpc_proxy_invoke(
protocol->proxy, protocol->proxy,
&wf_impl_client_protocol_on_authenticate_finished, &wf_impl_client_protocol_on_authenticate_finished,
protocol, protocol,
"authenticate", "authenticate",
"sj", "sj",
creds.type, creds.data); creds.type, &wf_impl_credentials_write, &creds);
wf_impl_credentials_cleanup(&creds); wf_impl_credentials_cleanup(&creds);
} }

View File

@ -1,4 +1,5 @@
#include "webfuse/impl/credentials.h" #include "webfuse/impl/credentials.h"
#include "webfuse/impl/json/writer.h"
#include <string.h> #include <string.h>
void wf_impl_credentials_init_default( void wf_impl_credentials_init_default(
@ -62,3 +63,19 @@ void wf_impl_credentials_add(
json_object_set_new(credentials->data, key, json_string(value)); json_object_set_new(credentials->data, key, json_string(value));
} }
void
wf_impl_credentials_write(
struct wf_json_writer * writer,
void * data)
{
struct wf_credentials * credentials = data;
char const * key;
json_t * value;
wf_impl_json_write_object_begin(writer);
json_object_foreach(credentials->data, key, value)
{
wf_impl_json_write_object_string(writer, key, json_string_value(value));
}
wf_impl_json_write_object_end(writer);
}

View File

@ -8,6 +8,8 @@ extern "C"
{ {
#endif #endif
struct wf_json_writer;
struct wf_credentials struct wf_credentials
{ {
char * type; char * type;
@ -41,6 +43,11 @@ extern void wf_impl_credentials_add(
char const * key, char const * key,
char const * value); char const * value);
extern void
wf_impl_credentials_write(
struct wf_json_writer * writer,
void * data);
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View File

@ -412,7 +412,7 @@ wf_impl_json_write_object_begin_object(
char const * key) char const * key)
{ {
wf_impl_json_write_object_key(writer, key); wf_impl_json_write_object_key(writer, key);
wf_impl_json_write_array_end(writer); wf_impl_json_write_object_begin(writer);
} }
// -- // --

View File

@ -2,12 +2,17 @@
#include "webfuse/impl/jsonrpc/proxy_request_manager.h" #include "webfuse/impl/jsonrpc/proxy_request_manager.h"
#include "webfuse/impl/jsonrpc/response_intern.h" #include "webfuse/impl/jsonrpc/response_intern.h"
#include "webfuse/impl/jsonrpc/error.h" #include "webfuse/impl/jsonrpc/error.h"
#include "webfuse/impl/json/writer.h"
#include "webfuse/impl/message.h"
#include "webfuse/status.h" #include "webfuse/status.h"
#include <libwebsockets.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#define WF_JSONRPC_PROXY_DEFAULT_MESSAGE_SIZE 1024
struct wf_jsonrpc_proxy * struct wf_jsonrpc_proxy *
wf_impl_jsonrpc_proxy_create( wf_impl_jsonrpc_proxy_create(
struct wf_timer_manager * manager, struct wf_timer_manager * manager,
@ -29,15 +34,17 @@ void wf_impl_jsonrpc_proxy_dispose(
} }
static json_t * wf_impl_jsonrpc_request_create( static struct wf_message *
wf_impl_jsonrpc_request_create(
char const * method, char const * method,
int id, int id,
char const * param_info, char const * param_info,
va_list args) va_list args)
{ {
json_t * request = json_object(); struct wf_json_writer * writer = wf_impl_json_writer_create(WF_JSONRPC_PROXY_DEFAULT_MESSAGE_SIZE, LWS_PRE);
json_object_set_new(request, "method", json_string(method)); wf_impl_json_write_object_begin(writer);
json_t * params = json_array(); wf_impl_json_write_object_string(writer, "method", method);
wf_impl_json_write_object_begin_array(writer, "params");
for (char const * param_type = param_info; '\0' != *param_type; param_type++) for (char const * param_type = param_info; '\0' != *param_type; param_type++)
{ {
@ -46,37 +53,41 @@ static json_t * wf_impl_jsonrpc_request_create(
case 's': case 's':
{ {
char const * const value = va_arg(args, char const *); char const * const value = va_arg(args, char const *);
json_array_append_new(params, json_string(value)); wf_impl_json_write_string(writer, value);
} }
break; break;
case 'i': case 'i':
{ {
int const value = va_arg(args, int); int const value = va_arg(args, int);
json_array_append_new(params, json_integer(value)); wf_impl_json_write_int(writer, value);
} }
break; break;
case 'j': case 'j':
{ {
json_t * const value = va_arg(args, json_t *); wf_jsonrpc_custom_write_fn * write = va_arg(args, wf_jsonrpc_custom_write_fn *);
json_array_append_new(params, value); void * data = va_arg(args, void *);
write(writer, data);
} }
break; break;
default: default:
fprintf(stderr, "fatal: unknown param_type '%c'\n", *param_type); fprintf(stderr, "fatal: unknown param_type '%c'\n", *param_type);
json_decref(params); break;
json_decref(request);
return NULL;
} }
} }
wf_impl_json_write_array_end(writer);
json_object_set_new(request, "params", params);
if (0 != id) if (0 != id)
{ {
json_object_set_new(request, "id", json_integer(id)); wf_impl_json_write_object_int(writer, "id", id);
} }
wf_impl_json_write_object_end(writer);
return request; size_t length;
char * message = wf_impl_json_writer_take(writer, &length);
wf_impl_json_writer_dispose(writer);
return wf_impl_message_create(message, length);
} }
void wf_impl_jsonrpc_proxy_init( void wf_impl_jsonrpc_proxy_init(
@ -110,18 +121,13 @@ void wf_impl_jsonrpc_proxy_vinvoke(
int id = wf_impl_jsonrpc_proxy_request_manager_add_request( int id = wf_impl_jsonrpc_proxy_request_manager_add_request(
proxy->request_manager, finished, user_data); proxy->request_manager, finished, user_data);
json_t * request = wf_impl_jsonrpc_request_create(method_name, id, param_info, args); struct wf_message * request = wf_impl_jsonrpc_request_create(method_name, id, param_info, args);
bool const is_send = ((NULL != request) && (proxy->send(request, proxy->user_data))); bool const is_send = proxy->send(request, proxy->user_data);
if (!is_send) if (!is_send)
{ {
wf_impl_jsonrpc_proxy_request_manager_cancel_request( wf_impl_jsonrpc_proxy_request_manager_cancel_request(
proxy->request_manager, id, WF_BAD, "Bad: failed to send request"); proxy->request_manager, id, WF_BAD, "Bad: failed to send request");
} }
if (NULL != request)
{
json_decref(request);
}
} }
extern void wf_impl_jsonrpc_proxy_vnotify( extern void wf_impl_jsonrpc_proxy_vnotify(
@ -130,13 +136,8 @@ extern void wf_impl_jsonrpc_proxy_vnotify(
char const * param_info, char const * param_info,
va_list args) va_list args)
{ {
json_t * request = wf_impl_jsonrpc_request_create(method_name, 0, param_info, args); struct wf_message * request = wf_impl_jsonrpc_request_create(method_name, 0, param_info, args);
proxy->send(request, proxy->user_data);
if (NULL != request)
{
proxy->send(request, proxy->user_data);
json_decref(request);
}
} }

View File

@ -21,6 +21,12 @@ extern "C" {
struct wf_jsonrpc_proxy; struct wf_jsonrpc_proxy;
struct wf_timer_manager; struct wf_timer_manager;
struct wf_json_writer;
typedef void
wf_jsonrpc_custom_write_fn(
struct wf_json_writer * writer,
void * data);
extern struct wf_jsonrpc_proxy * extern struct wf_jsonrpc_proxy *
wf_impl_jsonrpc_proxy_create( wf_impl_jsonrpc_proxy_create(

View File

@ -1,9 +1,15 @@
#include "webfuse/impl/jsonrpc/request.h" #include "webfuse/impl/jsonrpc/request.h"
#include "webfuse/impl/jsonrpc/error.h" #include "webfuse/impl/jsonrpc/error.h"
#include "webfuse/impl/json/writer.h"
#include "webfuse/impl/jsonrpc/response_writer.h"
#include "webfuse/impl/message.h"
#include <libwebsockets.h>
#include <stdlib.h> #include <stdlib.h>
struct wf_jsonrpc_request struct wf_jsonrpc_request
{ {
struct wf_jsonrpc_response_writer * writer;
int id; int id;
wf_jsonrpc_send_fn * send; wf_jsonrpc_send_fn * send;
void * user_data; void * user_data;
@ -29,6 +35,7 @@ wf_impl_jsonrpc_request_create(
void * user_data) void * user_data)
{ {
struct wf_jsonrpc_request * request = malloc(sizeof(struct wf_jsonrpc_request)); struct wf_jsonrpc_request * request = malloc(sizeof(struct wf_jsonrpc_request));
request->writer = wf_impl_jsonrpc_response_writer_create(id);
request->id = id; request->id = id;
request->send = send; request->send = send;
request->user_data = user_data; request->user_data = user_data;
@ -40,6 +47,7 @@ void
wf_impl_jsonrpc_request_dispose( wf_impl_jsonrpc_request_dispose(
struct wf_jsonrpc_request * request) struct wf_jsonrpc_request * request)
{ {
wf_impl_jsonrpc_response_writer_dispose(request->writer);
free(request); free(request);
} }
@ -50,18 +58,21 @@ wf_impl_jsonrpc_request_get_userdata(
return request->user_data; return request->user_data;
} }
struct wf_jsonrpc_response_writer *
wf_impl_jsonrpc_request_get_response_writer(
struct wf_jsonrpc_request * request)
{
return request->writer;
}
void void
wf_impl_jsonrpc_respond( wf_impl_jsonrpc_respond(
struct wf_jsonrpc_request * request, struct wf_jsonrpc_request * request)
json_t * result)
{ {
json_t * response = json_object(); struct wf_message * response = wf_impl_jsonrpc_response_writer_take_message(request->writer);
json_object_set_new(response, "result", result);
json_object_set_new(response, "id", json_integer(request->id));
request->send(response, request->user_data); request->send(response, request->user_data);
json_decref(response);
wf_impl_jsonrpc_request_dispose(request); wf_impl_jsonrpc_request_dispose(request);
} }
@ -70,11 +81,21 @@ void wf_impl_jsonrpc_respond_error(
int code, int code,
char const * message) char const * message)
{ {
json_t * response = json_object(); struct wf_json_writer * writer = wf_impl_json_writer_create(128, LWS_PRE);
json_object_set_new(response, "error", wf_impl_jsonrpc_error(code, message)); wf_impl_json_write_object_begin(writer);
json_object_set_new(response, "id", json_integer(request->id)); wf_impl_json_write_object_begin_object(writer, "error");
wf_impl_json_write_object_int(writer, "code", code);
wf_impl_json_write_object_string(writer, "message", message);
wf_impl_json_write_object_end(writer);
wf_impl_json_write_object_int(writer, "id", request->id);
wf_impl_json_write_object_end(writer);
size_t length;
char * data = wf_impl_json_writer_take(writer, &length);
wf_impl_json_writer_dispose(writer);
struct wf_message * response = wf_impl_message_create(data, length);
request->send(response, request->user_data); request->send(response, request->user_data);
json_decref(response);
wf_impl_jsonrpc_request_dispose(request); wf_impl_jsonrpc_request_dispose(request);
} }

View File

@ -20,6 +20,7 @@ extern "C"
#endif #endif
struct wf_jsonrpc_request; struct wf_jsonrpc_request;
struct wf_jsonrpc_response_writer;
extern bool wf_impl_jsonrpc_is_request( extern bool wf_impl_jsonrpc_is_request(
json_t * message); json_t * message);
@ -36,9 +37,12 @@ extern void wf_impl_jsonrpc_request_dispose(
extern void * wf_impl_jsonrpc_request_get_userdata( extern void * wf_impl_jsonrpc_request_get_userdata(
struct wf_jsonrpc_request * request); struct wf_jsonrpc_request * request);
extern struct wf_jsonrpc_response_writer *
wf_impl_jsonrpc_request_get_response_writer(
struct wf_jsonrpc_request * request);
extern void wf_impl_jsonrpc_respond( extern void wf_impl_jsonrpc_respond(
struct wf_jsonrpc_request * request, struct wf_jsonrpc_request * request);
json_t * result);
extern void wf_impl_jsonrpc_respond_error( extern void wf_impl_jsonrpc_respond_error(
struct wf_jsonrpc_request * request, struct wf_jsonrpc_request * request,

View File

@ -0,0 +1,67 @@
#include "webfuse/impl/jsonrpc/response_writer.h"
#include "webfuse/impl/message.h"
#include "webfuse/impl/json/writer.h"
#include <libwebsockets.h>
#include <stdlib.h>
#define WF_RESPONSE_WRITER_DEFAULT_MESSAGE_SIZE 1024
struct wf_jsonrpc_response_writer
{
struct wf_json_writer * json_writer;
int id;
};
struct wf_jsonrpc_response_writer *
wf_impl_jsonrpc_response_writer_create(int id)
{
struct wf_jsonrpc_response_writer * writer = malloc(sizeof(struct wf_jsonrpc_response_writer));
writer->json_writer = wf_impl_json_writer_create(WF_RESPONSE_WRITER_DEFAULT_MESSAGE_SIZE, LWS_PRE);
writer->id = id;
wf_impl_json_write_object_begin(writer->json_writer);
wf_impl_json_write_object_begin_object(writer->json_writer, "result");
return writer;
}
void
wf_impl_jsonrpc_response_writer_dispose(
struct wf_jsonrpc_response_writer * writer)
{
wf_impl_json_writer_dispose(writer->json_writer);
free(writer);
}
struct wf_message *
wf_impl_jsonrpc_response_writer_take_message(
struct wf_jsonrpc_response_writer * writer)
{
wf_impl_json_write_object_end(writer->json_writer);
wf_impl_json_write_object_int(writer->json_writer, "id", writer->id);
wf_impl_json_write_object_end(writer->json_writer);
size_t length;
char * data = wf_impl_json_writer_take(writer->json_writer, &length);
return wf_impl_message_create(data, length);
}
void
wf_impl_jsonrpc_response_add_int(
struct wf_jsonrpc_response_writer * writer,
char const * key,
int value)
{
wf_impl_json_write_object_int(writer->json_writer, key, value);
}
void
wf_impl_jsonrpc_response_add_string(
struct wf_jsonrpc_response_writer * writer,
char const * key,
char const * value)
{
wf_impl_json_write_object_string(writer->json_writer, key, value);
}

View File

@ -0,0 +1,40 @@
#ifndef WF_IMPL_JSONRPC_RESPONSE_WRITER_H
#define WF_IMPL_JSONRPC_RESPONSE_WRITER_H
#ifdef __cplusplus
extern "C"
{
#endif
struct wf_jsonrpc_response_writer;
struct wf_messge;
extern struct wf_jsonrpc_response_writer *
wf_impl_jsonrpc_response_writer_create(int id);
extern void
wf_impl_jsonrpc_response_writer_dispose(
struct wf_jsonrpc_response_writer * writer);
extern struct wf_message *
wf_impl_jsonrpc_response_writer_take_message(
struct wf_jsonrpc_response_writer * writer);
extern void
wf_impl_jsonrpc_response_add_int(
struct wf_jsonrpc_response_writer * writer,
char const * key,
int value);
extern void
wf_impl_jsonrpc_response_add_string(
struct wf_jsonrpc_response_writer * writer,
char const * key,
char const * value);
#ifdef __cplusplus
}
#endif
#endif

View File

@ -5,15 +5,16 @@
#include <stdbool.h> #include <stdbool.h>
#endif #endif
#include <jansson.h>
#ifdef __cplusplus #ifdef __cplusplus
extern "C" extern "C"
{ {
#endif #endif
struct wf_message;
typedef bool wf_jsonrpc_send_fn( typedef bool wf_jsonrpc_send_fn(
json_t * request, struct wf_message * request,
void * user_data); void * user_data);
#ifdef __cplusplus #ifdef __cplusplus

View File

@ -3,26 +3,23 @@
#include <stdlib.h> #include <stdlib.h>
#include <libwebsockets.h> #include <libwebsockets.h>
extern struct wf_message * wf_impl_message_create(json_t const * value) extern struct wf_message *
wf_impl_message_create(
char * data,
size_t length)
{ {
struct wf_message * message = NULL; struct wf_message * message = malloc(sizeof(struct wf_message));
size_t const length = json_dumpb(value, NULL, 0, JSON_COMPACT); message->data = data;
message->length = length;
if (0 < length)
{
char * data = malloc(sizeof(struct wf_message) + LWS_PRE + length);
message = (struct wf_message *) data;
message->data = &data[sizeof(struct wf_message) + LWS_PRE];
message->length = length;
json_dumpb(value, message->data, length, JSON_COMPACT);
}
return message; return message;
} }
void wf_impl_message_dispose( void
wf_impl_message_dispose(
struct wf_message * message) struct wf_message * message)
{ {
char * raw_data = message->data - LWS_PRE;
free(raw_data);
free(message); free(message);
} }

View File

@ -8,7 +8,6 @@
using std::size_t; using std::size_t;
#endif #endif
#include <jansson.h>
#include "webfuse/impl/util/slist.h" #include "webfuse/impl/util/slist.h"
struct wf_message struct wf_message
@ -23,10 +22,13 @@ extern "C"
{ {
#endif #endif
extern struct wf_message * wf_impl_message_create( extern struct wf_message *
json_t const * value); wf_impl_message_create(
char * value,
size_t length);
extern void wf_impl_message_dispose( extern void
wf_impl_message_dispose(
struct wf_message * message); struct wf_message * message);
#ifdef __cplusplus #ifdef __cplusplus

View File

@ -12,6 +12,7 @@
#include "webfuse/impl/status.h" #include "webfuse/impl/status.h"
#include "webfuse/impl/jsonrpc/request.h" #include "webfuse/impl/jsonrpc/request.h"
#include "webfuse/impl/jsonrpc/response_writer.h"
#include "webfuse/impl/timer/manager.h" #include "webfuse/impl/timer/manager.h"
#include "webfuse/impl/timer/timer.h" #include "webfuse/impl/timer/timer.h"
@ -136,8 +137,7 @@ static void wf_impl_server_protocol_authenticate(
if (result) if (result)
{ {
json_t * result = json_object(); wf_impl_jsonrpc_respond(request);
wf_impl_jsonrpc_respond(request, result);
} }
else else
{ {
@ -198,9 +198,9 @@ static void wf_impl_server_protocol_add_filesystem(
if (WF_GOOD == status) if (WF_GOOD == status)
{ {
json_t * result = json_object(); struct wf_jsonrpc_response_writer * writer = wf_impl_jsonrpc_request_get_response_writer(request);
json_object_set_new(result, "id", json_string(name)); wf_impl_jsonrpc_response_add_string(writer, "id", name);
wf_impl_jsonrpc_respond(request, result); wf_impl_jsonrpc_respond(request);
} }
else else
{ {

View File

@ -20,15 +20,13 @@
#define WF_DEFAULT_MESSAGE_SIZE (8 * 1024) #define WF_DEFAULT_MESSAGE_SIZE (8 * 1024)
static bool wf_impl_session_send( static bool wf_impl_session_send(
json_t * request, struct wf_message * message,
void * user_data) void * user_data)
{ {
struct wf_impl_session * session = user_data; struct wf_impl_session * session = user_data;
struct wf_message * message = wf_impl_message_create(request); bool result = false;
bool result = (session->is_authenticated || wf_impl_jsonrpc_is_response(request)) && (NULL != session->wsi); if (NULL != session->wsi)
if (result)
{ {
wf_impl_slist_append(&session->messages, &message->item); wf_impl_slist_append(&session->messages, &message->item);
lws_callback_on_writable(session->wsi); lws_callback_on_writable(session->wsi);

View File

@ -36,6 +36,7 @@ webfuse_static = static_library('webfuse',
'lib/webfuse/impl/jsonrpc/method.c', 'lib/webfuse/impl/jsonrpc/method.c',
'lib/webfuse/impl/jsonrpc/request.c', 'lib/webfuse/impl/jsonrpc/request.c',
'lib/webfuse/impl/jsonrpc/response.c', 'lib/webfuse/impl/jsonrpc/response.c',
'lib/webfuse/impl/jsonrpc/response_writer.c',
'lib/webfuse/impl/jsonrpc/error.c', 'lib/webfuse/impl/jsonrpc/error.c',
'lib/webfuse/impl/message.c', 'lib/webfuse/impl/message.c',
'lib/webfuse/impl/message_queue.c', 'lib/webfuse/impl/message_queue.c',

View File

@ -1,5 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include "webfuse/impl/jsonrpc/proxy.h" #include "webfuse/impl/jsonrpc/proxy.h"
#include "webfuse/impl/message.h"
#include "webfuse/status.h" #include "webfuse/status.h"
#include "webfuse/impl/timer/manager.h" #include "webfuse/impl/timer/manager.h"
@ -40,22 +41,23 @@ namespace
~SendContext() ~SendContext()
{ {
if (nullptr != response) json_decref(response);
{
json_decref(response);
}
} }
}; };
bool jsonrpc_send( bool jsonrpc_send(
json_t * request, wf_message * request,
void * user_data) void * user_data)
{ {
SendContext * context = reinterpret_cast<SendContext*>(user_data); SendContext * context = reinterpret_cast<SendContext*>(user_data);
context->is_called = true; context->is_called = true;
context->response = request; if (nullptr != context->response)
json_incref(request); {
json_decref(context->response);
}
context->response = json_loadb(request->data, request->length, 0, nullptr);
wf_impl_message_dispose(request);
return context->result; return context->result;
} }
@ -199,7 +201,7 @@ TEST(wf_jsonrpc_proxy, invoke_if_another_request_is_pending)
wf_impl_timer_manager_dispose(timer_manager); wf_impl_timer_manager_dispose(timer_manager);
} }
TEST(wf_jsonrpc_proxy, invoke_fails_if_request_is_invalid) TEST(wf_jsonrpc_proxy, invoke_invalid_request)
{ {
struct wf_timer_manager * timer_manager = wf_impl_timer_manager_create(); struct wf_timer_manager * timer_manager = wf_impl_timer_manager_create();
@ -211,10 +213,9 @@ TEST(wf_jsonrpc_proxy, invoke_fails_if_request_is_invalid)
void * finished_data = reinterpret_cast<void*>(&finished_context); void * finished_data = reinterpret_cast<void*>(&finished_context);
wf_impl_jsonrpc_proxy_invoke(proxy, &jsonrpc_finished, finished_data, "foo", "?", "error"); wf_impl_jsonrpc_proxy_invoke(proxy, &jsonrpc_finished, finished_data, "foo", "?", "error");
ASSERT_FALSE(send_context.is_called); ASSERT_TRUE(send_context.is_called);
ASSERT_TRUE(finished_context.is_called); ASSERT_FALSE(finished_context.is_called);
ASSERT_EQ(WF_BAD, jsonrpc_get_status(finished_context.error));
wf_impl_jsonrpc_proxy_dispose(proxy); wf_impl_jsonrpc_proxy_dispose(proxy);
wf_impl_timer_manager_dispose(timer_manager); wf_impl_timer_manager_dispose(timer_manager);
@ -368,7 +369,7 @@ TEST(wf_jsonrpc_proxy, notify)
wf_impl_timer_manager_dispose(timer_manager); wf_impl_timer_manager_dispose(timer_manager);
} }
TEST(wf_jsonrpc_proxy, notify_dont_send_invalid_request) TEST(wf_jsonrpc_proxy, notify_send_invalid_request)
{ {
struct wf_timer_manager * timer_manager = wf_impl_timer_manager_create(); struct wf_timer_manager * timer_manager = wf_impl_timer_manager_create();
@ -378,7 +379,7 @@ TEST(wf_jsonrpc_proxy, notify_dont_send_invalid_request)
wf_impl_jsonrpc_proxy_notify(proxy, "foo", "?"); wf_impl_jsonrpc_proxy_notify(proxy, "foo", "?");
ASSERT_FALSE(send_context.is_called); ASSERT_TRUE(send_context.is_called);
wf_impl_jsonrpc_proxy_dispose(proxy); wf_impl_jsonrpc_proxy_dispose(proxy);
wf_impl_timer_manager_dispose(timer_manager); wf_impl_timer_manager_dispose(timer_manager);

View File

@ -1,5 +1,6 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include "webfuse/impl/jsonrpc/request.h" #include "webfuse/impl/jsonrpc/request.h"
#include "webfuse/impl/message.h"
#include "webfuse/status.h" #include "webfuse/status.h"
namespace namespace
@ -7,17 +8,17 @@ namespace
struct Context struct Context
{ {
json_t * response; std::string response;
}; };
bool jsonrpc_send( bool jsonrpc_send(
json_t * request, wf_message * request,
void * user_data) void * user_data)
{ {
Context * context = reinterpret_cast<Context*>(user_data); Context * context = reinterpret_cast<Context*>(user_data);
context->response = request; context->response = std::string(request->data, request->length);
json_incref(request);
wf_impl_message_dispose(request);
return true; return true;
} }
@ -25,7 +26,7 @@ bool jsonrpc_send(
TEST(wf_jsonrpc_request, create_dispose) TEST(wf_jsonrpc_request, create_dispose)
{ {
Context context{nullptr}; Context context;
void * user_data = reinterpret_cast<void*>(&context); void * user_data = reinterpret_cast<void*>(&context);
struct wf_jsonrpc_request * request = struct wf_jsonrpc_request * request =
@ -39,18 +40,15 @@ TEST(wf_jsonrpc_request, create_dispose)
TEST(wf_jsonrpc_request, respond) TEST(wf_jsonrpc_request, respond)
{ {
Context context{nullptr}; Context context;
void * user_data = reinterpret_cast<void*>(&context); void * user_data = reinterpret_cast<void*>(&context);
struct wf_jsonrpc_request * request = struct wf_jsonrpc_request * request =
wf_impl_jsonrpc_request_create(42, &jsonrpc_send, user_data); wf_impl_jsonrpc_request_create(42, &jsonrpc_send, user_data);
wf_impl_jsonrpc_respond(request, json_string("okay")); wf_impl_jsonrpc_respond(request);
ASSERT_NE(nullptr, context.response); json_t * response = json_loads(context.response.c_str(), 0, nullptr);
json_t * response = reinterpret_cast<json_t*>(context.response);
ASSERT_TRUE(json_is_object(response)); ASSERT_TRUE(json_is_object(response));
json_t * id = json_object_get(response, "id"); json_t * id = json_object_get(response, "id");
@ -58,8 +56,7 @@ TEST(wf_jsonrpc_request, respond)
ASSERT_EQ(42, json_integer_value(id)); ASSERT_EQ(42, json_integer_value(id));
json_t * result = json_object_get(response, "result"); json_t * result = json_object_get(response, "result");
ASSERT_TRUE(json_is_string(result)); ASSERT_TRUE(json_is_object(result));
ASSERT_STREQ("okay", json_string_value(result));
ASSERT_EQ(nullptr, json_object_get(response, "error")); ASSERT_EQ(nullptr, json_object_get(response, "error"));
@ -68,7 +65,7 @@ TEST(wf_jsonrpc_request, respond)
TEST(wf_jsonrpc_request, respond_error) TEST(wf_jsonrpc_request, respond_error)
{ {
Context context{nullptr}; Context context;
void * user_data = reinterpret_cast<void*>(&context); void * user_data = reinterpret_cast<void*>(&context);
struct wf_jsonrpc_request * request = struct wf_jsonrpc_request * request =
@ -76,10 +73,7 @@ TEST(wf_jsonrpc_request, respond_error)
wf_impl_jsonrpc_respond_error(request, WF_BAD, "Bad"); wf_impl_jsonrpc_respond_error(request, WF_BAD, "Bad");
ASSERT_NE(nullptr, context.response); json_t * response = json_loads(context.response.c_str(), 0, nullptr);
json_t * response = reinterpret_cast<json_t*>(context.response);
ASSERT_TRUE(json_is_object(response)); ASSERT_TRUE(json_is_object(response));
json_t * id = json_object_get(response, "id"); json_t * id = json_object_get(response, "id");

View File

@ -1,6 +1,7 @@
#include <gtest/gtest.h> #include <gtest/gtest.h>
#include "webfuse/impl/jsonrpc/server.h" #include "webfuse/impl/jsonrpc/server.h"
#include "webfuse/impl/jsonrpc/request.h" #include "webfuse/impl/jsonrpc/request.h"
#include "webfuse/impl/message.h"
#include "webfuse/status.h" #include "webfuse/status.h"
namespace namespace
@ -12,14 +13,14 @@ namespace
}; };
bool jsonrpc_send( bool jsonrpc_send(
json_t * request, wf_message * request,
void * user_data) void * user_data)
{ {
Context * context = reinterpret_cast<Context*>(user_data); Context * context = reinterpret_cast<Context*>(user_data);
context->is_called = true; context->is_called = true;
context->response = request; context->response = json_loadb(request->data, request->length, 0, nullptr);
json_incref(request);
wf_impl_message_dispose(request);
return true; return true;
} }
@ -33,8 +34,7 @@ namespace
(void) params; (void) params;
(void) user_data; (void) user_data;
json_t * result = json_string("Hello"); wf_impl_jsonrpc_respond(request);
wf_impl_jsonrpc_respond(request, result);
} }
} }
@ -61,15 +61,14 @@ TEST(wf_jsonrpc_server, process_request)
ASSERT_EQ(23, json_integer_value(id)); ASSERT_EQ(23, json_integer_value(id));
json_t * result = json_object_get(context.response, "result"); json_t * result = json_object_get(context.response, "result");
ASSERT_TRUE(json_is_string(result)); ASSERT_TRUE(json_is_object(result));
ASSERT_STREQ("Hello", json_string_value(result));
json_decref(context.response); json_decref(context.response);
json_decref(request); json_decref(request);
wf_impl_jsonrpc_server_dispose(server); wf_impl_jsonrpc_server_dispose(server);
} }
TEST(wf_jsonrpc_server, process_request_with_oject_params) TEST(wf_jsonrpc_server, process_request_with_object_params)
{ {
struct wf_jsonrpc_server * server = wf_impl_jsonrpc_server_create(); struct wf_jsonrpc_server * server = wf_impl_jsonrpc_server_create();
wf_impl_jsonrpc_server_add(server, "sayHello", &sayHello, nullptr); wf_impl_jsonrpc_server_add(server, "sayHello", &sayHello, nullptr);
@ -91,8 +90,7 @@ TEST(wf_jsonrpc_server, process_request_with_oject_params)
ASSERT_EQ(23, json_integer_value(id)); ASSERT_EQ(23, json_integer_value(id));
json_t * result = json_object_get(context.response, "result"); json_t * result = json_object_get(context.response, "result");
ASSERT_TRUE(json_is_string(result)); ASSERT_TRUE(json_is_object(result));
ASSERT_STREQ("Hello", json_string_value(result));
json_decref(context.response); json_decref(context.response);
json_decref(request); json_decref(request);

View File

@ -1,22 +1,22 @@
#include <gtest/gtest.h>
#include <cstring>
#include "webfuse/impl/message.h" #include "webfuse/impl/message.h"
#include <cstring>
#include <cstdlib>
#include <libwebsockets.h>
#include <gtest/gtest.h>
TEST(wf_message, create) TEST(wf_message, create)
{ {
json_t * value = json_object(); char * data = (char*) malloc(LWS_PRE + 2);
data[LWS_PRE ] = '{';
data[LWS_PRE + 1] = '}';
struct wf_message * message = wf_impl_message_create(value); struct wf_message * message = wf_impl_message_create(&(data[LWS_PRE]), 2);
ASSERT_NE(nullptr, message); ASSERT_NE(nullptr, message);
ASSERT_EQ(2, message->length); ASSERT_EQ(2, message->length);
ASSERT_TRUE(0 == strncmp("{}", message->data, 2)); ASSERT_TRUE(0 == strncmp("{}", message->data, 2));
wf_impl_message_dispose(message); wf_impl_message_dispose(message);
json_decref(value);
} }
TEST(wf_message, fail_to_create)
{
struct wf_message * message = wf_impl_message_create(nullptr);
ASSERT_EQ(nullptr, message);
}

View File

@ -1,18 +1,23 @@
#include <gtest/gtest.h>
#include "webfuse/impl/message_queue.h" #include "webfuse/impl/message_queue.h"
#include "webfuse/impl/message.h" #include "webfuse/impl/message.h"
#include "webfuse/impl/util/slist.h" #include "webfuse/impl/util/slist.h"
#include <gtest/gtest.h>
#include <libwebsockets.h>
#include <cstring>
#include <cstdlib>
namespace namespace
{ {
struct wf_slist_item * create_message(char const * content) struct wf_slist_item * create_message(char const * content)
{ {
json_t * value = json_object(); std::string json = std::string("{\"content\": \"") + content + "\"}";
json_object_set_new(value, "content", json_string(content)); char * data = (char*) malloc(LWS_PRE + json.size());
struct wf_message * message = wf_impl_message_create(value); memcpy(&(data[LWS_PRE]), json.c_str(), json.size());
struct wf_message * message = wf_impl_message_create(&(data[LWS_PRE]), json.size());
json_decref(value);
return &message->item; return &message->item;
} }