Changeset 3518
- Timestamp:
- 03/24/08 14:13:57
- Files:
-
- trunk/ChangeLog (modified) (1 diff)
- trunk/libtinymail-camel/tny-camel-folder.c (modified) (3 diffs)
- trunk/libtinymail-camel/tny-camel-folder.h (modified) (1 diff)
- trunk/libtinymail/tny-folder.c (modified) (1 diff)
- trunk/libtinymail/tny-folder.h (modified) (2 diffs)
- trunk/libtinymail/tny-merge-folder.c (modified) (2 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
trunk/ChangeLog
r3516 r3518 2 2 3 3 * Rewrote tny_camel_folder_remove_msgs_default 4 * Added tny_folder_remove_msgs_async 5 6 * This was a minor API change 4 7 5 8 2008-03-20 Philip Van Hoof <pvanhoof@gnome.org> trunk/libtinymail-camel/tny-camel-folder.c
r3517 r3518 1107 1107 return; 1108 1108 } 1109 1110 1111 1112 1113 typedef struct 1114 { 1115 TnyCamelQueueable parent; 1116 1117 GError *err; 1118 TnyFolder *self; 1119 TnyList *headers; 1120 TnyFolderCallback callback; 1121 gpointer user_data; 1122 TnySessionCamel *session; 1123 gboolean cancelled; 1124 1125 } RemMsgsInfo; 1126 1127 1128 static void 1129 tny_camel_folder_remove_msgs_async_destroyer (gpointer thr_user_data) 1130 { 1131 RemMsgsInfo *info = thr_user_data; 1132 1133 /* thread reference */ 1134 g_object_unref (info->self); 1135 g_object_unref (info->headers); 1136 1137 if (info->err) 1138 g_error_free (info->err); 1139 1140 return; 1141 } 1142 1143 static gboolean 1144 tny_camel_folder_remove_msgs_async_callback (gpointer thr_user_data) 1145 { 1146 RemMsgsInfo *info = thr_user_data; 1147 if (info->callback) { 1148 tny_lockable_lock (info->session->priv->ui_lock); 1149 info->callback (info->self, info->cancelled, info->err, info->user_data); 1150 tny_lockable_unlock (info->session->priv->ui_lock); 1151 } 1152 return FALSE; 1153 } 1154 1155 static gpointer 1156 tny_camel_folder_remove_msgs_async_thread (gpointer thr_user_data) 1157 { 1158 RemMsgsInfo *info = (RemMsgsInfo*) thr_user_data; 1159 info->err = NULL; 1160 tny_folder_remove_msgs (info->self, info->headers, &info->err); 1161 info->cancelled = FALSE; 1162 1163 if (info->err != NULL) { 1164 if (camel_strstrcase (info->err->message, "cancel") != NULL) 1165 info->cancelled = TRUE; 1166 } 1167 1168 return NULL; 1169 } 1170 1171 static void 1172 tny_camel_folder_remove_msgs_async_cancelled_destroyer (gpointer thr_user_data) 1173 { 1174 RemMsgsInfo *info = thr_user_data; 1175 if (info->err) 1176 g_error_free (info->err); 1177 g_object_unref (info->self); 1178 g_object_unref (info->headers); 1179 1180 return; 1181 } 1182 1183 static gboolean 1184 tny_camel_folder_remove_msgs_async_cancelled_callback (gpointer thr_user_data) 1185 { 1186 RemMsgsInfo *info = thr_user_data; 1187 if (info->callback) { 1188 tny_lockable_lock (info->session->priv->ui_lock); 1189 info->callback (info->self, TRUE, info->err, info->user_data); 1190 tny_lockable_unlock (info->session->priv->ui_lock); 1191 } 1192 return FALSE; 1193 } 1194 1195 static void 1196 tny_camel_folder_remove_msgs_async (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data) 1197 { 1198 TNY_CAMEL_FOLDER_GET_CLASS (self)->remove_msgs_async(self, headers, callback, status_callback, user_data); 1199 return; 1200 } 1201 1202 1203 static void 1204 tny_camel_folder_remove_msgs_async_default (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data) 1205 { 1206 RemMsgsInfo *info; 1207 TnyCamelFolderPriv *priv = TNY_CAMEL_FOLDER_GET_PRIVATE (self); 1208 1209 /* Idle info for the callbacks */ 1210 info = g_slice_new (RemMsgsInfo); 1211 info->session = TNY_FOLDER_PRIV_GET_SESSION (priv); 1212 info->self = self; 1213 info->headers = headers; 1214 info->callback = callback; 1215 info->user_data = user_data; 1216 info->err = NULL; 1217 1218 /* thread reference */ 1219 g_object_ref (info->self); 1220 g_object_ref (info->headers); 1221 1222 _tny_camel_queue_launch (TNY_FOLDER_PRIV_GET_QUEUE (priv), 1223 tny_camel_folder_remove_msgs_async_thread, 1224 tny_camel_folder_remove_msgs_async_callback, 1225 tny_camel_folder_remove_msgs_async_destroyer, 1226 tny_camel_folder_remove_msgs_async_cancelled_callback, 1227 tny_camel_folder_remove_msgs_async_cancelled_destroyer, 1228 &info->cancelled, 1229 info, sizeof (RemMsgsInfo), __FUNCTION__); 1230 1231 return; 1232 } 1233 1234 1109 1235 1110 1236 static void … … 5621 5747 klass->get_url_string= tny_camel_folder_get_url_string; 5622 5748 klass->get_caps= tny_camel_folder_get_caps; 5749 klass->remove_msgs_async= tny_camel_folder_remove_msgs_async; 5623 5750 5624 5751 return; … … 5686 5813 class->get_url_string= tny_camel_folder_get_url_string_default; 5687 5814 class->get_caps= tny_camel_folder_get_caps_default; 5815 class->remove_msgs_async= tny_camel_folder_remove_msgs_async_default; 5688 5816 5689 5817 class->get_folders_async= tny_camel_folder_get_folders_async_default; trunk/libtinymail-camel/tny-camel-folder.h
r3304 r3518 90 90 gchar* (*get_url_string) (TnyFolder *self); 91 91 TnyFolderCaps (*get_caps) (TnyFolder *self); 92 void (*remove_msgs_async) (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data); 92 93 93 94 void (*get_folders_async) (TnyFolderStore *self, TnyList *list, TnyFolderStoreQuery *query, TnyGetFoldersCallback callback, TnyStatusCallback status_callback, gpointer user_data); trunk/libtinymail/tny-folder.c
r3436 r3518 781 781 } 782 782 783 784 785 /** 786 * tny_folder_remove_msgs_async: 787 * @self: a #TnyFolder 788 * @headers: a #TnyList with #TnyHeader items of the messages to remove 789 * @callback: (null-ok): a #TnyFolderCallback or NULL 790 * @status_callback: (null-ok): a #TnyStatusCallback or NULL 791 * @user_data: (null-ok): user data that will be passed to the callbacks 792 * 793 * Remove messages from a folder. It will use the #TnyMsgRemoveStrategy of 794 * @self to perform the removal itself. For more details, check out the 795 * documentation of the used #TnyMsgRemoveStrategy type. The default 796 * implementation for libtinymail-camel is the #TnyCamelMsgRemoveStrategy. 797 * 798 * Folder observers of @self will get only one header-removed trigger caused 799 * by this action (with all the removed headers in the #TnyFolderChange). 800 * 801 * since: 1.0 802 * audience: application-developer 803 **/ 804 void 805 tny_folder_remove_msgs_async (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data) 806 { 807 #ifdef DBC /* require */ 808 g_assert (TNY_IS_FOLDER (self)); 809 g_assert (headers); 810 g_assert (TNY_IS_LIST (headers)); 811 g_assert (TNY_FOLDER_GET_IFACE (self)->remove_msgs_async!= NULL); 812 #endif 813 814 TNY_FOLDER_GET_IFACE (self)->remove_msgs_async(self, headers, callback, status_callback, user_data); 815 return; 816 } 817 783 818 /** 784 819 * tny_folder_refresh_async: trunk/libtinymail/tny-folder.h
r3304 r3518 133 133 gchar* (*get_url_string) (TnyFolder *self); 134 134 TnyFolderCaps (*get_caps) (TnyFolder *self); 135 void (*remove_msgs_async) (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data); 136 135 137 }; 136 138 … … 176 178 TnyFolderCaps tny_folder_get_caps (TnyFolder *self); 177 179 gchar* tny_folder_get_url_string (TnyFolder *self); 180 void tny_folder_remove_msgs_async (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data); 178 181 179 182 G_END_DECLS trunk/libtinymail/tny-merge-folder.c
r3304 r3518 102 102 return; 103 103 } 104 105 106 107 typedef struct 108 { 109 TnyFolder *self; 110 TnyList *headers; 111 TnyFolderCallback callback; 112 TnyStatusCallback status_callback; 113 gpointer user_data; 114 gboolean cancelled, refresh; 115 guint depth; 116 GError *err; 117 } RemMsgsInfo; 118 119 120 static void 121 remove_msgs_async_destroyer (gpointer thr_user_data) 122 { 123 RemMsgsInfo *info = thr_user_data; 124 125 /* thread reference */ 126 g_object_unref (info->self); 127 g_object_unref (info->headers); 128 129 if (info->err) 130 g_error_free (info->err); 131 132 g_slice_free (RemMsgsInfo, thr_user_data); 133 134 return; 135 } 136 137 static gboolean 138 remove_msgs_async_callback (gpointer thr_user_data) 139 { 140 RemMsgsInfo *info = thr_user_data; 141 TnyMergeFolderPriv *priv = TNY_MERGE_FOLDER_GET_PRIVATE (info->self); 142 143 if (info->callback) { 144 tny_lockable_lock (priv->ui_locker); 145 info->callback (info->self, info->cancelled, info->err, info->user_data); 146 tny_lockable_unlock (priv->ui_locker); 147 } 148 149 return FALSE; 150 } 151 152 153 static gpointer 154 remove_msgs_async_thread (gpointer thr_user_data) 155 { 156 RemMsgsInfo *info = thr_user_data; 157 TnyFolder *self = info->self; 158 TnyMergeFolderPriv *priv = TNY_MERGE_FOLDER_GET_PRIVATE (self); 159 TnyIterator *iter; 160 GError *err = NULL; 161 TnyList *copy; 162 163 g_static_rec_mutex_lock (priv->lock); 164 copy = tny_list_copy (priv->mothers); 165 g_static_rec_mutex_unlock (priv->lock); 166 167 info->cancelled = FALSE; 168 169 iter = tny_list_create_iterator (copy); 170 while (!tny_iterator_is_done (iter)) 171 { 172 TnyFolder *cur = TNY_FOLDER (tny_iterator_get_current (iter)); 173 174 tny_folder_remove_msgs (cur, info->headers, &err); 175 176 /* TODO: Handler err */ 177 178 /* TODO: Handle progress status callbacks ( info->status_callback ) 179 * you might have to start using refresh_async for that (in a 180 * serialized way, else you'd launch a buch of concurrent threads 181 * and ain't going to be nice, perhaps). */ 182 183 g_object_unref (cur); 184 tny_iterator_next (iter); 185 } 186 187 g_object_unref (iter); 188 g_object_unref (copy); 189 190 info->err = NULL; 191 192 if (info->callback) 193 { 194 if (info->depth > 0) 195 { 196 g_idle_add_full (G_PRIORITY_HIGH, 197 remove_msgs_async_callback, 198 info, remove_msgs_async_destroyer); 199 } else { 200 remove_msgs_async_callback (info); 201 remove_msgs_async_destroyer (info); 202 } 203 } else { /* Thread reference */ 204 g_object_unref (info->self); 205 g_object_unref (info->headers); 206 } 207 208 g_thread_exit (NULL); 209 210 return NULL; 211 } 212 213 214 static void 215 tny_merge_folder_remove_msgs_async (TnyFolder *self, TnyList *headers, TnyFolderCallback callback, TnyStatusCallback status_callback, gpointer user_data) 216 { 217 RemMsgsInfo *info; 218 GThread *thread; 219 220 info = g_slice_new (RemMsgsInfo); 221 info->err = NULL; 222 info->self = self; 223 info->headers = headers; 224 info->callback = callback; 225 info->status_callback = status_callback; 226 info->user_data = user_data; 227 info->depth = g_main_depth (); 228 229 /* thread reference */ 230 g_object_ref (self); 231 g_object_ref (headers); 232 233 thread = g_thread_create (remove_msgs_async_thread, info, FALSE, NULL); 234 235 return; 236 } 237 104 238 105 239 static void … … 1740 1874 klass->get_caps= tny_merge_folder_get_caps; 1741 1875 klass->remove_msgs= tny_merge_folder_remove_msgs; 1876 klass->remove_msgs_async= tny_merge_folder_remove_msgs_async; 1742 1877 } 1743 1878
