~ubuntu-branches/ubuntu/maverick/evolution-data-server/maverick-proposed

« back to all changes in this revision

Viewing changes to servers/exchange/storage/exchange-hierarchy-favorites.c

  • Committer: Bazaar Package Importer
  • Author(s): Didier Roche
  • Date: 2010-05-17 17:02:06 UTC
  • mfrom: (1.1.79 upstream) (1.6.12 experimental)
  • Revision ID: james.westby@ubuntu.com-20100517170206-4ufr52vwrhh26yh0
Tags: 2.30.1-1ubuntu1
* Merge from debian experimental. Remaining change:
  (LP: #42199, #229669, #173703, #360344, #508494)
  + debian/control:
    - add Vcs-Bzr tag
    - don't use libgnome
    - Use Breaks instead of Conflicts against evolution 2.25 and earlier.
  + debian/evolution-data-server.install,
    debian/patches/45_libcamel_providers_version.patch:
    - use the upstream versioning, not a Debian-specific one 
  + debian/libedata-book1.2-dev.install, debian/libebackend-1.2-dev.install,
    debian/libcamel1.2-dev.install, debian/libedataserverui1.2-dev.install:
    - install html documentation
  + debian/rules:
    - don't build documentation it's shipped with the tarball

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2
 
 
3
 
/* Copyright (C) 2002-2004 Novell, Inc.
4
 
 *
5
 
 * This program is free software; you can redistribute it and/or
6
 
 * modify it under the terms of version 2 of the GNU Lesser General Public
7
 
 * License as published by the Free Software Foundation.
8
 
 *
9
 
 * This program is distributed in the hope that it will be useful,
10
 
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11
 
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12
 
 * General Public License for more details.
13
 
 *
14
 
 * You should have received a copy of the GNU Lesser General Public
15
 
 * License along with this program; if not, write to the
16
 
 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17
 
 * Boston, MA 02110-1301, USA.
18
 
 */
19
 
 
20
 
/* ExchangeHierarchyFavorites: class for the "Favorites" Public Folders
21
 
 * hierarchy (and favorites-handling code).
22
 
 */
23
 
 
24
 
#ifdef HAVE_CONFIG_H
25
 
#include <config.h>
26
 
#endif
27
 
 
28
 
#include "exchange-hierarchy-favorites.h"
29
 
#include "exchange-account.h"
30
 
#include "e-folder-exchange.h"
31
 
#include "e2k-propnames.h"
32
 
#include "e2k-uri.h"
33
 
#include "e2k-utils.h"
34
 
#include "exchange-esource.h"
35
 
 
36
 
#include <libedataserver/e-source-list.h>
37
 
 
38
 
#include <stdlib.h>
39
 
#include <string.h>
40
 
#include <unistd.h>
41
 
 
42
 
struct _ExchangeHierarchyFavoritesPrivate {
43
 
        gchar *public_uri, *shortcuts_uri;
44
 
        GHashTable *shortcuts;
45
 
};
46
 
 
47
 
#define PARENT_TYPE EXCHANGE_TYPE_HIERARCHY_SOMEDAV
48
 
static ExchangeHierarchySomeDAVClass *parent_class = NULL;
49
 
 
50
 
static GPtrArray *get_hrefs (ExchangeHierarchySomeDAV *hsd);
51
 
static ExchangeAccountFolderResult remove_folder (ExchangeHierarchy *hier,
52
 
                                                  EFolder *folder);
53
 
static void finalize (GObject *object);
54
 
 
55
 
static void
56
 
class_init (GObjectClass *object_class)
57
 
{
58
 
        ExchangeHierarchySomeDAVClass *somedav_class =
59
 
                EXCHANGE_HIERARCHY_SOMEDAV_CLASS (object_class);
60
 
        ExchangeHierarchyClass *hier_class =
61
 
                EXCHANGE_HIERARCHY_CLASS (object_class);
62
 
 
63
 
        parent_class = g_type_class_ref (PARENT_TYPE);
64
 
 
65
 
        /* virtual method override */
66
 
        object_class->finalize = finalize;
67
 
        hier_class->remove_folder = remove_folder;
68
 
        somedav_class->get_hrefs = get_hrefs;
69
 
}
70
 
 
71
 
static void
72
 
init (GObject *object)
73
 
{
74
 
        ExchangeHierarchyFavorites *hfav = EXCHANGE_HIERARCHY_FAVORITES (object);
75
 
 
76
 
        hfav->priv = g_new0 (ExchangeHierarchyFavoritesPrivate, 1);
77
 
        hfav->priv->shortcuts = g_hash_table_new_full (g_str_hash, g_str_equal,
78
 
                                                       g_free, g_free);
79
 
}
80
 
 
81
 
static void
82
 
finalize (GObject *object)
83
 
{
84
 
        ExchangeHierarchyFavorites *hfav = EXCHANGE_HIERARCHY_FAVORITES (object);
85
 
 
86
 
        g_hash_table_destroy (hfav->priv->shortcuts);
87
 
        g_free (hfav->priv->public_uri);
88
 
        g_free (hfav->priv->shortcuts_uri);
89
 
        g_free (hfav->priv);
90
 
 
91
 
        G_OBJECT_CLASS (parent_class)->finalize (object);
92
 
}
93
 
 
94
 
E2K_MAKE_TYPE (exchange_hierarchy_favorites, ExchangeHierarchyFavorites, class_init, init, PARENT_TYPE)
95
 
 
96
 
static void
97
 
add_hrefs (ExchangeHierarchy *hier, EFolder *folder, gpointer hrefs)
98
 
{
99
 
        g_ptr_array_add (hrefs, (gchar *)e2k_uri_path (e_folder_exchange_get_internal_uri (folder)));
100
 
}
101
 
 
102
 
static const gchar *shortcuts_props[] = {
103
 
        PR_FAV_DISPLAY_NAME,            /* PR_DISPLAY_NAME of referent */
104
 
        PR_FAV_DISPLAY_ALIAS,           /* if set, user-chosen display name */
105
 
        PR_FAV_PUBLIC_SOURCE_KEY,       /* PR_SOURCE_KEY of referent */
106
 
        PR_FAV_PARENT_SOURCE_KEY,       /* PR_FAV_PUBLIC_SOURCE_KEY of parent */
107
 
        PR_FAV_LEVEL_MASK               /* depth in hierarchy (first level is 1) */
108
 
};
109
 
static const gint n_shortcuts_props = G_N_ELEMENTS (shortcuts_props);
110
 
 
111
 
static GPtrArray *
112
 
get_hrefs (ExchangeHierarchySomeDAV *hsd)
113
 
{
114
 
        ExchangeHierarchy *hier = EXCHANGE_HIERARCHY (hsd);
115
 
        ExchangeHierarchyFavorites *hfav = EXCHANGE_HIERARCHY_FAVORITES (hsd);
116
 
        E2kContext *ctx = exchange_account_get_context (hier->account);
117
 
        GPtrArray *hrefs;
118
 
        E2kResultIter *iter;
119
 
        E2kResult *result, *results;
120
 
        E2kHTTPStatus status;
121
 
        GByteArray *source_key;
122
 
        const gchar *prop = E2K_PR_DAV_HREF, *shortcut_uri;
123
 
        gchar *perm_url, *folder_uri;
124
 
        gint i, nresults = 0, mode;
125
 
 
126
 
        hrefs = g_ptr_array_new ();
127
 
 
128
 
        exchange_account_is_offline (hier->account, &mode);
129
 
        if (mode != ONLINE_MODE) {
130
 
                exchange_hierarchy_webdav_offline_scan_subtree (EXCHANGE_HIERARCHY (hfav), add_hrefs, hrefs);
131
 
                return hrefs;
132
 
        }
133
 
        /* Scan the shortcut links and use PROPFIND to resolve the
134
 
         * permanent_urls. Unfortunately it doesn't seem to be possible
135
 
         * to BPROPFIND a group of permanent_urls.
136
 
         */
137
 
        iter = e2k_context_search_start (ctx, NULL, hfav->priv->shortcuts_uri,
138
 
                                         shortcuts_props, n_shortcuts_props,
139
 
                                         NULL, NULL, TRUE);
140
 
        while ((result = e2k_result_iter_next (iter))) {
141
 
                shortcut_uri = result->href;
142
 
                source_key = e2k_properties_get_prop (result->props, PR_FAV_PUBLIC_SOURCE_KEY);
143
 
                if (!source_key)
144
 
                        continue;
145
 
 
146
 
                perm_url = e2k_entryid_to_permanenturl (source_key, hfav->priv->public_uri);
147
 
 
148
 
                status = e2k_context_propfind (ctx, NULL, perm_url,
149
 
                                               &prop, 1, &results, &nresults);
150
 
                if (E2K_HTTP_STATUS_IS_SUCCESSFUL (status) && nresults) {
151
 
                        folder_uri = g_strdup (results[0].href);
152
 
                        g_ptr_array_add (hrefs, folder_uri);
153
 
                        g_hash_table_insert (hfav->priv->shortcuts,
154
 
                                             g_strdup (folder_uri),
155
 
                                             g_strdup (shortcut_uri));
156
 
                        e2k_results_free (results, nresults);
157
 
                }
158
 
 
159
 
                g_free (perm_url);
160
 
        }
161
 
 
162
 
        status = e2k_result_iter_free (iter);
163
 
        if (!E2K_HTTP_STATUS_IS_SUCCESSFUL (status)) {
164
 
                /* FIXME: need to be able to return an error */
165
 
                for (i = 0; i < hrefs->len; i++)
166
 
                        g_free (hrefs->pdata[i]);
167
 
                g_ptr_array_free (hrefs, TRUE);
168
 
                hrefs = NULL;
169
 
        }
170
 
 
171
 
        return hrefs;
172
 
}
173
 
/**
174
 
 * exchange_hierarchy_favorites_is_added:
175
 
 * @hier: the hierarchy
176
 
 * @folder: the Public Folder to check in the favorites tree
177
 
 *
178
 
 * Checks if @folder is present in the favorites hierarchy
179
 
 *
180
 
 * Return value: TRUE if @folder is already added as a favorite.
181
 
 **/
182
 
 
183
 
gboolean
184
 
exchange_hierarchy_favorites_is_added (ExchangeHierarchy *hier, EFolder *folder)
185
 
{
186
 
        ExchangeHierarchyFavorites *hfav =
187
 
                EXCHANGE_HIERARCHY_FAVORITES (hier);
188
 
        const gchar *folder_uri, *shortcut_uri;
189
 
 
190
 
        folder_uri = e_folder_exchange_get_internal_uri (folder);
191
 
        shortcut_uri = g_hash_table_lookup (hfav->priv->shortcuts, folder_uri);
192
 
 
193
 
        return shortcut_uri ? TRUE : FALSE;
194
 
}
195
 
 
196
 
static ExchangeAccountFolderResult
197
 
remove_folder (ExchangeHierarchy *hier, EFolder *folder)
198
 
{
199
 
        ExchangeHierarchyFavorites *hfav =
200
 
                EXCHANGE_HIERARCHY_FAVORITES (hier);
201
 
        const gchar *folder_uri, *shortcut_uri;
202
 
        E2kHTTPStatus status;
203
 
        const gchar *folder_type, *physical_uri;
204
 
 
205
 
        folder_uri = e_folder_exchange_get_internal_uri (folder);
206
 
        shortcut_uri = g_hash_table_lookup (hfav->priv->shortcuts, folder_uri);
207
 
        if (!shortcut_uri)
208
 
                return EXCHANGE_ACCOUNT_FOLDER_DOES_NOT_EXIST;
209
 
 
210
 
        status = e2k_context_delete (
211
 
                exchange_account_get_context (hier->account), NULL,
212
 
                shortcut_uri);
213
 
 
214
 
        if (E2K_HTTP_STATUS_IS_SUCCESSFUL (status)) {
215
 
                g_hash_table_remove (hfav->priv->shortcuts, folder_uri);
216
 
                exchange_hierarchy_removed_folder (hier, folder);
217
 
 
218
 
                /* Temp Fix for remove fav folders. see #59168 */
219
 
                /* remove ESources */
220
 
                folder_type = e_folder_get_type_string (folder);
221
 
                physical_uri = e_folder_get_physical_uri (folder);
222
 
 
223
 
                if (strcmp (folder_type, "calendar") == 0) {
224
 
                        remove_folder_esource (hier->account,
225
 
                                               EXCHANGE_CALENDAR_FOLDER,
226
 
                                               physical_uri);
227
 
                }
228
 
                else if (strcmp (folder_type, "tasks") == 0) {
229
 
                        remove_folder_esource (hier->account,
230
 
                                               EXCHANGE_TASKS_FOLDER,
231
 
                                               physical_uri);
232
 
                }
233
 
                else if (strcmp (folder_type, "contacts") == 0) {
234
 
                        remove_folder_esource (hier->account,
235
 
                                               EXCHANGE_CONTACTS_FOLDER,
236
 
                                               physical_uri);
237
 
                }
238
 
        }
239
 
 
240
 
        return exchange_hierarchy_webdav_status_to_folder_result (status);
241
 
}
242
 
 
243
 
/**
244
 
 * exchange_hierarchy_favorites_add_folder:
245
 
 * @hier: the hierarchy
246
 
 * @folder: the Public Folder to add to the favorites tree
247
 
 *
248
 
 * Adds a new folder to @hier.
249
 
 *
250
 
 * Return value: the folder result.
251
 
 **/
252
 
ExchangeAccountFolderResult
253
 
exchange_hierarchy_favorites_add_folder (ExchangeHierarchy *hier,
254
 
                                         EFolder *folder)
255
 
{
256
 
        ExchangeHierarchyFavorites *hfav;
257
 
        E2kProperties *props;
258
 
        E2kHTTPStatus status;
259
 
        const gchar *folder_uri, *permanent_uri;
260
 
        gchar *shortcut_uri;
261
 
 
262
 
        g_return_val_if_fail (EXCHANGE_IS_HIERARCHY (hier), EXCHANGE_ACCOUNT_FOLDER_GENERIC_ERROR);
263
 
        g_return_val_if_fail (E_IS_FOLDER (folder), EXCHANGE_ACCOUNT_FOLDER_GENERIC_ERROR);
264
 
        g_return_val_if_fail (e_folder_exchange_get_hierarchy (folder)->type == EXCHANGE_HIERARCHY_PUBLIC, EXCHANGE_ACCOUNT_FOLDER_GENERIC_ERROR);
265
 
 
266
 
        hfav = EXCHANGE_HIERARCHY_FAVORITES (hier);
267
 
        permanent_uri = e_folder_exchange_get_permanent_uri (folder);
268
 
 
269
 
        props = e2k_properties_new ();
270
 
        e2k_properties_set_string (props, PR_FAV_DISPLAY_NAME,
271
 
                                   g_strdup (e_folder_get_name (folder)));
272
 
        if (permanent_uri)
273
 
                e2k_properties_set_binary (props, PR_FAV_PUBLIC_SOURCE_KEY,
274
 
                                   e2k_permanenturl_to_entryid (permanent_uri));
275
 
        e2k_properties_set_int (props, PR_FAV_LEVEL_MASK, 1);
276
 
 
277
 
        status = e2k_context_proppatch_new (
278
 
                exchange_account_get_context (hier->account), NULL,
279
 
                hfav->priv->shortcuts_uri,
280
 
                e_folder_get_name (folder), NULL, NULL,
281
 
                props, &shortcut_uri, NULL);
282
 
        e2k_properties_free (props);
283
 
 
284
 
        if (E2K_HTTP_STATUS_IS_SUCCESSFUL (status)) {
285
 
                folder_uri = e_folder_exchange_get_internal_uri (folder);
286
 
 
287
 
                g_hash_table_insert (hfav->priv->shortcuts,
288
 
                                     g_strdup (folder_uri), shortcut_uri);
289
 
                return exchange_hierarchy_somedav_add_folder (EXCHANGE_HIERARCHY_SOMEDAV (hier),
290
 
                                                              folder_uri);
291
 
        } else
292
 
                return exchange_hierarchy_webdav_status_to_folder_result (status);
293
 
}
294
 
 
295
 
/**
296
 
 * exchange_hierarchy_favorites_new:
297
 
 * @account: an #ExchangeAccount
298
 
 * @hierarchy_name: the name of the hierarchy
299
 
 * @physical_uri_prefix: prefix for physical URIs in this hierarchy
300
 
 * @home_uri: the home URI of the owner's mailbox
301
 
 * @public_uri: the URI of the public folder tree
302
 
 * @owner_name: display name of the owner of the hierarchy
303
 
 * @owner_email: email address of the owner of the hierarchy
304
 
 * @source_uri: account source URI for folders in this hierarchy
305
 
 *
306
 
 * Creates a new Favorites hierarchy
307
 
 *
308
 
 * Return value: the new hierarchy.
309
 
 **/
310
 
ExchangeHierarchy *
311
 
exchange_hierarchy_favorites_new (ExchangeAccount *account,
312
 
                                  const gchar *hierarchy_name,
313
 
                                  const gchar *physical_uri_prefix,
314
 
                                  const gchar *home_uri,
315
 
                                  const gchar *public_uri,
316
 
                                  const gchar *owner_name,
317
 
                                  const gchar *owner_email,
318
 
                                  const gchar *source_uri)
319
 
{
320
 
        ExchangeHierarchy *hier;
321
 
        ExchangeHierarchyFavorites *hfav;
322
 
 
323
 
        g_return_val_if_fail (EXCHANGE_IS_ACCOUNT (account), NULL);
324
 
 
325
 
        hier = g_object_new (EXCHANGE_TYPE_HIERARCHY_FAVORITES, NULL);
326
 
 
327
 
        hfav = (ExchangeHierarchyFavorites *)hier;
328
 
        hfav->priv->public_uri = g_strdup (public_uri);
329
 
        hfav->priv->shortcuts_uri = e2k_uri_concat (home_uri, "NON_IPM_SUBTREE/Shortcuts");
330
 
 
331
 
        exchange_hierarchy_webdav_construct (EXCHANGE_HIERARCHY_WEBDAV (hier),
332
 
                                             account,
333
 
                                             EXCHANGE_HIERARCHY_FAVORITES,
334
 
                                             hierarchy_name,
335
 
                                             physical_uri_prefix,
336
 
                                             public_uri,
337
 
                                             owner_name, owner_email,
338
 
                                             source_uri,
339
 
                                             TRUE);
340
 
        return hier;
341
 
}