2 * Copyright (c) 2018 Samsung Electronics Co., Ltd All Rights Reserved
4 * Licensed under the Apache License, Version 2.0 (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://www.apache.org/licenses/LICENSE-2.0
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.
25 #include "autofill_private.h"
26 #include "autofill_proxy.h"
28 #define AUTOFILL_DAEMON_APP_ID "org.tizen.autofilld"
33 #define LOG_TAG "AUTOFILL"
35 static int _autofill_context_count = 0;
38 static bool fill_response_item_cb(rpc_port_autofill_response_item_h response_items, void *user_data)
41 char *presentation_text = NULL;
43 autofill_fill_response_group_h res_group = (autofill_fill_response_group_h)user_data;
48 rpc_port_autofill_response_item_get_id(response_items, &id);
49 rpc_port_autofill_response_item_get_presentation_text(response_items, &presentation_text);
50 rpc_port_autofill_response_item_get_value(response_items, &value);
52 LOGD("id : %s, presentation text : %s, value : %s", id, presentation_text, value);
54 autofill_fill_response_item_h ritem;
56 autofill_fill_response_item_create(&ritem);
57 autofill_fill_response_item_set_id(ritem, id);
58 autofill_fill_response_item_set_presentation_text(ritem, presentation_text);
59 autofill_fill_response_item_set_value(ritem, value);
61 autofill_fill_response_group_add_item(res_group, ritem);
66 if (presentation_text)
67 free(presentation_text);
72 autofill_fill_response_item_destroy(ritem);
77 static bool fill_response_group_cb(rpc_port_autofill_response_group_h response_groups, void *user_data)
79 autofill_fill_response_h rh = (autofill_fill_response_h)user_data;
80 autofill_fill_response_group_h res_group;
82 autofill_fill_response_group_create(&res_group);
84 rpc_port_autofill_response_group_foreach_response_items(response_groups, fill_response_item_cb, res_group);
86 autofill_fill_response_add_group(rh, res_group);
88 autofill_fill_response_group_destroy(res_group);
93 static void __fill_response_recv_cb(void *user_data, rpc_port_autofill_fill_response_h response_h)
97 autofill_h ah = user_data;
98 autofill_fill_response_h rh;
100 autofill_fill_response_create(&rh);
102 rpc_port_autofill_fill_response_get_app_id(response_h, &app_id);
103 rpc_port_autofill_fill_response_get_view_id(response_h, &view_id);
105 LOGD("app id : %s, view id : %s", app_id, view_id);
108 autofill_fill_response_set_app_id(rh, app_id);
113 autofill_fill_response_set_view_id(rh, view_id);
117 rpc_port_autofill_fill_response_foreach_response_groups(response_h, fill_response_group_cb, rh);
119 if (ah->autofill_fill_response_received_cb)
120 ah->autofill_fill_response_received_cb(ah, rh, ah->autofill_fill_response_data);
122 autofill_fill_response_destroy(rh);
125 static void __auth_info_recv_cb(void *user_data, rpc_port_autofill_auth_info_h auth_info_h)
127 autofill_auth_info_h aih;
128 autofill_h ah = user_data;
130 autofill_auth_info_create(&aih);
132 bool autofill_data_present = false;
133 bool authentication_needed = false;
135 char *view_id = NULL;
136 char *service_name = NULL;
137 char *service_logo_image_path = NULL;
138 char *service_message = NULL;
140 rpc_port_autofill_auth_info_get_app_id(auth_info_h, &app_id);
141 rpc_port_autofill_auth_info_get_view_id(auth_info_h, &view_id);
142 rpc_port_autofill_auth_info_get_exist_autofill_data(auth_info_h, &autofill_data_present);
143 rpc_port_autofill_auth_info_get_need_authentication(auth_info_h, &authentication_needed);
144 rpc_port_autofill_auth_info_get_service_name(auth_info_h, &service_name);
145 rpc_port_autofill_auth_info_get_service_logo_image_path(auth_info_h, &service_logo_image_path);
146 rpc_port_autofill_auth_info_get_service_message(auth_info_h, &service_message);
148 LOGD("app id : %s, view id : %s, service name : %s", app_id, view_id, service_name);
150 autofill_auth_info_set_app_id(aih, app_id);
151 autofill_auth_info_set_view_id(aih, view_id);
152 autofill_auth_info_set_autofill_data_present(aih, autofill_data_present);
153 autofill_auth_info_set_authentication_needed(aih, authentication_needed);
154 autofill_auth_info_set_service_name(aih, service_name);
155 autofill_auth_info_set_service_logo_image_path(aih, service_logo_image_path);
156 autofill_auth_info_set_service_message(aih, service_message);
167 if (service_logo_image_path)
168 free(service_logo_image_path);
171 free(service_message);
174 if (ah->autofill_auth_info_received_cb)
175 ah->autofill_auth_info_received_cb(ah, aih, ah->autofill_fill_response_data);
178 LOGW("no user data");
181 autofill_auth_info_destroy(aih);
185 static void __on_connected(rpc_port_proxy_AutofillAppPort_h h, void *user_data)
187 autofill_h ah = user_data;
189 LOGW("no user data");
193 ah->connected = true;
196 rpc_port_AutofillAppPort_autofill_fill_response_received_cb_h fill_response_received_cb = rpc_port_AutofillAppPort_autofill_fill_response_received_cb_create(__fill_response_recv_cb, false, ah);
197 rpc_port_AutofillAppPort_autofill_auth_info_received_cb_h auth_info_received_cb = rpc_port_AutofillAppPort_autofill_auth_info_received_cb_create(__auth_info_recv_cb, false, ah);
199 int r = rpc_port_proxy_AutofillAppPort_invoke_Register(h, ah->context_id, auth_info_received_cb, fill_response_received_cb);
201 LOGW("[ERROR] Failed to invoke Register");
203 if (ah->connection_callback)
204 ah->connection_callback(ah, AUTOFILL_CONNECTION_STATUS_CONNECTED, ah->connection_userdata);
208 static void __on_disconnected(rpc_port_proxy_AutofillAppPort_h h, void *user_data)
210 LOGD("disconnected");
212 autofill_h ah = user_data;
214 ah->connected = false;
216 if (ah && ah->connection_callback)
217 ah->connection_callback(ah, AUTOFILL_CONNECTION_STATUS_DISCONNECTED, ah->connection_userdata);
223 static void __on_rejected(rpc_port_proxy_AutofillAppPort_h h, void *user_data)
227 autofill_h ah = user_data;
229 if (ah && ah->connection_callback)
230 ah->connection_callback(ah, AUTOFILL_CONNECTION_STATUS_REJECTED, ah->connection_userdata);
234 EXPORT_API int autofill_create(autofill_h *ah)
239 return AUTOFILL_ERROR_INVALID_PARAMETER;
241 rpc_port_proxy_AutofillAppPort_callback_s rpc_callback = {
242 .connected = __on_connected,
243 .disconnected = __on_disconnected,
244 .rejected = __on_rejected
247 struct autofill_s *as = (autofill_h)calloc(1, sizeof(struct autofill_s));
249 return AUTOFILL_ERROR_OUT_OF_MEMORY;
251 ret = rpc_port_proxy_AutofillAppPort_create(AUTOFILL_DAEMON_APP_ID, &rpc_callback, as, &as->rpc_h);
252 if (ret != RPC_PORT_ERROR_NONE) {
253 LOGW("[ERROR] Failed to create rpc port. err = %d", ret);
255 return AUTOFILL_ERROR_OUT_OF_MEMORY;
258 as->context_id = _autofill_context_count++;
261 return AUTOFILL_ERROR_NONE;
264 EXPORT_API int autofill_destroy(autofill_h ah)
267 return AUTOFILL_ERROR_INVALID_PARAMETER;
269 ah->connection_callback = NULL;
270 ah->autofill_fill_response_received_cb = NULL;
271 ah->autofill_auth_info_received_cb = NULL;
274 rpc_port_proxy_AutofillAppPort_destroy(ah->rpc_h);
278 return AUTOFILL_ERROR_NONE;
281 EXPORT_API int autofill_connect(autofill_h ah, autofill_connection_status_changed_cb callback, void *user_data)
283 LOGD("autofill connect. handle : %p", ah);
287 if (!ah || !callback) {
288 LOGW("[ERROR] Invalid parameter");
289 return AUTOFILL_ERROR_INVALID_PARAMETER;
293 return AUTOFILL_ERROR_OPERATION_FAILED;
296 ah->connection_callback = callback;
297 ah->connection_userdata = user_data;
299 ret = rpc_port_proxy_AutofillAppPort_connect(ah->rpc_h);
300 if (ret != RPC_PORT_ERROR_NONE) {
302 case RPC_PORT_ERROR_IO_ERROR:
303 LOGW("[ERROR] Failed to connect rpc port. I/O Error");
305 case RPC_PORT_ERROR_OUT_OF_MEMORY:
306 LOGW("[ERROR] Failed to connect rpc port. Out of memory");
308 case RPC_PORT_ERROR_INVALID_PARAMETER:
309 LOGW("[ERROR] Failed to connect rpc port. Invalid parameter");
311 case RPC_PORT_ERROR_PERMISSION_DENIED:
312 LOGW("[ERROR] Failed to connect rpc port. Permission denied");
315 LOGW("[ERROR] Failed to connect rpc port. errcode = %d", ret);
318 return AUTOFILL_ERROR_OPERATION_FAILED;
321 return AUTOFILL_ERROR_NONE;
325 EXPORT_API int autofill_commit(autofill_h ah, autofill_save_view_info_h vi)
327 rpc_port_autofill_save_view_info_h vih;
331 autofill_hint_e autofill_hint;
335 LOGW("[ERROR] Invalid parameter");
336 return AUTOFILL_ERROR_INVALID_PARAMETER;
340 return AUTOFILL_ERROR_OPERATION_FAILED;
343 if (!ah->connected) {
344 LOGW("[ERROR] Not connected");
345 return AUTOFILL_ERROR_OPERATION_FAILED;
348 rpc_port_autofill_save_view_info_create(&vih);
349 rpc_port_autofill_save_view_info_set_view_id(vih, vi->view_id);
352 autofill_save_item_h it;
353 EINA_LIST_FOREACH(vi->autofill_save_item_list, l, it)
355 autofill_save_item_get_id(it, &id);
356 autofill_save_item_get_label(it, &label);
357 autofill_save_item_get_value(it, &value);
358 autofill_save_item_get_autofill_hint(it, &autofill_hint);
359 autofill_save_item_get_sensitive_data(it, &sensitive_data);
361 LOGD("it : %p, id : %s, label : %s, hint : %d, sensitive : %d", it, id, label, autofill_hint, sensitive_data);
363 rpc_port_autofill_save_item_h aih;
364 rpc_port_autofill_save_item_create(&aih);
365 rpc_port_autofill_save_item_set_id(aih, id);
366 rpc_port_autofill_save_item_set_label(aih, label);
367 rpc_port_autofill_save_item_set_value(aih, value);
368 rpc_port_autofill_save_item_set_autofill_hint(aih, (int)autofill_hint);
369 rpc_port_autofill_save_item_set_is_sensitive_data(aih, sensitive_data);
370 rpc_port_autofill_save_view_info_add_items(vih, aih);
387 rpc_port_autofill_save_item_destroy(aih);
390 LOGD("app id : %s, view id : %s", vi->app_id, vi->view_id);
392 int ret = rpc_port_proxy_AutofillAppPort_invoke_commit(ah->rpc_h, ah->context_id, vih);
394 rpc_port_autofill_save_view_info_destroy(vih);
396 if (ret != RPC_PORT_ERROR_NONE) {
397 LOGW("[ERROR] Failed to commit. rpc err = %d", ret);
398 return AUTOFILL_ERROR_OPERATION_FAILED;
401 return AUTOFILL_ERROR_NONE;