Merge lp:~ubuntu-branches/ubuntu/precise/telepathy-glib/precise-201111092112 into lp:ubuntu/precise/telepathy-glib

Proposed by Ubuntu Package Importer
Status: Rejected
Rejected by: James Westby
Proposed branch: lp:~ubuntu-branches/ubuntu/precise/telepathy-glib/precise-201111092112
Merge into: lp:ubuntu/precise/telepathy-glib
Diff against target: 2803 lines (+2792/-0) (has conflicts)
1 file modified
.pc/ludicrous-timeout-for-lp-buildd.patch/tests/dbus/contact-lists.c (+2792/-0)
Text conflict in .pc/ludicrous-timeout-for-lp-buildd.patch/tests/dbus/contact-lists.c
To merge this branch: bzr merge lp:~ubuntu-branches/ubuntu/precise/telepathy-glib/precise-201111092112
Reviewer Review Type Date Requested Status
Ubuntu branches Pending
Review via email: mp+81778@code.launchpad.net

Description of the change

The package importer has detected a possible inconsistency between the package history in the archive and the history in bzr. As the archive is authoritative the importer has made lp:ubuntu/precise/telepathy-glib reflect what is in the archive and the old bzr branch has been pushed to lp:~ubuntu-branches/ubuntu/precise/telepathy-glib/precise-201111092112. This merge proposal was created so that an Ubuntu developer can review the situations and perform a merge/upload if necessary. There are three typical cases where this can happen.
  1. Where someone pushes a change to bzr and someone else uploads the package without that change. This is the reason that this check is done by the importer. If this appears to be the case then a merge/upload should be done if the changes that were in bzr are still desirable.
  2. The importer incorrectly detected the above situation when someone made a change in bzr and then uploaded it.
  3. The importer incorrectly detected the above situation when someone just uploaded a package and didn't touch bzr.

If this case doesn't appear to be the first situation then set the status of the merge proposal to "Rejected" and help avoid the problem in future by filing a bug at https://bugs.launchpad.net/udd linking to this merge proposal.

(this is an automatically generated message)

To post a comment you must log in.

Unmerged revisions

70. By Ken VanDine

