void screenshooter_job_image_uploaded (ScreenshooterJob *job, const gchar *file_name, const gchar *delete_hash) { g_return_if_fail (SCREENSHOOTER_IS_JOB (job)); TRACE ("Emit image-uploaded signal."); exo_job_emit (EXO_JOB (job), job_signals[IMAGE_UPLOADED], 0, file_name, delete_hash); }
void screenshooter_job_ask_info (ScreenshooterJob *job, GtkListStore *info, const gchar *format, ...) { va_list va_args; gchar *message; g_return_if_fail (SCREENSHOOTER_IS_JOB (job)); g_return_if_fail (GTK_IS_LIST_STORE (info)); g_return_if_fail (format != NULL); if (G_UNLIKELY (exo_job_is_cancelled (EXO_JOB (job)))) return; va_start (va_args, format); message = g_strdup_vprintf (format, va_args); va_end (va_args); exo_job_emit (EXO_JOB (job), job_signals[ASK], 0, info, message); g_free (message); }
void cb_ask_for_information (ScreenshooterJob *job, GtkListStore *liststore, const gchar *message, gpointer unused) { GtkWidget *dialog; GtkWidget *information_label; GtkWidget *vbox, *main_alignment; GtkWidget *table; GtkWidget *user_entry, *password_entry, *title_entry, *comment_entry; GtkWidget *user_label, *password_label, *title_label, *comment_label; GtkTreeIter iter; gint response; g_return_if_fail (SCREENSHOOTER_IS_JOB (job)); g_return_if_fail (GTK_IS_LIST_STORE (liststore)); g_return_if_fail (message != NULL); TRACE ("Create the dialog to ask for user information."); /* Create the information dialog */ dialog = xfce_titled_dialog_new_with_buttons (_("Details about the screenshot for ZimageZ"), NULL, GTK_DIALOG_NO_SEPARATOR, GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_OK, GTK_RESPONSE_OK, NULL); gtk_window_set_position (GTK_WINDOW (dialog), GTK_WIN_POS_CENTER); gtk_box_set_spacing (GTK_BOX (GTK_DIALOG(dialog)->vbox), 12); gtk_window_set_icon_name (GTK_WINDOW (dialog), "gtk-info"); gtk_window_set_resizable (GTK_WINDOW (dialog), FALSE); gtk_dialog_set_default_response (GTK_DIALOG (dialog), GTK_RESPONSE_OK); /* Create the main alignment for the dialog */ main_alignment = gtk_alignment_new (0, 0, 1, 1); gtk_alignment_set_padding (GTK_ALIGNMENT (main_alignment), 6, 0, 12, 12); gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dialog)->vbox), main_alignment, TRUE, TRUE, 0); /* Create the main box for the dialog */ vbox = gtk_vbox_new (FALSE, 10); gtk_container_set_border_width (GTK_CONTAINER (vbox), 12); gtk_container_add (GTK_CONTAINER (main_alignment), vbox); /* Create the information label */ information_label = gtk_label_new (""); gtk_label_set_markup (GTK_LABEL (information_label), message); gtk_misc_set_alignment (GTK_MISC (information_label), 0, 0); gtk_container_add (GTK_CONTAINER (vbox), information_label); /* Create the layout table */ table = gtk_table_new (4, 2, FALSE); gtk_table_set_col_spacings (GTK_TABLE (table), 6); gtk_table_set_row_spacings (GTK_TABLE (table), 12); gtk_container_add (GTK_CONTAINER (vbox), table); /* Create the user label */ user_label = gtk_label_new (_("User:"******"Your Zimagez user name, if you do not have one yet" " please create one on the Web page linked above")); gtk_entry_set_activates_default (GTK_ENTRY (user_entry), TRUE); gtk_table_attach_defaults (GTK_TABLE (table), user_entry, 1, 2, 0, 1); /* Create the password label */ password_label = gtk_label_new (_("Password:"******"The password for the user above")); gtk_entry_set_visibility (GTK_ENTRY (password_entry), FALSE); gtk_entry_set_activates_default (GTK_ENTRY (password_entry), TRUE); gtk_table_attach_defaults (GTK_TABLE (table), password_entry, 1, 2, 1, 2); /* Create the title label */ title_label = gtk_label_new (_("Title:")); gtk_misc_set_alignment (GTK_MISC (title_label), 0, 0.5); gtk_table_attach (GTK_TABLE (table), title_label, 0, 1, 2, 3, GTK_FILL, GTK_FILL, 0, 0); /* Create the title entry */ title_entry = gtk_entry_new (); gtk_widget_set_tooltip_text (title_entry, _("The title of the screenshot, it will be used when" " displaying the screenshot on ZimageZ")); gtk_entry_set_activates_default (GTK_ENTRY (title_entry), TRUE); gtk_table_attach_defaults (GTK_TABLE (table), title_entry, 1, 2, 2, 3); /* Create the comment label */ comment_label = gtk_label_new (_("Comment:")); gtk_misc_set_alignment (GTK_MISC (comment_label), 0, 0.5); gtk_table_attach (GTK_TABLE (table), comment_label, 0, 1, 3, 4, GTK_FILL, GTK_FILL, 0, 0); /* Create the comment entry */ comment_entry = gtk_entry_new (); gtk_widget_set_tooltip_text (comment_entry, _("A comment on the screenshot, it will be used when" " displaying the screenshot on ZimageZ")); gtk_entry_set_activates_default (GTK_ENTRY (comment_entry), TRUE); gtk_table_attach_defaults (GTK_TABLE (table), comment_entry, 1, 2, 3, 4); /* Set the values */ gtk_tree_model_get_iter_first (GTK_TREE_MODEL (liststore), &iter); do { gint field_index; gchar *field_value = NULL; gtk_tree_model_get (GTK_TREE_MODEL (liststore), &iter, 0, &field_index, 1, &field_value, -1); switch (field_index) { case USER: gtk_entry_set_text (GTK_ENTRY (user_entry), field_value); break; case PASSWORD: gtk_entry_set_text (GTK_ENTRY (password_entry), field_value); break; case TITLE: gtk_entry_set_text (GTK_ENTRY (title_entry), field_value); break; case COMMENT: gtk_entry_set_text (GTK_ENTRY (comment_entry), field_value); break; default: break; } g_free (field_value); } while (gtk_tree_model_iter_next (GTK_TREE_MODEL (liststore), &iter)); gtk_widget_show_all (GTK_DIALOG(dialog)->vbox); response = gtk_dialog_run (GTK_DIALOG (dialog)); gtk_widget_hide (dialog); if (response == GTK_RESPONSE_CANCEL || response == GTK_RESPONSE_DELETE_EVENT) { exo_job_cancel (EXO_JOB (job)); } else if (response == GTK_RESPONSE_OK) { gtk_tree_model_get_iter_first (GTK_TREE_MODEL (liststore), &iter); do { gint field_index; gtk_tree_model_get (GTK_TREE_MODEL (liststore), &iter, 0, &field_index, -1); switch (field_index) { case USER: gtk_list_store_set (liststore, &iter, 1, gtk_entry_get_text (GTK_ENTRY (user_entry)), -1); break; case PASSWORD: gtk_list_store_set (liststore, &iter, 1, gtk_entry_get_text (GTK_ENTRY (password_entry)), -1); break; case TITLE: gtk_list_store_set (liststore, &iter, 1, gtk_entry_get_text (GTK_ENTRY (title_entry)), -1); break; case COMMENT: gtk_list_store_set (liststore, &iter, 1, gtk_entry_get_text (GTK_ENTRY (comment_entry)), -1); break; default: break; } } while (gtk_tree_model_iter_next (GTK_TREE_MODEL (liststore), &iter)); } gtk_widget_destroy (dialog); }
GList * thunar_io_scan_directory (ThunarJob *job, GFile *file, GFileQueryInfoFlags flags, gboolean recursively, gboolean unlinking, GError **error) { GFileEnumerator *enumerator; GFileInfo *info; GFileType type; GError *err = NULL; GFile *child_file; GList *child_files = NULL; GList *files = NULL; _thunar_return_val_if_fail (THUNAR_IS_JOB (job), NULL); _thunar_return_val_if_fail (G_IS_FILE (file), NULL); _thunar_return_val_if_fail (error == NULL || *error == NULL, NULL); /* abort if the job was cancelled */ if (exo_job_set_error_if_cancelled (EXO_JOB (job), error)) return NULL; /* don't recurse when we are scanning prior to unlinking and the current * file/dir is in the trash. In GVfs, only the top-level directories in * the trash can be modified and deleted directly. See * http://bugzilla.xfce.org/show_bug.cgi?id=7147 * for more information */ if (unlinking && thunar_g_file_is_trashed (file) && !thunar_g_file_is_root (file)) { return NULL; } /* query the file type */ type = g_file_query_file_type (file, flags, exo_job_get_cancellable (EXO_JOB (job))); /* abort if the job was cancelled */ if (exo_job_set_error_if_cancelled (EXO_JOB (job), error)) return NULL; /* ignore non-directory nodes */ if (type != G_FILE_TYPE_DIRECTORY) return NULL; /* try to read from the direectory */ enumerator = g_file_enumerate_children (file, G_FILE_ATTRIBUTE_STANDARD_TYPE "," G_FILE_ATTRIBUTE_STANDARD_NAME, flags, exo_job_get_cancellable (EXO_JOB (job)), &err); /* abort if there was an error or the job was cancelled */ if (err != NULL) { g_propagate_error (error, err); return NULL; } /* query info of the first child */ info = g_file_enumerator_next_file (enumerator, exo_job_get_cancellable (EXO_JOB (job)), &err); /* iterate over children one by one as long as there's no error */ while (info != NULL && err == NULL && !exo_job_is_cancelled (EXO_JOB (job))) { /* create GFile for the child and prepend it to the file list */ child_file = g_file_get_child (file, g_file_info_get_name (info)); files = thunar_g_file_list_prepend (files, child_file); /* if the child is a directory and we need to recurse ... just do so */ if (recursively && g_file_info_get_file_type (info) == G_FILE_TYPE_DIRECTORY) { child_files = thunar_io_scan_directory (job, child_file, flags, recursively, unlinking, &err); /* prepend children to the file list to make sure they're * processed first (required for unlinking) */ files = g_list_concat (child_files, files); } g_object_unref (child_file); g_object_unref (info); info = g_file_enumerator_next_file (enumerator, exo_job_get_cancellable (EXO_JOB (job)), &err); } /* release the enumerator */ g_object_unref (enumerator); if (G_UNLIKELY (err != NULL)) { g_propagate_error (error, err); thunar_g_file_list_free (files); return NULL; } else if (exo_job_set_error_if_cancelled (EXO_JOB (job), &err)) { g_propagate_error (error, err); thunar_g_file_list_free (files); return NULL; } return files; }
static gboolean zimagez_upload_job (ScreenshooterJob *job, GArray *param_values, GError **error) { const gchar *encoded_data; const gchar *image_path; const gchar *last_user; const gchar *proxy_uri; /* For translators: the first wildcard is the date, the second one the time, * e.g. "Taken on 12/31/99, at 23:13:48". */ gchar *comment = screenshooter_get_datetime (_("Taken on %x, at %X")); gchar *data = NULL; gchar *encoded_password = NULL; gchar *file_name = NULL; gchar *login_response = NULL; gchar *online_file_name = NULL; gchar *password = g_strdup (""); gchar *title; gchar *user; gsize data_length; gboolean response = FALSE; const gchar *serverurl = "http://www.zimagez.com/apiXml.php"; const gchar *method_login = "******"; const gchar *method_logout = "apiXml.xmlrpcLogout"; const gchar *method_upload = "apiXml.xmlrpcUpload"; SoupSession *session; SoupURI *soup_proxy_uri; GError *tmp_error = NULL; GtkTreeIter iter; GtkListStore *liststore; GValue response_value; g_return_val_if_fail (SCREENSHOOTER_IS_JOB (job), FALSE); g_return_val_if_fail (param_values != NULL, FALSE); g_return_val_if_fail (param_values->len == 3, FALSE); g_return_val_if_fail (G_VALUE_HOLDS_STRING (&g_array_index (param_values, GValue, 0)), FALSE); g_return_val_if_fail (G_VALUE_HOLDS_STRING (&g_array_index (param_values, GValue, 1)), FALSE); g_return_val_if_fail (G_VALUE_HOLDS_STRING (&g_array_index (param_values, GValue, 2)), FALSE); g_return_val_if_fail (error == NULL || *error == NULL, FALSE); g_object_set_data (G_OBJECT (job), "jobtype", "zimagez"); if (exo_job_set_error_if_cancelled (EXO_JOB (job), error)) { g_free (comment); g_free (password); return FALSE; } /* Get the last user */ last_user = g_value_get_string (&g_array_index (param_values, GValue, 1)); user = g_strdup (last_user); if (user == NULL) user = g_strdup (""); if (!g_utf8_validate (user, -1, NULL)) { g_free (user); user = g_strdup (""); } g_object_set_data_full (G_OBJECT (job), "user", g_strdup (user), (GDestroyNotify) g_free); /* Get the default title */ title = g_strdup (g_value_get_string (&g_array_index (param_values, GValue, 2))); if (title == NULL) title = g_strdup (""); if (!g_utf8_validate (title, -1, NULL)) { g_free (title); title = g_strdup (""); } /* Get the path of the image that is to be uploaded */ image_path = g_value_get_string (&g_array_index (param_values, GValue, 0)); /* Start the user soup session */ exo_job_info_message (EXO_JOB (job), _("Initialize the connection...")); session = soup_session_sync_new (); /* Set the proxy URI if any */ proxy_uri = g_getenv ("http_proxy"); if (proxy_uri != NULL) { soup_proxy_uri = soup_uri_new (proxy_uri); g_object_set (session, "proxy-uri", soup_proxy_uri, NULL); soup_uri_free (soup_proxy_uri); } TRACE ("Get the information liststore ready."); liststore = gtk_list_store_new (2, G_TYPE_INT, G_TYPE_STRING); TRACE ("Append the user"); gtk_list_store_append (liststore, &iter); gtk_list_store_set (liststore, &iter, 0, USER, 1, user, -1); TRACE ("Append the password"); gtk_list_store_append (liststore, &iter); gtk_list_store_set (liststore, &iter, 0, PASSWORD, 1, password, -1); TRACE ("Append the title"); gtk_list_store_append (liststore, &iter); gtk_list_store_set (liststore, &iter, 0, TITLE, 1, title, -1); TRACE ("Append the comment"); gtk_list_store_append (liststore, &iter); gtk_list_store_set (liststore, &iter, 0, COMMENT, 1, comment, -1); TRACE ("Ask the user to fill the information items."); screenshooter_job_ask_info (job, liststore, _("Please fill the following fields with your " "<a href=\"http://www.zimagez.com\">ZimageZ</a> \n" "user name, passsword and details about the screenshot.")); gtk_tree_model_get_iter_first (GTK_TREE_MODEL (liststore), &iter); do { gint field_index; gchar *field_value = NULL; gtk_tree_model_get (GTK_TREE_MODEL (liststore), &iter, 0, &field_index, 1, &field_value, -1); switch (field_index) { case USER: user = g_strdup (field_value); break; case PASSWORD: password = g_strdup (field_value); break; case TITLE: title = g_strdup (field_value); break; case COMMENT: comment = g_strdup (field_value); break; default: break; } g_free (field_value); } while (gtk_tree_model_iter_next (GTK_TREE_MODEL (liststore), &iter)); while (!response) { if (exo_job_set_error_if_cancelled (EXO_JOB (job), error)) { soup_session_abort (session); g_object_unref (session); g_free (user); g_free (password); g_free (title); g_free (comment); if (encoded_password != NULL) g_free (encoded_password); TRACE ("The upload job was cancelled."); return FALSE; } exo_job_info_message (EXO_JOB (job), _("Check the user information...")); /* Test if one of the information fields is empty */ if (has_empty_field (liststore)) { TRACE ("One of the fields was empty, let the user file it."); screenshooter_job_ask_info (job, liststore, _("<span weight=\"bold\" foreground=\"darkred\" " "stretch=\"semiexpanded\">You must fill all the " "fields.</span>")); continue; } encoded_password = g_utf8_strreverse (rot13 (password), -1); TRACE ("User: %s", user); TRACE ("Encoded password: %s", encoded_password); /* Start the user session */ TRACE ("Call the login method"); exo_job_info_message (EXO_JOB (job), _("Login on ZimageZ...")); if (!do_xmlrpc (session, serverurl, method_login, &tmp_error, &response_value, G_TYPE_STRING, user, G_TYPE_STRING, encoded_password, G_TYPE_INVALID)) { g_propagate_error (error, tmp_error); soup_session_abort (session); g_object_unref (session); g_free (password); g_free (title); g_free (comment); g_free (encoded_password); return FALSE; } TRACE ("Read the login response"); /* If the response is a boolean, there was an error */ if (G_VALUE_HOLDS_BOOLEAN (&response_value)) { response = g_value_get_boolean (&response_value); } /* Else we read the string response to get the session ID */ else if (G_VALUE_HOLDS_STRING (&response_value)) { TRACE ("Read the session ID"); login_response = g_strdup (g_value_get_string (&response_value)); response = TRUE; } /* We received an unexpected reply */ else { GError *tmp_err = g_error_new (SOUP_XMLRPC_FAULT, SOUP_XMLRPC_FAULT_PARSE_ERROR_NOT_WELL_FORMED, "%s", _("An unexpected reply from ZimageZ was received." " The upload of the screenshot failed.")); soup_session_abort (session); g_object_unref (session); g_free (user); g_free (password); g_free (title); g_free (comment); g_free (encoded_password); g_propagate_error (error, tmp_err); return FALSE; } g_value_unset (&response_value); if (!response) { /* Login failed, erase the password and ask for the correct on to the user */ gtk_tree_model_get_iter_first (GTK_TREE_MODEL (liststore), &iter); do { gint field_index; gtk_tree_model_get (GTK_TREE_MODEL (liststore), &iter, 0, &field_index, -1); if (field_index == PASSWORD) { gtk_list_store_set (liststore, &iter, 1, g_strdup (""), -1); break; } } while (gtk_tree_model_iter_next (GTK_TREE_MODEL (liststore), &iter)); screenshooter_job_ask_info (job, liststore, _("<span weight=\"bold\" foreground=\"darkred\" " "stretch=\"semiexpanded\">The user and the " "password you entered do not match. " "Please retry.</span>")); gtk_tree_model_get_iter_first (GTK_TREE_MODEL (liststore), &iter); do { gint field_index; gchar *field_value = NULL; gtk_tree_model_get (GTK_TREE_MODEL (liststore), &iter, 0, &field_index, 1, &field_value, -1); switch (field_index) { case USER: user = g_strdup (field_value); break; case PASSWORD: password = g_strdup (field_value); break; case TITLE: title = g_strdup (field_value); break; case COMMENT: comment = g_strdup (field_value); break; default: break; } g_free (field_value); } while (gtk_tree_model_iter_next (GTK_TREE_MODEL (liststore), &iter)); } } g_object_set_data_full (G_OBJECT (job), "user", g_strdup (user), (GDestroyNotify) g_free); g_free (user); g_free (password); g_free (encoded_password); /* Get the contents of the image file and encode it to base64 */ g_file_get_contents (image_path, &data, &data_length, NULL); encoded_data = g_base64_encode ((guchar*)data, data_length); g_free (data); /* Get the basename of the image path */ file_name = g_path_get_basename (image_path); exo_job_info_message (EXO_JOB (job), _("Upload the screenshot...")); TRACE ("Call the upload method"); do_xmlrpc (session, serverurl, method_upload, &tmp_error, &response_value, G_TYPE_STRING, encoded_data, G_TYPE_STRING, file_name, G_TYPE_STRING, title, G_TYPE_STRING, comment, G_TYPE_STRING, login_response, G_TYPE_INVALID); g_free (title); g_free (comment); g_free (file_name); if (tmp_error) { soup_session_abort (session); g_object_unref (session); g_propagate_error (error, tmp_error); return FALSE; } /* If the response is a boolean, there was an error */ if (G_VALUE_HOLDS_BOOLEAN (&response_value)) { if (!g_value_get_boolean (&response_value)) { GError *tmp_err = g_error_new (G_IO_ERROR, G_IO_ERROR_FAILED, _("An error occurred while uploading the screenshot.")); soup_session_abort (session); g_object_unref (session); g_propagate_error (error, tmp_err); return FALSE; } } /* Else we get the file name */ else if (G_VALUE_HOLDS_STRING (&response_value)) { TRACE ("The screenshot has been uploaded, get the file name."); online_file_name = g_strdup (g_value_get_string (&response_value)); } /* We received un unexpected reply */ else { GError *tmp_err = g_error_new (SOUP_XMLRPC_FAULT, SOUP_XMLRPC_FAULT_PARSE_ERROR_NOT_WELL_FORMED, "%s", _("An unexpected reply from ZimageZ was received." " The upload of the screenshot failed.")); soup_session_abort (session); g_object_unref (session); g_propagate_error (error, tmp_err); return FALSE; } g_value_unset (&response_value); /* End the user session */ exo_job_info_message (EXO_JOB (job), _("Close the session on ZimageZ...")); TRACE ("Closing the user session"); do_xmlrpc (session, serverurl, method_logout, &tmp_error, &response_value, G_TYPE_STRING, login_response, G_TYPE_INVALID); if (G_IS_VALUE (&response_value)) g_value_unset (&response_value); /* Clean the soup session */ soup_session_abort (session); g_object_unref (session); g_free (login_response); screenshooter_job_image_uploaded (job, online_file_name); if (tmp_error) { g_propagate_error (error, tmp_error); return FALSE; } return TRUE; }