2 * Copyright (c) 2018 Samsung Electronics Co., Ltd.
4 * Licensed under the Flora License, Version 1.1 (the License);
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://floralicense.org/license/
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an AS IS BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
17 #include "cloud/cloud_request.h"
18 #include "cloud/car_info_serializer.h"
19 #include "cloud/http_request.h"
26 #define PATH_API_RACING "/api/racing"
27 #define CONFIG_CAR_API_KEY "car"
31 cloud_request_car_list_data_cb cb;
33 } car_api_get_request_context_t;
37 cloud_request_car_post_finish_cb cb;
39 } car_api_post_request_context_t;
44 } car_api_post_request_response_t;
50 } car_api_get_request_response_t;
52 GQuark g_spawn_error_quark();
53 static void car_api_post_task_thread_cb(GTask *task, gpointer source_object, gpointer task_data, GCancellable *cancellable);
54 static void car_api_post_task_ready_cb(GObject *source_object, GAsyncResult *res, gpointer user_data);
55 static void car_api_post_task_context_free(car_api_post_request_context_t *context);
56 static void car_api_post_request_response_free(car_api_post_request_response_t *response);
58 static void car_api_get_task_context_free(car_api_get_request_context_t *context);
59 static void car_api_get_request_response_free(car_api_get_request_response_t *response);
60 static void car_api_get_task_thread_cb(GTask *task, gpointer source_object, gpointer task_data, GCancellable *cancellable);
61 static void car_api_get_task_ready_cb(GObject *source_object, GAsyncResult *res, gpointer user_data);
63 #define G_ERROR_DOMAIN g_spawn_error_quark()
65 GCancellable *cloud_request_api_racing_get(const char *ap_mac, cloud_request_car_list_data_cb cb, void *user_data)
67 GCancellable *cancellable = g_cancellable_new();
69 GTask *task = g_task_new(NULL, cancellable, car_api_get_task_ready_cb, NULL);
70 g_task_set_source_tag(task, cloud_request_api_racing_get);
71 g_task_set_return_on_cancel(task, FALSE);
73 car_api_get_request_context_t *context = g_new0(car_api_get_request_context_t, 1);
74 context->ap_mac = strndup(ap_mac, strlen(ap_mac));
76 context->user_data = user_data;
78 g_task_set_task_data(task, context, (GDestroyNotify)car_api_get_task_context_free);
79 g_task_run_in_thread(task, car_api_get_task_thread_cb);
86 GCancellable *cloud_request_api_racing_post(const car_info_t *car_info, cloud_request_car_post_finish_cb cb, void *user_data)
88 GCancellable *cancellable = g_cancellable_new();
90 GTask *task = g_task_new(NULL, cancellable, car_api_post_task_ready_cb, NULL);
91 g_task_set_source_tag(task, cloud_request_api_racing_post);
92 g_task_set_return_on_cancel(task, FALSE);
94 car_api_post_request_context_t *context = g_new0(car_api_post_request_context_t, 1);
95 context->car = car_info_copy(car_info);
97 context->user_data = user_data;
99 g_task_set_task_data(task, context, (GDestroyNotify)car_api_post_task_context_free);
100 g_task_run_in_thread(task, car_api_post_task_thread_cb);
102 g_object_unref(task);
107 GQuark g_spawn_error_quark()
109 return g_quark_from_static_string("cloud_request");
112 static void car_api_post_task_context_free(car_api_post_request_context_t *context)
116 car_info_destroy(context->car);
120 static void car_api_post_request_response_free(car_api_post_request_response_t *response)
124 g_free(response->response_msg);
128 static void car_api_post_task_thread_cb(GTask *task, gpointer source_object, gpointer task_data, GCancellable *cancellable)
130 car_api_post_request_context_t *context = (car_api_post_request_context_t *)task_data;
132 if (g_task_return_error_if_cancelled(task)) {
136 car_api_post_request_response_t *response = g_new0(car_api_post_request_response_t, 1);
138 char *json = car_info_serializer_serialize(context->car);
140 char *url = http_request_get_url(PATH_API_RACING, CONFIG_CAR_API_KEY);
142 int retval = http_request_post(url, json, &(response->response_msg), &(response->response_code));
145 _D("URL FROM CONFIG (RACING POST): %s", url);
149 GError *err = g_error_new(G_ERROR_DOMAIN, retval, "http_request_post failed!");
150 g_task_return_error(task, err);
153 g_task_return_pointer(task, response, (GDestroyNotify)car_api_post_request_response_free);
156 static void car_api_post_task_ready_cb(GObject *source_object, GAsyncResult *res, gpointer user_data)
158 GTask *task = G_TASK(res);
159 GError *error = NULL;
161 //If no error occurred g_task_propagate_pointer transfers ownership, so later response have to be freed.
162 car_api_post_request_response_t *response = g_task_propagate_pointer(task, &error);
164 _E("POST async task failed with msg: %s", error->message);
168 car_api_post_request_context_t *context = g_task_get_task_data(task);
170 request_result_e result = (response->response_code == 200 || response->response_code == 201) ?
175 context->cb(result, context->user_data);
178 car_api_post_request_response_free(response);
181 static void car_api_get_task_context_free(car_api_get_request_context_t *context)
185 g_free(context->ap_mac);
189 static void car_api_get_request_response_free(car_api_get_request_response_t *response)
192 ret_if(response->size <= 0);
194 for (int i = 0; i < response->size; i++)
196 car_info_destroy(response->cars[i]);
198 g_free(response->cars);
202 static void car_api_get_task_thread_cb(GTask *task, gpointer source_object, gpointer task_data, GCancellable *cancellable)
204 car_api_get_request_context_t *context = (car_api_get_request_context_t *)task_data;
206 if (g_task_return_error_if_cancelled(task)) {
210 car_api_get_request_response_t *response = g_new0(car_api_get_request_response_t, 1);
211 char *response_json = NULL;
213 char *url_with_api = http_request_get_url(PATH_API_RACING, CONFIG_CAR_API_KEY);
215 GString *url = g_string_new(url_with_api);
216 g_string_append(url, "?apMac=");
217 g_string_append(url, context->ap_mac);
220 _D("URL FROM CONFIG (RACING GET): %s", url);
222 int retval = http_request_get(url->str, &response_json, &(response->response_code));
223 g_string_free(url, TRUE);
226 GError *err = g_error_new(G_ERROR_DOMAIN, retval, "http_request_get failed!");
227 g_task_return_error(task, err);
230 response->cars = car_info_serializer_deserialize_array(response_json, &(response->size));
233 g_free(response_json);
234 g_task_return_pointer(task, response, (GDestroyNotify)car_api_get_request_response_free);
237 static void car_api_get_task_ready_cb(GObject *source_object, GAsyncResult *res, gpointer user_data)
239 GTask *task = G_TASK(res);
240 GError *error = NULL;
242 //If no error occurred g_task_propagate_pointer transfers ownership, so later response have to be freed.
243 car_api_get_request_response_t *response = g_task_propagate_pointer(task, &error);
245 _E("GET async task failed with msg: %s", error->message);
249 car_api_get_request_context_t *context = g_task_get_task_data(task);
251 request_result_e result = (response->response_code == 200) ? SUCCESS : FAILURE;
254 context->cb(result, response->cars, response->size, context->user_data);
257 car_api_get_request_response_free(response);