Mercurial > dovecot > core-2.2
comparison src/lib-imap-storage/imap-msgpart-url.c @ 14594:27c8a6c9088d
Error handling API changes to previous IMAP URL related changes.
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Sat, 02 Jun 2012 19:01:25 +0300 |
parents | 07e6ca397a72 |
children | 6fb61872b30a |
comparison
equal
deleted
inserted
replaced
14593:e445670e7332 | 14594:27c8a6c9088d |
---|---|
42 mpurl->partial_offset = url->partial_offset; | 42 mpurl->partial_offset = url->partial_offset; |
43 mpurl->partial_size = url->partial_size; | 43 mpurl->partial_size = url->partial_size; |
44 return mpurl; | 44 return mpurl; |
45 } | 45 } |
46 | 46 |
47 struct imap_msgpart_url * | 47 int imap_msgpart_url_parse(struct mail_user *user, struct mailbox *selected_box, |
48 imap_msgpart_url_parse(struct mail_user *user, struct mailbox *selected_box, | 48 const char *urlstr, struct imap_msgpart_url **url_r, |
49 const char *urlstr, const char **error_r) | 49 const char **error_r) |
50 { | 50 { |
51 struct mailbox_status box_status; | 51 struct mailbox_status box_status; |
52 struct imap_url base_url, *url; | 52 struct imap_url base_url, *url; |
53 const char *error; | 53 const char *error; |
54 | 54 |
60 base_url.mailbox = mailbox_get_vname(selected_box); | 60 base_url.mailbox = mailbox_get_vname(selected_box); |
61 base_url.uidvalidity = box_status.uidvalidity; | 61 base_url.uidvalidity = box_status.uidvalidity; |
62 } | 62 } |
63 | 63 |
64 /* parse url */ | 64 /* parse url */ |
65 url = imap_url_parse(urlstr, NULL, &base_url, | 65 if (imap_url_parse(urlstr, &base_url, |
66 IMAP_URL_PARSE_REQUIRE_RELATIVE, &error); | 66 IMAP_URL_PARSE_REQUIRE_RELATIVE, &url, &error) < 0) { |
67 if (url == NULL) { | |
68 *error_r = t_strconcat("Invalid IMAP URL: ", error, NULL); | 67 *error_r = t_strconcat("Invalid IMAP URL: ", error, NULL); |
69 return NULL; | 68 return -1; |
70 } | 69 } |
71 if (url->mailbox == NULL) { | 70 if (url->mailbox == NULL) { |
72 *error_r = "Mailbox-relative IMAP URL, but no mailbox selected"; | 71 *error_r = "Mailbox-relative IMAP URL, but no mailbox selected"; |
73 return NULL; | 72 return -1; |
74 } | 73 } |
75 if (url->uid == 0 || url->search_program != NULL) { | 74 if (url->uid == 0 || url->search_program != NULL) { |
76 *error_r = "Invalid messagepart IMAP URL"; | 75 *error_r = "Invalid messagepart IMAP URL"; |
77 return NULL; | 76 return -1; |
78 } | 77 } |
79 return imap_msgpart_url_create(user, url); | 78 *url_r = imap_msgpart_url_create(user, url); |
79 return 0; | |
80 } | 80 } |
81 | 81 |
82 struct mailbox *imap_msgpart_url_get_mailbox(struct imap_msgpart_url *mpurl) | 82 struct mailbox *imap_msgpart_url_get_mailbox(struct imap_msgpart_url *mpurl) |
83 { | 83 { |
84 return mpurl->box; | 84 return mpurl->box; |
85 } | 85 } |
86 | 86 |
87 struct mailbox * | 87 int imap_msgpart_url_open_mailbox(struct imap_msgpart_url *mpurl, |
88 imap_msgpart_url_open_mailbox(struct imap_msgpart_url *mpurl, | 88 struct mailbox **box_r, const char **error_r) |
89 const char **error_r) | |
90 { | 89 { |
91 struct mailbox_status box_status; | 90 struct mailbox_status box_status; |
92 enum mail_error error_code; | 91 enum mail_error error_code; |
93 enum mailbox_flags flags = MAILBOX_FLAG_READONLY; | 92 enum mailbox_flags flags = MAILBOX_FLAG_READONLY; |
94 struct mail_namespace *ns; | 93 struct mail_namespace *ns; |
95 struct mailbox *box; | 94 struct mailbox *box; |
96 | 95 |
97 if (mpurl->box != NULL) | 96 if (mpurl->box != NULL) { |
98 return mpurl->box; | 97 *box_r = mpurl->box; |
98 return 1; | |
99 } | |
99 | 100 |
100 /* find mailbox namespace */ | 101 /* find mailbox namespace */ |
101 ns = mail_namespace_find(mpurl->user->namespaces, mpurl->mailbox); | 102 ns = mail_namespace_find(mpurl->user->namespaces, mpurl->mailbox); |
102 if (ns == NULL) { | 103 if (ns == NULL) { |
103 *error_r = "Nonexistent mailbox namespace"; | 104 *error_r = "Nonexistent mailbox namespace"; |
104 return NULL; | 105 return 0; |
105 } | 106 } |
106 | 107 |
107 /* open mailbox */ | 108 /* open mailbox */ |
108 box = mailbox_alloc(ns->list, mpurl->mailbox, flags); | 109 box = mailbox_alloc(ns->list, mpurl->mailbox, flags); |
109 if (mailbox_open(box) < 0) { | 110 if (mailbox_open(box) < 0) { |
110 *error_r = mail_storage_get_last_error(mailbox_get_storage(box), | 111 *error_r = mail_storage_get_last_error(mailbox_get_storage(box), |
111 &error_code); | 112 &error_code); |
112 mailbox_free(&box); | 113 mailbox_free(&box); |
113 return NULL; | 114 return error_code == MAIL_ERROR_TEMP ? -1 : 0; |
114 } | 115 } |
115 | 116 |
116 /* verify UIDVALIDITY */ | 117 /* verify UIDVALIDITY */ |
117 mailbox_get_open_status(box, STATUS_UIDVALIDITY, &box_status); | 118 mailbox_get_open_status(box, STATUS_UIDVALIDITY, &box_status); |
118 if (mpurl->uidvalidity > 0 && | 119 if (mpurl->uidvalidity > 0 && |
119 box_status.uidvalidity != mpurl->uidvalidity) { | 120 box_status.uidvalidity != mpurl->uidvalidity) { |
120 *error_r = "Invalid UIDVALIDITY"; | 121 *error_r = "Invalid UIDVALIDITY"; |
121 mailbox_free(&box); | 122 mailbox_free(&box); |
122 return NULL; | 123 return 0; |
123 } | 124 } |
124 mpurl->box = box; | 125 mpurl->box = box; |
125 return box; | 126 *box_r = box; |
126 } | 127 return 1; |
127 | 128 } |
128 struct mail * | 129 |
129 imap_msgpart_url_open_mail(struct imap_msgpart_url *mpurl, const char **error_r) | 130 int imap_msgpart_url_open_mail(struct imap_msgpart_url *mpurl, |
131 struct mail **mail_r, const char **error_r) | |
130 { | 132 { |
131 struct mailbox_transaction_context *t; | 133 struct mailbox_transaction_context *t; |
132 struct mail *mail; | 134 struct mailbox *box; |
133 | 135 struct mail *mail; |
134 if (mpurl->mail != NULL) | 136 int ret; |
135 return mpurl->mail; | 137 |
138 if (mpurl->mail != NULL) { | |
139 *mail_r = mpurl->mail; | |
140 return 1; | |
141 } | |
136 | 142 |
137 /* open mailbox if it is not yet open */ | 143 /* open mailbox if it is not yet open */ |
138 if (mpurl->box == NULL) { | 144 if ((ret = imap_msgpart_url_open_mailbox(mpurl, &box, error_r)) <= 0) |
139 if (imap_msgpart_url_open_mailbox(mpurl, error_r) == NULL) | 145 return ret; |
140 return NULL; | |
141 } | |
142 | 146 |
143 /* start transaction */ | 147 /* start transaction */ |
144 t = mailbox_transaction_begin(mpurl->box, 0); | 148 t = mailbox_transaction_begin(box, 0); |
145 mail = mail_alloc(t, 0, NULL); | 149 mail = mail_alloc(t, 0, NULL); |
146 | 150 |
147 /* find the message */ | 151 /* find the message */ |
148 if (!mail_set_uid(mail, mpurl->uid)) { | 152 if (!mail_set_uid(mail, mpurl->uid)) { |
149 *error_r = "Message not found"; | 153 *error_r = "Message not found"; |
150 mail_free(&mail); | 154 mail_free(&mail); |
151 mailbox_transaction_rollback(&t); | 155 mailbox_transaction_rollback(&t); |
152 return NULL; | 156 return 0; |
153 } | 157 } |
154 | 158 |
155 mpurl->trans = t; | 159 mpurl->trans = t; |
156 mpurl->mail = mail; | 160 mpurl->mail = mail; |
157 return mail; | 161 *mail_r = mail; |
158 } | 162 return 1; |
159 | 163 } |
160 bool imap_msgpart_url_read_part(struct imap_msgpart_url *mpurl, | 164 |
161 struct istream **stream_r, uoff_t *size_r, | 165 int imap_msgpart_url_read_part(struct imap_msgpart_url *mpurl, |
162 const char **error_r) | 166 struct istream **stream_r, uoff_t *size_r, |
163 { | 167 const char **error_r) |
168 { | |
169 struct mail *mail; | |
164 struct istream *input; | 170 struct istream *input; |
165 uoff_t part_size; | 171 uoff_t part_size; |
172 int ret; | |
166 | 173 |
167 if (mpurl->input != NULL) { | 174 if (mpurl->input != NULL) { |
168 i_stream_seek(mpurl->input, 0); | 175 i_stream_seek(mpurl->input, 0); |
169 *stream_r = mpurl->input; | 176 *stream_r = mpurl->input; |
170 *size_r = mpurl->part_size; | 177 *size_r = mpurl->part_size; |
171 return TRUE; | 178 return 1; |
172 } | 179 } |
173 | 180 |
174 /* open mailbox if it is not yet open */ | 181 /* open mail if it is not yet open */ |
175 if (mpurl->mail == NULL) { | 182 if ((ret = imap_msgpart_url_open_mail(mpurl, &mail, error_r)) <= 0) |
176 if (imap_msgpart_url_open_mail(mpurl, error_r) == NULL) | 183 return ret; |
177 return FALSE; | |
178 } | |
179 | 184 |
180 /* open the referenced part as a stream */ | 185 /* open the referenced part as a stream */ |
181 if (!imap_msgpart_open(mpurl->mail, mpurl->section, | 186 if ((ret = imap_msgpart_open(mail, mpurl->section, |
182 mpurl->partial_offset, mpurl->partial_size, | 187 mpurl->partial_offset, mpurl->partial_size, |
183 &input, &part_size, error_r)) | 188 &input, &part_size, error_r)) <= 0) |
184 return FALSE; | 189 return ret; |
185 | 190 |
186 mpurl->input = input; | 191 mpurl->input = input; |
187 mpurl->part_size = part_size; | 192 mpurl->part_size = part_size; |
188 | 193 |
189 *stream_r = input; | 194 *stream_r = input; |
190 *size_r = part_size; | 195 *size_r = part_size; |
191 return TRUE; | 196 return 1; |
192 } | 197 } |
193 | 198 |
194 bool imap_msgpart_url_verify(struct imap_msgpart_url *mpurl, | 199 int imap_msgpart_url_verify(struct imap_msgpart_url *mpurl, |
195 const char **error_r) | 200 const char **error_r) |
196 { | 201 { |
202 struct mail *mail; | |
203 int ret; | |
204 | |
197 if (mpurl->input != NULL) | 205 if (mpurl->input != NULL) |
198 return TRUE; | 206 return 1; |
199 | 207 |
200 /* open mailbox if it is not yet open */ | 208 /* open mail if it is not yet open */ |
201 if (mpurl->mail == NULL) { | 209 if ((ret = imap_msgpart_url_open_mail(mpurl, &mail, error_r)) <= 0) |
202 if (imap_msgpart_url_open_mail(mpurl, error_r) == NULL) | 210 return ret; |
203 return FALSE; | |
204 } | |
205 | 211 |
206 /* open the referenced part as a stream */ | 212 /* open the referenced part as a stream */ |
207 if (!imap_msgpart_verify(mpurl->mail, mpurl->section, error_r)) | 213 return imap_msgpart_verify(mail, mpurl->section, error_r); |
208 return FALSE; | |
209 return TRUE; | |
210 } | 214 } |
211 | 215 |
212 void imap_msgpart_url_free(struct imap_msgpart_url **_mpurl) | 216 void imap_msgpart_url_free(struct imap_msgpart_url **_mpurl) |
213 { | 217 { |
214 struct imap_msgpart_url *mpurl = *_mpurl; | 218 struct imap_msgpart_url *mpurl = *_mpurl; |