1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2 /*
3 * Copyright (C) 2016 Red Hat, Inc. (www.redhat.com)
4 *
5 * This library is free software: you can redistribute it and/or modify it
6 * under the terms of the GNU Lesser General Public License as published by
7 * the Free Software Foundation.
8 *
9 * This library is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
11 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
12 * for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public License
15 * along with this library. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18 #include "evolution-data-server-config.h"
19
20 #include <stdio.h>
21
22 #include "camel/camel.h"
23 #include "camel-maildir-summary.h"
24
25 #include "camel-maildir-message-info.h"
26
27 struct _CamelMaildirMessageInfoPrivate {
28 gchar *filename;
29 };
30
31 enum {
32 PROP_0,
33 PROP_FILENAME
34 };
35
G_DEFINE_TYPE_WITH_PRIVATE(CamelMaildirMessageInfo,camel_maildir_message_info,CAMEL_TYPE_MESSAGE_INFO_BASE)36 G_DEFINE_TYPE_WITH_PRIVATE (CamelMaildirMessageInfo, camel_maildir_message_info, CAMEL_TYPE_MESSAGE_INFO_BASE)
37
38 static CamelMessageInfo *
39 maildir_message_info_clone (const CamelMessageInfo *mi,
40 CamelFolderSummary *assign_summary)
41 {
42 CamelMessageInfo *result;
43
44 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mi), NULL);
45
46 result = CAMEL_MESSAGE_INFO_CLASS (camel_maildir_message_info_parent_class)->clone (mi, assign_summary);
47 if (!result)
48 return NULL;
49
50 if (CAMEL_IS_MAILDIR_MESSAGE_INFO (result)) {
51 CamelMaildirMessageInfo *mmi, *mmi_result;
52
53 mmi = CAMEL_MAILDIR_MESSAGE_INFO (mi);
54 mmi_result = CAMEL_MAILDIR_MESSAGE_INFO (result);
55
56 /* safe-guard that the mmi's filename doesn't change before it's copied to mmi_result */
57 camel_message_info_property_lock (mi);
58
59 camel_maildir_message_info_set_filename (mmi_result, camel_maildir_message_info_get_filename (mmi));
60
61 camel_message_info_property_unlock (mi);
62 }
63
64 return result;
65 }
66
67 static gboolean
maildir_message_info_load(CamelMessageInfo * mi,const CamelMIRecord * record,gchar ** bdata_ptr)68 maildir_message_info_load (CamelMessageInfo *mi,
69 const CamelMIRecord *record,
70 /* const */ gchar **bdata_ptr)
71 {
72 CamelMaildirMessageInfo *mmi;
73
74 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mi), FALSE);
75 g_return_val_if_fail (record != NULL, FALSE);
76 g_return_val_if_fail (bdata_ptr != NULL, FALSE);
77
78 if (!CAMEL_MESSAGE_INFO_CLASS (camel_maildir_message_info_parent_class)->load ||
79 !CAMEL_MESSAGE_INFO_CLASS (camel_maildir_message_info_parent_class)->load (mi, record, bdata_ptr))
80 return FALSE;
81
82 mmi = CAMEL_MAILDIR_MESSAGE_INFO (mi);
83
84 camel_maildir_message_info_take_filename (mmi, camel_maildir_summary_info_to_name (mi));
85
86 return TRUE;
87 }
88
89 static void
maildir_message_info_set_property(GObject * object,guint property_id,const GValue * value,GParamSpec * pspec)90 maildir_message_info_set_property (GObject *object,
91 guint property_id,
92 const GValue *value,
93 GParamSpec *pspec)
94 {
95 CamelMaildirMessageInfo *mmi = CAMEL_MAILDIR_MESSAGE_INFO (object);
96
97 switch (property_id) {
98 case PROP_FILENAME:
99 camel_maildir_message_info_set_filename (mmi, g_value_get_string (value));
100 return;
101 }
102
103 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
104 }
105
106 static void
maildir_message_info_get_property(GObject * object,guint property_id,GValue * value,GParamSpec * pspec)107 maildir_message_info_get_property (GObject *object,
108 guint property_id,
109 GValue *value,
110 GParamSpec *pspec)
111 {
112 CamelMaildirMessageInfo *mmi = CAMEL_MAILDIR_MESSAGE_INFO (object);
113
114 switch (property_id) {
115 case PROP_FILENAME:
116 g_value_set_string (value, camel_maildir_message_info_get_filename (mmi));
117 return;
118 }
119
120 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
121 }
122
123 static void
maildir_message_info_dispose(GObject * object)124 maildir_message_info_dispose (GObject *object)
125 {
126 CamelMaildirMessageInfo *mmi = CAMEL_MAILDIR_MESSAGE_INFO (object);
127
128 g_free (mmi->priv->filename);
129 mmi->priv->filename = NULL;
130
131 /* Chain up to parent's method. */
132 G_OBJECT_CLASS (camel_maildir_message_info_parent_class)->dispose (object);
133 }
134
135 static void
camel_maildir_message_info_class_init(CamelMaildirMessageInfoClass * class)136 camel_maildir_message_info_class_init (CamelMaildirMessageInfoClass *class)
137 {
138 CamelMessageInfoClass *mi_class;
139 GObjectClass *object_class;
140
141 mi_class = CAMEL_MESSAGE_INFO_CLASS (class);
142 mi_class->clone = maildir_message_info_clone;
143 mi_class->load = maildir_message_info_load;
144
145 object_class = G_OBJECT_CLASS (class);
146 object_class->set_property = maildir_message_info_set_property;
147 object_class->get_property = maildir_message_info_get_property;
148 object_class->dispose = maildir_message_info_dispose;
149
150 /**
151 * CamelMaildirMessageInfo:filename
152 *
153 * File name of the message on the disk.
154 *
155 * Since: 3.24
156 **/
157 g_object_class_install_property (
158 object_class,
159 PROP_FILENAME,
160 g_param_spec_string (
161 "filename",
162 "Filename",
163 NULL,
164 NULL,
165 G_PARAM_READWRITE |
166 G_PARAM_EXPLICIT_NOTIFY |
167 G_PARAM_STATIC_STRINGS));
168 }
169
170 static void
camel_maildir_message_info_init(CamelMaildirMessageInfo * mmi)171 camel_maildir_message_info_init (CamelMaildirMessageInfo *mmi)
172 {
173 mmi->priv = camel_maildir_message_info_get_instance_private (mmi);
174 }
175
176 const gchar *
camel_maildir_message_info_get_filename(const CamelMaildirMessageInfo * mmi)177 camel_maildir_message_info_get_filename (const CamelMaildirMessageInfo *mmi)
178 {
179 CamelMessageInfo *mi;
180 const gchar *result;
181
182 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mmi), NULL);
183
184 mi = CAMEL_MESSAGE_INFO (mmi);
185
186 camel_message_info_property_lock (mi);
187 result = mmi->priv->filename;
188 camel_message_info_property_unlock (mi);
189
190 return result;
191 }
192
193 gchar *
camel_maildir_message_info_dup_filename(const CamelMaildirMessageInfo * mmi)194 camel_maildir_message_info_dup_filename (const CamelMaildirMessageInfo *mmi)
195 {
196 CamelMessageInfo *mi;
197 gchar *result;
198
199 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mmi), NULL);
200
201 mi = CAMEL_MESSAGE_INFO (mmi);
202
203 camel_message_info_property_lock (mi);
204 result = g_strdup (mmi->priv->filename);
205 camel_message_info_property_unlock (mi);
206
207 return result;
208 }
209
210 gboolean
camel_maildir_message_info_set_filename(CamelMaildirMessageInfo * mmi,const gchar * filename)211 camel_maildir_message_info_set_filename (CamelMaildirMessageInfo *mmi,
212 const gchar *filename)
213 {
214 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mmi), FALSE);
215
216 return camel_maildir_message_info_take_filename (mmi, g_strdup (filename));
217 }
218
219 gboolean
camel_maildir_message_info_take_filename(CamelMaildirMessageInfo * mmi,gchar * filename)220 camel_maildir_message_info_take_filename (CamelMaildirMessageInfo *mmi,
221 gchar *filename)
222 {
223 CamelMessageInfo *mi;
224 gboolean changed;
225
226 g_return_val_if_fail (CAMEL_IS_MAILDIR_MESSAGE_INFO (mmi), FALSE);
227
228 mi = CAMEL_MESSAGE_INFO (mmi);
229
230 camel_message_info_property_lock (mi);
231
232 changed = g_strcmp0 (mmi->priv->filename, filename) != 0;
233
234 if (changed) {
235 g_free (mmi->priv->filename);
236 mmi->priv->filename = filename;
237 } else if (filename != mmi->priv->filename) {
238 g_free (filename);
239 }
240
241 camel_message_info_property_unlock (mi);
242
243 if (changed && !camel_message_info_get_abort_notifications (mi)) {
244 g_object_notify (G_OBJECT (mmi), "filename");
245 camel_message_info_set_dirty (mi, TRUE);
246 }
247
248 return changed;
249 }
250