Mercurial > pidgin.yaz
annotate src/log.c @ 7506:240aca6344b6
[gaim-migrate @ 8119]
I'm going climbing soon, but I'll be around later to make Mandrake
9.1 RPMs. 9.2 ISOs haven't been released to the public yet, AFAIK.
This is some more disconnection dialog stuff from Daniel Atallah.
It fixes a memleak (that I think I introduced), makes the most
recently disconnected account the selected account, and makes the
window manager close work correctly.
datallah: The fix for the window-manager-close-button is the
"case GTK_RESPONSE_DELETE_EVENT:" line.
committer: Tailor Script <tailor@pidgin.im>
author | Mark Doliner <mark@kingant.net> |
---|---|
date | Thu, 13 Nov 2003 23:57:45 +0000 |
parents | 3e85281aef0b |
children | f771759739c1 |
rev | line source |
---|---|
7431 | 1 /** |
2 * @file log.c Logging API | |
3 * @ingroup core | |
4 * | |
5 * gaim | |
6 * | |
7 * Copyright (C) 2003 Buzz Lightyear | |
7436 | 8 * |
7431 | 9 * This program is free software; you can redistribute it and/or modify |
10 * it under the terms of the GNU General Public License as published by | |
11 * the Free Software Foundation; either version 2 of the License, or | |
12 * (at your option) any later version. | |
13 * | |
14 * This program is distributed in the hope that it will be useful, | |
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
17 * GNU General Public License for more details. | |
18 * | |
19 * You should have received a copy of the GNU General Public License | |
20 * along with this program; if not, write to the Free Software | |
21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA | |
4184 | 22 */ |
4195 | 23 |
7431 | 24 #include "account.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
25 #include "debug.h" |
7431 | 26 #include "internal.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
27 #include "log.h" |
5548 | 28 #include "prefs.h" |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
29 #include "util.h" |
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
30 |
7457 | 31 static GaimLogLogger html_logger; |
7431 | 32 static GaimLogLogger txt_logger; |
33 static GaimLogLogger old_logger; | |
5872
059d95c67cda
[gaim-migrate @ 6304]
Christian Hammond <chipx86@chipx86.com>
parents:
5839
diff
changeset
|
34 |
7431 | 35 /************************************************************************** |
36 * PUBLIC LOGGING FUNCTIONS *********************************************** | |
37 **************************************************************************/ | |
4184 | 38 |
7431 | 39 GaimLog *gaim_log_new(GaimLogType type, const char *name, GaimAccount *account, time_t time) |
40 { | |
41 GaimLog *log = g_new0(GaimLog, 1); | |
42 log->name = g_strdup(name); | |
43 log->account = account; | |
44 log->time = time; | |
45 log->logger = gaim_log_logger_get(); | |
7440 | 46 if (log->logger && log->logger->create) |
47 log->logger->create(log); | |
7431 | 48 return log; |
4184 | 49 } |
50 | |
7431 | 51 void gaim_log_free(GaimLog *log) |
4184 | 52 { |
7431 | 53 g_return_if_fail(log); |
54 if (log->logger && log->logger->finalize) | |
55 log->logger->finalize(log); | |
56 g_free(log->name); | |
57 g_free(log); | |
58 } | |
7436 | 59 |
4184 | 60 |
7436 | 61 void gaim_log_write(GaimLog *log, GaimMessageFlags type, |
7431 | 62 const char *from, time_t time, const char *message) |
63 { | |
64 g_return_if_fail(log); | |
65 g_return_if_fail(log->logger); | |
7442 | 66 g_return_if_fail(log->logger->write); |
7431 | 67 |
7442 | 68 (log->logger->write)(log, type, from, time, message); |
4184 | 69 } |
70 | |
7431 | 71 char *gaim_log_read(GaimLog *log, GaimLogReadFlags *flags) |
4184 | 72 { |
7431 | 73 g_return_val_if_fail(log && log->logger, NULL); |
7462 | 74 if (log->logger->read) { |
75 char *ret = (log->logger->read)(log, flags); | |
7478
3c21f3084ff0
[gaim-migrate @ 8091]
Herman Bloggs <hermanator12002@yahoo.com>
parents:
7473
diff
changeset
|
76 gaim_str_strip_cr(ret); |
7462 | 77 return ret; |
78 } | |
7470 | 79 return (_("<b><font color=\"red\">The logger has no read function</font></b>")); |
4184 | 80 } |
81 | |
7431 | 82 /**************************************************************************** |
83 * LOGGER FUNCTIONS ********************************************************* | |
84 ****************************************************************************/ | |
4184 | 85 |
7431 | 86 static GaimLogLogger *current_logger = NULL; |
87 static GSList *loggers = NULL; | |
7436 | 88 |
7431 | 89 static void logger_pref_cb(const char *name, GaimPrefType type, |
90 gpointer value, gpointer data) | |
91 { | |
92 GaimLogLogger *logger; | |
93 GSList *l = loggers; | |
94 while (l) { | |
95 logger = l->data; | |
96 if (!strcmp(logger->id, value)) { | |
97 gaim_log_logger_set(logger); | |
98 return; | |
4184 | 99 } |
7431 | 100 l = l->next; |
101 } | |
102 gaim_log_logger_set(&txt_logger); | |
103 } | |
4184 | 104 |
105 | |
7440 | 106 GaimLogLogger *gaim_log_logger_new(void(*create)(GaimLog *), |
7436 | 107 void(*write)(GaimLog *, GaimMessageFlags, const char *, |
7431 | 108 time_t, const char *), |
109 void(*finalize)(GaimLog *), GList*(*list)(const char*, GaimAccount*), | |
110 char*(*read)(GaimLog*, GaimLogReadFlags*)) | |
111 { | |
112 GaimLogLogger *logger = g_new0(GaimLogLogger, 1); | |
7440 | 113 logger->create = create; |
7431 | 114 logger->write = write; |
115 logger->finalize = finalize; | |
116 logger->list = list; | |
117 logger->read = read; | |
118 return logger; | |
4184 | 119 } |
120 | |
7431 | 121 void gaim_log_logger_free(GaimLogLogger *logger) |
4184 | 122 { |
7431 | 123 g_free(logger); |
124 } | |
4184 | 125 |
7431 | 126 void gaim_log_logger_add (GaimLogLogger *logger) |
127 { | |
128 g_return_if_fail(logger); | |
129 if (g_slist_find(loggers, logger)) | |
130 return; | |
131 loggers = g_slist_append(loggers, logger); | |
132 } | |
133 | |
134 void gaim_log_logger_remove (GaimLogLogger *logger) | |
135 { | |
136 g_return_if_fail(logger); | |
137 g_slist_remove(loggers, logger); | |
4184 | 138 } |
139 | |
7431 | 140 void gaim_log_logger_set (GaimLogLogger *logger) |
4184 | 141 { |
7431 | 142 g_return_if_fail(logger); |
143 current_logger = logger; | |
7436 | 144 } |
4184 | 145 |
7431 | 146 GaimLogLogger *gaim_log_logger_get() |
147 { | |
148 return current_logger; | |
149 } | |
4184 | 150 |
7431 | 151 GList *gaim_log_logger_get_options(void) |
152 { | |
153 GSList *n; | |
154 GList *list = NULL; | |
155 GaimLogLogger *data; | |
4184 | 156 |
7431 | 157 for (n = loggers; n; n = n->next) { |
158 data = n->data; | |
159 if (!data->write) | |
160 continue; | |
7494 | 161 list = g_list_append(list, _(data->name)); |
7431 | 162 list = g_list_append(list, data->id); |
4184 | 163 } |
164 | |
7431 | 165 return list; |
166 } | |
167 | |
7436 | 168 static gint log_compare(gconstpointer y, gconstpointer z) |
7431 | 169 { |
7436 | 170 const GaimLog *a = y; |
171 const GaimLog *b = z; | |
172 | |
7431 | 173 return b->time - a->time; |
174 } | |
175 | |
176 GList *gaim_log_get_logs(const char *name, GaimAccount *account) | |
177 { | |
178 GList *logs = NULL; | |
179 GSList *n; | |
180 for (n = loggers; n; n = n->next) { | |
181 GaimLogLogger *logger = n->data; | |
182 if (!logger->list) | |
183 continue; | |
184 logs = g_list_concat(logs, logger->list(name, account)); | |
185 } | |
7436 | 186 |
7431 | 187 return g_list_sort(logs, log_compare); |
188 } | |
189 | |
190 void gaim_log_init(void) | |
7436 | 191 { |
7431 | 192 gaim_prefs_add_none("/core/logging"); |
193 gaim_prefs_add_string("/core/logging/format", "txt"); | |
7457 | 194 gaim_log_logger_add(&html_logger); |
7431 | 195 gaim_log_logger_add(&txt_logger); |
196 gaim_log_logger_add(&old_logger); | |
197 gaim_prefs_connect_callback("/core/logging/format", | |
198 logger_pref_cb, NULL); | |
199 gaim_prefs_trigger_callback("/core/logging/format"); | |
200 } | |
201 | |
202 /**************************************************************************** | |
203 * LOGGERS ****************************************************************** | |
204 ****************************************************************************/ | |
205 | |
206 static GList *log_lister_common(const char *screenname, GaimAccount *account, const char *ext, GaimLogLogger *logger) | |
207 { | |
208 GDir *dir; | |
209 GList *list = NULL; | |
7501 | 210 const char *filename, *tmp; |
7431 | 211 char *me = g_strdup(gaim_normalize(account, gaim_account_get_username(account))); |
4184 | 212 |
7431 | 213 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO |
214 (gaim_find_prpl(gaim_account_get_protocol(account)))->list_icon(account, NULL); | |
215 char *path = g_build_filename(gaim_user_dir(), "logs", prpl, me, gaim_normalize(account, screenname), NULL); | |
216 | |
7447 | 217 g_free(me); |
218 | |
7431 | 219 if (!(dir = g_dir_open(path, 0, NULL))) { |
220 g_free(path); | |
221 return NULL; | |
222 } | |
223 while ((filename = g_dir_read_name(dir))) { | |
7501 | 224 tmp = filename + (strlen(filename) - strlen(ext)); |
225 if (tmp > filename && !strcmp(tmp, ext)) { | |
7431 | 226 const char *l = filename; |
227 struct tm time; | |
228 GaimLog *log; | |
229 char d[5]; | |
7436 | 230 |
7431 | 231 strncpy(d, l, 4); |
232 d[4] = '\0'; | |
233 time.tm_year = atoi(d) - 1900; | |
234 l = l + 5; | |
235 | |
236 strncpy(d, l, 2); | |
237 d[2] = '\0'; | |
238 time.tm_mon = atoi(d) - 1; | |
239 l = l + 3; | |
240 | |
241 strncpy(d, l, 2); | |
242 time.tm_mday = atoi(d); | |
243 l = l + 3; | |
244 | |
245 strncpy(d, l, 2); | |
246 time.tm_hour = atoi(d); | |
247 l = l + 2; | |
7436 | 248 |
7431 | 249 strncpy(d, l, 2); |
250 time.tm_min = atoi(d); | |
251 l = l + 2; | |
252 | |
253 strncpy(d, l, 2); | |
254 time.tm_sec = atoi(d); | |
255 l = l + 2; | |
256 log = gaim_log_new(GAIM_LOG_IM, screenname, account, mktime(&time)); | |
257 log->logger = logger; | |
258 log->logger_data = g_build_filename(path, filename, NULL); | |
259 list = g_list_append(list, log); | |
4184 | 260 } |
261 } | |
7431 | 262 g_dir_close(dir); |
7447 | 263 g_free(path); |
7431 | 264 return list; |
265 } | |
4184 | 266 |
7431 | 267 #if 0 /* Maybe some other time. */ |
7443 | 268 /**************** |
7431 | 269 ** XML LOGGER ** |
270 ****************/ | |
271 | |
272 static const char *str_from_msg_type (GaimMessageFlags type) | |
273 { | |
7443 | 274 |
7431 | 275 return ""; |
7443 | 276 |
7431 | 277 } |
278 | |
7443 | 279 static void xml_logger_write(GaimLog *log, |
280 GaimMessageFlags type, | |
7431 | 281 const char *from, time_t time, const char *message) |
282 { | |
283 char date[64]; | |
284 char *xhtml = NULL; | |
285 if (!log->logger_data) { | |
286 /* This log is new. We could use the loggers 'new' function, but | |
287 * creating a new file there would result in empty files in the case | |
288 * that you open a convo with someone, but don't say anything. | |
289 */ | |
290 char *ud = gaim_user_dir(); | |
291 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); | |
292 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
293 (gaim_find_prpl(gaim_account_get_protocol(log->account)))->list_icon(log->account, NULL); | |
294 char *dir; | |
295 FILE *file; | |
296 | |
7453 | 297 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.xml", localtime(&log->time)); |
7443 | 298 |
7431 | 299 dir = g_build_filename(ud, "logs", NULL); |
300 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
301 g_free(dir); | |
7443 | 302 dir = g_build_filename(ud, "logs", |
7431 | 303 prpl, NULL); |
304 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
305 g_free(dir); | |
7443 | 306 dir = g_build_filename(ud, "logs", |
7431 | 307 prpl, guy, NULL); |
308 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
7443 | 309 g_free(dir); |
310 dir = g_build_filename(ud, "logs", | |
7431 | 311 prpl, guy, gaim_normalize(log->account, log->name), NULL); |
312 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
7447 | 313 g_free(guy); |
7443 | 314 |
7431 | 315 char *filename = g_build_filename(dir, date, NULL); |
316 g_free(dir); | |
7443 | 317 |
7431 | 318 file = fopen(dir, "r"); |
319 if(!file) | |
320 mkdir(dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
321 else | |
322 fclose(file); | |
7443 | 323 |
7431 | 324 log->logger_data = fopen(filename, "a"); |
325 if (!log->logger_data) { | |
326 gaim_debug(GAIM_DEBUG_ERROR, "log", "Could not create log file %s\n", filename); | |
327 return; | |
328 } | |
329 fprintf(log->logger_data, "<?xml version='1.0' encoding='UTF-8' ?>\n" | |
330 "<?xml-stylesheet href='file:///usr/src/web/htdocs/log-stylesheet.xsl' type='text/xml' ?>\n"); | |
7443 | 331 |
7453 | 332 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); |
7431 | 333 fprintf(log->logger_data, "<conversation time='%s' screenname='%s' protocol='%s'>\n", |
334 date, log->name, prpl); | |
335 } | |
7443 | 336 |
7453 | 337 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); |
7431 | 338 gaim_markup_html_to_xhtml(message, &xhtml, NULL); |
339 if (from) | |
7443 | 340 fprintf(log->logger_data, "<message %s %s from='%s' time='%s'>%s</message>\n", |
341 str_from_msg_type(type), | |
7431 | 342 type & GAIM_MESSAGE_SEND ? "direction='sent'" : |
343 type & GAIM_MESSAGE_RECV ? "direction='received'" : "", | |
344 from, date, xhtml); | |
345 else | |
7443 | 346 fprintf(log->logger_data, "<message %s %s time='%s'>%s</message>\n", |
347 str_from_msg_type(type), | |
7431 | 348 type & GAIM_MESSAGE_SEND ? "direction='sent'" : |
349 type & GAIM_MESSAGE_RECV ? "direction='received'" : "", | |
7443 | 350 date, xhtml): |
7431 | 351 fflush(log->logger_data); |
352 g_free(xhtml); | |
7443 | 353 } |
354 | |
7431 | 355 static void xml_logger_finalize(GaimLog *log) |
356 { | |
357 if (log->logger_data) { | |
358 fprintf(log->logger_data, "</conversation>\n"); | |
359 fclose(log->logger_data); | |
360 log->logger_data = NULL; | |
361 } | |
362 } | |
7443 | 363 |
7431 | 364 static GList *xml_logger_list(const char *sn, GaimAccount *account) |
365 { | |
366 return log_lister_common(sn, account, ".xml", &xml_logger); | |
4184 | 367 } |
368 | |
7431 | 369 static GaimLogLogger xml_logger = { |
370 N_("XML"), "xml", | |
371 NULL, | |
372 xml_logger_write, | |
373 xml_logger_finalize, | |
374 xml_logger_list, | |
375 NULL | |
376 }; | |
377 #endif | |
5563
9eb5b13fd412
[gaim-migrate @ 5965]
Christian Hammond <chipx86@chipx86.com>
parents:
5560
diff
changeset
|
378 |
7431 | 379 /**************************** |
7457 | 380 ** HTML LOGGER ************* |
381 ****************************/ | |
382 | |
383 static void html_logger_write(GaimLog *log, GaimMessageFlags type, | |
384 const char *from, time_t time, const char *message) | |
385 { | |
7489 | 386 GaimConnection *gc = gaim_account_get_connection(log->account); |
7457 | 387 char date[64]; |
388 if(!log->logger_data) { | |
389 /* This log is new */ | |
390 char *ud = gaim_user_dir(); | |
391 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); | |
392 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
393 (gaim_find_prpl(gaim_account_get_protocol(log->account)))->list_icon(log->account, NULL); | |
394 char *dir; | |
395 char *filename; | |
396 FILE *file; | |
397 | |
398 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.html", localtime(&log->time)); | |
399 | |
400 dir = g_build_filename(ud, "logs", NULL); | |
401 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
402 g_free(dir); | |
403 dir = g_build_filename(ud, "logs", | |
404 prpl, NULL); | |
405 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
406 g_free(dir); | |
407 dir = g_build_filename(ud, "logs", | |
408 prpl, guy, NULL); | |
409 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
410 g_free(dir); | |
411 dir = g_build_filename(ud, "logs", | |
412 prpl, guy, gaim_normalize(log->account, log->name), NULL); | |
413 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
414 g_free(guy); | |
415 | |
416 filename = g_build_filename(dir, date, NULL); | |
417 g_free(dir); | |
418 | |
419 file = fopen(dir, "r"); | |
420 if(!file) | |
421 mkdir(dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
422 else | |
423 fclose(file); | |
424 | |
425 log->logger_data = fopen(filename, "a"); | |
426 if (!log->logger_data) { | |
427 gaim_debug(GAIM_DEBUG_ERROR, "log", "Could not create log file %s\n", filename); | |
428 return; | |
429 } | |
430 g_free(filename); | |
431 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); | |
432 fprintf(log->logger_data, "<html><head><title>"); | |
433 fprintf(log->logger_data, "Conversation with %s at %s on %s (%s)", | |
434 log->name, date, gaim_account_get_username(log->account), prpl); | |
435 fprintf(log->logger_data, "</title></head><body>"); | |
436 fprintf(log->logger_data, | |
437 "<h3>Conversation with %s at %s on %s (%s)</h3>\n", | |
438 log->name, date, gaim_account_get_username(log->account), prpl); | |
439 } | |
440 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); | |
7489 | 441 if (type & GAIM_MESSAGE_SYSTEM) |
442 fprintf(log->logger_data, "(%s)<b> %s</b><br/>\n", date, message); | |
443 else if (type & GAIM_MESSAGE_WHISPER) | |
444 fprintf(log->logger_data, "<font color=\"#6C2585\">(%s)<b> %s:</b></font> %s<br/>\n", | |
445 date, from, message); | |
446 else if (type & GAIM_MESSAGE_AUTO_RESP) { | |
447 if (type & GAIM_MESSAGE_SEND) | |
448 fprintf(log->logger_data, _("<font color=\"#16569E\">(%s) <b>%s <AUTO-REPLY>:</b></font> %s<br/>\n"), date, from, message); | |
449 else if (type & GAIM_MESSAGE_RECV) | |
450 fprintf(log->logger_data, _("<font color=\"#A82F2F\">(%s) <b>%s <AUTO-REPLY>:</b></font> %s<br/>\n"), date, from, message); | |
451 } else if (type & GAIM_MESSAGE_RECV) | |
452 fprintf(log->logger_data, "<font color=\"#A82F2F\">(%s) <b>%s:</b></font> <font sml=\"%s\">%s</font><br/>\n", | |
453 date, from, gc->prpl->info->name, message); | |
7491 | 454 else if (type & GAIM_MESSAGE_SEND) |
7489 | 455 fprintf(log->logger_data, "<font color=\"#16569E\">(%s) <b>%s:</b></font> <font sml=\"%s\">%s</font><br/>\n", |
456 date, from, gc->prpl->info->name, message); | |
7457 | 457 fflush(log->logger_data); |
458 } | |
459 | |
460 static void html_logger_finalize(GaimLog *log) | |
461 { | |
7463 | 462 if (log->logger_data) { |
463 fprintf(log->logger_data, "</body></html>"); | |
7457 | 464 fclose(log->logger_data); |
7463 | 465 } |
7457 | 466 } |
467 | |
468 static GList *html_logger_list(const char *sn, GaimAccount *account) | |
469 { | |
470 return log_lister_common(sn, account, ".html", &html_logger); | |
471 } | |
472 | |
473 static char *html_logger_read(GaimLog *log, GaimLogReadFlags *flags) | |
474 { | |
475 char *read, *minus_header; | |
476 *flags = GAIM_LOG_READ_NO_NEWLINE; | |
477 if (!log->logger_data) | |
7472 | 478 return g_strdup(_("<font color=\"red\"><b>log->logger_data was NULL!</b></font>")); |
7457 | 479 if (g_file_get_contents((char *)log->logger_data, &read, NULL, NULL)) { |
480 minus_header = strchr(read, '\n'); | |
481 if (!minus_header) | |
482 minus_header = g_strdup(read); | |
483 else | |
484 minus_header = g_strdup(minus_header + 1); | |
485 g_free(read); | |
486 return minus_header; | |
487 } | |
7471 | 488 return g_strdup(_("<font color=\"red\"><b>Could not read file: %s</b></font>")); |
7457 | 489 } |
490 | |
491 static GaimLogLogger html_logger = { | |
492 N_("HTML"), "html", | |
493 NULL, | |
494 html_logger_write, | |
495 html_logger_finalize, | |
496 html_logger_list, | |
497 html_logger_read | |
498 }; | |
499 | |
500 | |
501 | |
502 | |
503 /**************************** | |
7431 | 504 ** PLAIN TEXT LOGGER ******* |
505 ****************************/ | |
4184 | 506 |
7436 | 507 static void txt_logger_write(GaimLog *log, |
508 GaimMessageFlags type, | |
7431 | 509 const char *from, time_t time, const char *message) |
510 { | |
511 char date[64]; | |
512 char *stripped = NULL; | |
513 if (!log->logger_data) { | |
514 /* This log is new. We could use the loggers 'new' function, but | |
515 * creating a new file there would result in empty files in the case | |
516 * that you open a convo with someone, but don't say anything. | |
517 */ | |
518 char *ud = gaim_user_dir(); | |
7473 | 519 char *filename; |
7431 | 520 char *guy = g_strdup(gaim_normalize(log->account, gaim_account_get_username(log->account))); |
521 const char *prpl = GAIM_PLUGIN_PROTOCOL_INFO | |
522 (gaim_find_prpl(gaim_account_get_protocol(log->account)))->list_icon(log->account, NULL); | |
523 char *dir; | |
524 FILE *file; | |
7436 | 525 |
7453 | 526 strftime(date, sizeof(date), "%Y-%m-%d.%H%M%S.txt", localtime(&log->time)); |
7436 | 527 |
7431 | 528 dir = g_build_filename(ud, "logs", NULL); |
529 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
530 g_free(dir); | |
7436 | 531 dir = g_build_filename(ud, "logs", |
7431 | 532 prpl, NULL); |
533 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
534 g_free(dir); | |
7436 | 535 dir = g_build_filename(ud, "logs", |
7431 | 536 prpl, guy, NULL); |
537 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
7436 | 538 g_free(dir); |
539 dir = g_build_filename(ud, "logs", | |
7431 | 540 prpl, guy, gaim_normalize(log->account, log->name), NULL); |
541 mkdir (dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
7447 | 542 g_free(guy); |
7436 | 543 |
7473 | 544 filename = g_build_filename(dir, date, NULL); |
7431 | 545 g_free(dir); |
7436 | 546 |
7431 | 547 file = fopen(dir, "r"); |
548 if(!file) | |
549 mkdir(dir, S_IRUSR | S_IWUSR | S_IXUSR); | |
550 else | |
551 fclose(file); | |
7436 | 552 |
7431 | 553 log->logger_data = fopen(filename, "a"); |
554 if (!log->logger_data) { | |
555 gaim_debug(GAIM_DEBUG_ERROR, "log", "Could not create log file %s\n", filename); | |
556 return; | |
4184 | 557 } |
7447 | 558 g_free(filename); |
7453 | 559 strftime(date, sizeof(date), "%Y-%m-%d %H:%M:%S", localtime(&log->time)); |
7431 | 560 fprintf(log->logger_data, "Conversation with %s at %s on %s (%s)\n", |
561 log->name, date, gaim_account_get_username(log->account), prpl); | |
562 } | |
7436 | 563 |
7453 | 564 strftime(date, sizeof(date), "%H:%M:%S", localtime(&time)); |
7431 | 565 stripped = gaim_markup_strip_html(message); |
7489 | 566 if (type & GAIM_MESSAGE_SEND || |
567 type & GAIM_MESSAGE_RECV) | |
568 fprintf(log->logger_data, "(%s) %s: %s\n", date, from, stripped); | |
569 else if (type & GAIM_MESSAGE_SYSTEM) | |
570 fprintf(log->logger_data, "(%s) %s\n", date, stripped); | |
571 else if (type & GAIM_MESSAGE_AUTO_RESP) | |
572 fprintf(log->logger_data, _("(%s) %s <AUTO-REPLY>: %s\n"), date, from, stripped); | |
573 else if (type & GAIM_MESSAGE_NO_LOG) { | |
574 /* This shouldn't happen */ | |
575 g_free(stripped); | |
576 return; | |
577 } else if (type & GAIM_MESSAGE_WHISPER) | |
578 fprintf(log->logger_data, "(%s) *%s* %s", date, from, stripped); | |
579 else | |
580 fprintf(log->logger_data, "(%s) %s%s %s\n", date, from ? from : "", from ? ":" : "", stripped); | |
581 | |
7431 | 582 fflush(log->logger_data); |
583 g_free(stripped); | |
584 } | |
585 | |
586 static void txt_logger_finalize(GaimLog *log) | |
587 { | |
588 if (log->logger_data) | |
589 fclose(log->logger_data); | |
590 } | |
591 | |
592 static GList *txt_logger_list(const char *sn, GaimAccount *account) | |
593 { | |
594 return log_lister_common(sn, account, ".txt", &txt_logger); | |
595 } | |
596 | |
597 static char *txt_logger_read(GaimLog *log, GaimLogReadFlags *flags) | |
598 { | |
599 char *read, *minus_header; | |
7457 | 600 *flags = 0; |
7431 | 601 if (!log->logger_data) |
7472 | 602 return g_strdup(_("<font color=\"red\"><b>log->logger_data was NULL!</b></font>")); |
7431 | 603 if (g_file_get_contents((char *)log->logger_data, &read, NULL, NULL)) { |
604 minus_header = strchr(read, '\n'); | |
605 if (!minus_header) | |
606 minus_header = g_strdup(read); | |
7436 | 607 else |
7431 | 608 minus_header = g_strdup(minus_header + 1); |
609 g_free(read); | |
610 return minus_header; | |
611 } | |
7471 | 612 return g_strdup(_("<font color=\"red\"><b>Could not read file: %s</b></font>")); |
7436 | 613 } |
7431 | 614 |
615 static GaimLogLogger txt_logger = { | |
616 N_("Plain text"), "txt", | |
617 NULL, | |
618 txt_logger_write, | |
619 txt_logger_finalize, | |
620 txt_logger_list, | |
621 txt_logger_read | |
622 }; | |
623 | |
624 /**************** | |
625 * OLD LOGGER *** | |
626 ****************/ | |
627 | |
628 /* The old logger doesn't write logs, only reads them. This is to include | |
629 * old logs in the log viewer transparently. | |
630 */ | |
631 | |
632 struct old_logger_data { | |
633 char *path; | |
634 int offset; | |
635 int length; | |
636 }; | |
637 | |
7436 | 638 static GList *old_logger_list(const char *sn, GaimAccount *account) |
7431 | 639 { |
640 FILE *file; | |
641 char buf[BUF_LONG]; | |
642 struct tm tm; | |
643 struct old_logger_data *data = NULL; | |
644 char day[4], month[4], year[5]; | |
645 char *logfile = g_strdup_printf("%s.log", gaim_normalize(account, sn)); | |
646 char *date; | |
647 char *path = g_build_filename(gaim_user_dir(), "logs", logfile, NULL); | |
648 char *newlog; | |
649 | |
650 GaimLog *log = NULL; | |
651 GList *list = NULL; | |
652 | |
7473 | 653 g_free(logfile); |
654 | |
7461 | 655 if (!(file = fopen(path, "rb"))) { |
7447 | 656 g_free(path); |
7431 | 657 return NULL; |
7447 | 658 } |
7436 | 659 |
7431 | 660 while (fgets(buf, BUF_LONG, file)) { |
661 if ((newlog = strstr(buf, "---- New C"))) { | |
662 int length; | |
663 int offset; | |
664 GDate gdate; | |
665 char convostart[32]; | |
666 char *temp = strchr(buf, '@'); | |
7436 | 667 |
7431 | 668 if (temp == NULL || strlen(temp) < 2) |
669 continue; | |
7436 | 670 |
7431 | 671 temp++; |
672 length = strcspn(temp, "-"); | |
673 if (length > 31) length = 31; | |
7436 | 674 |
7431 | 675 offset = ftell(file); |
7436 | 676 |
7431 | 677 if (data) { |
7436 | 678 data->length = offset - data->offset - length; |
679 if(strstr(buf, "----</H3><BR>")) { | |
680 data->length -= | |
681 strlen("<HR><BR><H3 Align=Center> ---- New Conversation @ ") + | |
682 strlen("----</H3><BR>"); | |
683 } else { | |
684 data->length -= | |
685 strlen("---- New Conversation @ ") + strlen("----"); | |
686 } | |
687 | |
7461 | 688 if(strchr(buf, '\r')) |
689 data->length--; | |
690 | |
7431 | 691 if (data->length != 0) |
692 list = g_list_append(list, log); | |
693 else | |
694 gaim_log_free(log); | |
695 } | |
696 | |
697 log = gaim_log_new(GAIM_LOG_IM, sn, account, -1); | |
698 log->logger = &old_logger; | |
699 | |
7436 | 700 data = g_new0(struct old_logger_data, 1); |
7431 | 701 data->offset = offset; |
702 data->path = path; | |
703 log->logger_data = data; | |
704 | |
7436 | 705 |
7431 | 706 g_snprintf(convostart, length, "%s", temp); |
707 sscanf(convostart, "%*s %s %s %d:%d:%d %s", | |
708 month, day, &tm.tm_hour, &tm.tm_min, &tm.tm_sec, year); | |
709 date = g_strdup_printf("%s %s %s", month, day, year); | |
710 g_date_set_parse(&gdate, date); | |
711 tm.tm_mday = g_date_get_day(&gdate); | |
712 tm.tm_mon = g_date_get_month(&gdate) - 1; | |
713 tm.tm_year = g_date_get_year(&gdate) - 1900; | |
714 log->time = mktime(&tm); | |
715 | |
4184 | 716 } |
717 } | |
7431 | 718 fclose(file); |
719 return list; | |
4184 | 720 } |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
721 |
7431 | 722 char * old_logger_read (GaimLog *log, GaimLogReadFlags *flags) |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
723 { |
7431 | 724 struct old_logger_data *data = log->logger_data; |
7461 | 725 FILE *file = fopen(data->path, "rb"); |
7431 | 726 char *read = g_malloc(data->length + 1); |
727 fseek(file, data->offset, SEEK_SET); | |
728 fread(read, data->length, 1, file); | |
729 read[data->length] = '\0'; | |
7436 | 730 *flags = 0; |
731 if(strstr(read, "<BR>")) | |
732 *flags |= GAIM_LOG_READ_NO_NEWLINE; | |
7431 | 733 return read; |
734 } | |
4359
5fb47ec9bfe4
[gaim-migrate @ 4625]
Christian Hammond <chipx86@chipx86.com>
parents:
4227
diff
changeset
|
735 |
7431 | 736 static GaimLogLogger old_logger = { |
737 "old logger", "old", | |
738 NULL, NULL, NULL, | |
739 old_logger_list, | |
740 old_logger_read | |
741 }; |