No issues found
1 /*
2 * This program is free software; you can redistribute it and/or
3 * modify it under the terms of the GNU Lesser General Public
4 * License as published by the Free Software Foundation; either
5 * version 2 of the License, or (at your option) version 3.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
10 * Lesser General Public License for more details.
11 *
12 * You should have received a copy of the GNU Lesser General Public
13 * License along with the program; if not, see <http://www.gnu.org/licenses/>
14 *
15 *
16 * Authors:
17 * David Trowbridge <trowbrds@cs.colorado.edu>
18 *
19 * Copyright (C) 1999-2008 Novell, Inc. (www.novell.com)
20 *
21 */
22
23 #ifdef HAVE_CONFIG_H
24 #include <config.h>
25 #endif
26
27 #include "url-editor-dialog.h"
28
29 #include <string.h>
30 #include <glib/gi18n.h>
31
32 #include <e-util/e-util.h>
33 #include <e-util/e-util-private.h>
34
35 #include <shell/e-shell.h>
36
37 G_DEFINE_TYPE (
38 UrlEditorDialog,
39 url_editor_dialog,
40 GTK_TYPE_DIALOG)
41
42 static void
43 create_uri (UrlEditorDialog *dialog)
44 {
45 EPublishUri *uri;
46
47 uri = dialog->uri;
48
49 if (uri->service_type == TYPE_URI) {
50 if (uri->location)
51 g_free (uri->location);
52 uri->location = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->server_entry)));
53 } else {
54 const gchar *method = "file";
55 gchar *server, *file, *port, *username, *password;
56
57 server = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->server_entry)));
58 file = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->file_entry)));
59 port = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->port_entry)));
60 username = g_uri_escape_string (gtk_entry_get_text (GTK_ENTRY (dialog->username_entry)), "", FALSE);
61 password = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->password_entry)));
62
63 switch (uri->service_type) {
64 case TYPE_SMB:
65 method = "smb";
66 break;
67
68 case TYPE_SFTP:
69 method = "sftp";
70 break;
71
72 case TYPE_ANON_FTP:
73 g_free (username);
74 username = g_strdup ("anonymous");
75 case TYPE_FTP:
76 method = "ftp";
77 break;
78
79 case TYPE_DAV:
80 method = "dav";
81 break;
82
83 case TYPE_DAVS:
84 method = "davs";
85 break;
86 }
87
88 if (uri->location)
89 g_free (uri->location);
90 uri->location = g_strdup_printf (
91 "%s://%s%s%s%s%s%s%s",
92 method,
93 username, (username[0] != '\0') ? "@" : "",
94 server,
95 (port[0] != '\0') ? ":" : "", port,
96 (file[0] != '/') ? "/" : "", file);
97
98 g_free (server);
99 g_free (file);
100 g_free (port);
101 g_free (username);
102 g_free (password);
103 }
104
105 uri->fb_duration_value = gtk_spin_button_get_value (GTK_SPIN_BUTTON (dialog->fb_duration_spin));
106 uri->fb_duration_type = gtk_combo_box_get_active (GTK_COMBO_BOX (dialog->fb_duration_combo));
107 }
108
109 static void
110 check_input (UrlEditorDialog *dialog)
111 {
112 gint n = 0;
113 GSList *sources;
114 EPublishUri *uri;
115
116 uri = dialog->uri;
117
118 if (gtk_combo_box_get_active (GTK_COMBO_BOX (dialog->type_selector)) == 1) {
119 gtk_widget_show (dialog->fb_duration_label);
120 gtk_widget_show (dialog->fb_duration_spin);
121 gtk_widget_show (dialog->fb_duration_combo);
122 } else {
123 gtk_widget_hide (dialog->fb_duration_label);
124 gtk_widget_hide (dialog->fb_duration_spin);
125 gtk_widget_hide (dialog->fb_duration_combo);
126 }
127
128 if (gtk_widget_get_sensitive (dialog->events_selector)) {
129 sources = e_source_selector_get_selection (E_SOURCE_SELECTOR (dialog->events_selector));
130 n += g_slist_length (sources);
131 }
132 if (n == 0)
133 goto fail;
134
135 /* This should probably be more complex, since ' ' isn't a valid server name */
136 switch (uri->service_type) {
137 case TYPE_SMB:
138 case TYPE_SFTP:
139 case TYPE_FTP:
140 case TYPE_DAV:
141 case TYPE_DAVS:
142 case TYPE_ANON_FTP:
143 if (!strlen (gtk_entry_get_text (GTK_ENTRY (dialog->server_entry)))) goto fail;
144 if (!strlen (gtk_entry_get_text (GTK_ENTRY (dialog->file_entry)))) goto fail;
145 break;
146 case TYPE_URI:
147 if (!strlen (gtk_entry_get_text (GTK_ENTRY (dialog->server_entry)))) goto fail;
148 break;
149 }
150
151 create_uri (dialog);
152
153 gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog), GTK_RESPONSE_OK, TRUE);
154 return;
155 fail:
156 gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog), GTK_RESPONSE_OK, FALSE);
157 }
158
159 static void
160 source_selection_changed (ESourceSelector *selector,
161 UrlEditorDialog *dialog)
162 {
163 check_input (dialog);
164 }
165
166 static void
167 publish_service_changed (GtkComboBox *combo,
168 UrlEditorDialog *dialog)
169 {
170 gint selected = gtk_combo_box_get_active (combo);
171 EPublishUri *uri;
172
173 uri = dialog->uri;
174
175 /* Big mess that switches around all the fields to match the source type
176 * the user has selected. Tries to keep field contents where possible */
177 switch (selected) {
178 case TYPE_SMB:
179 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->server_label), "_Server:");
180 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->port_label), "_Port:");
181 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->port_label), "S_hare:");
182 gtk_entry_set_text (GTK_ENTRY (dialog->port_entry), "");
183 gtk_widget_show (dialog->file_hbox);
184 gtk_widget_show (dialog->optional_label);
185 gtk_widget_show (dialog->port_hbox);
186 gtk_widget_show (dialog->username_hbox);
187 gtk_widget_show (dialog->password_hbox);
188 gtk_widget_show (dialog->remember_pw);
189 break;
190 case TYPE_SFTP:
191 case TYPE_FTP:
192 case TYPE_DAV:
193 case TYPE_DAVS:
194 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->server_label), "_Server:");
195 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->port_label), "_Port:");
196 if (uri->service_type == TYPE_SMB)
197 gtk_entry_set_text (GTK_ENTRY (dialog->port_entry), "");
198 else if (uri->service_type == TYPE_URI)
199 gtk_entry_set_text (GTK_ENTRY (dialog->server_entry), "");
200 gtk_widget_show (dialog->file_hbox);
201 gtk_widget_show (dialog->optional_label);
202 gtk_widget_show (dialog->port_hbox);
203 gtk_widget_show (dialog->username_hbox);
204 gtk_widget_show (dialog->password_hbox);
205 gtk_widget_show (dialog->remember_pw);
206 break;
207 case TYPE_ANON_FTP:
208 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->server_label), "_Server:");
209 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->port_label), "_Port:");
210 if (uri->service_type == TYPE_SMB)
211 gtk_entry_set_text (GTK_ENTRY (dialog->port_entry), "");
212 else if (uri->service_type == TYPE_URI)
213 gtk_entry_set_text (GTK_ENTRY (dialog->server_entry), "");
214 gtk_widget_show (dialog->file_hbox);
215 gtk_widget_show (dialog->optional_label);
216 gtk_widget_show (dialog->port_hbox);
217 gtk_widget_hide (dialog->username_hbox);
218 gtk_widget_hide (dialog->password_hbox);
219 gtk_widget_hide (dialog->remember_pw);
220 break;
221 case TYPE_URI:
222 gtk_label_set_text_with_mnemonic (GTK_LABEL (dialog->server_label), "_Location (URI):");
223 if (uri->service_type != TYPE_URI)
224 gtk_entry_set_text (GTK_ENTRY (dialog->server_entry), "");
225 gtk_widget_hide (dialog->file_hbox);
226 gtk_widget_hide (dialog->optional_label);
227 gtk_widget_hide (dialog->port_hbox);
228 gtk_widget_hide (dialog->username_hbox);
229 gtk_widget_hide (dialog->password_hbox);
230 gtk_widget_hide (dialog->remember_pw);
231 }
232 uri->service_type = selected;
233 check_input (dialog);
234 }
235
236 static void
237 type_selector_changed (GtkComboBox *combo,
238 UrlEditorDialog *dialog)
239 {
240 gint selected = gtk_combo_box_get_active (combo);
241 EPublishUri *uri;
242
243 uri = dialog->uri;
244 uri->publish_format = selected;
245
246 check_input (dialog);
247 }
248
249 static void
250 frequency_changed_cb (GtkComboBox *combo,
251 UrlEditorDialog *dialog)
252 {
253 gint selected = gtk_combo_box_get_active (combo);
254
255 EPublishUri *uri;
256
257 uri = dialog->uri;
258 uri->publish_frequency = selected;
259 }
260
261 static void
262 server_entry_changed (GtkEntry *entry,
263 UrlEditorDialog *dialog)
264 {
265 check_input (dialog);
266 }
267
268 static void
269 file_entry_changed (GtkEntry *entry,
270 UrlEditorDialog *dialog)
271 {
272 check_input (dialog);
273 }
274
275 static void
276 port_entry_changed (GtkEntry *entry,
277 UrlEditorDialog *dialog)
278 {
279 }
280
281 static void
282 username_entry_changed (GtkEntry *entry,
283 UrlEditorDialog *dialog)
284 {
285 }
286
287 static void
288 password_entry_changed (GtkEntry *entry,
289 UrlEditorDialog *dialog)
290 {
291 }
292
293 static void
294 remember_pw_toggled (GtkToggleButton *toggle,
295 UrlEditorDialog *dialog)
296 {
297 }
298
299 static void
300 set_from_uri (UrlEditorDialog *dialog)
301 {
302 EPublishUri *uri;
303 SoupURI *soup_uri;
304 const gchar *scheme;
305 const gchar *user;
306 const gchar *host;
307 const gchar *path;
308 guint port;
309
310 uri = dialog->uri;
311
312 soup_uri = soup_uri_new (uri->location);
313 g_return_if_fail (soup_uri != NULL);
314
315 /* determine our service type */
316 scheme = soup_uri_get_scheme (soup_uri);
317 g_return_if_fail (scheme != NULL);
318
319 if (strcmp (scheme, "smb") == 0)
320 uri->service_type = TYPE_SMB;
321 else if (strcmp (scheme, "sftp") == 0)
322 uri->service_type = TYPE_SFTP;
323 else if (strcmp (scheme, "ftp") == 0)
324 /* we set TYPE_FTP here for now. if we don't find a
325 * username later, we'll change it to TYPE_ANON_FTP */
326 uri->service_type = TYPE_FTP;
327 else if (strcmp (scheme, "dav") == 0)
328 uri->service_type = TYPE_DAV;
329 else if (strcmp (scheme, "davs") == 0)
330 uri->service_type = TYPE_DAVS;
331 else
332 uri->service_type = TYPE_URI;
333
334 user = soup_uri_get_user (soup_uri);
335 host = soup_uri_get_host (soup_uri);
336 port = soup_uri_get_port (soup_uri);
337 path = soup_uri_get_path (soup_uri);
338
339 if (user != NULL)
340 gtk_entry_set_text (GTK_ENTRY (dialog->username_entry), user);
341
342 if (host != NULL)
343 gtk_entry_set_text (GTK_ENTRY (dialog->server_entry), host);
344
345 if (port > 0) {
346 gchar *port_str;
347 port_str = g_strdup_printf ("%d", port);
348 gtk_entry_set_text (GTK_ENTRY (dialog->port_entry), port_str);
349 g_free (port_str);
350 }
351
352 if (path != NULL)
353 gtk_entry_set_text (GTK_ENTRY (dialog->file_entry), path);
354
355 if (uri->service_type == TYPE_URI)
356 gtk_entry_set_text (GTK_ENTRY (dialog->server_entry), uri->location);
357
358 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->publish_service), uri->service_type);
359
360 soup_uri_free (soup_uri);
361 }
362
363 static gboolean
364 url_editor_dialog_construct (UrlEditorDialog *dialog)
365 {
366 EShell *shell;
367 GtkWidget *toplevel;
368 GtkWidget *content_area;
369 GtkSizeGroup *group;
370 EPublishUri *uri;
371 ESourceRegistry *registry;
372
373 dialog->builder = gtk_builder_new ();
374 e_load_ui_builder_definition (dialog->builder, "publish-calendar.ui");
375
376 #define GW(name) ((dialog->name) = e_builder_get_widget (dialog->builder, #name))
377 GW (type_selector);
378 GW (fb_duration_label);
379 GW (fb_duration_spin);
380 GW (fb_duration_combo);
381 GW (publish_frequency);
382
383 GW (events_swin);
384
385 GW (publish_service);
386 GW (server_entry);
387 GW (file_entry);
388
389 GW (port_entry);
390 GW (username_entry);
391 GW (password_entry);
392 GW (remember_pw);
393
394 GW (optional_label);
395
396 GW (port_hbox);
397 GW (username_hbox);
398 GW (password_hbox);
399 GW (server_hbox);
400 GW (file_hbox);
401
402 GW (port_label);
403 GW (username_label);
404 GW (password_label);
405 GW (server_label);
406 GW (file_label);
407 #undef GW
408
409 uri = dialog->uri;
410
411 content_area = gtk_dialog_get_content_area (GTK_DIALOG (dialog));
412 toplevel = e_builder_get_widget (dialog->builder, "publishing toplevel");
413 gtk_container_add (GTK_CONTAINER (content_area), toplevel);
414
415 gtk_container_set_border_width (GTK_CONTAINER (dialog), 6);
416
417 dialog->cancel = gtk_dialog_add_button (GTK_DIALOG (dialog), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL);
418 dialog->ok = gtk_dialog_add_button (GTK_DIALOG (dialog), GTK_STOCK_OK, GTK_RESPONSE_OK);
419 gtk_dialog_set_default_response (GTK_DIALOG (dialog), GTK_RESPONSE_OK);
420 gtk_window_set_modal (GTK_WINDOW (dialog), TRUE);
421 gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog), GTK_RESPONSE_OK, FALSE);
422
423 shell = e_shell_get_default ();
424 registry = e_shell_get_registry (shell);
425 dialog->events_selector = e_source_selector_new (
426 registry, E_SOURCE_EXTENSION_CALENDAR);
427 gtk_widget_show (dialog->events_selector);
428 gtk_container_add (GTK_CONTAINER (dialog->events_swin), dialog->events_selector);
429
430 group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
431 gtk_size_group_add_widget (group, dialog->type_selector);
432 gtk_size_group_add_widget (group, dialog->publish_frequency);
433 g_object_unref (group);
434
435 group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
436 gtk_size_group_add_widget (group, dialog->publish_service);
437 gtk_size_group_add_widget (group, dialog->server_entry);
438 gtk_size_group_add_widget (group, dialog->file_entry);
439 gtk_size_group_add_widget (group, dialog->port_entry);
440 gtk_size_group_add_widget (group, dialog->username_entry);
441 gtk_size_group_add_widget (group, dialog->password_entry);
442 g_object_unref (group);
443
444 if (uri == NULL) {
445 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->publish_frequency), 0);
446 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->type_selector), 0);
447 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->publish_service), 0);
448
449 dialog->uri = g_new0 (EPublishUri, 1);
450 uri = dialog->uri;
451 uri->enabled = TRUE;
452 } else {
453 ESource *source;
454 GSList *p;
455
456 for (p = uri->events; p; p = g_slist_next (p)) {
457 const gchar *uid = p->data;
458
459 source = e_source_registry_ref_source (
460 registry, uid);
461 e_source_selector_select_source (
462 E_SOURCE_SELECTOR (dialog->events_selector),
463 source);
464 g_object_unref (source);
465 }
466
467 if (uri->location && strlen (uri->location)) {
468 set_from_uri (dialog);
469 }
470
471 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->publish_frequency), uri->publish_frequency);
472 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->type_selector), uri->publish_format);
473
474 uri->password = e_passwords_get_password (NULL, uri->location);
475 if (uri->password) {
476 if (strlen (uri->password) != 0) {
477 gtk_entry_set_text (GTK_ENTRY (dialog->password_entry), uri->password);
478 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (dialog->remember_pw), TRUE);
479 } else {
480 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (dialog->remember_pw), FALSE);
481 }
482 }
483 }
484
485 gtk_spin_button_set_value (GTK_SPIN_BUTTON (dialog->fb_duration_spin), uri->fb_duration_value);
486 gtk_combo_box_set_active (GTK_COMBO_BOX (dialog->fb_duration_combo), uri->fb_duration_type);
487
488 type_selector_changed (GTK_COMBO_BOX (dialog->type_selector), dialog);
489 frequency_changed_cb (GTK_COMBO_BOX (dialog->publish_frequency), dialog);
490 publish_service_changed (GTK_COMBO_BOX (dialog->publish_service), dialog);
491
492 g_signal_connect (
493 dialog->publish_service, "changed",
494 G_CALLBACK (publish_service_changed), dialog);
495 g_signal_connect (
496 dialog->type_selector, "changed",
497 G_CALLBACK (type_selector_changed), dialog);
498 g_signal_connect (
499 dialog->publish_frequency, "changed",
500 G_CALLBACK (frequency_changed_cb), dialog);
501 g_signal_connect (
502 dialog->events_selector, "selection_changed",
503 G_CALLBACK (source_selection_changed), dialog);
504
505 g_signal_connect (
506 dialog->server_entry, "changed",
507 G_CALLBACK (server_entry_changed), dialog);
508 g_signal_connect (
509 dialog->file_entry, "changed",
510 G_CALLBACK (file_entry_changed), dialog);
511 g_signal_connect (
512 dialog->port_entry, "changed",
513 G_CALLBACK (port_entry_changed), dialog);
514 g_signal_connect (
515 dialog->username_entry, "changed",
516 G_CALLBACK (username_entry_changed), dialog);
517 g_signal_connect (
518 dialog->password_entry,"changed",
519 G_CALLBACK (password_entry_changed), dialog);
520 g_signal_connect (
521 dialog->remember_pw, "toggled",
522 G_CALLBACK (remember_pw_toggled), dialog);
523
524 check_input (dialog);
525
526 return TRUE;
527 }
528
529 GtkWidget *
530 url_editor_dialog_new (GtkTreeModel *url_list_model,
531 EPublishUri *uri)
532 {
533 UrlEditorDialog *dialog;
534
535 dialog = (UrlEditorDialog *) g_object_new (URL_EDITOR_DIALOG_TYPE, NULL);
536 dialog->url_list_model = g_object_ref (url_list_model);
537 dialog->uri = uri;
538
539 if (!uri)
540 gtk_window_set_title (GTK_WINDOW (dialog), _("New Location"));
541 else
542 gtk_window_set_title (GTK_WINDOW (dialog), _("Edit Location"));
543
544 if (url_editor_dialog_construct (dialog))
545 return GTK_WIDGET (dialog);
546
547 g_object_unref (dialog);
548 return NULL;
549 }
550
551 static void
552 url_editor_dialog_dispose (GObject *obj)
553 {
554 UrlEditorDialog *dialog = (UrlEditorDialog *) obj;
555
556 if (dialog->url_list_model) {
557 g_object_unref (dialog->url_list_model);
558 dialog->url_list_model = NULL;
559 }
560 if (dialog->builder) {
561 g_object_unref (dialog->builder);
562 dialog->builder = NULL;
563 }
564
565 G_OBJECT_CLASS (url_editor_dialog_parent_class)->dispose (obj);
566 }
567
568 static void
569 url_editor_dialog_class_init (UrlEditorDialogClass *class)
570 {
571 GObjectClass *object_class;
572
573 object_class = G_OBJECT_CLASS (class);
574 object_class->dispose = url_editor_dialog_dispose;
575 }
576
577 static void
578 url_editor_dialog_init (UrlEditorDialog *dialog)
579 {
580 }
581
582 gboolean
583 url_editor_dialog_run (UrlEditorDialog *dialog)
584 {
585 gint response;
586
587 response = gtk_dialog_run (GTK_DIALOG (dialog));
588 if (response == GTK_RESPONSE_OK) {
589 GSList *l, *p;
590
591 if (dialog->uri->password)
592 g_free (dialog->uri->password);
593 if (dialog->uri->events) {
594 g_slist_foreach (dialog->uri->events, (GFunc) g_free, NULL);
595 dialog->uri->events = NULL;
596 }
597
598 create_uri (dialog);
599
600 dialog->uri->password = g_strdup (gtk_entry_get_text (GTK_ENTRY (dialog->password_entry)));
601
602 if (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (dialog->remember_pw))) {
603 e_passwords_add_password (dialog->uri->location, dialog->uri->password);
604 e_passwords_remember_password (NULL, dialog->uri->location);
605 } else {
606 e_passwords_forget_password (NULL, dialog->uri->location);
607 }
608
609 l = e_source_selector_get_selection (E_SOURCE_SELECTOR (dialog->events_selector));
610 for (p = l; p; p = g_slist_next (p)) {
611 ESource *source;
612 const gchar *uid;
613
614 source = E_SOURCE (p->data);
615 uid = e_source_get_uid (source);
616 dialog->uri->events = g_slist_append (
617 dialog->uri->events, g_strdup (uid));
618 }
619 }
620 gtk_widget_hide (GTK_WIDGET (dialog));
621
622 return response == GTK_RESPONSE_OK;
623 }