releasing version 0.16.2-1ubuntu1

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file '.pc/ludicrous-timeout-for-lp-buildd.patch/tests/dbus/contact-lists.c'
--- .pc/ludicrous-timeout-for-lp-buildd.patch/tests/dbus/contact-lists.c 2011-11-09 15:08:17 +0000
+++ .pc/ludicrous-timeout-for-lp-buildd.patch/tests/dbus/contact-lists.c 2011-11-09 21:18:30 +0000
@@ -1,3 +1,4 @@
1<<<<<<< TREE
1/* Feature test for contact lists2/* Feature test for contact lists
2 *3 *
3 * Copyright © 2007-2010 Collabora Ltd. <http://www.collabora.co.uk/>4 * Copyright © 2007-2010 Collabora Ltd. <http://www.collabora.co.uk/>
@@ -2827,3 +2828,2794 @@
28272828
2828 return g_test_run ();2829 return g_test_run ();
2829}2830}
2831=======
2832/* Feature test for contact lists
2833 *
2834 * Copyright © 2007-2010 Collabora Ltd. <http://www.collabora.co.uk/>
2835 * Copyright © 2007-2008 Nokia Corporation
2836 *
2837 * Copying and distribution of this file, with or without modification,
2838 * are permitted in any medium without royalty provided the copyright
2839 * notice and this notice are preserved.
2840 */
2841
2842#include <telepathy-glib/connection.h>
2843
2844#include "examples/cm/contactlist/conn.h"
2845#include "tests/lib/util.h"
2846
2847typedef enum {
2848 CONTACTS_CHANGED,
2849 GROUPS_CHANGED,
2850 GROUPS_CREATED,
2851 GROUPS_REMOVED,
2852 GROUP_RENAMED,
2853 BLOCKED_CONTACTS_CHANGED
2854} LogEntryType;
2855
2856typedef struct {
2857 LogEntryType type;
2858 /* ContactsChanged */
2859 GHashTable *contacts_changed;
2860 TpIntset *contacts_removed;
2861 /* GroupsChanged */
2862 GArray *contacts;
2863 /* GroupsChanged, GroupsCreated, GroupRenamed */
2864 GStrv groups_added;
2865 /* GroupsChanged, GroupsRemoved, GroupRenamed */
2866 GStrv groups_removed;
2867 /* BlockedContactsChanged */
2868 GHashTable *blocked_contacts;
2869 GHashTable *unblocked_contacts;
2870} LogEntry;
2871
2872static void
2873log_entry_free (LogEntry *le)
2874{
2875 if (le->contacts_changed != NULL)
2876 g_hash_table_unref (le->contacts_changed);
2877
2878 if (le->contacts_removed != NULL)
2879 tp_intset_destroy (le->contacts_removed);
2880
2881 if (le->contacts != NULL)
2882 g_array_unref (le->contacts);
2883
2884 g_strfreev (le->groups_added);
2885 g_strfreev (le->groups_removed);
2886
2887 if (le->blocked_contacts != NULL)
2888 g_hash_table_unref (le->blocked_contacts);
2889
2890 if (le->unblocked_contacts != NULL)
2891 g_hash_table_unref (le->unblocked_contacts);
2892
2893 g_slice_free (LogEntry, le);
2894}
2895
2896typedef struct {
2897 TpDBusDaemon *dbus;
2898 ExampleContactListConnection *service_conn;
2899 TpBaseConnection *service_conn_as_base;
2900 gchar *conn_name;
2901 gchar *conn_path;
2902 TpConnection *conn;
2903
2904 TpChannel *publish;
2905 TpChannel *subscribe;
2906 TpChannel *stored;
2907 TpChannel *deny;
2908
2909 TpChannel *group;
2910
2911 TpHandleRepoIface *contact_repo;
2912 TpHandle sjoerd;
2913 TpHandle helen;
2914 TpHandle wim;
2915 TpHandle bill;
2916 TpHandle ninja;
2917 TpHandle canceller;
2918
2919 GArray *arr;
2920
2921 /* list of LogEntry */
2922 GPtrArray *log;
2923
2924 GAsyncResult *prepare_result;
2925 GHashTable *contact_attributes;
2926
2927 GMainLoop *main_loop;
2928} Test;
2929
2930static void
2931test_quit_loop (gpointer p)
2932{
2933 Test *test = p;
2934
2935 g_main_loop_quit (test->main_loop);
2936}
2937
2938static void
2939contacts_changed_with_id_cb (TpConnection *connection,
2940 GHashTable *changes,
2941 GHashTable *identifiers,
2942 GHashTable *removals,
2943 gpointer user_data,
2944 GObject *weak_object G_GNUC_UNUSED)
2945{
2946 Test *test = user_data;
2947 LogEntry *le = g_slice_new0 (LogEntry);
2948 GHashTableIter i;
2949 gpointer key, value;
2950
2951 if (g_hash_table_size (changes) > 0)
2952 g_assert_cmpuint (g_hash_table_size (changes), ==,
2953 g_hash_table_size (identifiers));
2954 else
2955 g_assert_cmpuint (g_hash_table_size (removals), >, 0);
2956
2957 le->type = CONTACTS_CHANGED;
2958 le->contacts_changed = g_boxed_copy (TP_HASH_TYPE_CONTACT_SUBSCRIPTION_MAP,
2959 changes);
2960
2961 /* We asserted above that we have as many identifiers as we have changes. */
2962 g_hash_table_iter_init (&i, identifiers);
2963 while (g_hash_table_iter_next (&i, &key, &value))
2964 {
2965 TpHandle handle = GPOINTER_TO_UINT (key);
2966
2967 g_assert_cmpstr (value, ==,
2968 tp_handle_inspect (test->contact_repo, handle));
2969 }
2970
2971 le->contacts_removed = tp_intset_new ();
2972
2973 g_hash_table_iter_init (&i, removals);
2974 while (g_hash_table_iter_next (&i, &key, &value))
2975 {
2976 TpHandle handle = GPOINTER_TO_UINT (key);
2977
2978 g_assert_cmpstr (value, ==,
2979 tp_handle_inspect (test->contact_repo, handle));
2980 tp_intset_add (le->contacts_removed, handle);
2981 }
2982
2983 g_ptr_array_add (test->log, le);
2984}
2985
2986static void
2987contacts_changed_cb (TpConnection *connection,
2988 GHashTable *changes,
2989 const GArray *removals,
2990 gpointer user_data,
2991 GObject *weak_object G_GNUC_UNUSED)
2992{
2993 Test *test = user_data;
2994 LogEntry *le;
2995 GHashTableIter i;
2996 gpointer key, value;
2997 TpIntset *removal_set;
2998
2999 g_assert (g_hash_table_size (changes) > 0 || removals->len > 0);
3000
3001 /* We should have had a ContactsChangedByID signal immediately before this
3002 * signal */
3003 g_assert_cmpuint (test->log->len, >, 0);
3004
3005 le = g_ptr_array_index (test->log, test->log->len - 1);
3006 g_assert_cmpuint (le->type, ==, CONTACTS_CHANGED);
3007
3008 /* The changes should all have been the same as in the previous signal */
3009 g_assert_cmpuint (g_hash_table_size (changes), ==,
3010 g_hash_table_size (le->contacts_changed));
3011
3012 g_hash_table_iter_init (&i, changes);
3013 while (g_hash_table_iter_next (&i, &key, &value))
3014 {
3015 GValueArray *existing = g_hash_table_lookup (le->contacts_changed, key);
3016 GValueArray *emitted = value;
3017 guint existing_sub, existing_pub, emitted_sub, emitted_pub;
3018 const gchar *existing_req, *emitted_req;
3019
3020 g_assert (existing != NULL);
3021
3022 tp_value_array_unpack (existing, 3, &existing_sub, &existing_pub,
3023 &existing_req);
3024 tp_value_array_unpack (emitted, 3, &emitted_sub, &emitted_pub,
3025 &emitted_req);
3026
3027 g_assert_cmpuint (existing_sub, ==, emitted_sub);
3028 g_assert_cmpuint (existing_pub, ==, emitted_pub);
3029 g_assert_cmpstr (existing_req, ==, emitted_req);
3030 }
3031
3032 removal_set = tp_intset_from_array (removals);
3033
3034 if (!tp_intset_is_equal (removal_set, le->contacts_removed))
3035 g_error ("Removals from ContactsChangedById (%s) != "
3036 "Removals from ContactsChanged (%s)",
3037 tp_intset_dump (le->contacts_removed),
3038 tp_intset_dump (removal_set));
3039
3040 tp_intset_destroy (removal_set);
3041}
3042
3043static void
3044groups_changed_cb (TpConnection *connection,
3045 const GArray *contacts,
3046 const gchar **groups_added,
3047 const gchar **groups_removed,
3048 gpointer user_data,
3049 GObject *weak_object G_GNUC_UNUSED)
3050{
3051 Test *test = user_data;
3052 LogEntry *le = g_slice_new0 (LogEntry);
3053
3054 g_assert (contacts->len > 0);
3055 g_assert ((groups_added != NULL && groups_added[0] != NULL) ||
3056 (groups_removed != NULL && groups_removed[0] != NULL));
3057
3058 le->type = GROUPS_CHANGED;
3059 le->contacts = g_array_sized_new (FALSE, FALSE, sizeof (guint),
3060 contacts->len);
3061 g_array_append_vals (le->contacts, contacts->data, contacts->len);
3062 le->groups_added = g_strdupv ((GStrv) groups_added);
3063 le->groups_removed = g_strdupv ((GStrv) groups_removed);
3064
3065 g_ptr_array_add (test->log, le);
3066}
3067
3068static void
3069groups_created_cb (TpConnection *connection,
3070 const gchar **groups_added,
3071 gpointer user_data,
3072 GObject *weak_object G_GNUC_UNUSED)
3073{
3074 Test *test = user_data;
3075 LogEntry *le = g_slice_new0 (LogEntry);
3076
3077 g_assert (groups_added != NULL);
3078 g_assert (groups_added[0] != NULL);
3079
3080 le->type = GROUPS_CREATED;
3081 le->groups_added = g_strdupv ((GStrv) groups_added);
3082
3083 g_ptr_array_add (test->log, le);
3084}
3085
3086static void
3087groups_removed_cb (TpConnection *connection,
3088 const gchar **groups_removed,
3089 gpointer user_data,
3090 GObject *weak_object G_GNUC_UNUSED)
3091{
3092 Test *test = user_data;
3093 LogEntry *le = g_slice_new0 (LogEntry);
3094
3095 g_assert (groups_removed != NULL);
3096 g_assert (groups_removed[0] != NULL);
3097
3098 le->type = GROUPS_REMOVED;
3099 le->groups_removed = g_strdupv ((GStrv) groups_removed);
3100
3101 g_ptr_array_add (test->log, le);
3102}
3103
3104static void
3105group_renamed_cb (TpConnection *connection,
3106 const gchar *old_name,
3107 const gchar *new_name,
3108 gpointer user_data,
3109 GObject *weak_object G_GNUC_UNUSED)
3110{
3111 Test *test = user_data;
3112 LogEntry *le = g_slice_new0 (LogEntry);
3113
3114 le->type = GROUP_RENAMED;
3115 le->groups_added = g_new0 (gchar *, 2);
3116 le->groups_added[0] = g_strdup (new_name);
3117 le->groups_removed = g_new0 (gchar *, 2);
3118 le->groups_removed[0] = g_strdup (old_name);
3119
3120 g_ptr_array_add (test->log, le);
3121}
3122
3123static void
3124blocked_contacts_changed_cb (TpConnection *connection,
3125 GHashTable *blocked_contacts,
3126 GHashTable *unblocked_contacts,
3127 gpointer user_data,
3128 GObject *weak_object G_GNUC_UNUSED)
3129{
3130 Test *test = user_data;
3131 LogEntry *le = g_slice_new0 (LogEntry);
3132
3133 le->type = BLOCKED_CONTACTS_CHANGED;
3134 le->blocked_contacts = g_hash_table_ref (blocked_contacts);
3135 le->unblocked_contacts = g_hash_table_ref (unblocked_contacts);
3136
3137 g_ptr_array_add (test->log, le);
3138}
3139
3140static void
3141maybe_queue_disconnect (TpProxySignalConnection *sc)
3142{
3143 if (sc != NULL)
3144 g_test_queue_destroy (
3145 (GDestroyNotify) tp_proxy_signal_connection_disconnect, sc);
3146}
3147
3148static void
3149setup_pre_connect (
3150 Test *test,
3151 gconstpointer data)
3152{
3153 GError *error = NULL;
3154 const gchar *account;
3155
3156 g_type_init ();
3157 tp_debug_set_flags ("all");
3158 test->dbus = tp_tests_dbus_daemon_dup_or_die ();
3159 test->main_loop = g_main_loop_new (NULL, FALSE);
3160
3161 /* Some tests want 'account' to be an invalid identifier, so that Connect()
3162 * will fail (and the status will change to Disconnected).
3163 */
3164 if (!tp_strdiff (data, "break-account-parameter"))
3165 account = "";
3166 else
3167 account = "me@example.com";
3168
3169 test->service_conn = tp_tests_object_new_static_class (
3170 EXAMPLE_TYPE_CONTACT_LIST_CONNECTION,
3171 "account", account,
3172 "simulation-delay", 0,
3173 "protocol", "example-contact-list",
3174 NULL);
3175 test->service_conn_as_base = TP_BASE_CONNECTION (test->service_conn);
3176 g_assert (test->service_conn != NULL);
3177 g_assert (test->service_conn_as_base != NULL);
3178
3179 g_assert (tp_base_connection_register (test->service_conn_as_base, "example",
3180 &test->conn_name, &test->conn_path, &error));
3181 g_assert_no_error (error);
3182
3183 test->contact_repo = tp_base_connection_get_handles (
3184 test->service_conn_as_base, TP_HANDLE_TYPE_CONTACT);
3185
3186 test->conn = tp_connection_new (test->dbus, test->conn_name, test->conn_path,
3187 &error);
3188 g_assert (test->conn != NULL);
3189 g_assert_no_error (error);
3190
3191 /* Prepare the connection far enough to know its own interfaces. */
3192 tp_tests_proxy_run_until_prepared (test->conn, NULL);
3193}
3194
3195static void
3196setup (Test *test,
3197 gconstpointer data)
3198{
3199 GQuark features[] = { TP_CONNECTION_FEATURE_CONNECTED, 0 };
3200
3201 setup_pre_connect (test, data);
3202
3203 tp_cli_connection_call_connect (test->conn, -1, NULL, NULL, NULL, NULL);
3204 tp_tests_proxy_run_until_prepared (test->conn, features);
3205
3206 g_assert (tp_proxy_is_prepared (test->conn, TP_CONNECTION_FEATURE_CORE));
3207 g_assert (tp_proxy_is_prepared (test->conn,
3208 TP_CONNECTION_FEATURE_CONNECTED));
3209
3210 test->log = g_ptr_array_new ();
3211
3212 maybe_queue_disconnect (
3213 tp_cli_connection_interface_contact_list_connect_to_contacts_changed_with_id (
3214 test->conn, contacts_changed_with_id_cb, test, NULL, NULL, NULL));
3215 maybe_queue_disconnect (
3216 tp_cli_connection_interface_contact_list_connect_to_contacts_changed (
3217 test->conn, contacts_changed_cb, test, NULL, NULL, NULL));
3218 maybe_queue_disconnect (
3219 tp_cli_connection_interface_contact_groups_connect_to_groups_changed (
3220 test->conn, groups_changed_cb, test, NULL, NULL, NULL));
3221 maybe_queue_disconnect (
3222 tp_cli_connection_interface_contact_groups_connect_to_groups_created (
3223 test->conn, groups_created_cb, test, NULL, NULL, NULL));
3224 maybe_queue_disconnect (
3225 tp_cli_connection_interface_contact_groups_connect_to_groups_removed (
3226 test->conn, groups_removed_cb, test, NULL, NULL, NULL));
3227 maybe_queue_disconnect (
3228 tp_cli_connection_interface_contact_groups_connect_to_group_renamed (
3229 test->conn, group_renamed_cb, test, NULL, NULL, NULL));
3230 maybe_queue_disconnect (
3231 tp_cli_connection_interface_contact_blocking_connect_to_blocked_contacts_changed (
3232 test->conn, blocked_contacts_changed_cb, test, NULL, NULL, NULL));
3233
3234 test->sjoerd = tp_handle_ensure (test->contact_repo, "sjoerd@example.com",
3235 NULL, NULL);
3236 g_assert (test->sjoerd != 0);
3237 test->helen = tp_handle_ensure (test->contact_repo, "helen@example.com",
3238 NULL, NULL);
3239 g_assert (test->helen != 0);
3240 test->wim = tp_handle_ensure (test->contact_repo, "wim@example.com",
3241 NULL, NULL);
3242 g_assert (test->wim != 0);
3243 test->bill = tp_handle_ensure (test->contact_repo, "bill@example.com",
3244 NULL, NULL);
3245 g_assert (test->bill != 0);
3246 test->ninja = tp_handle_ensure (test->contact_repo, "ninja@example.com",
3247 NULL, NULL);
3248 g_assert (test->ninja != 0);
3249 test->canceller = tp_handle_ensure (test->contact_repo,
3250 "canceller@cancel.example.com", NULL, NULL);
3251 g_assert (test->canceller != 0);
3252
3253 test->arr = g_array_new (FALSE, FALSE, sizeof (TpHandle));
3254}
3255
3256static void
3257test_clear_log (Test *test)
3258{
3259 g_ptr_array_foreach (test->log, (GFunc) log_entry_free, NULL);
3260 g_ptr_array_set_size (test->log, 0);
3261}
3262
3263static void
3264teardown_pre_connect (
3265 Test *test,
3266 gconstpointer data)
3267{
3268 test->service_conn_as_base = NULL;
3269 g_object_unref (test->service_conn);
3270 g_free (test->conn_name);
3271 g_free (test->conn_path);
3272 tp_clear_object (&test->conn);
3273 tp_clear_object (&test->dbus);
3274 tp_clear_pointer (&test->main_loop, g_main_loop_unref);
3275}
3276
3277static void
3278teardown (Test *test,
3279 gconstpointer data)
3280{
3281 TpConnection *conn;
3282 gboolean ok;
3283 GError *error = NULL;
3284
3285 g_array_free (test->arr, TRUE);
3286
3287 test_clear_log (test);
3288 g_ptr_array_free (test->log, TRUE);
3289
3290 tp_handle_unref (test->contact_repo, test->sjoerd);
3291 tp_handle_unref (test->contact_repo, test->helen);
3292 tp_handle_unref (test->contact_repo, test->wim);
3293 tp_handle_unref (test->contact_repo, test->bill);
3294 tp_handle_unref (test->contact_repo, test->ninja);
3295 tp_handle_unref (test->contact_repo, test->canceller);
3296
3297 tp_clear_object (&test->publish);
3298 tp_clear_object (&test->subscribe);
3299 tp_clear_object (&test->stored);
3300 tp_clear_object (&test->group);
3301
3302 /* make a new TpConnection just to disconnect the underlying Connection,
3303 * so we don't leak it */
3304 conn = tp_connection_new (test->dbus, test->conn_name, test->conn_path,
3305 &error);
3306 g_assert (conn != NULL);
3307 g_assert_no_error (error);
3308 ok = tp_cli_connection_run_disconnect (conn, -1, &error, NULL);
3309 g_assert (ok);
3310 g_assert_no_error (error);
3311 g_assert (!tp_connection_run_until_ready (conn, FALSE, &error, NULL));
3312 g_assert_error (error, TP_ERRORS, TP_ERROR_CANCELLED);
3313 g_clear_error (&error);
3314
3315 tp_clear_pointer (&test->contact_attributes, g_hash_table_unref);
3316
3317 teardown_pre_connect (test, data);
3318}
3319
3320static TpChannel *
3321test_ensure_channel (Test *test,
3322 guint channel_type,
3323 const gchar *id)
3324{
3325 GError *error = NULL;
3326 GHashTable *asv, *props;
3327 gchar *path;
3328 TpChannel *ret;
3329
3330 asv = tp_asv_new (
3331 TP_PROP_CHANNEL_CHANNEL_TYPE,
3332 G_TYPE_STRING, TP_IFACE_CHANNEL_TYPE_CONTACT_LIST,
3333 TP_PROP_CHANNEL_TARGET_HANDLE_TYPE,
3334 G_TYPE_UINT, channel_type,
3335 TP_PROP_CHANNEL_TARGET_ID,
3336 G_TYPE_STRING, id,
3337 NULL);
3338 tp_cli_connection_interface_requests_run_ensure_channel (test->conn, -1,
3339 asv, NULL, &path, &props, &error, NULL);
3340 g_assert_no_error (error);
3341 ret = tp_channel_new_from_properties (test->conn, path, props,
3342 &error);
3343 g_assert (ret != NULL);
3344 g_assert_no_error (error);
3345 g_free (path);
3346 g_hash_table_unref (props);
3347 g_hash_table_unref (asv);
3348
3349 tp_tests_proxy_run_until_prepared (ret, NULL);
3350 return ret;
3351}
3352
3353static void
3354test_assert_one_contact_changed (Test *test,
3355 guint index,
3356 TpHandle handle,
3357 TpSubscriptionState expected_sub_state,
3358 TpSubscriptionState expected_pub_state,
3359 const gchar *expected_pub_request)
3360{
3361 LogEntry *le;
3362 GValueArray *va;
3363 guint sub_state;
3364 guint pub_state;
3365 const gchar *pub_request;
3366
3367 le = g_ptr_array_index (test->log, index);
3368 g_assert_cmpint (le->type, ==, CONTACTS_CHANGED);
3369
3370 g_assert_cmpuint (g_hash_table_size (le->contacts_changed), ==, 1);
3371 va = g_hash_table_lookup (le->contacts_changed, GUINT_TO_POINTER (handle));
3372 g_assert (va != NULL);
3373 tp_value_array_unpack (va, 3,
3374 &sub_state,
3375 &pub_state,
3376 &pub_request);
3377 g_assert_cmpuint (sub_state, ==, expected_sub_state);
3378 g_assert_cmpuint (pub_state, ==, expected_pub_state);
3379 g_assert_cmpstr (pub_request, ==, expected_pub_request);
3380
3381 g_assert_cmpuint (tp_intset_size (le->contacts_removed), ==, 0);
3382}
3383
3384static void
3385test_assert_one_contact_removed (Test *test,
3386 guint index,
3387 TpHandle handle)
3388{
3389 LogEntry *le;
3390
3391 le = g_ptr_array_index (test->log, index);
3392 g_assert_cmpint (le->type, ==, CONTACTS_CHANGED);
3393
3394 g_assert_cmpuint (g_hash_table_size (le->contacts_changed), ==, 0);
3395 g_assert_cmpuint (tp_intset_size (le->contacts_removed), ==, 1);
3396 g_assert (tp_intset_is_member (le->contacts_removed, handle));
3397}
3398
3399static void
3400test_assert_one_group_joined (Test *test,
3401 guint index,
3402 TpHandle handle,
3403 const gchar *group)
3404{
3405 LogEntry *le;
3406
3407 le = g_ptr_array_index (test->log, index);
3408 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
3409 g_assert_cmpuint (le->contacts->len, ==, 1);
3410 g_assert_cmpuint (g_array_index (le->contacts, guint, 0), ==, handle);
3411 g_assert (le->groups_added != NULL);
3412 g_assert_cmpstr (le->groups_added[0], ==, group);
3413 g_assert_cmpstr (le->groups_added[1], ==, NULL);
3414 g_assert (le->groups_removed == NULL || le->groups_removed[0] == NULL);
3415}
3416
3417static void
3418test_assert_one_group_left (Test *test,
3419 guint index,
3420 TpHandle handle,
3421 const gchar *group)
3422{
3423 LogEntry *le;
3424
3425 le = g_ptr_array_index (test->log, index);
3426 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
3427 g_assert_cmpuint (le->contacts->len, ==, 1);
3428 g_assert_cmpuint (g_array_index (le->contacts, guint, 0), ==, handle);
3429 g_assert (le->groups_added == NULL || le->groups_added[0] == NULL);
3430 g_assert (le->groups_removed != NULL);
3431 g_assert_cmpstr (le->groups_removed[0], ==, group);
3432 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
3433}
3434
3435static void
3436test_assert_one_group_created (Test *test,
3437 guint index,
3438 const gchar *group)
3439{
3440 LogEntry *le;
3441
3442 le = g_ptr_array_index (test->log, index);
3443 g_assert_cmpint (le->type, ==, GROUPS_CREATED);
3444 g_assert (le->groups_added != NULL);
3445 g_assert_cmpstr (le->groups_added[0], ==, group);
3446 g_assert_cmpstr (le->groups_added[1], ==, NULL);
3447}
3448
3449static void
3450test_assert_one_group_removed (Test *test,
3451 guint index,
3452 const gchar *group)
3453{
3454 LogEntry *le;
3455
3456 le = g_ptr_array_index (test->log, index);
3457 g_assert_cmpint (le->type, ==, GROUPS_REMOVED);
3458 g_assert (le->groups_removed != NULL);
3459 g_assert_cmpstr (le->groups_removed[0], ==, group);
3460 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
3461}
3462
3463static void
3464test_assert_one_contact_blocked (Test *test,
3465 guint index,
3466 TpHandle handle,
3467 const gchar *id)
3468{
3469 LogEntry *le;
3470
3471 le = g_ptr_array_index (test->log, index);
3472 g_assert_cmpint (le->type, ==, BLOCKED_CONTACTS_CHANGED);
3473
3474 g_assert (le->blocked_contacts != NULL);
3475 g_assert_cmpuint (g_hash_table_size (le->blocked_contacts), ==, 1);
3476 g_assert_cmpstr (g_hash_table_lookup (le->blocked_contacts, GUINT_TO_POINTER (handle)),
3477 ==, id);
3478
3479 g_assert (le->unblocked_contacts != NULL);
3480 g_assert_cmpuint (g_hash_table_size (le->unblocked_contacts), ==, 0);
3481}
3482
3483static void
3484test_assert_one_contact_unblocked (Test *test,
3485 guint index,
3486 TpHandle handle,
3487 const gchar *id)
3488{
3489 LogEntry *le;
3490
3491 le = g_ptr_array_index (test->log, index);
3492 g_assert_cmpint (le->type, ==, BLOCKED_CONTACTS_CHANGED);
3493
3494 g_assert (le->blocked_contacts != NULL);
3495 g_assert_cmpuint (g_hash_table_size (le->blocked_contacts), ==, 0);
3496
3497 g_assert (le->unblocked_contacts != NULL);
3498 g_assert_cmpuint (g_hash_table_size (le->unblocked_contacts), ==, 1);
3499 g_assert_cmpstr (g_hash_table_lookup (le->unblocked_contacts, GUINT_TO_POINTER (handle)),
3500 ==, id);
3501}
3502
3503static void
3504test_nothing (Test *test,
3505 gconstpointer nil G_GNUC_UNUSED)
3506{
3507 /* this is actually a valuable test - it ensures that shutting down the
3508 * CM before the contact list has been retrieved works! */
3509}
3510
3511static void
3512test_initial_channels (Test *test,
3513 gconstpointer nil G_GNUC_UNUSED)
3514{
3515 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3516 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST,
3517 "subscribe");
3518 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
3519 test->deny = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "deny");
3520
3521 g_assert_cmpuint (
3522 tp_intset_size (tp_channel_group_get_members (test->publish)), ==, 4);
3523 g_assert_cmpuint (
3524 tp_intset_size (tp_channel_group_get_local_pending (test->publish)),
3525 ==, 2);
3526 g_assert_cmpuint (
3527 tp_intset_size (tp_channel_group_get_remote_pending (test->publish)),
3528 ==, 0);
3529 g_assert (tp_intset_is_member (tp_channel_group_get_members (test->publish),
3530 test->sjoerd));
3531 g_assert (tp_intset_is_member (
3532 tp_channel_group_get_local_pending (test->publish),
3533 test->wim));
3534
3535 g_assert_cmpuint (
3536 tp_intset_size (tp_channel_group_get_members (test->subscribe)), ==, 4);
3537 g_assert_cmpuint (
3538 tp_intset_size (tp_channel_group_get_local_pending (test->subscribe)),
3539 ==, 0);
3540 g_assert_cmpuint (
3541 tp_intset_size (tp_channel_group_get_remote_pending (test->subscribe)),
3542 ==, 2);
3543 g_assert (tp_intset_is_member (
3544 tp_channel_group_get_members (test->subscribe),
3545 test->sjoerd));
3546 g_assert (tp_intset_is_member (
3547 tp_channel_group_get_remote_pending (test->subscribe),
3548 test->helen));
3549
3550 g_assert_cmpuint (
3551 tp_intset_size (tp_channel_group_get_members (test->stored)), ==, 8);
3552 g_assert_cmpuint (
3553 tp_intset_size (tp_channel_group_get_local_pending (test->stored)),
3554 ==, 0);
3555 g_assert_cmpuint (
3556 tp_intset_size (tp_channel_group_get_remote_pending (test->stored)),
3557 ==, 0);
3558 g_assert (tp_intset_is_member (tp_channel_group_get_members (test->stored),
3559 test->sjoerd));
3560
3561 g_assert (!tp_intset_is_member (tp_channel_group_get_members (test->publish),
3562 test->ninja));
3563 g_assert (!tp_intset_is_member (tp_channel_group_get_members (
3564 test->subscribe),
3565 test->ninja));
3566 g_assert (!tp_intset_is_member (tp_channel_group_get_members (test->stored),
3567 test->ninja));
3568
3569 g_assert_cmpuint (
3570 tp_intset_size (tp_channel_group_get_members (test->deny)), ==, 2);
3571 g_assert_cmpuint (
3572 tp_intset_size (tp_channel_group_get_local_pending (test->deny)),
3573 ==, 0);
3574 g_assert_cmpuint (
3575 tp_intset_size (tp_channel_group_get_remote_pending (test->deny)),
3576 ==, 0);
3577 g_assert (tp_intset_is_member (tp_channel_group_get_members (test->deny),
3578 test->bill));
3579}
3580
3581static void
3582test_properties (Test *test,
3583 gconstpointer nil G_GNUC_UNUSED)
3584{
3585 GHashTable *asv;
3586 GError *error = NULL;
3587 guint32 blocking_caps;
3588 gboolean valid;
3589
3590 tp_cli_dbus_properties_run_get_all (test->conn, -1,
3591 TP_IFACE_CONNECTION_INTERFACE_CONTACT_LIST, &asv, &error, NULL);
3592 g_assert_no_error (error);
3593 g_assert_cmpuint (g_hash_table_size (asv), >=, 3);
3594 g_assert (tp_asv_get_boolean (asv, "ContactListPersists", NULL));
3595 g_assert (tp_asv_get_boolean (asv, "CanChangeContactList", NULL));
3596 g_assert (tp_asv_get_boolean (asv, "RequestUsesMessage", NULL));
3597 g_hash_table_unref (asv);
3598
3599 tp_cli_dbus_properties_run_get_all (test->conn, -1,
3600 TP_IFACE_CONNECTION_INTERFACE_CONTACT_GROUPS, &asv, &error, NULL);
3601 g_assert_no_error (error);
3602 g_assert_cmpuint (g_hash_table_size (asv), >=, 3);
3603 g_assert (G_VALUE_HOLDS_BOOLEAN (tp_asv_lookup (asv, "DisjointGroups")));
3604 g_assert (!tp_asv_get_boolean (asv, "DisjointGroups", NULL));
3605 g_assert (G_VALUE_HOLDS_UINT (tp_asv_lookup (asv, "GroupStorage")));
3606 g_assert_cmpuint (tp_asv_get_uint32 (asv, "GroupStorage", NULL), ==,
3607 TP_CONTACT_METADATA_STORAGE_TYPE_ANYONE);
3608 /* Don't assert about the contents yet - we might not have received the
3609 * contact list yet */
3610 g_assert (G_VALUE_HOLDS (tp_asv_lookup (asv, "Groups"), G_TYPE_STRV));
3611 g_hash_table_unref (asv);
3612
3613 /* this has the side-effect of waiting for the contact list to be received */
3614 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3615
3616 tp_cli_dbus_properties_run_get_all (test->conn, -1,
3617 TP_IFACE_CONNECTION_INTERFACE_CONTACT_LIST, &asv, &error, NULL);
3618 g_assert_no_error (error);
3619 g_assert_cmpuint (g_hash_table_size (asv), >=, 3);
3620 g_assert (tp_asv_get_boolean (asv, "ContactListPersists", NULL));
3621 g_assert (tp_asv_get_boolean (asv, "CanChangeContactList", NULL));
3622 g_assert (tp_asv_get_boolean (asv, "RequestUsesMessage", NULL));
3623 g_hash_table_unref (asv);
3624
3625 tp_cli_dbus_properties_run_get_all (test->conn, -1,
3626 TP_IFACE_CONNECTION_INTERFACE_CONTACT_GROUPS, &asv, &error, NULL);
3627 g_assert_no_error (error);
3628 g_assert_cmpuint (g_hash_table_size (asv), >=, 3);
3629 g_assert (G_VALUE_HOLDS_BOOLEAN (tp_asv_lookup (asv, "DisjointGroups")));
3630 g_assert (G_VALUE_HOLDS_UINT (tp_asv_lookup (asv, "GroupStorage")));
3631 g_assert (tp_asv_get_strv (asv, "Groups") != NULL);
3632 g_assert (tp_strv_contains (tp_asv_get_strv (asv, "Groups"), "Cambridge"));
3633 g_assert (tp_strv_contains (tp_asv_get_strv (asv, "Groups"), "Montreal"));
3634 g_assert (tp_strv_contains (tp_asv_get_strv (asv, "Groups"),
3635 "Francophones"));
3636 g_hash_table_unref (asv);
3637
3638 tp_cli_dbus_properties_run_get_all (test->conn, -1,
3639 TP_IFACE_CONNECTION_INTERFACE_CONTACT_BLOCKING, &asv, &error, NULL);
3640 g_assert_no_error (error);
3641 g_assert_cmpuint (g_hash_table_size (asv), ==, 1);
3642 blocking_caps = tp_asv_get_uint32 (asv, "ContactBlockingCapabilities",
3643 &valid);
3644 g_assert (valid);
3645 g_assert_cmpuint (blocking_caps, ==, 0);
3646 g_hash_table_unref (asv);
3647
3648 g_assert_cmpuint (test->log->len, ==, 0);
3649}
3650
3651static void
3652contact_attrs_cb (TpConnection *conn G_GNUC_UNUSED,
3653 GHashTable *attributes,
3654 const GError *error,
3655 gpointer user_data,
3656 GObject *object G_GNUC_UNUSED)
3657{
3658 Test *test = user_data;
3659
3660 g_assert_no_error ((GError *) error);
3661 tp_clear_pointer (&test->contact_attributes, g_hash_table_unref);
3662 test->contact_attributes = g_boxed_copy (TP_HASH_TYPE_CONTACT_ATTRIBUTES_MAP,
3663 attributes);
3664}
3665
3666static void
3667test_assert_contact_list_attrs (Test *test,
3668 TpHandle handle,
3669 TpSubscriptionState expected_sub_state,
3670 TpSubscriptionState expected_pub_state,
3671 const gchar *expected_pub_request)
3672{
3673 GHashTable *asv;
3674 gboolean valid;
3675
3676 g_assert_cmpuint (g_hash_table_size (test->contact_attributes), >=, 1);
3677 asv = g_hash_table_lookup (test->contact_attributes,
3678 GUINT_TO_POINTER (handle));
3679 g_assert (asv != NULL);
3680 g_assert_cmpuint (tp_asv_get_uint32 (asv,
3681 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_LIST_SUBSCRIBE, &valid), ==,
3682 expected_sub_state);
3683 g_assert (valid);
3684 g_assert_cmpuint (tp_asv_get_uint32 (asv,
3685 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_LIST_PUBLISH, &valid), ==,
3686 expected_pub_state);
3687 g_assert (valid);
3688 g_assert_cmpstr (tp_asv_get_string (asv,
3689 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_LIST_PUBLISH_REQUEST), ==,
3690 expected_pub_request);
3691 g_assert (valid);
3692}
3693
3694/* We simplify here by assuming that contacts are in at most one group,
3695 * which happens to be true for all of these tests. */
3696static void
3697test_assert_contact_groups_attr (Test *test,
3698 TpHandle handle,
3699 const gchar *group)
3700{
3701 GHashTable *asv;
3702 const gchar * const *strv;
3703
3704 g_assert_cmpuint (g_hash_table_size (test->contact_attributes), >=, 1);
3705 asv = g_hash_table_lookup (test->contact_attributes,
3706 GUINT_TO_POINTER (handle));
3707 g_assert (asv != NULL);
3708 tp_asv_dump (asv);
3709 g_assert (tp_asv_lookup (asv,
3710 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_GROUPS_GROUPS) != NULL);
3711 g_assert (G_VALUE_HOLDS (tp_asv_lookup (asv,
3712 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_GROUPS_GROUPS), G_TYPE_STRV));
3713 strv = tp_asv_get_strv (asv,
3714 TP_TOKEN_CONNECTION_INTERFACE_CONTACT_GROUPS_GROUPS);
3715
3716 if (group == NULL)
3717 {
3718 if (strv != NULL)
3719 g_assert_cmpstr (strv[0], ==, NULL);
3720 }
3721 else
3722 {
3723 g_assert (strv != NULL);
3724 g_assert_cmpstr (strv[0], ==, group);
3725 g_assert_cmpstr (strv[1], ==, NULL);
3726 }
3727}
3728
3729static void
3730test_assert_contact_state (Test *test,
3731 TpHandle handle,
3732 TpSubscriptionState expected_sub_state,
3733 TpSubscriptionState expected_pub_state,
3734 const gchar *expected_pub_request,
3735 const gchar *expected_group)
3736{
3737 const gchar * const interfaces[] = {
3738 TP_IFACE_CONNECTION_INTERFACE_CONTACT_LIST,
3739 TP_IFACE_CONNECTION_INTERFACE_CONTACT_GROUPS,
3740 NULL };
3741
3742 tp_connection_get_contact_attributes (test->conn, -1,
3743 1, &handle, interfaces, FALSE, contact_attrs_cb,
3744 test, test_quit_loop, NULL);
3745 g_main_loop_run (test->main_loop);
3746
3747 g_assert_cmpuint (g_hash_table_size (test->contact_attributes), ==, 1);
3748 test_assert_contact_list_attrs (test, handle, expected_sub_state,
3749 expected_pub_state, expected_pub_request);
3750 test_assert_contact_groups_attr (test, handle, expected_group);
3751}
3752
3753static void
3754test_contacts (Test *test,
3755 gconstpointer nil G_GNUC_UNUSED)
3756{
3757 /* ensure the contact list has been received */
3758 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3759
3760 test_assert_contact_state (test, test->sjoerd,
3761 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, "Cambridge");
3762 test_assert_contact_state (test, test->wim,
3763 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_ASK,
3764 "I'm more metal than you!", NULL);
3765 test_assert_contact_state (test, test->helen,
3766 TP_SUBSCRIPTION_STATE_ASK, TP_SUBSCRIPTION_STATE_NO, NULL, "Cambridge");
3767 test_assert_contact_state (test, test->ninja,
3768 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
3769 test_assert_contact_state (test, test->bill,
3770 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
3771}
3772
3773static void
3774test_contact_list_attrs (Test *test,
3775 gconstpointer nil G_GNUC_UNUSED)
3776{
3777 const gchar * const interfaces[] = {
3778 TP_IFACE_CONNECTION_INTERFACE_CONTACT_GROUPS,
3779 NULL };
3780
3781 tp_connection_get_contact_list_attributes (test->conn, -1,
3782 interfaces, FALSE, contact_attrs_cb, test, test_quit_loop, NULL);
3783 g_main_loop_run (test->main_loop);
3784
3785 test_assert_contact_list_attrs (test, test->sjoerd,
3786 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL);
3787 test_assert_contact_list_attrs (test, test->wim,
3788 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_ASK,
3789 "I'm more metal than you!");
3790 test_assert_contact_list_attrs (test, test->helen,
3791 TP_SUBSCRIPTION_STATE_ASK, TP_SUBSCRIPTION_STATE_NO, NULL);
3792
3793 test_assert_contact_groups_attr (test, test->sjoerd, "Cambridge");
3794 test_assert_contact_groups_attr (test, test->wim, NULL);
3795 test_assert_contact_groups_attr (test, test->helen, "Cambridge");
3796
3797 /* bill is blocked, but is not on the contact list as such; the ninja isn't
3798 * in the initial state at all */
3799 g_assert (g_hash_table_lookup (test->contact_attributes,
3800 GUINT_TO_POINTER (test->bill)) == NULL);
3801 g_assert (g_hash_table_lookup (test->contact_attributes,
3802 GUINT_TO_POINTER (test->ninja)) == NULL);
3803}
3804
3805static void
3806test_accept_publish_request (Test *test,
3807 gconstpointer mode)
3808{
3809 GError *error = NULL;
3810
3811 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3812
3813 g_assert_cmpuint (
3814 tp_intset_size (tp_channel_group_get_local_pending (test->publish)),
3815 ==, 2);
3816 g_assert (tp_intset_is_member (
3817 tp_channel_group_get_local_pending (test->publish),
3818 test->wim));
3819
3820 g_array_append_val (test->arr, test->wim);
3821
3822 if (!tp_strdiff (mode, "old"))
3823 tp_cli_channel_interface_group_run_add_members (test->publish,
3824 -1, test->arr, "", &error, NULL);
3825 else
3826 tp_cli_connection_interface_contact_list_run_authorize_publication (
3827 test->conn, -1, test->arr, &error, NULL);
3828
3829 g_assert_no_error (error);
3830
3831 /* by the time the method returns, we should have had the
3832 * change-notification, too */
3833 g_assert_cmpuint (
3834 tp_intset_size (tp_channel_group_get_local_pending (test->publish)),
3835 ==, 1);
3836 g_assert (tp_intset_is_member (
3837 tp_channel_group_get_members (test->publish),
3838 test->wim));
3839 g_assert (!tp_intset_is_member (
3840 tp_channel_group_get_local_pending (test->publish),
3841 test->wim));
3842
3843 g_assert_cmpuint (test->log->len, ==, 1);
3844 test_assert_one_contact_changed (test, 0, test->wim, TP_SUBSCRIPTION_STATE_NO,
3845 TP_SUBSCRIPTION_STATE_YES, "");
3846 test_assert_contact_state (test, test->wim,
3847 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_YES, NULL, NULL);
3848}
3849
3850static void
3851test_reject_publish_request (Test *test,
3852 gconstpointer mode)
3853{
3854 GError *error = NULL;
3855
3856 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3857
3858 g_assert (tp_intset_is_member (
3859 tp_channel_group_get_local_pending (test->publish),
3860 test->wim));
3861 g_assert (!tp_intset_is_member (
3862 tp_channel_group_get_members (test->publish),
3863 test->wim));
3864
3865 g_array_append_val (test->arr, test->wim);
3866
3867 if (!tp_strdiff (mode, "old"))
3868 {
3869 tp_cli_channel_interface_group_run_remove_members (test->publish,
3870 -1, test->arr, "", &error, NULL);
3871 }
3872 else if (!tp_strdiff (mode, "unpublish"))
3873 {
3874 /* directly equivalent, but in practice people won't do this */
3875 tp_cli_connection_interface_contact_list_run_unpublish (
3876 test->conn, -1, test->arr, &error, NULL);
3877 }
3878 else
3879 {
3880 /* this isn't directly equivalent, but in practice it's what people
3881 * will do */
3882 tp_cli_connection_interface_contact_list_run_remove_contacts (
3883 test->conn, -1, test->arr, &error, NULL);
3884 }
3885
3886 g_assert_no_error (error);
3887
3888 /* by the time the method returns, we should have had the
3889 * removal-notification, too */
3890 g_assert_cmpuint (
3891 tp_intset_size (tp_channel_group_get_local_pending (test->publish)),
3892 ==, 1);
3893 g_assert (!tp_intset_is_member (
3894 tp_channel_group_get_members (test->publish),
3895 test->wim));
3896 g_assert (!tp_intset_is_member (
3897 tp_channel_group_get_local_pending (test->publish),
3898 test->wim));
3899
3900 g_assert_cmpuint (test->log->len, ==, 1);
3901
3902 /* because Wim wasn't really on our contact list, he's removed as a
3903 * side-effect, even if we only unpublished */
3904 test_assert_one_contact_removed (test, 0, test->wim);
3905
3906 test_assert_contact_state (test, test->wim,
3907 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
3908}
3909
3910static void
3911test_add_to_publish_pre_approve (Test *test,
3912 gconstpointer mode)
3913{
3914 GError *error = NULL;
3915
3916 /* Unilaterally adding a member to the publish channel doesn't work, but
3917 * in the new contact list manager the method "succeeds" anyway, and
3918 * any subsequent subscription request succeeds instantly. */
3919
3920 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
3921 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
3922 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
3923
3924 g_array_append_val (test->arr, test->ninja);
3925
3926 g_assert (!tp_intset_is_member (
3927 tp_channel_group_get_local_pending (test->publish),
3928 test->ninja));
3929
3930 if (!tp_strdiff (mode, "old"))
3931 tp_cli_channel_interface_group_run_add_members (test->publish,
3932 -1, test->arr, "", &error, NULL);
3933 else
3934 tp_cli_connection_interface_contact_list_run_authorize_publication (
3935 test->conn, -1, test->arr, &error, NULL);
3936
3937 g_assert_no_error (error);
3938
3939 g_assert (!tp_intset_is_member (
3940 tp_channel_group_get_local_pending (test->publish),
3941 test->ninja));
3942
3943 /* the example CM's fake contacts accept requests that contain "please" */
3944 if (!tp_strdiff (mode, "old"))
3945 tp_cli_channel_interface_group_run_add_members (test->subscribe,
3946 -1, test->arr, "Please may I see your presence?", &error, NULL);
3947 else
3948 tp_cli_connection_interface_contact_list_run_request_subscription (
3949 test->conn, -1, test->arr, "Please may I see your presence?", &error,
3950 NULL);
3951
3952 g_assert_no_error (error);
3953
3954 /* by the time the method returns, we should have had the
3955 * change-notification, too */
3956 g_assert (tp_intset_is_member (
3957 tp_channel_group_get_remote_pending (test->subscribe),
3958 test->ninja));
3959 g_assert (tp_intset_is_member (
3960 tp_channel_group_get_members (test->stored),
3961 test->ninja));
3962 g_assert (!tp_intset_is_member (
3963 tp_channel_group_get_remote_pending (test->stored),
3964 test->ninja));
3965
3966 /* after a short delay, the contact accepts our request */
3967 while (tp_intset_is_member (
3968 tp_channel_group_get_remote_pending (test->subscribe),
3969 test->ninja))
3970 g_main_context_iteration (NULL, TRUE);
3971
3972 g_assert (tp_intset_is_member (
3973 tp_channel_group_get_members (test->subscribe),
3974 test->ninja));
3975 g_assert (!tp_intset_is_member (
3976 tp_channel_group_get_remote_pending (test->subscribe),
3977 test->ninja));
3978
3979 /* the contact also requests our presence after a short delay - we
3980 * pre-approved, so they go straight to full membership */
3981 while (!tp_intset_is_member (
3982 tp_channel_group_get_members (test->publish),
3983 test->ninja) || test->log->len < 3)
3984 g_main_context_iteration (NULL, TRUE);
3985
3986 g_assert (tp_intset_is_member (
3987 tp_channel_group_get_members (test->publish),
3988 test->ninja));
3989 g_assert (!tp_intset_is_member (
3990 tp_channel_group_get_local_pending (test->publish),
3991 test->ninja));
3992
3993 g_assert_cmpuint (test->log->len, ==, 3);
3994 test_assert_one_contact_changed (test, 0, test->ninja, TP_SUBSCRIPTION_STATE_ASK,
3995 TP_SUBSCRIPTION_STATE_NO, "");
3996 test_assert_one_contact_changed (test, 1, test->ninja, TP_SUBSCRIPTION_STATE_YES,
3997 TP_SUBSCRIPTION_STATE_NO, "");
3998 test_assert_one_contact_changed (test, 2, test->ninja, TP_SUBSCRIPTION_STATE_YES,
3999 TP_SUBSCRIPTION_STATE_YES, "");
4000
4001 test_assert_contact_state (test, test->ninja,
4002 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, NULL);
4003}
4004
4005static void
4006test_add_to_publish_no_op (Test *test,
4007 gconstpointer mode)
4008{
4009 GError *error = NULL;
4010
4011 /* Adding a member to the publish channel when they're already there is
4012 * valid. */
4013
4014 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4015
4016 g_assert (tp_intset_is_member (
4017 tp_channel_group_get_members (test->publish),
4018 test->sjoerd));
4019
4020 g_array_append_val (test->arr, test->sjoerd);
4021
4022 if (!tp_strdiff (mode, "old"))
4023 tp_cli_channel_interface_group_run_add_members (test->publish,
4024 -1, test->arr, "", &error, NULL);
4025 else
4026 tp_cli_connection_interface_contact_list_run_authorize_publication (
4027 test->conn, -1, test->arr, &error, NULL);
4028
4029 g_assert_no_error (error);
4030
4031 g_assert (tp_intset_is_member (
4032 tp_channel_group_get_members (test->publish),
4033 test->sjoerd));
4034
4035 g_assert_cmpuint (test->log->len, ==, 0);
4036 test_assert_contact_state (test, test->sjoerd,
4037 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, "Cambridge");
4038}
4039
4040static void
4041test_remove_from_publish (Test *test,
4042 gconstpointer mode)
4043{
4044 GError *error = NULL;
4045
4046 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4047
4048 g_assert_cmpuint (
4049 tp_intset_size (tp_channel_group_get_members (test->publish)),
4050 ==, 4);
4051 g_assert (tp_intset_is_member (
4052 tp_channel_group_get_members (test->publish),
4053 test->sjoerd));
4054
4055 g_array_append_val (test->arr, test->sjoerd);
4056
4057 if (!tp_strdiff (mode, "old"))
4058 tp_cli_channel_interface_group_run_remove_members (test->publish,
4059 -1, test->arr, "", &error, NULL);
4060 else
4061 tp_cli_connection_interface_contact_list_run_unpublish (
4062 test->conn, -1, test->arr, &error, NULL);
4063
4064 g_assert_no_error (error);
4065
4066 /* by the time the method returns, we should have had the
4067 * removal-notification, too */
4068 g_assert (!tp_intset_is_member (
4069 tp_channel_group_get_members (test->publish),
4070 test->sjoerd));
4071
4072 /* the contact re-requests our presence after a short delay */
4073 while (!tp_intset_is_member (
4074 tp_channel_group_get_local_pending (test->publish),
4075 test->sjoerd) ||
4076 test->log->len < 2)
4077 g_main_context_iteration (NULL, TRUE);
4078
4079 g_assert (!tp_intset_is_member (
4080 tp_channel_group_get_members (test->publish),
4081 test->sjoerd));
4082 g_assert (tp_intset_is_member (
4083 tp_channel_group_get_local_pending (test->publish),
4084 test->sjoerd));
4085
4086 g_assert_cmpuint (test->log->len, ==, 2);
4087 test_assert_one_contact_changed (test, 0, test->sjoerd,
4088 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_NO, "");
4089 test_assert_one_contact_changed (test, 1, test->sjoerd,
4090 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_ASK,
4091 "May I see your presence, please?");
4092 test_assert_contact_state (test, test->sjoerd,
4093 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_ASK,
4094 "May I see your presence, please?", "Cambridge");
4095}
4096
4097static void
4098test_remove_from_publish_no_op (Test *test,
4099 gconstpointer mode)
4100{
4101 GError *error = NULL;
4102
4103 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4104
4105 g_assert_cmpuint (
4106 tp_intset_size (tp_channel_group_get_members (test->publish)),
4107 ==, 4);
4108 g_assert (!tp_intset_is_member (
4109 tp_channel_group_get_members (test->publish),
4110 test->ninja));
4111
4112 g_array_append_val (test->arr, test->ninja);
4113
4114 if (!tp_strdiff (mode, "old"))
4115 tp_cli_channel_interface_group_run_remove_members (test->publish,
4116 -1, test->arr, "", &error, NULL);
4117 else
4118 tp_cli_connection_interface_contact_list_run_unpublish (
4119 test->conn, -1, test->arr, &error, NULL);
4120
4121 g_assert_no_error (error);
4122
4123 g_assert_cmpuint (test->log->len, ==, 0);
4124 test_assert_contact_state (test, test->ninja,
4125 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4126}
4127
4128static void
4129test_cancelled_publish_request (Test *test,
4130 gconstpointer mode)
4131{
4132 GError *error = NULL;
4133
4134 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4135 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4136 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4137
4138 g_assert_cmpuint (
4139 tp_intset_size (tp_channel_group_get_members (test->subscribe)),
4140 ==, 4);
4141 g_assert (!tp_intset_is_member (
4142 tp_channel_group_get_members (test->subscribe),
4143 test->canceller));
4144 g_assert (!tp_intset_is_member (
4145 tp_channel_group_get_remote_pending (test->subscribe),
4146 test->canceller));
4147
4148 /* the example CM's fake contacts accept requests that contain "please" */
4149 g_array_append_val (test->arr, test->canceller);
4150
4151 tp_cli_connection_interface_contact_list_run_request_subscription (
4152 test->conn, -1, test->arr, "Please may I see your presence?",
4153 &error, NULL);
4154
4155 /* It starts off the same as test_accept_subscribe_request, but because
4156 * we're using an identifier with special significance, the contact cancels
4157 * the request immediately after */
4158 while (tp_intset_is_member (
4159 tp_channel_group_get_local_pending (test->publish),
4160 test->canceller) ||
4161 test->log->len < 4)
4162 g_main_context_iteration (NULL, TRUE);
4163
4164 g_assert (!tp_intset_is_member (
4165 tp_channel_group_get_members (test->publish),
4166 test->canceller));
4167 g_assert (!tp_intset_is_member (
4168 tp_channel_group_get_local_pending (test->publish),
4169 test->canceller));
4170
4171 g_assert_cmpuint (test->log->len, ==, 4);
4172 test_assert_one_contact_changed (test, 0, test->canceller,
4173 TP_SUBSCRIPTION_STATE_ASK, TP_SUBSCRIPTION_STATE_NO, "");
4174 test_assert_one_contact_changed (test, 1, test->canceller,
4175 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_NO, "");
4176 test_assert_one_contact_changed (test, 2, test->canceller,
4177 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_ASK,
4178 "May I see your presence, please?");
4179 test_assert_one_contact_changed (test, 3, test->canceller,
4180 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_REMOVED_REMOTELY, "");
4181 test_assert_contact_state (test, test->canceller,
4182 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_REMOVED_REMOTELY,
4183 NULL, NULL);
4184
4185 test_clear_log (test);
4186
4187 /* We can acknowledge the cancellation with Unpublish() or
4188 * RemoveContacts(). We can't use the old API here, because in the old API,
4189 * the contact has already vanished from the Group */
4190 if (!tp_strdiff (mode, "remove-after"))
4191 tp_cli_connection_interface_contact_list_run_remove_contacts (test->conn,
4192 -1, test->arr, &error, NULL);
4193 else
4194 tp_cli_connection_interface_contact_list_run_unpublish (
4195 test->conn, -1, test->arr, &error, NULL);
4196
4197 while (test->log->len < 1)
4198 g_main_context_iteration (NULL, TRUE);
4199
4200 g_assert_cmpuint (test->log->len, ==, 1);
4201
4202 if (!tp_strdiff (mode, "remove-after"))
4203 test_assert_one_contact_removed (test, 0, test->canceller);
4204 else
4205 test_assert_one_contact_changed (test, 0, test->canceller,
4206 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_NO, "");
4207}
4208
4209static void
4210test_add_to_stored (Test *test,
4211 gconstpointer mode)
4212{
4213 GError *error = NULL;
4214
4215 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4216 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4217 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST,
4218 "subscribe");
4219
4220 g_assert_cmpuint (
4221 tp_intset_size (tp_channel_group_get_members (test->stored)),
4222 ==, 8);
4223 g_assert (!tp_intset_is_member (
4224 tp_channel_group_get_members (test->stored),
4225 test->ninja));
4226
4227 g_array_append_val (test->arr, test->ninja);
4228
4229 if (!tp_strdiff (mode, "old"))
4230 {
4231 tp_cli_channel_interface_group_run_add_members (test->stored,
4232 -1, test->arr, "", &error, NULL);
4233 }
4234 else
4235 {
4236 /* there's no specific API for adding contacts to stored (it's not a
4237 * very useful action in general), but setting an alias has it as a
4238 * side-effect */
4239 GHashTable *table = g_hash_table_new (NULL, NULL);
4240
4241 g_hash_table_insert (table, GUINT_TO_POINTER (test->ninja),
4242 "The Wee Ninja");
4243 tp_cli_connection_interface_aliasing_run_set_aliases (test->conn,
4244 -1, table, &error, NULL);
4245 g_hash_table_unref (table);
4246 }
4247
4248 g_assert_no_error (error);
4249
4250 /* by the time the method returns, we should have had the
4251 * change-notification, too */
4252 g_assert_cmpuint (
4253 tp_intset_size (tp_channel_group_get_members (test->stored)),
4254 ==, 9);
4255 g_assert (tp_intset_is_member (
4256 tp_channel_group_get_members (test->stored),
4257 test->ninja));
4258
4259 g_assert (!tp_intset_is_member (
4260 tp_channel_group_get_members (test->subscribe),
4261 test->ninja));
4262 g_assert (!tp_intset_is_member (
4263 tp_channel_group_get_members (test->publish),
4264 test->ninja));
4265
4266 g_assert_cmpuint (test->log->len, ==, 1);
4267 test_assert_one_contact_changed (test, 0, test->ninja,
4268 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, "");
4269 test_assert_contact_state (test, test->ninja,
4270 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4271}
4272
4273static void
4274test_add_to_stored_no_op (Test *test,
4275 gconstpointer mode)
4276{
4277 GError *error = NULL;
4278
4279 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4280
4281 g_assert_cmpuint (
4282 tp_intset_size (tp_channel_group_get_members (test->stored)),
4283 ==, 8);
4284 g_assert (tp_intset_is_member (
4285 tp_channel_group_get_members (test->stored),
4286 test->sjoerd));
4287
4288 g_array_append_val (test->arr, test->sjoerd);
4289
4290 if (!tp_strdiff (mode, "old"))
4291 {
4292 tp_cli_channel_interface_group_run_add_members (test->stored,
4293 -1, test->arr, "", &error, NULL);
4294 }
4295 else
4296 {
4297 /* there's no specific API for adding contacts to stored (it's not a
4298 * very useful action in general), but setting an alias has it as a
4299 * side-effect */
4300 GHashTable *table = g_hash_table_new (NULL, NULL);
4301
4302 g_hash_table_insert (table, GUINT_TO_POINTER (test->sjoerd),
4303 "Sjoerd");
4304 tp_cli_connection_interface_aliasing_run_set_aliases (test->conn,
4305 -1, table, &error, NULL);
4306 g_hash_table_unref (table);
4307 }
4308
4309 g_assert_no_error (error);
4310
4311 g_assert_cmpuint (test->log->len, ==, 0);
4312 test_assert_contact_state (test, test->sjoerd,
4313 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, "Cambridge");
4314}
4315
4316static void
4317test_remove_from_stored (Test *test,
4318 gconstpointer mode)
4319{
4320 GError *error = NULL;
4321
4322 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4323 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4324 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST,
4325 "subscribe");
4326
4327 g_assert (tp_intset_is_member (
4328 tp_channel_group_get_members (test->stored),
4329 test->sjoerd));
4330
4331 g_array_append_val (test->arr, test->sjoerd);
4332
4333 if (!tp_strdiff (mode, "old"))
4334 tp_cli_channel_interface_group_run_remove_members (test->stored,
4335 -1, test->arr, "", &error, NULL);
4336 else
4337 tp_cli_connection_interface_contact_list_run_remove_contacts (test->conn,
4338 -1, test->arr, &error, NULL);
4339
4340 g_assert_no_error (error);
4341
4342 /* by the time the method returns, we should have had the
4343 * removal-notification, too */
4344 g_assert (!tp_intset_is_member (
4345 tp_channel_group_get_members (test->stored),
4346 test->sjoerd));
4347 g_assert (!tp_intset_is_member (
4348 tp_channel_group_get_members (test->subscribe),
4349 test->sjoerd));
4350 g_assert (!tp_intset_is_member (
4351 tp_channel_group_get_members (test->publish),
4352 test->sjoerd));
4353
4354 g_assert_cmpuint (test->log->len, ==, 1);
4355 test_assert_one_contact_removed (test, 0, test->sjoerd);
4356 test_assert_contact_state (test, test->sjoerd,
4357 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4358}
4359
4360static void
4361test_remove_from_stored_no_op (Test *test,
4362 gconstpointer mode)
4363{
4364 GError *error = NULL;
4365
4366 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4367
4368 g_assert_cmpuint (
4369 tp_intset_size (tp_channel_group_get_members (test->stored)),
4370 ==, 8);
4371 g_assert (!tp_intset_is_member (
4372 tp_channel_group_get_members (test->stored),
4373 test->ninja));
4374
4375 g_array_append_val (test->arr, test->ninja);
4376
4377 if (!tp_strdiff (mode, "old"))
4378 tp_cli_channel_interface_group_run_remove_members (test->stored,
4379 -1, test->arr, "", &error, NULL);
4380 else
4381 tp_cli_connection_interface_contact_list_run_remove_contacts (test->conn,
4382 -1, test->arr, &error, NULL);
4383
4384 g_assert_no_error (error);
4385
4386 g_assert_cmpuint (test->log->len, ==, 0);
4387 test_assert_contact_state (test, test->ninja,
4388 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4389}
4390
4391static void
4392test_accept_subscribe_request (Test *test,
4393 gconstpointer mode)
4394{
4395 GError *error = NULL;
4396
4397 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4398 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4399 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4400
4401 g_assert_cmpuint (
4402 tp_intset_size (tp_channel_group_get_members (test->subscribe)),
4403 ==, 4);
4404 g_assert (!tp_intset_is_member (
4405 tp_channel_group_get_members (test->subscribe),
4406 test->ninja));
4407 g_assert (!tp_intset_is_member (
4408 tp_channel_group_get_remote_pending (test->subscribe),
4409 test->ninja));
4410
4411 /* the example CM's fake contacts accept requests that contain "please" */
4412 g_array_append_val (test->arr, test->ninja);
4413
4414 if (!tp_strdiff (mode, "old"))
4415 tp_cli_channel_interface_group_run_add_members (test->subscribe,
4416 -1, test->arr, "Please may I see your presence?", &error, NULL);
4417 else
4418 tp_cli_connection_interface_contact_list_run_request_subscription (
4419 test->conn, -1, test->arr, "Please may I see your presence?",
4420 &error, NULL);
4421
4422 g_assert_no_error (error);
4423
4424 /* by the time the method returns, we should have had the
4425 * change-notification, too */
4426 g_assert (tp_intset_is_member (
4427 tp_channel_group_get_remote_pending (test->subscribe),
4428 test->ninja));
4429 g_assert (tp_intset_is_member (
4430 tp_channel_group_get_members (test->stored),
4431 test->ninja));
4432 g_assert (!tp_intset_is_member (
4433 tp_channel_group_get_remote_pending (test->stored),
4434 test->ninja));
4435
4436 /* after a short delay, the contact accepts our request */
4437 while (tp_intset_is_member (
4438 tp_channel_group_get_remote_pending (test->subscribe),
4439 test->ninja))
4440 g_main_context_iteration (NULL, TRUE);
4441
4442 g_assert (tp_intset_is_member (
4443 tp_channel_group_get_members (test->subscribe),
4444 test->ninja));
4445 g_assert (!tp_intset_is_member (
4446 tp_channel_group_get_remote_pending (test->subscribe),
4447 test->ninja));
4448
4449 /* the contact also requests our presence after a short delay */
4450 while (!tp_intset_is_member (
4451 tp_channel_group_get_local_pending (test->publish),
4452 test->ninja) ||
4453 test->log->len < 3)
4454 g_main_context_iteration (NULL, TRUE);
4455
4456 g_assert (!tp_intset_is_member (
4457 tp_channel_group_get_members (test->publish),
4458 test->ninja));
4459 g_assert (tp_intset_is_member (
4460 tp_channel_group_get_local_pending (test->publish),
4461 test->ninja));
4462
4463 g_assert_cmpuint (test->log->len, ==, 3);
4464 test_assert_one_contact_changed (test, 0, test->ninja,
4465 TP_SUBSCRIPTION_STATE_ASK, TP_SUBSCRIPTION_STATE_NO, "");
4466 test_assert_one_contact_changed (test, 1, test->ninja,
4467 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_NO, "");
4468 test_assert_one_contact_changed (test, 2, test->ninja,
4469 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_ASK,
4470 "May I see your presence, please?");
4471 test_assert_contact_state (test, test->ninja,
4472 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_ASK,
4473 "May I see your presence, please?", NULL);
4474}
4475
4476static void
4477test_reject_subscribe_request (Test *test,
4478 gconstpointer mode)
4479{
4480 GError *error = NULL;
4481
4482 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4483 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4484
4485 g_assert_cmpuint (
4486 tp_intset_size (tp_channel_group_get_members (test->subscribe)),
4487 ==, 4);
4488 g_assert (!tp_intset_is_member (
4489 tp_channel_group_get_members (test->subscribe),
4490 test->ninja));
4491 g_assert (!tp_intset_is_member (
4492 tp_channel_group_get_remote_pending (test->subscribe),
4493 test->ninja));
4494
4495 /* the example CM's fake contacts reject requests that don't contain
4496 * "please" */
4497 g_array_append_val (test->arr, test->ninja);
4498
4499 if (!tp_strdiff (mode, "old"))
4500 tp_cli_channel_interface_group_run_add_members (test->subscribe,
4501 -1, test->arr, "I demand to see your presence?", &error, NULL);
4502 else
4503 tp_cli_connection_interface_contact_list_run_request_subscription (
4504 test->conn, -1, test->arr, "I demand to see your presence?",
4505 &error, NULL);
4506
4507 g_assert_no_error (error);
4508
4509 /* by the time the method returns, we should have had the
4510 * change-notification, too */
4511 g_assert (tp_intset_is_member (
4512 tp_channel_group_get_remote_pending (test->subscribe),
4513 test->ninja));
4514 g_assert (tp_intset_is_member (
4515 tp_channel_group_get_members (test->stored),
4516 test->ninja));
4517 g_assert (!tp_intset_is_member (
4518 tp_channel_group_get_remote_pending (test->stored),
4519 test->ninja));
4520
4521 /* after a short delay, the contact rejects our request. Say please! */
4522 while (tp_intset_is_member (
4523 tp_channel_group_get_remote_pending (test->subscribe),
4524 test->ninja) ||
4525 test->log->len < 2)
4526 g_main_context_iteration (NULL, TRUE);
4527
4528 g_assert (!tp_intset_is_member (
4529 tp_channel_group_get_members (test->subscribe),
4530 test->ninja));
4531 g_assert (!tp_intset_is_member (
4532 tp_channel_group_get_remote_pending (test->subscribe),
4533 test->ninja));
4534
4535 /* the ninja is still on the stored list */
4536 g_assert (tp_intset_is_member (
4537 tp_channel_group_get_members (test->stored),
4538 test->ninja));
4539 g_assert (!tp_intset_is_member (
4540 tp_channel_group_get_remote_pending (test->stored),
4541 test->ninja));
4542
4543 g_assert_cmpuint (test->log->len, ==, 2);
4544 test_assert_one_contact_changed (test, 0, test->ninja,
4545 TP_SUBSCRIPTION_STATE_ASK, TP_SUBSCRIPTION_STATE_NO, "");
4546 test_assert_one_contact_changed (test, 1, test->ninja,
4547 TP_SUBSCRIPTION_STATE_REMOVED_REMOTELY, TP_SUBSCRIPTION_STATE_NO, "");
4548 test_assert_contact_state (test, test->ninja,
4549 TP_SUBSCRIPTION_STATE_REMOVED_REMOTELY, TP_SUBSCRIPTION_STATE_NO, NULL,
4550 NULL);
4551
4552 test_clear_log (test);
4553
4554 /* We can acknowledge the failure to subscribe with Unsubscribe() or
4555 * RemoveContacts(). We can't use the old API here, because in the old API,
4556 * the contact has already vanished from the Group */
4557 if (!tp_strdiff (mode, "remove-after"))
4558 tp_cli_connection_interface_contact_list_run_remove_contacts (test->conn,
4559 -1, test->arr, &error, NULL);
4560 else
4561 tp_cli_connection_interface_contact_list_run_unsubscribe (
4562 test->conn, -1, test->arr, &error, NULL);
4563
4564 /* the ninja falls off our subscribe list */
4565 while (test->log->len < 1)
4566 g_main_context_iteration (NULL, TRUE);
4567
4568 g_assert_cmpuint (test->log->len, ==, 1);
4569
4570 if (!tp_strdiff (mode, "remove-after"))
4571 test_assert_one_contact_removed (test, 0, test->ninja);
4572 else
4573 test_assert_one_contact_changed (test, 0, test->ninja,
4574 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, "");
4575}
4576
4577static void
4578test_remove_from_subscribe (Test *test,
4579 gconstpointer mode)
4580{
4581 GError *error = NULL;
4582
4583 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4584 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4585
4586 g_assert_cmpuint (
4587 tp_intset_size (tp_channel_group_get_members (test->subscribe)),
4588 ==, 4);
4589 g_assert (tp_intset_is_member (
4590 tp_channel_group_get_members (test->subscribe),
4591 test->sjoerd));
4592
4593 g_array_append_val (test->arr, test->sjoerd);
4594
4595 if (!tp_strdiff (mode, "old"))
4596 tp_cli_channel_interface_group_run_remove_members (test->subscribe,
4597 -1, test->arr, "", &error, NULL);
4598 else
4599 tp_cli_connection_interface_contact_list_run_unsubscribe (
4600 test->conn, -1, test->arr, &error, NULL);
4601
4602 g_assert_no_error (error);
4603
4604 /* by the time the method returns, we should have had the
4605 * removal-notification, too */
4606 g_assert (!tp_intset_is_member (
4607 tp_channel_group_get_members (test->subscribe),
4608 test->sjoerd));
4609 g_assert (tp_intset_is_member (
4610 tp_channel_group_get_members (test->stored),
4611 test->sjoerd));
4612
4613 g_assert_cmpuint (test->log->len, ==, 1);
4614 test_assert_one_contact_changed (test, 0, test->sjoerd,
4615 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_YES, "");
4616 test_assert_contact_state (test, test->sjoerd,
4617 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_YES, NULL, "Cambridge");
4618}
4619
4620static void
4621test_remove_from_subscribe_pending (Test *test,
4622 gconstpointer mode)
4623{
4624 GError *error = NULL;
4625
4626 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4627 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4628
4629 g_assert_cmpuint (
4630 tp_intset_size (tp_channel_group_get_remote_pending (test->subscribe)),
4631 ==, 2);
4632 g_assert (tp_intset_is_member (
4633 tp_channel_group_get_remote_pending (test->subscribe),
4634 test->helen));
4635
4636 g_array_append_val (test->arr, test->helen);
4637
4638 if (!tp_strdiff (mode, "old"))
4639 tp_cli_channel_interface_group_run_remove_members (test->subscribe,
4640 -1, test->arr, "", &error, NULL);
4641 else
4642 tp_cli_connection_interface_contact_list_run_unsubscribe (
4643 test->conn, -1, test->arr, &error, NULL);
4644
4645 g_assert_no_error (error);
4646
4647 /* by the time the method returns, we should have had the
4648 * removal-notification, too */
4649 g_assert (!tp_intset_is_member (
4650 tp_channel_group_get_members (test->subscribe),
4651 test->helen));
4652 g_assert (!tp_intset_is_member (
4653 tp_channel_group_get_remote_pending (test->subscribe),
4654 test->helen));
4655 g_assert (tp_intset_is_member (
4656 tp_channel_group_get_members (test->stored),
4657 test->helen));
4658
4659 g_assert_cmpuint (test->log->len, ==, 1);
4660 test_assert_one_contact_changed (test, 0, test->helen,
4661 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, "");
4662 test_assert_contact_state (test, test->helen,
4663 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, "Cambridge");
4664}
4665
4666static void
4667test_remove_from_subscribe_no_op (Test *test,
4668 gconstpointer mode)
4669{
4670 GError *error = NULL;
4671
4672 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "subscribe");
4673
4674 g_assert_cmpuint (
4675 tp_intset_size (tp_channel_group_get_members (test->subscribe)),
4676 ==, 4);
4677 g_assert (!tp_intset_is_member (
4678 tp_channel_group_get_members (test->subscribe),
4679 test->ninja));
4680
4681 g_array_append_val (test->arr, test->ninja);
4682
4683 if (!tp_strdiff (mode, "old"))
4684 tp_cli_channel_interface_group_run_remove_members (test->subscribe,
4685 -1, test->arr, "", &error, NULL);
4686 else
4687 tp_cli_connection_interface_contact_list_run_unsubscribe (
4688 test->conn, -1, test->arr, &error, NULL);
4689
4690 g_assert_no_error (error);
4691
4692 g_assert_cmpuint (test->log->len, ==, 0);
4693 test_assert_contact_state (test, test->ninja,
4694 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4695}
4696
4697static void
4698test_add_to_group (Test *test,
4699 gconstpointer mode)
4700{
4701 GError *error = NULL;
4702 LogEntry *le;
4703 guint i;
4704
4705 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4706 "Cambridge");
4707 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
4708 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
4709 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST,
4710 "subscribe");
4711
4712 g_assert_cmpuint (
4713 tp_intset_size (tp_channel_group_get_members (test->group)),
4714 ==, 4);
4715 g_assert (!tp_intset_is_member (
4716 tp_channel_group_get_members (test->group),
4717 test->ninja));
4718
4719 g_array_append_val (test->arr, test->ninja);
4720
4721 if (!tp_strdiff (mode, "old"))
4722 tp_cli_channel_interface_group_run_add_members (test->group,
4723 -1, test->arr, "", &error, NULL);
4724 else
4725 tp_cli_connection_interface_contact_groups_run_add_to_group (test->conn,
4726 -1, "Cambridge", test->arr, &error, NULL);
4727
4728 g_assert_no_error (error);
4729
4730 /* by the time the method returns, we should have had the
4731 * change-notification, too */
4732 g_assert_cmpuint (
4733 tp_intset_size (tp_channel_group_get_members (test->group)),
4734 ==, 5);
4735 g_assert (tp_intset_is_member (
4736 tp_channel_group_get_members (test->group),
4737 test->ninja));
4738
4739 g_assert (tp_intset_is_member (
4740 tp_channel_group_get_members (test->stored),
4741 test->ninja));
4742 g_assert (!tp_intset_is_member (
4743 tp_channel_group_get_members (test->subscribe),
4744 test->ninja));
4745 g_assert (!tp_intset_is_member (
4746 tp_channel_group_get_members (test->publish),
4747 test->ninja));
4748
4749 g_assert_cmpuint (test->log->len, ==, 2);
4750
4751 le = g_ptr_array_index (test->log, 0);
4752
4753 if (le->type == CONTACTS_CHANGED)
4754 {
4755 test_assert_one_contact_changed (test, 0, test->ninja,
4756 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, "");
4757 i = 1;
4758 }
4759 else
4760 {
4761 test_assert_one_contact_changed (test, 1, test->ninja,
4762 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, "");
4763 i = 0;
4764 }
4765
4766 /* either way, the i'th entry is now the GroupsChanged signal */
4767 test_assert_one_group_joined (test, i, test->ninja, "Cambridge");
4768
4769 test_assert_contact_state (test, test->ninja,
4770 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, "Cambridge");
4771}
4772
4773static void
4774test_add_to_group_no_op (Test *test,
4775 gconstpointer mode)
4776{
4777 GError *error = NULL;
4778
4779 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4780 "Cambridge");
4781
4782 g_assert (tp_intset_is_member (
4783 tp_channel_group_get_members (test->group),
4784 test->sjoerd));
4785
4786 g_array_append_val (test->arr, test->sjoerd);
4787
4788 if (!tp_strdiff (mode, "old"))
4789 tp_cli_channel_interface_group_run_add_members (test->group,
4790 -1, test->arr, "", &error, NULL);
4791 else
4792 tp_cli_connection_interface_contact_groups_run_add_to_group (test->conn,
4793 -1, "Cambridge", test->arr, &error, NULL);
4794
4795 g_assert_no_error (error);
4796
4797 g_assert_cmpuint (test->log->len, ==, 0);
4798 test_assert_contact_state (test, test->sjoerd,
4799 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, "Cambridge");
4800}
4801
4802static void
4803test_remove_from_group (Test *test,
4804 gconstpointer mode)
4805{
4806 GError *error = NULL;
4807
4808 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4809 "Cambridge");
4810
4811 g_assert (tp_intset_is_member (
4812 tp_channel_group_get_members (test->group),
4813 test->sjoerd));
4814
4815 g_array_append_val (test->arr, test->sjoerd);
4816
4817 if (!tp_strdiff (mode, "old"))
4818 tp_cli_channel_interface_group_run_remove_members (test->group,
4819 -1, test->arr, "", &error, NULL);
4820 else
4821 tp_cli_connection_interface_contact_groups_run_remove_from_group (
4822 test->conn, -1, "Cambridge", test->arr, &error, NULL);
4823
4824 g_assert_no_error (error);
4825
4826 /* by the time the method returns, we should have had the
4827 * removal-notification, too */
4828 g_assert (!tp_intset_is_member (
4829 tp_channel_group_get_members (test->group),
4830 test->sjoerd));
4831
4832 g_assert_cmpuint (test->log->len, ==, 1);
4833 test_assert_one_group_left (test, 0, test->sjoerd, "Cambridge");
4834 test_assert_contact_state (test, test->sjoerd,
4835 TP_SUBSCRIPTION_STATE_YES, TP_SUBSCRIPTION_STATE_YES, NULL, NULL);
4836}
4837
4838static void
4839test_remove_from_group_no_op (Test *test,
4840 gconstpointer mode)
4841{
4842 GError *error = NULL;
4843
4844 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4845 "Cambridge");
4846
4847 g_assert (!tp_intset_is_member (
4848 tp_channel_group_get_members (test->group),
4849 test->ninja));
4850
4851 g_array_append_val (test->arr, test->ninja);
4852
4853 if (!tp_strdiff (mode, "old"))
4854 tp_cli_channel_interface_group_run_remove_members (test->group,
4855 -1, test->arr, "", &error, NULL);
4856 else
4857 tp_cli_connection_interface_contact_groups_run_remove_from_group (
4858 test->conn, -1, "Cambridge", test->arr, &error, NULL);
4859
4860 g_assert_no_error (error);
4861
4862 g_assert_cmpuint (test->log->len, ==, 0);
4863 test_assert_contact_state (test, test->ninja,
4864 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
4865}
4866
4867static void
4868test_remove_group (Test *test,
4869 gconstpointer mode)
4870{
4871 GError *error = NULL;
4872
4873 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4874 "Cambridge");
4875
4876 g_assert (!tp_intset_is_empty (
4877 tp_channel_group_get_members (test->group)));
4878
4879 if (!tp_strdiff (mode, "old"))
4880 {
4881 /* The old API can't remove non-empty groups... */
4882 tp_cli_channel_run_close (test->group, -1, &error, NULL);
4883 g_assert_error (error, TP_ERRORS, TP_ERROR_NOT_AVAILABLE);
4884
4885 g_assert_cmpuint (test->log->len, ==, 0);
4886 }
4887 else
4888 {
4889 /* ... but the new API can */
4890 LogEntry *le;
4891
4892 tp_cli_connection_interface_contact_groups_run_remove_group (test->conn,
4893 -1, "Cambridge", &error, NULL);
4894 g_assert_no_error (error);
4895
4896 g_assert (tp_proxy_get_invalidated (test->group) != NULL);
4897 g_assert_cmpuint (test->log->len, ==, 2);
4898 test_assert_one_group_removed (test, 0, "Cambridge");
4899
4900 le = g_ptr_array_index (test->log, 1);
4901 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
4902 g_assert_cmpuint (le->contacts->len, ==, 4);
4903 g_assert (le->groups_added == NULL || le->groups_added[0] == NULL);
4904 g_assert (le->groups_removed != NULL);
4905 g_assert_cmpstr (le->groups_removed[0], ==, "Cambridge");
4906 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
4907 }
4908}
4909
4910static void
4911test_remove_group_empty (Test *test,
4912 gconstpointer mode)
4913{
4914 GError *error = NULL;
4915
4916 g_assert_cmpuint (test->log->len, ==, 0);
4917 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4918 "people who understand const in C");
4919
4920 g_assert_cmpuint (test->log->len, ==, 1);
4921 test_assert_one_group_created (test, 0, "people who understand const in C");
4922
4923 g_assert (tp_intset_is_empty (
4924 tp_channel_group_get_members (test->group)));
4925
4926 tp_cli_channel_run_close (test->group, -1, &error, NULL);
4927 g_assert_no_error (error);
4928
4929 g_assert_cmpuint (test->log->len, ==, 2);
4930 test_assert_one_group_removed (test, 1, "people who understand const in C");
4931}
4932
4933static void
4934test_set_contact_groups (Test *test,
4935 gconstpointer nil G_GNUC_UNUSED)
4936{
4937 GError *error = NULL;
4938 LogEntry *le;
4939 const gchar *montreal_strv[] = { "Montreal", NULL };
4940
4941 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4942 "Cambridge");
4943
4944 g_assert_cmpuint (
4945 tp_intset_size (tp_channel_group_get_members (test->group)),
4946 ==, 4);
4947 g_assert (tp_intset_is_member (
4948 tp_channel_group_get_members (test->group),
4949 test->sjoerd));
4950
4951 g_array_append_val (test->arr, test->sjoerd);
4952 g_array_append_val (test->arr, test->wim);
4953
4954 tp_cli_connection_interface_contact_groups_run_set_contact_groups (
4955 test->conn, -1, test->sjoerd, montreal_strv, &error, NULL);
4956
4957 g_assert_no_error (error);
4958
4959 /* by the time the method returns, we should have had the
4960 * change-notification, too */
4961 g_assert_cmpuint (
4962 tp_intset_size (tp_channel_group_get_members (test->group)),
4963 ==, 3);
4964 g_assert (!tp_intset_is_member (
4965 tp_channel_group_get_members (test->group),
4966 test->sjoerd));
4967
4968 g_assert_cmpuint (test->log->len, ==, 1);
4969
4970 le = g_ptr_array_index (test->log, 0);
4971 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
4972 g_assert_cmpuint (le->contacts->len, ==, 1);
4973 g_assert_cmpuint (g_array_index (le->contacts, guint, 0), ==, test->sjoerd);
4974 g_assert (le->groups_added != NULL);
4975 g_assert_cmpstr (le->groups_added[0], ==, "Montreal");
4976 g_assert_cmpstr (le->groups_added[1], ==, NULL);
4977 g_assert (le->groups_removed != NULL);
4978 g_assert_cmpstr (le->groups_removed[0], ==, "Cambridge");
4979 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
4980}
4981
4982static void
4983test_set_contact_groups_no_op (Test *test,
4984 gconstpointer nil G_GNUC_UNUSED)
4985{
4986 GError *error = NULL;
4987 const gchar *cambridge_strv[] = { "Cambridge", NULL };
4988
4989 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
4990 "Cambridge");
4991
4992 g_assert_cmpuint (
4993 tp_intset_size (tp_channel_group_get_members (test->group)),
4994 ==, 4);
4995 g_assert (tp_intset_is_member (
4996 tp_channel_group_get_members (test->group),
4997 test->sjoerd));
4998
4999 g_array_append_val (test->arr, test->sjoerd);
5000 g_array_append_val (test->arr, test->wim);
5001
5002 tp_cli_connection_interface_contact_groups_run_set_contact_groups (
5003 test->conn, -1, test->sjoerd, cambridge_strv, &error, NULL);
5004
5005 g_assert_no_error (error);
5006
5007 g_assert_cmpuint (
5008 tp_intset_size (tp_channel_group_get_members (test->group)),
5009 ==, 4);
5010 g_assert (tp_intset_is_member (
5011 tp_channel_group_get_members (test->group),
5012 test->sjoerd));
5013
5014 g_assert_cmpuint (test->log->len, ==, 0);
5015}
5016
5017static void
5018test_set_group_members (Test *test,
5019 gconstpointer nil G_GNUC_UNUSED)
5020{
5021 GError *error = NULL;
5022 LogEntry *le;
5023
5024 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
5025 "Cambridge");
5026
5027 g_assert_cmpuint (
5028 tp_intset_size (tp_channel_group_get_members (test->group)),
5029 ==, 4);
5030 g_assert (tp_intset_is_member (
5031 tp_channel_group_get_members (test->group),
5032 test->sjoerd));
5033 g_assert (tp_intset_is_member (
5034 tp_channel_group_get_members (test->group),
5035 test->helen));
5036 g_assert (!tp_intset_is_member (
5037 tp_channel_group_get_members (test->group),
5038 test->wim));
5039
5040 g_array_append_val (test->arr, test->sjoerd);
5041 g_array_append_val (test->arr, test->wim);
5042
5043 tp_cli_connection_interface_contact_groups_run_set_group_members (test->conn,
5044 -1, "Cambridge", test->arr, &error, NULL);
5045
5046 g_assert_no_error (error);
5047
5048 /* by the time the method returns, we should have had the
5049 * change-notification, too */
5050 g_assert_cmpuint (
5051 tp_intset_size (tp_channel_group_get_members (test->group)),
5052 ==, 2);
5053 g_assert (tp_intset_is_member (
5054 tp_channel_group_get_members (test->group),
5055 test->wim));
5056 g_assert (tp_intset_is_member (
5057 tp_channel_group_get_members (test->group),
5058 test->sjoerd));
5059 g_assert (!tp_intset_is_member (
5060 tp_channel_group_get_members (test->group),
5061 test->helen));
5062
5063 g_assert_cmpuint (test->log->len, ==, 2);
5064
5065 /* Wim was added */
5066 test_assert_one_group_joined (test, 0, test->wim, "Cambridge");
5067
5068 /* The three other members, other than Sjoerd, left */
5069 le = g_ptr_array_index (test->log, 1);
5070 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
5071 g_assert_cmpuint (le->contacts->len, ==, 3);
5072 g_assert (le->groups_added == NULL || le->groups_added[0] == NULL);
5073 g_assert (le->groups_removed != NULL);
5074 g_assert_cmpstr (le->groups_removed[0], ==, "Cambridge");
5075 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
5076}
5077
5078static void
5079test_rename_group (Test *test,
5080 gconstpointer nil G_GNUC_UNUSED)
5081{
5082 LogEntry *le;
5083 GError *error = NULL;
5084
5085 test->group = test_ensure_channel (test, TP_HANDLE_TYPE_GROUP,
5086 "Cambridge");
5087
5088 g_assert_cmpuint (
5089 tp_intset_size (tp_channel_group_get_members (test->group)),
5090 ==, 4);
5091
5092 tp_cli_connection_interface_contact_groups_run_rename_group (test->conn,
5093 -1, "Cambridge", "Grantabrugge", &error, NULL);
5094 g_assert_no_error (error);
5095
5096 g_assert (tp_proxy_get_invalidated (test->group) != NULL);
5097 g_assert_cmpuint (test->log->len, ==, 4);
5098
5099 le = g_ptr_array_index (test->log, 0);
5100 g_assert_cmpint (le->type, ==, GROUP_RENAMED);
5101 g_assert (le->groups_added != NULL);
5102 g_assert_cmpstr (le->groups_added[0], ==, "Grantabrugge");
5103 g_assert_cmpstr (le->groups_added[1], ==, NULL);
5104 g_assert (le->groups_removed != NULL);
5105 g_assert_cmpstr (le->groups_removed[0], ==, "Cambridge");
5106 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
5107
5108 test_assert_one_group_created (test, 1, "Grantabrugge");
5109
5110 test_assert_one_group_removed (test, 2, "Cambridge");
5111
5112 le = g_ptr_array_index (test->log, 3);
5113 g_assert_cmpint (le->type, ==, GROUPS_CHANGED);
5114 g_assert_cmpuint (le->contacts->len, ==, 4);
5115 g_assert (le->groups_added != NULL);
5116 g_assert_cmpstr (le->groups_added[0], ==, "Grantabrugge");
5117 g_assert_cmpstr (le->groups_added[1], ==, NULL);
5118 g_assert_cmpstr (le->groups_removed[0], ==, "Cambridge");
5119 g_assert_cmpstr (le->groups_removed[1], ==, NULL);
5120}
5121
5122static void
5123test_rename_group_overwrite (Test *test,
5124 gconstpointer nil G_GNUC_UNUSED)
5125{
5126 GError *error = NULL;
5127
5128 tp_cli_connection_interface_contact_groups_run_rename_group (test->conn,
5129 -1, "Cambridge", "Montreal", &error, NULL);
5130 g_assert_error (error, TP_ERRORS, TP_ERROR_NOT_AVAILABLE);
5131 g_assert_cmpuint (test->log->len, ==, 0);
5132 g_clear_error (&error);
5133}
5134
5135static void
5136test_rename_group_absent (Test *test,
5137 gconstpointer nil G_GNUC_UNUSED)
5138{
5139 GError *error = NULL;
5140
5141 tp_cli_connection_interface_contact_groups_run_rename_group (test->conn,
5142 -1, "Badgers", "Mushrooms", &error, NULL);
5143 g_assert_error (error, TP_ERRORS, TP_ERROR_DOES_NOT_EXIST);
5144 g_assert_cmpuint (test->log->len, ==, 0);
5145 g_clear_error (&error);
5146}
5147
5148/* Signature of a function which does something with test->arr */
5149typedef void (*ManipulateContactsFunc) (
5150 Test *test,
5151 GError **error);
5152
5153static void
5154block_contacts (Test *test,
5155 ManipulateContactsFunc func)
5156{
5157 GError *error = NULL;
5158
5159 test->deny = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "deny");
5160 test->stored = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "stored");
5161
5162 g_assert_cmpuint (
5163 tp_intset_size (tp_channel_group_get_members (test->deny)),
5164 ==, 2);
5165 g_assert (!tp_intset_is_member (
5166 tp_channel_group_get_members (test->deny),
5167 test->ninja));
5168
5169 g_array_append_val (test->arr, test->ninja);
5170 func (test, &error);
5171 g_assert_no_error (error);
5172
5173 /* by the time the method returns, we should have had the
5174 * change-notification, on both the deny channel and the ContactBlocking
5175 * connection interface */
5176 g_assert_cmpuint (
5177 tp_intset_size (tp_channel_group_get_members (test->deny)),
5178 ==, 3);
5179 g_assert (tp_intset_is_member (
5180 tp_channel_group_get_members (test->deny),
5181 test->ninja));
5182
5183 g_assert (!tp_intset_is_member (
5184 tp_channel_group_get_members (test->stored),
5185 test->ninja));
5186 test_assert_contact_state (test, test->ninja,
5187 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
5188
5189 g_assert_cmpuint (test->log->len, ==, 1);
5190 test_assert_one_contact_blocked (test, 0, test->ninja,
5191 tp_handle_inspect (test->contact_repo, test->ninja));
5192}
5193
5194static void
5195block_contacts_no_op (Test *test,
5196 ManipulateContactsFunc func)
5197{
5198 GError *error = NULL;
5199
5200 test->deny = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "deny");
5201
5202 g_assert (tp_intset_is_member (
5203 tp_channel_group_get_members (test->deny),
5204 test->bill));
5205
5206 g_array_append_val (test->arr, test->bill);
5207 func (test, &error);
5208 g_assert_no_error (error);
5209
5210 g_assert (tp_intset_is_member (
5211 tp_channel_group_get_members (test->deny),
5212 test->bill));
5213 test_assert_contact_state (test, test->bill,
5214 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
5215
5216 /* We shouldn't emit spurious empty BlockedContactsChanged signals. */
5217 g_assert_cmpuint (test->log->len, ==, 0);
5218}
5219
5220static void
5221unblock_contacts (Test *test,
5222 ManipulateContactsFunc func)
5223{
5224 GError *error = NULL;
5225
5226 test->deny = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "deny");
5227 test->publish = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "publish");
5228 test->subscribe = test_ensure_channel (test, TP_HANDLE_TYPE_LIST,
5229 "subscribe");
5230
5231 g_assert (tp_intset_is_member (
5232 tp_channel_group_get_members (test->deny),
5233 test->bill));
5234
5235 g_array_append_val (test->arr, test->bill);
5236 func (test, &error);
5237 g_assert_no_error (error);
5238
5239 /* by the time the method returns, we should have had the
5240 * removal-notification, too */
5241 g_assert (!tp_intset_is_member (
5242 tp_channel_group_get_members (test->deny),
5243 test->bill));
5244 test_assert_contact_state (test, test->bill,
5245 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
5246
5247 g_assert_cmpuint (test->log->len, ==, 1);
5248 test_assert_one_contact_unblocked (test, 0, test->bill,
5249 tp_handle_inspect (test->contact_repo, test->bill));
5250}
5251
5252static void
5253unblock_contacts_no_op (Test *test,
5254 ManipulateContactsFunc func)
5255{
5256 GError *error = NULL;
5257
5258 test->deny = test_ensure_channel (test, TP_HANDLE_TYPE_LIST, "deny");
5259
5260 g_assert (!tp_intset_is_member (
5261 tp_channel_group_get_members (test->deny),
5262 test->ninja));
5263
5264 g_array_append_val (test->arr, test->ninja);
5265 func (test, &error);
5266 g_assert_no_error (error);
5267 g_assert (!tp_intset_is_member (
5268 tp_channel_group_get_members (test->deny),
5269 test->ninja));
5270 test_assert_contact_state (test, test->ninja,
5271 TP_SUBSCRIPTION_STATE_NO, TP_SUBSCRIPTION_STATE_NO, NULL, NULL);
5272
5273 /* We shouldn't emit spurious empty BlockedContactsChanged signals. */
5274 g_assert_cmpuint (test->log->len, ==, 0);
5275}
5276
5277static void
5278add_to_deny (Test *test,
5279 GError **error)
5280{
5281 tp_cli_channel_interface_group_run_add_members (test->deny,
5282 -1, test->arr, "", error, NULL);
5283}
5284
5285static void
5286test_add_to_deny (Test *test,
5287 gconstpointer nil G_GNUC_UNUSED)
5288{
5289 block_contacts (test, add_to_deny);
5290}
5291
5292static void
5293test_add_to_deny_no_op (Test *test,
5294 gconstpointer nil G_GNUC_UNUSED)
5295{
5296 block_contacts_no_op (test, add_to_deny);
5297}
5298
5299static void
5300remove_from_deny (Test *test,
5301 GError **error)
5302{
5303 tp_cli_channel_interface_group_run_remove_members (test->deny,
5304 -1, test->arr, "", error, NULL);
5305}
5306
5307static void
5308test_remove_from_deny (Test *test,
5309 gconstpointer nil G_GNUC_UNUSED)
5310{
5311 unblock_contacts (test, remove_from_deny);
5312}
5313
5314static void
5315test_remove_from_deny_no_op (Test *test,
5316 gconstpointer nil G_GNUC_UNUSED)
5317{
5318 unblock_contacts_no_op (test, remove_from_deny);
5319}
5320
5321static void
5322test_request_blocked_contacts (Test *test,
5323 gconstpointer nil G_GNUC_UNUSED)
5324{
5325 GHashTable *blocked_contacts;
5326 GError *error = NULL;
5327
5328 tp_cli_connection_interface_contact_blocking_run_request_blocked_contacts (
5329 test->conn, -1, &blocked_contacts, &error, NULL);
5330 g_assert_no_error (error);
5331 g_assert (blocked_contacts != NULL);
5332
5333 /* Both Bill and the shadowy Steve are blocked; Steve does not appear in this
5334 * test, as he is in poor health.
5335 */
5336 g_assert_cmpuint (g_hash_table_size (blocked_contacts), ==, 2);
5337 g_assert_cmpstr (tp_handle_inspect (test->contact_repo, test->bill), ==,
5338 g_hash_table_lookup (blocked_contacts, GUINT_TO_POINTER (test->bill)));
5339 g_hash_table_unref (blocked_contacts);
5340}
5341
5342static void
5343request_blocked_contacts_succeeded_cb (
5344 TpConnection *conn,
5345 GHashTable *blocked_contacts,
5346 const GError *error,
5347 gpointer user_data,
5348 GObject *weak_object)
5349{
5350 g_assert_no_error (error);
5351
5352 /* As above. */
5353 g_assert_cmpuint (g_hash_table_size (blocked_contacts), ==, 2);
5354}
5355
5356static void
5357test_request_blocked_contacts_pre_connect (Test *test,
5358 gconstpointer nil G_GNUC_UNUSED)
5359{
5360 gboolean ok;
5361
5362 /* This verifies that calling RequestBlockedContacts()
5363 * before Connect(), when Connect() ultimately succeeds, returns correctly.
5364 */
5365 tp_cli_connection_interface_contact_blocking_call_request_blocked_contacts (
5366 test->conn, -1, request_blocked_contacts_succeeded_cb,
5367 test, test_quit_loop, NULL);
5368 tp_cli_connection_call_connect (test->conn, -1, NULL, NULL, NULL, NULL);
5369 g_main_loop_run (test->main_loop);
5370
5371 ok = tp_cli_connection_run_disconnect (test->conn, -1, NULL, NULL);
5372 g_assert (ok);
5373}
5374
5375static void
5376request_blocked_contacts_failed_cb (
5377 TpConnection *conn,
5378 GHashTable *blocked_contacts,
5379 const GError *error,
5380 gpointer user_data,
5381 GObject *weak_object)
5382{
5383 g_assert_error (error, TP_ERRORS, TP_ERROR_DISCONNECTED);
5384}
5385
5386static void
5387test_request_blocked_contacts_connect_failed (Test *test,
5388 gconstpointer nil G_GNUC_UNUSED)
5389{
5390 /* This verifies that calling RequestBlockedContacts() (twice, no less)
5391 * before Connect(), when Connect() ultimately fails, returns an appropriate
5392 * error.
5393 */
5394 tp_cli_connection_interface_contact_blocking_call_request_blocked_contacts (
5395 test->conn, -1, request_blocked_contacts_failed_cb,
5396 test, test_quit_loop, NULL);
5397 tp_cli_connection_interface_contact_blocking_call_request_blocked_contacts (
5398 test->conn, -1, request_blocked_contacts_failed_cb,
5399 test, test_quit_loop, NULL);
5400
5401 /* We expect calling Connect() to fail because the handle was invalid, but
5402 * don't wait around for it.
5403 */
5404 tp_cli_connection_call_connect (test->conn, -1, NULL, NULL, NULL, NULL);
5405 /* Spin the mainloop twice, once for each outstanding call. */
5406 g_main_loop_run (test->main_loop);
5407 g_main_loop_run (test->main_loop);
5408}
5409
5410static void
5411call_block_contacts (Test *test,
5412 GError **error)
5413{
5414 tp_cli_connection_interface_contact_blocking_run_block_contacts (test->conn,
5415 -1, test->arr, FALSE, error, NULL);
5416}
5417
5418static void
5419test_block_contacts (Test *test,
5420 gconstpointer nil G_GNUC_UNUSED)
5421{
5422 block_contacts (test, call_block_contacts);
5423}
5424
5425static void
5426test_block_contacts_no_op (Test *test,
5427 gconstpointer nil G_GNUC_UNUSED)
5428{
5429 block_contacts_no_op (test, call_block_contacts);
5430}
5431
5432static void
5433call_unblock_contacts (Test *test,
5434 GError **error)
5435{
5436 tp_cli_connection_interface_contact_blocking_run_unblock_contacts (
5437 test->conn, -1, test->arr, error, NULL);
5438}
5439
5440static void
5441test_unblock_contacts (Test *test,
5442 gconstpointer nil G_GNUC_UNUSED)
5443{
5444 unblock_contacts (test, call_unblock_contacts);
5445}
5446
5447static void
5448test_unblock_contacts_no_op (Test *test,
5449 gconstpointer nil G_GNUC_UNUSED)
5450{
5451 unblock_contacts_no_op (test, call_unblock_contacts);
5452}
5453
5454int
5455main (int argc,
5456 char **argv)
5457{
5458 g_type_init ();
5459 tp_tests_abort_after (30);
5460 tp_debug_set_flags ("all");
5461
5462 g_test_init (&argc, &argv, NULL);
5463
5464 g_test_add ("/contact-lists/nothing",
5465 Test, NULL, setup, test_nothing, teardown);
5466
5467 g_test_add ("/contact-lists/initial-channels",
5468 Test, NULL, setup, test_initial_channels, teardown);
5469 g_test_add ("/contact-lists/properties",
5470 Test, NULL, setup, test_properties, teardown);
5471 g_test_add ("/contact-lists/contacts",
5472 Test, NULL, setup, test_contacts, teardown);
5473 g_test_add ("/contact-lists/contact-list-attrs",
5474 Test, NULL, setup, test_contact_list_attrs, teardown);
5475
5476 g_test_add ("/contact-lists/accept-publish-request",
5477 Test, NULL, setup, test_accept_publish_request, teardown);
5478 g_test_add ("/contact-lists/reject-publish-request",
5479 Test, NULL, setup, test_reject_publish_request, teardown);
5480 g_test_add ("/contact-lists/reject-publish-request/unpublish",
5481 Test, "unpublish", setup, test_reject_publish_request, teardown);
5482 g_test_add ("/contact-lists/add-to-publish/pre-approve",
5483 Test, NULL, setup, test_add_to_publish_pre_approve, teardown);
5484 g_test_add ("/contact-lists/add-to-publish/no-op",
5485 Test, NULL, setup, test_add_to_publish_no_op, teardown);
5486 g_test_add ("/contact-lists/remove-from-publish",
5487 Test, NULL, setup, test_remove_from_publish, teardown);
5488 g_test_add ("/contact-lists/remove-from-publish/no-op",
5489 Test, NULL, setup, test_remove_from_publish_no_op, teardown);
5490
5491 g_test_add ("/contact-lists/accept-publish-request/old",
5492 Test, "old", setup, test_accept_publish_request, teardown);
5493 g_test_add ("/contact-lists/reject-publish-request/old",
5494 Test, "old", setup, test_reject_publish_request, teardown);
5495 g_test_add ("/contact-lists/add-to-publish/pre-approve/old",
5496 Test, "old", setup, test_add_to_publish_pre_approve, teardown);
5497 g_test_add ("/contact-lists/add-to-publish/no-op/old",
5498 Test, "old", setup, test_add_to_publish_no_op, teardown);
5499 g_test_add ("/contact-lists/remove-from-publish/old",
5500 Test, "old", setup, test_remove_from_publish, teardown);
5501 g_test_add ("/contact-lists/remove-from-publish/no-op/old",
5502 Test, "old", setup, test_remove_from_publish_no_op, teardown);
5503
5504 g_test_add ("/contact-lists/cancelled-publish-request",
5505 Test, NULL, setup, test_cancelled_publish_request, teardown);
5506 g_test_add ("/contact-lists/cancelled-publish-request",
5507 Test, "remove-after", setup, test_cancelled_publish_request, teardown);
5508
5509 g_test_add ("/contact-lists/add-to-stored",
5510 Test, NULL, setup, test_add_to_stored, teardown);
5511 g_test_add ("/contact-lists/add-to-stored/no-op",
5512 Test, NULL, setup, test_add_to_stored_no_op, teardown);
5513 g_test_add ("/contact-lists/remove-from-stored",
5514 Test, NULL, setup, test_remove_from_stored, teardown);
5515 g_test_add ("/contact-lists/remove-from-stored/no-op",
5516 Test, NULL, setup, test_remove_from_stored_no_op, teardown);
5517
5518 g_test_add ("/contact-lists/add-to-stored/old",
5519 Test, "old", setup, test_add_to_stored, teardown);
5520 g_test_add ("/contact-lists/add-to-stored/no-op/old",
5521 Test, "old", setup, test_add_to_stored_no_op, teardown);
5522 g_test_add ("/contact-lists/remove-from-stored/old",
5523 Test, "old", setup, test_remove_from_stored, teardown);
5524 g_test_add ("/contact-lists/remove-from-stored/no-op/old",
5525 Test, "old", setup, test_remove_from_stored_no_op, teardown);
5526
5527 g_test_add ("/contact-lists/accept-subscribe-request",
5528 Test, NULL, setup, test_accept_subscribe_request, teardown);
5529 g_test_add ("/contact-lists/reject-subscribe-request",
5530 Test, NULL, setup, test_reject_subscribe_request, teardown);
5531 g_test_add ("/contact-lists/remove-from-subscribe",
5532 Test, NULL, setup, test_remove_from_subscribe, teardown);
5533 g_test_add ("/contact-lists/remove-from-subscribe/pending",
5534 Test, NULL, setup, test_remove_from_subscribe_pending, teardown);
5535 g_test_add ("/contact-lists/remove-from-subscribe/no-op",
5536 Test, NULL, setup, test_remove_from_subscribe_no_op, teardown);
5537
5538 g_test_add ("/contact-lists/accept-subscribe-request/old",
5539 Test, "old", setup, test_accept_subscribe_request, teardown);
5540 g_test_add ("/contact-lists/reject-subscribe-request/old",
5541 Test, "old", setup, test_reject_subscribe_request, teardown);
5542 g_test_add ("/contact-lists/remove-from-subscribe/old",
5543 Test, "old", setup, test_remove_from_subscribe, teardown);
5544 g_test_add ("/contact-lists/remove-from-subscribe/pending/old",
5545 Test, "old", setup, test_remove_from_subscribe_pending, teardown);
5546 g_test_add ("/contact-lists/remove-from-subscribe/no-op/old",
5547 Test, "old", setup, test_remove_from_subscribe_no_op, teardown);
5548
5549 g_test_add ("/contact-lists/reject-subscribe-request/remove-after",
5550 Test, "remove-after", setup, test_reject_subscribe_request, teardown);
5551
5552 g_test_add ("/contact-lists/add-to-group",
5553 Test, NULL, setup, test_add_to_group, teardown);
5554 g_test_add ("/contact-lists/add-to-group/no-op",
5555 Test, NULL, setup, test_add_to_group_no_op, teardown);
5556 g_test_add ("/contact-lists/remove-from-group",
5557 Test, NULL, setup, test_remove_from_group, teardown);
5558 g_test_add ("/contact-lists/remove-from-group/no-op",
5559 Test, NULL, setup, test_remove_from_group_no_op, teardown);
5560 g_test_add ("/contact-lists/remove-group",
5561 Test, NULL, setup, test_remove_group, teardown);
5562 g_test_add ("/contact-lists/remove-group/empty",
5563 Test, NULL, setup, test_remove_group_empty, teardown);
5564
5565 g_test_add ("/contact-lists/add-to-group/old",
5566 Test, "old", setup, test_add_to_group, teardown);
5567 g_test_add ("/contact-lists/add-to-group/no-op/old",
5568 Test, "old", setup, test_add_to_group_no_op, teardown);
5569 g_test_add ("/contact-lists/remove-from-group/old",
5570 Test, "old", setup, test_remove_from_group, teardown);
5571 g_test_add ("/contact-lists/remove-from-group/no-op/old",
5572 Test, "old", setup, test_remove_from_group_no_op, teardown);
5573 g_test_add ("/contact-lists/remove-group/old",
5574 Test, "old", setup, test_remove_group, teardown);
5575 g_test_add ("/contact-lists/remove-group/empty/old",
5576 Test, "old", setup, test_remove_group_empty, teardown);
5577
5578 g_test_add ("/contact-lists/set_contact_groups",
5579 Test, NULL, setup, test_set_contact_groups, teardown);
5580 g_test_add ("/contact-lists/set_contact_groups/no-op",
5581 Test, NULL, setup, test_set_contact_groups_no_op, teardown);
5582 g_test_add ("/contact-lists/set_group_members",
5583 Test, NULL, setup, test_set_group_members, teardown);
5584
5585 g_test_add ("/contact-lists/rename_group",
5586 Test, NULL, setup, test_rename_group, teardown);
5587 g_test_add ("/contact-lists/rename_group/absent",
5588 Test, NULL, setup, test_rename_group_absent, teardown);
5589 g_test_add ("/contact-lists/rename_group/overwrite",
5590 Test, NULL, setup, test_rename_group_overwrite, teardown);
5591
5592 g_test_add ("/contact-lists/add-to-deny",
5593 Test, NULL, setup, test_add_to_deny, teardown);
5594 g_test_add ("/contact-lists/add-to-deny/no-op",
5595 Test, NULL, setup, test_add_to_deny_no_op, teardown);
5596 g_test_add ("/contact-lists/remove-from-deny",
5597 Test, NULL, setup, test_remove_from_deny, teardown);
5598 g_test_add ("/contact-lists/remove-from-deny/no-op",
5599 Test, NULL, setup, test_remove_from_deny_no_op, teardown);
5600
5601 g_test_add ("/contact-lists/request-blocked-contacts",
5602 Test, NULL, setup, test_request_blocked_contacts, teardown);
5603 g_test_add ("/contact-lists/request-blocked-contacts-before-connect",
5604 Test, NULL, setup_pre_connect,
5605 test_request_blocked_contacts_pre_connect, teardown_pre_connect);
5606 g_test_add ("/contact-lists/request-blocked-contacts-connect-failed",
5607 Test, "break-account-parameter", setup_pre_connect,
5608 test_request_blocked_contacts_connect_failed,
5609 teardown_pre_connect);
5610 g_test_add ("/contact-lists/block-contacts",
5611 Test, NULL, setup, test_block_contacts, teardown);
5612 g_test_add ("/contact-lists/block-contacts/no-op",
5613 Test, NULL, setup, test_block_contacts_no_op, teardown);
5614 g_test_add ("/contact-lists/unblock-contacts",
5615 Test, NULL, setup, test_unblock_contacts, teardown);
5616 g_test_add ("/contact-lists/unblock-contacts/no-op",
5617 Test, NULL, setup, test_unblock_contacts_no_op, teardown);
5618
5619 return g_test_run ();
5620}
5621>>>>>>> MERGE-SOURCE

Subscribers

People subscribed via source and target branches

to all changes: