72d830aef60887341705d800bc1c71dbb4bf4794
[profile/ivi/gsignond.git] / test / db / dbtest.c
1 /* vi: set et sw=4 ts=4 cino=t0,(0: */
2 /* -*- Mode: C; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 /*
4  * This file is part of gsignond
5  *
6  * Copyright (C) 2012 Intel Corporation.
7  *
8  *
9  * This library is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2.1 of the License, or (at your option) any later version.
13  *
14  * This library is distributed in the hope that it will be useful, but
15  * WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with this library; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
22  * 02110-1301 USA
23  */
24
25 #include <check.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <sqlite3.h>
29 #include <glib/gstdio.h>
30
31 #include "gsignond/gsignond-config.h"
32 #include "gsignond/gsignond-log.h"
33 #include "gsignond/gsignond-credentials.h"
34 #include "gsignond/gsignond-secret-storage.h"
35 #include "common/db/gsignond-db-error.h"
36 #include "common/db/gsignond-db-secret-database.h"
37 #include "common/db/gsignond-db-sql-database.h"
38 #include "daemon/gsignond-daemon.h"
39 #include "daemon/db/gsignond-db-metadata-database.h"
40 #include "daemon/db/gsignond-db-credentials-database.h"
41
42 static GSequence*
43 _sequence_new (gchar *data)
44 {
45     GSequence *value = NULL;
46     value = g_sequence_new (NULL);
47     g_sequence_append (value, (guint8 *)data);
48     return value;
49 }
50
51 typedef struct {
52     GHashTable *table;
53     int status;
54 } Data;
55
56 static void
57 _compare_key_value(
58         gchar *key,
59         GVariant *value,
60         Data *user_data)
61 {
62     GVariant *value2 = (GVariant *)g_hash_table_lookup (user_data->table, key);
63
64     if (value2 && g_variant_get_size (value) == g_variant_get_size (value2)
65                && memcmp (g_variant_get_data(value2), 
66                           g_variant_get_data(value),
67                           g_variant_get_size(value2)) == 0
68                && g_variant_is_of_type(value2, g_variant_get_type (value)))  {
69         return;
70     }
71     user_data->status = 0;
72 }
73
74 static gboolean
75 _compare_sequences (
76         GSequence *one,
77         GSequence *two)
78 {
79     GSequenceIter *iter1 = NULL, *iter2 = NULL;
80     gboolean equal = TRUE;
81
82     if (one == NULL && two == NULL)
83         return TRUE;
84
85     if ((one != NULL && two == NULL) ||
86         (one == NULL && two != NULL) ||
87         (g_sequence_get_length (one) != g_sequence_get_length (two)))
88         return FALSE;
89
90     if (one == two)
91         return TRUE;
92
93     iter1 = g_sequence_get_begin_iter (one);
94     while (!g_sequence_iter_is_end (iter1)) {
95         iter2 = g_sequence_get_iter_at_pos (two,
96                     g_sequence_iter_get_position (iter1));
97         if (g_strcmp0 (g_sequence_get (iter1), g_sequence_get (iter2)) != 0) {
98             equal = FALSE;
99             break;
100         }
101         iter1 = g_sequence_iter_next (iter1);
102     }
103
104     return equal;
105 }
106
107 static GSignondIdentityInfo *
108 _get_filled_identity_info_2 (
109         GSignondIdentityInfo **identity_inp,
110         gboolean add_creds,
111         gboolean add_methods,
112         gboolean add_realms,
113         gboolean add_acl,
114         gboolean add_owner)
115 {
116     guint32 type = 456;
117     const gchar *username = "username1";
118     const gchar *secret = "secret1";
119     const gchar *caption = "caption1";
120     GSignondIdentityInfo *identity = NULL;
121     GSignondSecurityContextList *ctx_list = NULL;
122     GSignondSecurityContext *ctx1, *ctx2, *ctx3 ;
123     GHashTable *methods = NULL;
124     GSequence *seq1 = NULL, *seq_realms;
125     identity = *identity_inp;
126
127     if (identity == NULL)
128         identity = gsignond_identity_info_new ();
129     gsignond_identity_info_set_identity_new (identity);
130     gsignond_identity_info_set_secret (identity, secret);
131     gsignond_identity_info_set_store_secret (identity, TRUE);
132     if (add_creds) {
133         gsignond_identity_info_set_username (identity, username);
134         gsignond_identity_info_set_username_secret (identity, TRUE);
135         gsignond_identity_info_set_caption (identity, caption);
136     }
137
138     /*realms*/
139     if (add_realms) {
140         seq_realms = _sequence_new("realms1");
141         gsignond_identity_info_set_realms (identity, seq_realms);
142         g_sequence_free (seq_realms);
143     }
144
145     /*methods*/
146     if (add_methods) {
147         methods = g_hash_table_new_full ((GHashFunc)g_str_hash,
148                 (GEqualFunc)g_str_equal,
149                 (GDestroyNotify)NULL,
150                 (GDestroyNotify)g_sequence_free);
151         seq1 = _sequence_new("mech11"); g_sequence_append (seq1, "mech12");
152         g_hash_table_insert (methods, "method1", seq1);
153         g_hash_table_insert (methods, "method2", _sequence_new("mech21"));
154         g_hash_table_insert (methods, "method3", _sequence_new("mech31"));
155         gsignond_identity_info_set_methods (identity, methods);
156         g_hash_table_unref (methods);
157     }
158
159     /*acl*/
160     ctx1 = gsignond_security_context_new_from_values ("sysctx1", "appctx1");
161     ctx2 = gsignond_security_context_new_from_values ("sysctx2", "appctx2");
162     ctx3 = gsignond_security_context_new_from_values ("sysctx3", "appctx3");
163     ctx_list = g_list_append (ctx_list,ctx1);
164     ctx_list = g_list_append (ctx_list,ctx2);
165     ctx_list = g_list_append (ctx_list,ctx3);
166     if (add_acl) {
167         gsignond_identity_info_set_access_control_list (identity, ctx_list);
168     }
169
170     /*owners*/
171     if (add_owner) {
172         gsignond_identity_info_set_owner (identity, ctx1);
173     }
174     gsignond_security_context_list_free (ctx_list);
175
176     gsignond_identity_info_set_validated (identity, FALSE);
177     gsignond_identity_info_set_identity_type (identity, type);
178     return identity;
179 }
180
181 static GSignondIdentityInfo *
182 _get_filled_identity_info (void)
183 {
184     GSignondIdentityInfo *identity = NULL;
185     return _get_filled_identity_info_2 (&identity,
186             TRUE, TRUE, TRUE, TRUE, TRUE);
187 }
188
189 START_TEST (test_identity_info)
190 {
191     guint32 id = 125;
192     guint32 type = 456;
193     const gchar *username = "username1";
194     const gchar *secret = "secret1";
195     const gchar *caption = "caption1";
196     GSignondIdentityInfo *identity = NULL;
197     GSignondIdentityInfo *identity2 = NULL;
198     GSignondSecurityContextList *ctx_list = NULL, *list = NULL;
199     GSignondSecurityContext *ctx, *ctx1, *ctx2, *ctx3 ;
200     GHashTable *methods = NULL, *methods2;
201     GSequence *seq1 = NULL, *seq_realms, *seq21, *mechs;
202     GList *list2;
203
204     identity = gsignond_identity_info_new ();
205     fail_if (identity == NULL);
206
207     fail_unless (gsignond_identity_info_get_id (identity) == 0);
208     fail_unless (gsignond_identity_info_get_is_identity_new (identity)== TRUE);
209     fail_unless (gsignond_identity_info_get_username (identity) == NULL);
210     fail_unless (gsignond_identity_info_get_is_username_secret (
211             identity) == FALSE);
212     fail_unless (gsignond_identity_info_get_secret (identity) == NULL);
213     fail_unless (gsignond_identity_info_get_store_secret (identity) == FALSE);
214     fail_unless (gsignond_identity_info_get_caption (identity) == NULL);
215     fail_unless (gsignond_identity_info_get_realms (identity) == NULL);
216     fail_unless (gsignond_identity_info_get_methods (identity) == NULL);
217     fail_unless (gsignond_identity_info_get_mechanisms (
218             identity, "testmech") == NULL);
219     fail_unless (gsignond_identity_info_get_access_control_list (
220             identity) == NULL);
221     fail_unless (gsignond_identity_info_get_owner (identity) == NULL);
222     fail_unless (gsignond_identity_info_get_validated (identity) == FALSE);
223     fail_unless (gsignond_identity_info_get_identity_type (identity) == -1);
224
225     fail_unless (gsignond_identity_info_set_id (identity, id) == TRUE);
226
227     fail_unless (id == gsignond_identity_info_get_id (identity));
228
229     fail_unless (gsignond_identity_info_set_identity_new (identity) == TRUE);
230
231     fail_unless (gsignond_identity_info_get_is_identity_new (
232             identity) == TRUE);
233
234     fail_unless (gsignond_identity_info_set_username (
235             identity, NULL) == FALSE);
236
237     fail_unless (gsignond_identity_info_get_username (identity) == NULL);
238
239     fail_unless (gsignond_identity_info_set_username (
240             identity, username) == TRUE);
241
242     fail_unless (g_strcmp0 (username, gsignond_identity_info_get_username (
243             identity)) == 0);
244
245     fail_unless (gsignond_identity_info_set_username_secret (
246             identity, TRUE) == TRUE);
247
248     fail_unless (gsignond_identity_info_get_is_username_secret (
249             identity) == TRUE);
250
251     fail_unless (gsignond_identity_info_set_secret (identity, NULL) == FALSE);
252
253     fail_unless (gsignond_identity_info_get_secret (identity) == NULL);
254
255     fail_unless (gsignond_identity_info_set_secret (identity, secret) == TRUE);
256
257     fail_unless (g_strcmp0 (secret, gsignond_identity_info_get_secret (
258             identity)) == 0);
259
260     fail_unless (gsignond_identity_info_set_store_secret (
261             identity, TRUE) == TRUE);
262
263     fail_unless (gsignond_identity_info_get_store_secret (
264             identity) == TRUE);
265
266     fail_unless (gsignond_identity_info_set_caption (identity, NULL) == FALSE);
267
268     fail_unless (gsignond_identity_info_get_caption (identity) == NULL);
269
270     fail_unless (gsignond_identity_info_set_caption (
271             identity, caption) == TRUE);
272
273     fail_unless (g_strcmp0 (caption, gsignond_identity_info_get_caption (
274             identity)) == 0);
275
276     /*realms*/
277     seq_realms = _sequence_new("realms1");
278     fail_unless (gsignond_identity_info_set_realms (
279             identity, seq_realms) == TRUE);
280
281     seq1 = gsignond_identity_info_get_realms (identity);
282     fail_if (seq1 == NULL);
283     fail_unless (_compare_sequences (seq1, seq_realms) == TRUE);
284     g_sequence_free (seq1); seq1 = NULL;
285     g_sequence_free (seq_realms);
286
287     /*methods*/
288     methods = g_hash_table_new_full ((GHashFunc)g_str_hash,
289             (GEqualFunc)g_str_equal,
290             (GDestroyNotify)NULL,
291             (GDestroyNotify)g_sequence_free);
292     seq1 = _sequence_new("mech11"); g_sequence_append (seq1, "mech12");
293     fail_unless (gsignond_identity_info_set_methods (
294             identity, methods) == TRUE);
295     g_hash_table_insert (methods, "method1", seq1);
296     g_hash_table_insert (methods, "method2", _sequence_new("mech21"));
297     g_hash_table_insert (methods, "method3", _sequence_new("mech31"));
298     g_hash_table_insert (methods, "method4", _sequence_new("mech41"));
299     fail_unless (gsignond_identity_info_set_methods (
300             identity, methods) == TRUE);
301
302     methods2 = gsignond_identity_info_get_methods (identity);
303     fail_if (methods2 == NULL);
304     seq21 = g_hash_table_lookup (methods, "method1");
305     fail_if (seq21 == NULL);
306     fail_unless (_compare_sequences (seq1, seq21) == TRUE);
307     g_hash_table_unref (methods2);
308     g_hash_table_unref (methods);
309
310     fail_unless (gsignond_identity_info_get_mechanisms (
311             identity, "method20") == NULL);
312
313     mechs = gsignond_identity_info_get_mechanisms (
314                 identity, "method1");
315     fail_if (mechs == NULL);
316     g_sequence_free (mechs);
317
318     fail_unless (gsignond_identity_info_remove_method (
319             identity, "method20") == FALSE);
320     fail_unless (gsignond_identity_info_remove_method (
321             identity, "method4") == TRUE);
322
323     /*acl*/
324     ctx1 = gsignond_security_context_new_from_values ("sysctx1", "appctx1");
325     ctx2 = gsignond_security_context_new_from_values ("sysctx2", "appctx2");
326     ctx3 = gsignond_security_context_new_from_values ("sysctx3", "appctx3");
327     ctx_list = g_list_append (ctx_list,ctx1);
328     ctx_list = g_list_append (ctx_list,ctx2);
329     ctx_list = g_list_append (ctx_list,ctx3);
330     fail_unless (gsignond_identity_info_set_access_control_list (
331             identity, ctx_list) == TRUE);
332
333     list = gsignond_identity_info_get_access_control_list (identity);
334     fail_if (list == NULL);
335     list2 = g_list_nth (list, 0);
336     ctx = (GSignondSecurityContext *) list2->data;
337     fail_unless (gsignond_security_context_compare (ctx, ctx1) == 0);
338     list2 = g_list_nth (list, 1);
339     ctx = (GSignondSecurityContext *) list2->data;
340     fail_unless (gsignond_security_context_compare (ctx, ctx2) == 0);
341     list2 = g_list_nth (list, 2);
342     ctx = (GSignondSecurityContext *) list2->data;
343     fail_unless (gsignond_security_context_compare (ctx, ctx3) == 0);
344     gsignond_security_context_list_free (list); list = NULL;
345
346     /*owners*/
347     fail_unless (gsignond_identity_info_set_owner (
348             identity, ctx1) == TRUE);
349     ctx = gsignond_identity_info_get_owner (identity);
350     fail_if (ctx == NULL);
351     fail_unless (gsignond_security_context_compare (ctx, ctx1) == 0);
352     gsignond_security_context_free (ctx); ctx = NULL;
353
354     fail_unless (gsignond_identity_info_set_validated (
355             identity, FALSE) == TRUE);
356
357     fail_unless (gsignond_identity_info_get_validated (identity) == FALSE);
358
359     fail_unless (gsignond_identity_info_set_identity_type (
360             identity, type) == TRUE);
361
362     fail_unless (type == gsignond_identity_info_get_identity_type (identity));
363
364     /*copy*/
365     identity2 = gsignond_dictionary_copy (identity);
366     fail_if (identity2 == NULL);
367     fail_unless (gsignond_identity_info_compare (identity, identity2) == TRUE);
368     gsignond_identity_info_unref (identity2);
369     fail_unless (gsignond_identity_info_compare (identity, identity) == TRUE);
370
371     gsignond_security_context_list_free (ctx_list); ctx_list = NULL;
372
373     gsignond_identity_info_unref (identity);
374 }
375 END_TEST
376
377 static gboolean
378 _gsignond_query_read_int (
379         sqlite3_stmt *stmt,
380         gint *status)
381 {
382     *status = sqlite3_column_int (stmt, 0);
383     return TRUE;
384 }
385 static gboolean
386 _gsignond_query_read_string (
387         sqlite3_stmt *stmt,
388         gint *status)
389 {
390     const gchar* str = NULL;
391     *status = 0;
392     str = (const gchar *)sqlite3_column_text (stmt, 0);
393     if (str && strlen(str) > 0 &&
394         g_strcmp0 (str, "username1") == 0) {
395         *status = 1;
396     }
397     return TRUE;
398 }
399
400 START_TEST (test_sql_database)
401 {
402     GSignondDbSecretDatabase *database = NULL;
403     gchar *filename = NULL;
404     const gchar *dir = NULL;
405     GSignondCredentials *creds = NULL;
406     guint32 id = 1, method = 2;
407     GHashTable *data = NULL;
408     GSignondDictionary *data2 = NULL;
409     Data input;
410     sqlite3_stmt *stmt = NULL;
411     gint status=0;
412     GList *list = NULL;
413     GHashTable* hashtable = NULL;
414     GArray *array = NULL;
415     GSignondDbSqlDatabase *sqldb = NULL;
416     GError *error = NULL;
417
418     /* Secret Storage */
419     database = gsignond_db_secret_database_new ();
420     fail_if (database == NULL);
421     sqldb = GSIGNOND_DB_SQL_DATABASE (database);
422
423     fail_unless (gsignond_db_sql_database_clear (sqldb) == FALSE);
424     fail_unless (gsignond_db_sql_database_is_open (sqldb) == FALSE);
425     fail_unless (gsignond_db_secret_database_load_credentials (
426             database, 1) == NULL);
427     fail_unless (gsignond_db_secret_database_update_credentials (
428             database, NULL) == FALSE);
429     fail_unless (gsignond_db_secret_database_remove_credentials (
430             database, 1) == FALSE);
431     fail_unless (gsignond_db_secret_database_load_data (
432             database, 1, 2) == NULL);
433     fail_unless (gsignond_db_secret_database_update_data (
434             database, 1, 2, NULL) == FALSE);
435     fail_unless (gsignond_db_secret_database_remove_data (
436             database, 1, 2) == FALSE);
437
438     dir = "/tmp/gsignond";
439     g_mkdir_with_parents (dir, S_IRWXU);
440     filename = g_build_filename (dir, "sql_db_test.db", NULL);
441     fail_unless (gsignond_db_sql_database_open (sqldb, filename,
442             SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE) == TRUE);
443     /* don't open the db again if its already open */
444     fail_unless (gsignond_db_sql_database_open (sqldb, filename,
445             SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE) == TRUE);
446     g_free (filename);
447
448     creds = gsignond_credentials_new ();
449     fail_if (creds == NULL);
450
451     fail_unless (gsignond_credentials_set_data (
452             creds, id, "user 1", "pass 1") == TRUE);
453
454     fail_unless (gsignond_db_secret_database_update_credentials (
455             database, creds) == TRUE);
456     g_object_unref (creds); creds = NULL;
457
458     creds = gsignond_db_secret_database_load_credentials (database, id);
459     fail_if (creds == NULL);
460     g_object_unref (creds);
461
462     /* remove the added credentials */
463     fail_unless (gsignond_db_secret_database_remove_credentials (
464             database, id) == TRUE);
465
466     /* add data to store */
467     data = g_hash_table_new_full ((GHashFunc)g_str_hash,
468             (GEqualFunc)g_str_equal,
469             (GDestroyNotify)NULL,
470             (GDestroyNotify)g_variant_unref);
471     fail_if (data == NULL);
472
473     GVariantBuilder builder;
474     g_variant_builder_init (&builder, G_VARIANT_TYPE_VARDICT);
475     g_variant_builder_add (&builder, "{sv}", "key1", g_variant_new_string ("string_value"));
476     g_variant_builder_add (&builder, "{sv}", "key2",g_variant_new_double (12223.4223));
477     g_variant_builder_add (&builder, "{sv}", "key3",g_variant_new_uint16(20));
478     g_variant_builder_add (&builder, "{sv}", "key4",g_variant_new("^ay", "byte_value"));
479
480     g_hash_table_insert (data, "dummy_client_id", g_variant_builder_end (&builder));
481
482     fail_unless (gsignond_db_secret_database_update_data (
483             database, id, method, data) == TRUE);
484     data2 = gsignond_db_secret_database_load_data (database, id, method);
485     fail_if (data2 == NULL);
486     input.table = data;
487     input.status = 1;
488     g_hash_table_foreach (data2, (GHFunc)_compare_key_value, &input);
489     fail_if (input.status != 1);
490
491     gsignond_dictionary_unref (data2);
492     g_hash_table_unref(data);
493
494
495     /*sql database tests*/
496     fail_unless (gsignond_db_sql_database_clear (sqldb) == TRUE);
497     stmt = gsignond_db_sql_database_prepare_statement (
498             sqldb, "INSERT INTO CREDENTIALS "
499             "(id, username, password) VALUES (1, \"username1\",\"password\");");
500     fail_if (stmt == NULL);
501     fail_unless (sqlite3_finalize (stmt) == SQLITE_OK); stmt = NULL;
502
503     fail_unless (gsignond_db_sql_database_exec (
504             sqldb, "INSERT INTO CREDENTIALS (id, username, password) "
505                     "VALUES (1, \"username1\",\"password\");") == TRUE);
506
507     fail_unless (gsignond_db_sql_database_exec (
508             sqldb, "INSERT INTO CREDENTIALS (id, username, password) "
509                     "VALUES (2, \"username2\",\"password2\");") == TRUE);
510
511     fail_unless (gsignond_db_sql_database_exec (
512             sqldb, "SELECT id from CREDENTIALS limit 1;") == TRUE);
513
514     fail_unless (gsignond_db_sql_database_query_exec (
515             sqldb, "SELECT id from CREDENTIALS limit 1;",
516             (GSignondDbSqlDatabaseQueryCallback)_gsignond_query_read_int,
517             &status) == 1);
518     fail_unless (status == 1);
519
520     fail_unless (gsignond_db_sql_database_query_exec (
521             sqldb, "SELECT username from CREDENTIALS where id=1;",
522             (GSignondDbSqlDatabaseQueryCallback)_gsignond_query_read_string,
523             &status) == 1);
524     fail_unless (status == 1);
525
526     list = gsignond_db_sql_database_query_exec_string_list (
527             sqldb, "SELECT username from CREDENTIALS;");
528     fail_if (list == NULL);
529     fail_unless (g_list_length (list) == 2);
530     g_list_free_full (list, g_free);
531
532     hashtable = gsignond_db_sql_database_query_exec_string_tuple (
533             sqldb, "SELECT username, password from CREDENTIALS;");
534     fail_if (hashtable == NULL);
535     fail_unless (g_hash_table_size (hashtable) == 2);
536     g_hash_table_unref (hashtable);
537
538     hashtable = gsignond_db_sql_database_query_exec_int_string_tuple (
539             sqldb, "SELECT id, username from CREDENTIALS "
540                         "where password=\"password2\";");
541     fail_if (hashtable == NULL);
542     fail_unless (g_hash_table_size (hashtable) == 1);
543     g_hash_table_unref (hashtable);
544
545     fail_unless (gsignond_db_sql_database_query_exec_int (
546             sqldb,"SELECT id from CREDENTIALS where username=\"username2\";",
547             &status) == TRUE);
548     fail_unless (status == 2);
549
550     array = gsignond_db_sql_database_query_exec_int_array (
551             sqldb,"SELECT id from CREDENTIALS;");
552     fail_if (array == NULL);
553     fail_unless (array->len == 2);
554     g_array_free (array, TRUE);
555
556     stmt = gsignond_db_sql_database_prepare_statement (
557             sqldb, "SELECT id from CREDENTIALS where username=\"username1\";");
558     fail_if (stmt == NULL);
559     fail_unless (gsignond_db_sql_database_query_exec_stmt (
560             sqldb, stmt, NULL, NULL) == 1);
561     stmt = NULL;
562
563     fail_unless (gsignond_db_sql_database_start_transaction (sqldb) == TRUE);
564     fail_unless (gsignond_db_sql_database_commit_transaction (sqldb) == TRUE);
565     fail_unless (gsignond_db_sql_database_start_transaction (sqldb) == TRUE);
566     fail_unless (gsignond_db_sql_database_rollback_transaction (sqldb) == TRUE);
567     fail_unless (gsignond_db_sql_database_start_transaction (sqldb) == TRUE);
568     fail_unless (gsignond_db_sql_database_start_transaction (sqldb) == FALSE);
569     fail_unless (gsignond_db_sql_database_rollback_transaction (sqldb) == TRUE);
570
571     fail_unless (gsignond_db_sql_database_transaction_exec (
572             sqldb, "SELECT id from CREDENTIALS "
573                    "where username=\"username1\";") == TRUE);
574
575     fail_unless (gsignond_db_sql_database_get_db_version (
576             sqldb, "PRAGMA user_version;") == 1);
577
578     error = gsignond_db_create_error(GSIGNOND_DB_ERROR_UNKNOWN,"Unknown error");
579     gsignond_db_sql_database_clear_last_error (sqldb);
580     fail_unless (gsignond_db_sql_database_get_last_error (sqldb) == NULL);
581     gsignond_db_sql_database_set_last_error (sqldb, error);
582     fail_unless (gsignond_db_sql_database_get_last_error (sqldb) != NULL);
583     gsignond_db_sql_database_clear_last_error (sqldb);
584     fail_unless (gsignond_db_sql_database_get_last_error (sqldb) == NULL);
585
586     fail_unless (gsignond_db_sql_database_exec (
587             sqldb, "INSERT INTO CREDENTIALS (id, username, password) "
588                     "VALUES (4, \"username4\",\"password3\");") == TRUE);
589     fail_unless (gsignond_db_sql_database_get_last_insert_rowid (
590             sqldb) == 4);
591
592     fail_unless (gsignond_db_secret_database_remove_data (
593             database, id, method) == TRUE);
594     fail_unless (gsignond_db_sql_database_clear (sqldb) == TRUE);
595     fail_unless (gsignond_db_sql_database_close (sqldb) == TRUE);
596     g_object_unref(database);
597 }
598 END_TEST
599
600 START_TEST (test_secret_storage)
601 {
602     GSignondSecretStorage *storage = NULL;
603     GSignondConfig *config = NULL;
604     GSignondCredentials *creds = NULL;
605     guint32 id = 1, method = 2;
606     GHashTable *data = NULL;
607     GHashTable *data2 = NULL;
608     Data input;
609     const gchar *dir = NULL;
610
611     config = gsignond_config_new ();
612     gsignond_config_set_string (config, GSIGNOND_CONFIG_GENERAL_SECURE_DIR, "/tmp/gsignond");
613     
614     /* Secret Storage */
615     storage = g_object_new (GSIGNOND_TYPE_SECRET_STORAGE,
616             "config", config, NULL);
617     g_object_unref(config);
618     fail_if (storage == NULL);
619
620     dir = gsignond_config_get_string (config,
621             GSIGNOND_CONFIG_GENERAL_SECURE_DIR);
622     if (!dir) {
623         dir = g_get_user_data_dir ();
624     }
625     g_mkdir_with_parents (dir, S_IRWXU);
626
627     fail_unless (gsignond_secret_storage_get_last_error (storage) == NULL);
628     fail_unless (gsignond_secret_storage_clear_db (storage) == FALSE);
629     fail_unless (gsignond_secret_storage_is_open_db (storage) == FALSE);
630     fail_unless (gsignond_secret_storage_load_credentials (storage, 1) == NULL);
631     fail_unless (gsignond_secret_storage_update_credentials (
632             storage, NULL) == FALSE);
633     fail_unless (gsignond_secret_storage_remove_credentials (
634             storage, 1) == FALSE);
635     fail_unless (gsignond_secret_storage_load_data (
636             storage, 1, 2) == NULL);
637     fail_unless (gsignond_secret_storage_update_data (
638             storage, 1, 2, NULL) == FALSE);
639     fail_unless (gsignond_secret_storage_remove_data (
640             storage, 1, 2) == FALSE);
641
642     fail_unless (gsignond_secret_storage_open_db (storage) == TRUE);
643     /* don't open the db again if its already open */
644     fail_unless (gsignond_secret_storage_open_db (storage) == TRUE);
645
646     creds = gsignond_credentials_new ();
647     fail_if (creds == NULL);
648
649     fail_unless (gsignond_credentials_set_data (
650             creds, id, "user 1", "pass 1") == TRUE);
651
652     fail_unless (gsignond_secret_storage_update_credentials (
653             storage, creds) == TRUE);
654     g_object_unref (creds); creds = NULL;
655
656     creds = gsignond_secret_storage_load_credentials (storage, id);
657     fail_if (creds == NULL);
658
659     fail_unless (gsignond_secret_storage_check_credentials (
660             storage, creds) == TRUE);
661
662     gsignond_credentials_set_id (creds, 3);
663     fail_unless (gsignond_secret_storage_check_credentials (
664             storage, creds) == FALSE);
665     g_object_unref (creds);
666
667     /* remove the added credentials */
668     fail_unless (gsignond_secret_storage_remove_credentials (
669             storage, id) == TRUE);
670
671     /* add data to store */
672     data = g_hash_table_new_full ((GHashFunc)g_str_hash,
673             (GEqualFunc)g_str_equal,
674             (GDestroyNotify)NULL,
675             (GDestroyNotify)g_variant_unref);
676     fail_if (data == NULL);
677
678     g_hash_table_insert (data,"key1",g_variant_new_string ("string_value"));
679     g_hash_table_insert (data,"key2",g_variant_new_double (12223.4223));
680     g_hash_table_insert (data,"key3",g_variant_new_uint16(20));
681     g_hash_table_insert (data,"key4",g_variant_new("^ay", "byte_value"));
682
683     fail_unless (gsignond_secret_storage_update_data (
684             storage, id, method, data) == TRUE);
685     data2 = gsignond_secret_storage_load_data (storage, id, method);
686     fail_if (data2 == NULL);
687     input.table = data;
688     input.status = 1;
689     g_hash_table_foreach (data2, (GHFunc)_compare_key_value, &input);
690     fail_if (input.status != 1);
691
692     gsignond_dictionary_unref(data2);
693     g_hash_table_unref(data);
694
695     fail_unless (gsignond_secret_storage_remove_data (
696             storage, id, method) == TRUE);
697     fail_unless (gsignond_secret_storage_clear_db (storage) == TRUE);
698     fail_unless (gsignond_secret_storage_close_db (storage) == TRUE);
699     g_object_unref(storage);
700 }
701 END_TEST
702
703 START_TEST (test_metadata_database)
704 {
705     GSignondConfig *config = NULL;
706     guint32 methodid = 0;
707     guint32 identity_id = 5;
708     const gchar *method1 = "method1";
709     GSignondIdentityInfo *identity = NULL, *identity2= NULL;
710     GSignondIdentityInfoList *identities = NULL;
711     GSignondSecurityContext *ctx1 = NULL;
712     GList *methods = NULL, *reflist = NULL;
713     GSignondSecurityContextList *acl;
714     GSignondSecurityContext *owner = NULL;
715
716     config = gsignond_config_new ();
717     gsignond_config_set_string (config, GSIGNOND_CONFIG_GENERAL_SECURE_DIR, "/tmp/gsignond");
718     GSignondDbMetadataDatabase* metadata_db = NULL;
719     metadata_db = gsignond_db_metadata_database_new (config);
720     g_object_unref(config);
721     fail_if (metadata_db == NULL);
722
723     ctx1 = gsignond_security_context_new_from_values ("sysctx1", "appctx1");
724     identity = _get_filled_identity_info_2 (&identity,
725             FALSE, FALSE, FALSE, FALSE, FALSE);
726     fail_unless (gsignond_db_metadata_database_insert_method (
727             metadata_db, method1, &methodid) == FALSE);
728     fail_unless (gsignond_db_metadata_database_get_method_id (
729             metadata_db, method1) == 0);
730     fail_unless (gsignond_db_metadata_database_get_methods (
731             metadata_db, identity_id, ctx1) == NULL);
732     fail_unless (gsignond_db_metadata_database_get_methods (
733             metadata_db, identity_id, ctx1) == NULL);
734     fail_unless (gsignond_db_metadata_database_update_identity (
735             metadata_db, identity) == FALSE);
736     fail_unless (gsignond_db_metadata_database_get_identity (
737             metadata_db, identity_id) == NULL);
738     fail_unless (gsignond_db_metadata_database_get_identities (
739             metadata_db, NULL) == NULL);
740     fail_unless (gsignond_db_metadata_database_remove_identity (
741             metadata_db, identity_id) == FALSE);
742     fail_unless (gsignond_db_metadata_database_remove_reference (
743             metadata_db, identity_id, ctx1, "reference1") == FALSE);
744     fail_unless (gsignond_db_metadata_database_get_references (
745             metadata_db, identity_id, ctx1) == NULL);
746     fail_unless (gsignond_db_metadata_database_get_accesscontrol_list (
747             metadata_db, identity_id) == NULL);
748     fail_unless (gsignond_db_metadata_database_get_owner (
749             metadata_db, identity_id) == NULL);
750
751     fail_unless (gsignond_db_metadata_database_open (metadata_db) == TRUE);
752
753     fail_unless (gsignond_db_metadata_database_open (metadata_db) == TRUE);
754
755     fail_unless (gsignond_db_sql_database_clear (
756             GSIGNOND_DB_SQL_DATABASE (metadata_db)) == TRUE);
757
758     fail_unless (gsignond_db_metadata_database_get_accesscontrol_list (
759             metadata_db, identity_id) == NULL);
760
761     fail_unless (gsignond_db_metadata_database_get_owner (
762             metadata_db, identity_id) == NULL);
763
764     fail_unless (gsignond_db_metadata_database_get_method_id (
765             metadata_db, method1) == 0);
766     fail_unless (gsignond_db_metadata_database_insert_method (
767                         metadata_db, method1, &methodid) == TRUE);
768
769     fail_unless (methodid == gsignond_db_metadata_database_get_method_id (
770             metadata_db, method1));
771
772     /*update_identity*/
773     identity = _get_filled_identity_info_2 (&identity,
774             TRUE, FALSE, FALSE, FALSE, FALSE);
775     fail_unless (gsignond_db_metadata_database_update_identity (
776             metadata_db, identity) == 0);
777
778     identity = _get_filled_identity_info_2 (&identity,
779             FALSE, TRUE, FALSE, FALSE, FALSE);
780     fail_unless (gsignond_db_metadata_database_update_identity (
781             metadata_db, identity) == 0);
782
783     identity = _get_filled_identity_info_2 (&identity,
784             FALSE, FALSE, TRUE, FALSE, FALSE);
785     fail_unless (gsignond_db_metadata_database_update_identity (
786             metadata_db, identity) == 0);
787
788     identity = _get_filled_identity_info_2 (&identity,
789             FALSE, FALSE, FALSE, TRUE, FALSE);
790     fail_unless (gsignond_db_metadata_database_update_identity (
791             metadata_db, identity) == 0);
792
793     identity = _get_filled_identity_info_2 (&identity,
794            FALSE, FALSE, FALSE, FALSE, TRUE);
795     identity_id = gsignond_db_metadata_database_update_identity (
796             metadata_db, identity);
797     fail_unless (identity_id != 0);
798     gsignond_identity_info_set_id (identity, identity_id);
799
800     identity2 = gsignond_db_metadata_database_get_identity (
801             metadata_db, identity_id);
802     fail_if (identity2 == NULL);
803     gsignond_identity_info_unref (identity2);
804
805     /*get_identity/identities*/
806     fail_unless (gsignond_db_metadata_database_get_identity (
807             metadata_db, 2222) == NULL);
808
809     identities = gsignond_db_metadata_database_get_identities (metadata_db, NULL);
810     fail_unless (identities != NULL);
811     fail_unless (g_list_length (identities) == 1);
812     gsignond_identity_info_list_free (identities);
813
814     /*methods*/
815     methods = gsignond_db_metadata_database_get_methods (metadata_db,
816                 identity_id, ctx1);
817     fail_if (methods == NULL);
818     g_list_free_full (methods, g_free);
819
820     /*references*/
821     fail_unless (gsignond_db_metadata_database_get_references (
822                 metadata_db, identity_id, ctx1) == NULL);
823     fail_unless (gsignond_db_metadata_database_remove_reference (
824             metadata_db, identity_id, ctx1, "reference1" ) == FALSE);
825
826     fail_unless (gsignond_db_metadata_database_insert_reference (
827             metadata_db, identity_id, ctx1, "reference1") == TRUE);
828
829     fail_unless (gsignond_db_metadata_database_insert_reference (
830             metadata_db, identity_id, ctx1, "reference1") == TRUE);
831
832     reflist = gsignond_db_metadata_database_get_references (
833             metadata_db, identity_id, ctx1);
834     fail_if (reflist == NULL);
835     fail_unless (g_list_length (reflist) == 1);
836     g_list_free_full (reflist, g_free);
837
838     fail_unless (gsignond_db_metadata_database_remove_reference (
839             metadata_db, identity_id, ctx1, "reference1" ) == TRUE);
840     gsignond_security_context_free (ctx1);
841
842     /*acl*/
843     acl = gsignond_db_metadata_database_get_accesscontrol_list (metadata_db,
844             identity_id);
845     fail_if (acl == NULL);
846     gsignond_security_context_list_free (acl);
847
848     /*owner*/
849     owner = gsignond_db_metadata_database_get_owner (metadata_db,
850             identity_id);
851     fail_if (owner == NULL);
852
853     fail_unless (gsignond_db_metadata_database_remove_identity (
854             metadata_db, identity_id) == TRUE);
855     fail_unless (gsignond_db_metadata_database_get_identities (
856             metadata_db, NULL) == NULL);
857
858     fail_unless (gsignond_db_metadata_database_get_methods (
859             metadata_db, identity_id, owner) == NULL);
860
861     gsignond_security_context_free (owner);
862
863     gsignond_identity_info_unref (identity);
864
865     fail_unless (gsignond_db_sql_database_close (
866             GSIGNOND_DB_SQL_DATABASE (metadata_db)) == TRUE);
867     g_object_unref(metadata_db);
868 }
869 END_TEST
870
871 START_TEST (test_credentials_database)
872 {
873     GSignondConfig *config = NULL;
874     guint32 identity_id = 5;
875     GSignondIdentityInfo *identity = NULL, *identity2= NULL;
876     GSignondIdentityInfoList *identities = NULL;
877     GSignondSecurityContext *ctx1 = NULL;
878     GList *methods = NULL, *reflist = NULL;
879     GSignondSecurityContextList *acl = NULL ;
880     GSignondSecurityContext *owner = NULL;
881     GSignondDbCredentialsDatabase *credentials_db = NULL;
882     GSignondSecretStorage *storage =NULL;
883     GHashTable *data = NULL;
884     GHashTable *data2 = NULL;
885     Data input;
886     GSignondDictionary *cap_filter = NULL;
887     GSignondDictionary *type_filter = NULL;
888     GSignondDictionary *cap_type_filter = NULL;
889     GSignondDictionary *no_cap_filter = NULL;
890
891     config = gsignond_config_new ();
892     gsignond_config_set_string (config, GSIGNOND_CONFIG_GENERAL_SECURE_DIR, "/tmp/gsignond");
893     storage = g_object_new (GSIGNOND_TYPE_SECRET_STORAGE,
894             "config", config, NULL);
895     g_object_unref(config);
896     credentials_db = gsignond_db_credentials_database_new (
897             config, storage);
898     g_object_unref (storage);
899     fail_if (credentials_db == NULL);
900
901     fail_unless (gsignond_db_credentials_database_open_secret_storage (
902             credentials_db) == TRUE);
903
904     fail_unless (gsignond_db_credentials_database_clear (
905             credentials_db) == TRUE);
906
907     identity = _get_filled_identity_info ();
908
909     /*identity load/update*/
910     identity_id = gsignond_db_credentials_database_update_identity (
911             credentials_db, identity);
912     fail_unless (identity_id != 0);
913     gsignond_identity_info_set_id (identity, identity_id);
914
915     fail_unless (gsignond_db_credentials_database_load_identity (
916                 credentials_db, 555, FALSE) == NULL);
917     identity2 = gsignond_db_credentials_database_load_identity (
918             credentials_db, identity_id, FALSE);
919     fail_if (identity2 == NULL);
920     gsignond_identity_info_unref (identity2);
921
922     identity2 = gsignond_db_credentials_database_load_identity (
923             credentials_db, identity_id, TRUE);
924     fail_if (identity2 == NULL);
925
926     fail_unless (g_strcmp0 (gsignond_identity_info_get_username (
927             identity2), "username1") == 0);
928     fail_unless (g_strcmp0 (gsignond_identity_info_get_secret (
929             identity2), "secret1") == 0);
930     gsignond_identity_info_unref (identity2);
931
932     fail_unless (gsignond_db_credentials_database_check_secret (
933             credentials_db, identity_id, "username2", "secret1") == FALSE);
934
935     fail_unless (gsignond_db_credentials_database_check_secret (
936             credentials_db, identity_id, "username1", "secret2") == FALSE);
937
938     fail_unless (gsignond_db_credentials_database_check_secret (
939             credentials_db, 0, "username1", "secret2") == FALSE);
940
941     fail_unless (gsignond_db_credentials_database_check_secret (
942             credentials_db, identity_id, "username1", "secret1") == TRUE);
943
944     ctx1 = gsignond_security_context_new_from_values ("sysctx1", "appctx1");
945     methods = gsignond_db_credentials_database_get_methods (credentials_db,
946                 identity_id, ctx1);
947     fail_if (methods == NULL);
948     g_list_free_full (methods, g_free);
949
950     /* add data to store */
951     data = g_hash_table_new_full ((GHashFunc)g_str_hash,
952             (GEqualFunc)g_str_equal,
953             (GDestroyNotify)NULL,
954             (GDestroyNotify)g_variant_unref);
955     g_hash_table_insert (data,"key1",g_variant_new_string ("string_value"));
956     g_hash_table_insert (data,"key2",g_variant_new_double (12223.4223));
957     g_hash_table_insert (data,"key3",g_variant_new_uint16(20));
958     g_hash_table_insert (data,"key4",g_variant_new("^ay", "byte_value"));
959
960     fail_unless (gsignond_db_credentials_database_update_data (
961             credentials_db, 0, "method1", data) == FALSE);
962
963     fail_unless (gsignond_db_credentials_database_update_data (
964             credentials_db, identity_id, "method1", data) == TRUE);
965
966     fail_unless (gsignond_db_credentials_database_update_data (
967             credentials_db, identity_id, "method1", data) == TRUE);
968
969     fail_unless (gsignond_db_credentials_database_load_data (
970             credentials_db, 0, "method1") == NULL);
971     fail_unless (gsignond_db_credentials_database_load_data (
972             credentials_db, identity_id, "method2") == NULL);
973
974     data2 = gsignond_db_credentials_database_load_data (credentials_db,
975             identity_id, "method1");
976     fail_if (data2 == NULL);
977     input.table = data;
978     input.status = 1;
979     g_hash_table_foreach (data2, (GHFunc)_compare_key_value, &input);
980     fail_if (input.status != 1);
981     gsignond_dictionary_unref(data2);
982     g_hash_table_unref(data);
983
984     fail_unless (gsignond_db_credentials_database_remove_data (
985             credentials_db, 0, "method1") == FALSE);
986
987     fail_unless (gsignond_db_credentials_database_remove_data (
988             credentials_db, identity_id, "method1") == TRUE);
989
990     /*references*/
991     fail_unless (gsignond_db_credentials_database_insert_reference (
992             credentials_db, identity_id, ctx1, "reference1") == TRUE);
993
994     reflist = gsignond_db_credentials_database_get_references (credentials_db,
995                 identity_id, ctx1);
996     fail_if (reflist == NULL);
997     fail_unless (g_list_length (reflist) == 1);
998     g_list_free_full (reflist, g_free);
999
1000     fail_unless (gsignond_db_credentials_database_remove_reference (
1001             credentials_db, identity_id, ctx1, "reference2") == FALSE);
1002
1003     fail_unless (gsignond_db_credentials_database_remove_reference (
1004             credentials_db, identity_id, ctx1, "reference1") == TRUE);
1005     gsignond_security_context_free (ctx1);
1006
1007     acl = gsignond_db_credentials_database_get_accesscontrol_list (
1008             credentials_db, identity_id);
1009     fail_if (acl == NULL);
1010     gsignond_security_context_list_free (acl);
1011
1012     owner = gsignond_db_credentials_database_get_owner (
1013             credentials_db, identity_id);
1014     fail_if (owner == NULL);
1015     gsignond_security_context_free (owner);
1016
1017     owner = gsignond_db_credentials_database_get_identity_owner (
1018             credentials_db, identity_id);
1019     fail_if (owner == NULL);
1020     gsignond_security_context_free (owner);
1021
1022     /* load_identities : matched with caption and security context */
1023     cap_filter = gsignond_dictionary_new ();
1024     GSignondSecurityContext *ctx =
1025                 gsignond_security_context_new_from_values("sysctx1", "appctx1");
1026     gsignond_dictionary_set_string (cap_filter, "Caption", "cap");
1027     gsignond_dictionary_set(cap_filter, "Owner",
1028                  gsignond_security_context_to_variant(ctx));
1029     gsignond_security_context_free (ctx);
1030     identities = gsignond_db_credentials_database_load_identities (
1031             credentials_db, cap_filter);
1032     gsignond_dictionary_unref (cap_filter);
1033
1034     fail_if (identities == NULL);
1035     fail_unless (g_list_length (identities) == 1);
1036     gsignond_identity_info_list_free (identities);
1037
1038     /* load_identities: matched with type */
1039     type_filter = gsignond_dictionary_new();
1040     gsignond_dictionary_set_int32 (type_filter, "Type", 456);
1041     identities = gsignond_db_credentials_database_load_identities (
1042             credentials_db, type_filter);
1043     gsignond_dictionary_unref (type_filter);
1044
1045     fail_if (identities == NULL);
1046     fail_unless (g_list_length (identities) == 1);
1047     gsignond_identity_info_list_free (identities);
1048
1049     /* load_identities: matched with type and caption */
1050     cap_type_filter = gsignond_dictionary_new();
1051     gsignond_dictionary_set_int32 (cap_type_filter, "Type", 456);
1052     gsignond_dictionary_set_string (cap_type_filter, "Caption", "CAP");
1053     identities = gsignond_db_credentials_database_load_identities (
1054             credentials_db, cap_type_filter);
1055     gsignond_dictionary_unref (cap_type_filter);
1056
1057     fail_if (identities == NULL);
1058     fail_unless (g_list_length (identities) == 1);
1059     gsignond_identity_info_list_free (identities);
1060
1061     /* Negative load_identities query */
1062     no_cap_filter = gsignond_dictionary_new();
1063     gsignond_dictionary_set_string (no_cap_filter, "Caption", "non_existing");
1064
1065     identities = gsignond_db_credentials_database_load_identities (
1066             credentials_db, no_cap_filter);
1067     gsignond_dictionary_unref (no_cap_filter);
1068     fail_unless (identities == NULL);
1069
1070     fail_unless (gsignond_db_credentials_database_remove_identity (
1071             credentials_db, identity_id) == TRUE);
1072     gsignond_identity_info_unref (identity);
1073
1074     g_object_unref(credentials_db);
1075 }
1076 END_TEST
1077
1078 Suite* db_suite (void)
1079 {
1080     Suite *s = suite_create ("Database");
1081
1082     TCase *tc_core = tcase_create ("Tests");
1083     tcase_add_test (tc_core, test_identity_info);
1084
1085     tcase_add_test (tc_core, test_sql_database);
1086     tcase_add_test (tc_core, test_secret_storage);
1087     tcase_add_test (tc_core, test_metadata_database);
1088     tcase_add_test (tc_core, test_credentials_database);
1089     suite_add_tcase (s, tc_core);
1090     return s;
1091 }
1092
1093 int main (void)
1094 {
1095     int number_failed;
1096
1097 #if !GLIB_CHECK_VERSION (2, 36, 0)
1098     g_type_init ();
1099 #endif
1100
1101     Suite *s = db_suite ();
1102     SRunner *sr = srunner_create (s);
1103     srunner_run_all (sr, CK_NORMAL);
1104     number_failed = srunner_ntests_failed (sr);
1105     srunner_free (sr);
1106     return (number_failed == 0) ? EXIT_SUCCESS : EXIT_FAILURE;
1107 }
1108