You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
960 lines
29 KiB
960 lines
29 KiB
/* ============================================================
|
|
*
|
|
* This file is a part of kipi-plugins project
|
|
* http://www.kipi-plugins.org
|
|
*
|
|
* Date : 2007-16-07
|
|
* Description : a kipi plugin to export images to Picasa web service
|
|
*
|
|
* Copyright (C) 2007-2008 by Vardhman Jain <vardhman at gmail dot com>
|
|
* Copyright (C) 2008 by Gilles Caulier <caulier dot gilles at gmail dot com>
|
|
*
|
|
* This program is free software; you can redistribute it
|
|
* and/or modify it under the terms of the GNU General
|
|
* Public License as published by the Free Software Foundation;
|
|
* either version 2, or (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* ============================================================ */
|
|
|
|
// C++ includes.
|
|
|
|
#include <cstring>
|
|
#include <cstdio>
|
|
#include <cstdlib>
|
|
#include <string>
|
|
|
|
// TQt includes.
|
|
|
|
#include <tqcstring.h>
|
|
#include <tqtextstream.h>
|
|
#include <tqfile.h>
|
|
#include <tqfileinfo.h>
|
|
#include <tqimage.h>
|
|
#include <tqstringlist.h>
|
|
#include <tqurl.h>
|
|
#include <tqlineedit.h>
|
|
#include <tqmessagebox.h>
|
|
#include <tqdom.h>
|
|
|
|
// KDE includes.
|
|
|
|
#include <tdelocale.h>
|
|
#include <tdeio/job.h>
|
|
#include <kdebug.h>
|
|
#include <kmimetype.h>
|
|
#include <kstandarddirs.h>
|
|
#include <kmdcodec.h>
|
|
#include <tdeapplication.h>
|
|
#include <tdemessagebox.h>
|
|
#include <tdeio/jobclasses.h>
|
|
#include <kurl.h>
|
|
|
|
// LibKExiv2 includes.
|
|
|
|
#include <libkexiv2/kexiv2.h>
|
|
|
|
// LibKDcraw includes.
|
|
|
|
#include <libkdcraw/version.h>
|
|
#include <libkdcraw/kdcraw.h>
|
|
|
|
#if KDCRAW_VERSION < 0x000106
|
|
#include <libkdcraw/dcrawbinary.h>
|
|
#endif
|
|
|
|
// Local includes.
|
|
|
|
#include "pluginsversion.h"
|
|
#include "mpform.h"
|
|
#include "picasawebitem.h"
|
|
#include "picasawebtalker.h"
|
|
#include "picasawebwindow.h"
|
|
#include "picasaweblogin.h"
|
|
#include "picasawebtalker.moc"
|
|
|
|
class PicasawebLogin;
|
|
|
|
namespace KIPIPicasawebExportPlugin
|
|
{
|
|
|
|
PicasawebTalker::PicasawebTalker( TQWidget* parent )
|
|
: m_parent( parent ), m_job( 0 )
|
|
{
|
|
m_apikey="49d585bafa0758cb5c58ab67198bf632";
|
|
m_secret="34b39925e6273ffd";
|
|
|
|
connect(this, TQ_SIGNAL(signalError(const TQString&)),
|
|
this, TQ_SLOT(slotError(const TQString&)));
|
|
|
|
authProgressDlg=new TQProgressDialog();
|
|
}
|
|
|
|
PicasawebTalker::~PicasawebTalker()
|
|
{
|
|
if (m_job)
|
|
m_job->kill();
|
|
}
|
|
|
|
TQString PicasawebTalker::getApiSig(TQString secret, TQStringList headers)
|
|
{
|
|
TQStringList compressed ;//= new List<string>(headers.Length);
|
|
|
|
for ( TQStringList::Iterator it = headers.begin(); it != headers.end(); ++it ) {
|
|
TQStringList str=TQStringList::split("=",(*it));
|
|
compressed.append(str[0].stripWhiteSpace()+str[1].stripWhiteSpace());
|
|
}
|
|
|
|
compressed.sort();
|
|
TQString merged=compressed.join("");
|
|
TQString final = secret + merged;
|
|
const char *test=final.ascii();
|
|
KMD5 context (test);
|
|
//kdDebug()<< "Test Hex Digest output: " << context.hexDigest().data() << endl;
|
|
return context.hexDigest().data();
|
|
}
|
|
|
|
void PicasawebTalker::getToken(const TQString& username, const TQString& password )
|
|
{
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
TQString url = "https://www.google.com/accounts/ClientLogin";
|
|
|
|
PicasawebLogin *loginDialog = new PicasawebLogin(kapp->activeWindow(), TQString("LoginWindow"), username, password);
|
|
/*if (username!=NULL && username.length() > 0){
|
|
// kdDebug()<<"Showing stored username"<< username << endl;
|
|
loginDialog->setUsername(username);
|
|
if (password != NULL && password.length() > 0){
|
|
// kdDebug()<<"Showing stored password"<< password << endl;
|
|
loginDialog->setPassword(password);
|
|
// kdDebug()<<"Showing stored password"<< password << endl;
|
|
}
|
|
}
|
|
*/
|
|
|
|
TQString username_edit, password_edit;
|
|
|
|
if (!loginDialog)
|
|
{
|
|
kdDebug()<<" Out of memory error "<< endl;
|
|
}
|
|
|
|
if (loginDialog->exec() == TQDialog::Accepted)
|
|
{
|
|
username_edit = loginDialog->username();
|
|
password_edit = loginDialog->password();
|
|
}
|
|
else
|
|
{
|
|
//Return something which say authentication needed.
|
|
return ;
|
|
}
|
|
|
|
m_username = username_edit;
|
|
username_edit = username;
|
|
TQString accountType = "GOOGLE";
|
|
|
|
if (!(username_edit.endsWith("@gmail.com")))
|
|
username_edit += "@gmail.com";
|
|
|
|
TQByteArray buffer;
|
|
TQStringList qsl;
|
|
qsl.append("Email="+username_edit);
|
|
qsl.append("Passwd="+password_edit);
|
|
qsl.append("accountType="+accountType);
|
|
qsl.append("service=lh2");
|
|
qsl.append("source=kipi-picasaweb-client");
|
|
TQString dataParameters = qsl.join("&");
|
|
|
|
TQTextStream ts(buffer, IO_Append|IO_WriteOnly);
|
|
ts.setEncoding(TQTextStream::UnicodeUTF8);
|
|
ts << dataParameters;
|
|
|
|
TDEIO::TransferJob* job = TDEIO::http_post(url, buffer, false);
|
|
job->addMetaData("content-type", "Content-Type: application/x-www-form-urlencoded" );
|
|
m_state = FE_GETTOKEN;
|
|
authProgressDlg->setLabelText(i18n("Getting the token"));
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy( true );
|
|
}
|
|
|
|
void PicasawebTalker::authenticate(const TQString& token, const TQString& username, const TQString& password)
|
|
{
|
|
if (!token || token.length() < 1)
|
|
{
|
|
checkToken(token);
|
|
m_username = username;
|
|
m_password = password; //this would be needed if the checktoken failed
|
|
//we would need to reauthenticate using auth
|
|
}
|
|
else
|
|
{
|
|
getToken(username, password);
|
|
}
|
|
}
|
|
|
|
void PicasawebTalker::checkToken(const TQString& /*token*/)
|
|
{
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
TQString url = "https://www.google.com/accounts/ClientLogin";
|
|
TQString auth_string = "GoogleLogin auth=" + m_token;
|
|
TQByteArray tmp;
|
|
TDEIO::TransferJob* job = TDEIO::http_post(url, tmp, false);
|
|
job->addMetaData("customHTTPHeader", "Authorization: " + auth_string);
|
|
|
|
job->addMetaData("content-type", "Content-Type: application/x-www-form-urlencoded");
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_CHECKTOKEN;
|
|
authProgressDlg->setLabelText(i18n("Checking if previous token is still valid"));
|
|
authProgressDlg->setProgress(1,4);
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy( true );
|
|
}
|
|
|
|
/** PicasaWeb's Album listing request/response
|
|
* First a request is sent to the url below and then we might(?) get a redirect URL
|
|
* WE then need to send the GET request to the Redirect url (this however gets taken care off by the
|
|
* TDEIO libraries.
|
|
* This uses the authenticated album list fetching to get all the albums included the unlisted-albums
|
|
* which is not returned for an unauthorised request as done without the Authorization header.
|
|
*/
|
|
void PicasawebTalker::listAllAlbums() {
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
TQString url = "http://picasaweb.google.com/data/feed/api/user/" + m_username + "?kind=album";
|
|
TQByteArray tmp;
|
|
TQString auth_string = "GoogleLogin auth=" + m_token;
|
|
TDEIO::TransferJob* job = TDEIO::get(url, !tmp.isNull(), false);
|
|
job->addMetaData("content-type", "Content-Type: application/x-www-form-urlencoded" );
|
|
job->addMetaData("customHTTPHeader", "Authorization: " + auth_string );
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_LISTALBUMS;
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy( true );
|
|
|
|
}
|
|
|
|
void PicasawebTalker::getPhotoProperty(const TQString& method,const TQString& argList)
|
|
{
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
TQString url="http://www.picasaweb.com/services/rest/?";
|
|
TQStringList headers;
|
|
headers.append("api_key="+ m_apikey);
|
|
headers.append("method="+method);
|
|
headers.append("frob="+ m_frob);
|
|
headers.append(argList);
|
|
TQString md5=getApiSig(m_secret,headers);
|
|
headers.append("api_sig="+ md5);
|
|
TQString queryStr=headers.join("&");
|
|
TQString postUrl=url+queryStr;
|
|
TQByteArray tmp;
|
|
TDEIO::TransferJob* job = TDEIO::http_post(postUrl, tmp, false);
|
|
job->addMetaData("content-type", "Content-Type: application/x-www-form-urlencoded" );
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_GETPHOTOPROPERTY;
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy( true );
|
|
//authProgressDlg->setLabelText("Getting the Token from the server");
|
|
//authProgressDlg->setProgress(3,4);
|
|
}
|
|
|
|
void PicasawebTalker::addPhotoTag(const TQString& photoURI, const TQString& tag)
|
|
{
|
|
//if (m_job && m_state != FE_ADDTAG){ //we shouldn't kill the old tag request
|
|
// m_job->kill();
|
|
// m_job = 0;
|
|
//}
|
|
|
|
TQString addTagXML = TQString("<entry xmlns='http://www.w3.org/2005/Atom'> "
|
|
"<title>%1</title> "
|
|
"<category scheme='http://schemas.google.com/g/2005#kind' "
|
|
"term='http://schemas.google.com/photos/2007#tag'/> "
|
|
"</entry>").arg(tag);
|
|
TQString postUrl = TQString("%1").arg(photoURI);
|
|
TQByteArray buffer;
|
|
TQTextStream ts(buffer, IO_Append|IO_WriteOnly);
|
|
ts.setEncoding(TQTextStream::UnicodeUTF8);
|
|
ts << addTagXML;
|
|
|
|
TQString auth_string = "GoogleLogin auth=" + m_token;
|
|
TDEIO::TransferJob* job = TDEIO::http_post(postUrl, buffer, false);
|
|
job->addMetaData("content-type", "Content-Type: application/atom+xml");
|
|
job->addMetaData("content-length", TQString("Content-Length: %1").arg(addTagXML.length()));
|
|
job->addMetaData("customHTTPHeader", "Authorization: " + auth_string );
|
|
|
|
//connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
// this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_ADDTAG;
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy(true);
|
|
}
|
|
|
|
void PicasawebTalker::listPhotos(const TQString& /*albumName*/)
|
|
{
|
|
// TODO
|
|
}
|
|
|
|
void PicasawebTalker::createAlbum(const TQString& albumTitle, const TQString& albumDesc,
|
|
const TQString& location, uint timestamp, const TQString& access,
|
|
const TQString& media_keywords, bool isCommentsEnabled)
|
|
{
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
TQString newAlbumXML = TQString("<entry xmlns='http://www.w3.org/2005/Atom' "
|
|
"xmlns:media='http://search.yahoo.com/mrss/' "
|
|
"xmlns:gphoto='http://schemas.google.com/photos/2007'> "
|
|
"<title type='text'>%1</title> "
|
|
"<summary type='text'>%2</summary> "
|
|
"<gphoto:location>%3</gphoto:location> "
|
|
"<gphoto:access>%4</gphoto:access> "
|
|
"<gphoto:commentingEnabled>%5</gphoto:commentingEnabled> "
|
|
"<gphoto:timestamp>%6</gphoto:timestamp> "
|
|
"<media:group> "
|
|
"<media:keywords>%7</media:keywords> "
|
|
"</media:group> "
|
|
"<category scheme='http://schemas.google.com/g/2005#kind' "
|
|
"term='http://schemas.google.com/photos/2007#album'></category> "
|
|
"</entry> ").arg(albumTitle)
|
|
.arg(albumDesc)
|
|
.arg(location)
|
|
.arg(access)
|
|
.arg(isCommentsEnabled==true?"true":"false")
|
|
.arg(timestamp)
|
|
.arg(media_keywords);
|
|
|
|
TQByteArray buffer;
|
|
TQTextStream ts(buffer, IO_Append|IO_WriteOnly);
|
|
ts.setEncoding(TQTextStream::UnicodeUTF8);
|
|
ts << newAlbumXML;
|
|
|
|
MPForm form;
|
|
TQString postUrl = "http://www.picasaweb.google.com/data/feed/api/user/" + m_username ;
|
|
TQString auth_string = "GoogleLogin auth=" + m_token;
|
|
TDEIO::TransferJob* job = TDEIO::http_post(postUrl, buffer, false);
|
|
job->addMetaData("content-type", "Content-Type: application/atom+xml");
|
|
job->addMetaData("content-length", TQString("Content-Length: %1").arg(newAlbumXML.length()));
|
|
job->addMetaData("customHTTPHeader", "Authorization: " + auth_string );
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_CREATEALBUM;
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy(true);
|
|
}
|
|
|
|
bool PicasawebTalker::addPhoto(const TQString& photoPath, FPhotoInfo& info,
|
|
const TQString& albumId, bool rescale,
|
|
int maxDim, int imageQuality)
|
|
{
|
|
// Disabling this totally may be checking the m_state and doing selecting
|
|
// disabling is a better idea
|
|
/*if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}*/
|
|
|
|
TQString album_id = albumId;
|
|
|
|
if (album_id.length() == 0)
|
|
album_id = "test";
|
|
|
|
TQString postUrl = "http://www.picasaweb.google.com/data/feed/api/user/" + KURL::encode_string(m_username) + "/albumid/" + album_id;
|
|
TQString path = postUrl;
|
|
TQStringList headers;
|
|
MPForm form;
|
|
TQString auth_string = "GoogleLogin auth=" + m_token;
|
|
|
|
//form.addPair("Authorization", auth_string);
|
|
|
|
//Create the Body in atom-xml
|
|
TQStringList body_xml;
|
|
body_xml.append("<entry xmlns=\'http://www.w3.org/2005/Atom\'>");
|
|
body_xml.append("<title>"+ info.title +"</title>");
|
|
body_xml.append("<summary>"+ info.description +"</summary>");
|
|
body_xml.append("<category scheme=\"http://schemas.google.com/g/2005#kind\" "
|
|
"term=\"http://schemas.google.com/photos/2007#photo\" />");
|
|
body_xml.append("</entry>");
|
|
|
|
TQString body = body_xml.join("");
|
|
|
|
form.addPair("test", body, "application/atom+xml");
|
|
|
|
// save the tags for this photo in to the tags hashmap
|
|
tags_map.insert(info.title, info.tags);
|
|
TQImage image;
|
|
|
|
// Check if RAW file.
|
|
#if KDCRAW_VERSION < 0x000106
|
|
TQString rawFilesExt(KDcrawIface::DcrawBinary::instance()->rawFiles());
|
|
#else
|
|
TQString rawFilesExt(KDcrawIface::KDcraw::rawFiles());
|
|
#endif
|
|
TQFileInfo fileInfo(photoPath);
|
|
if (rawFilesExt.upper().contains(fileInfo.extension(false).upper()))
|
|
KDcrawIface::KDcraw::loadDcrawPreview(image, photoPath);
|
|
else
|
|
image.load(photoPath);
|
|
|
|
if (!image.isNull())
|
|
{
|
|
path = locateLocal("tmp", TQFileInfo(photoPath).baseName().stripWhiteSpace() + ".jpg");
|
|
|
|
if (rescale && (image.width() > maxDim || image.height() > maxDim))
|
|
image = image.smoothScale(maxDim, maxDim, TQImage::ScaleMin);
|
|
|
|
image.save(path, "JPEG", imageQuality);
|
|
|
|
// Restore all metadata.
|
|
|
|
KExiv2Iface::KExiv2 exiv2Iface;
|
|
|
|
if (exiv2Iface.load(photoPath))
|
|
{
|
|
exiv2Iface.setImageProgramId(TQString("Kipi-plugins"), TQString(kipiplugins_version));
|
|
exiv2Iface.setImageDimensions(image.size());
|
|
exiv2Iface.save(path);
|
|
}
|
|
else
|
|
{
|
|
kdWarning(51000) << "(picasawebExport::Image doesn't have exif data)" << endl;
|
|
}
|
|
|
|
kdDebug() << "Resizing and saving to temp file: " << path << endl;
|
|
}
|
|
|
|
if (!form.addFile("photo", path))
|
|
return false;
|
|
|
|
form.finish();
|
|
|
|
TDEIO::TransferJob* job = TDEIO::http_post(postUrl, form.formData(), false);
|
|
job->addMetaData("content-type", form.contentType());
|
|
job->addMetaData("customHTTPHeader", "Authorization: " + auth_string );
|
|
|
|
connect(job, TQ_SIGNAL(data(TDEIO::Job*, const TQByteArray&)),
|
|
this, TQ_SLOT(data(TDEIO::Job*, const TQByteArray&)));
|
|
|
|
connect(job, TQ_SIGNAL(result(TDEIO::Job *)),
|
|
this, TQ_SLOT(slotResult(TDEIO::Job *)));
|
|
|
|
m_state = FE_ADDPHOTO;
|
|
m_job = job;
|
|
m_buffer.resize(0);
|
|
emit signalBusy(true);
|
|
return true;
|
|
}
|
|
|
|
TQString PicasawebTalker::getUserName()
|
|
{
|
|
return m_username;
|
|
}
|
|
|
|
TQString PicasawebTalker::getUserId()
|
|
{
|
|
return m_userId;
|
|
}
|
|
|
|
void PicasawebTalker::cancel()
|
|
{
|
|
if (m_job)
|
|
{
|
|
m_job->kill();
|
|
m_job = 0;
|
|
}
|
|
|
|
if (authProgressDlg && !authProgressDlg->isHidden())
|
|
authProgressDlg->hide();
|
|
}
|
|
|
|
void PicasawebTalker::info(TDEIO::Job* /*job*/, const TQString& /*str*/)
|
|
{
|
|
}
|
|
|
|
void PicasawebTalker::data(TDEIO::Job*, const TQByteArray& data)
|
|
{
|
|
if (data.isEmpty())
|
|
return;
|
|
|
|
int oldSize = m_buffer.size();
|
|
m_buffer.resize(m_buffer.size() + data.size());
|
|
TQString output_data = TQString(data);
|
|
memcpy(m_buffer.data()+oldSize, data.data(), data.size());
|
|
}
|
|
|
|
void PicasawebTalker::slotError(const TQString & error)
|
|
{
|
|
TQString transError;
|
|
int errorNo = 0;
|
|
|
|
if (!error.isEmpty())
|
|
errorNo = atoi(error.latin1());
|
|
|
|
switch (errorNo)
|
|
{
|
|
case 2:
|
|
transError=i18n("No photo specified");break;
|
|
case 3:
|
|
transError=i18n("General upload failure");break;
|
|
case 4:
|
|
transError=i18n("Filesize was zero");break;
|
|
case 5:
|
|
transError=i18n("Filetype was not recognised");break;
|
|
case 6:
|
|
transError=i18n("User exceeded upload limit");break;
|
|
case 96:
|
|
transError=i18n("Invalid signature"); break;
|
|
case 97:
|
|
transError=i18n("Missing signature"); break;
|
|
case 98:
|
|
transError=i18n("Login Failed / Invalid auth token"); break;
|
|
case 100:
|
|
transError=i18n("Invalid API Key"); break;
|
|
case 105:
|
|
transError=i18n("Service currently unavailable");break;
|
|
case 108:
|
|
transError=i18n("Invalid Frob");break;
|
|
case 111:
|
|
transError=i18n("Format \"xxx\" not found"); break;
|
|
case 112:
|
|
transError=i18n("Method \"xxx\" not found"); break;
|
|
case 114:
|
|
transError=i18n("Invalid SOAP envelope");break;
|
|
case 115:
|
|
transError=i18n("Invalid XML-RPC Method Call");break;
|
|
case 116:
|
|
transError=i18n("The POST method is now required for all setters"); break;
|
|
default:
|
|
transError=i18n("Unknown error");
|
|
};
|
|
|
|
KMessageBox::error(kapp->activeWindow(), i18n("Error Occured: %1\n We can not proceed further").arg(transError));
|
|
//kdDebug()<<"Not handling the error now will see it later"<<endl;
|
|
}
|
|
|
|
void PicasawebTalker::slotResult(TDEIO::Job *job)
|
|
{
|
|
m_job = 0;
|
|
emit signalBusy(false);
|
|
|
|
if (job->error())
|
|
{
|
|
if (m_state == FE_ADDPHOTO)
|
|
{
|
|
emit signalAddPhotoFailed(job->errorString());
|
|
}
|
|
else
|
|
{
|
|
job->showErrorDialog(m_parent);
|
|
}
|
|
|
|
return;
|
|
}
|
|
|
|
switch(m_state)
|
|
{
|
|
case(FE_LOGIN):
|
|
//parseResponseLogin(m_buffer);
|
|
break;
|
|
case(FE_CREATEALBUM):
|
|
parseResponseCreateAlbum(m_buffer);
|
|
break;
|
|
case(FE_LISTALBUMS):
|
|
parseResponseListAlbums(m_buffer);
|
|
break;
|
|
case(FE_GETFROB):
|
|
break;
|
|
case(FE_GETTOKEN):
|
|
parseResponseGetToken(m_buffer);
|
|
break;
|
|
case(FE_CHECKTOKEN):
|
|
parseResponseCheckToken(m_buffer);
|
|
break;
|
|
case(FE_GETAUTHORIZED):
|
|
break;
|
|
case(FE_LISTPHOTOS):
|
|
parseResponseListPhotos(m_buffer);
|
|
break;
|
|
case(FE_GETPHOTOPROPERTY):
|
|
parseResponsePhotoProperty(m_buffer);
|
|
break;
|
|
case(FE_ADDPHOTO):
|
|
parseResponseAddPhoto(m_buffer);
|
|
break;
|
|
case(FE_ADDTAG):
|
|
parseResponseAddTag(m_buffer);
|
|
break;
|
|
}
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseCheckToken(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString errorString;
|
|
TQString username;
|
|
TQString transReturn(data);
|
|
// If checktoken failed.
|
|
// getToken ...
|
|
|
|
if(transReturn.startsWith("Error="))
|
|
success = false;
|
|
else
|
|
success = true;
|
|
|
|
if(!success)
|
|
getToken(m_username, m_password);
|
|
//emit signalError(errorString);
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseGetToken(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString errorString;
|
|
TQString str(data);
|
|
//Check the response code should it be 200, proceed
|
|
//if it is 403 handle the error mesg
|
|
//figure out the auth string from this response
|
|
|
|
if (str.find("Auth="))
|
|
{
|
|
TQStringList strList = TQStringList::split("Auth=", str);
|
|
m_token = strList[1];
|
|
success = 1;
|
|
}
|
|
|
|
if(success)
|
|
{
|
|
authProgressDlg->hide();
|
|
emit signalTokenObtained(m_token);
|
|
}
|
|
else
|
|
{
|
|
emit signalError(errorString);
|
|
}
|
|
|
|
emit signalBusy(false);
|
|
}
|
|
|
|
void PicasawebTalker::getHTMLResponseCode(const TQString& /*str*/)
|
|
{
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseListAlbums(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString str(data);
|
|
TQDomDocument doc( "feed" );
|
|
if ( !doc.setContent( data ) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
TQDomElement docElem = doc.documentElement();
|
|
TQDomNode node = docElem.firstChild();
|
|
TQDomElement e;
|
|
TQString feed_id, feed_updated, feed_title, feed_subtitle;
|
|
TQString feed_icon_url, feed_link_url;
|
|
TQString feed_username, feed_user_uri;
|
|
|
|
TQString album_id, album_title, album_description;
|
|
m_albumsList = new TQValueList <PicasaWebAlbum>();
|
|
|
|
while(!node.isNull())
|
|
{
|
|
if (node.isElement() && node.nodeName() == "entry")
|
|
{
|
|
success = true;
|
|
e = node.toElement();
|
|
TQDomNode details=e.firstChild();
|
|
PicasaWebAlbum fps;
|
|
TQDomNode detailsNode = details;
|
|
|
|
while(!detailsNode.isNull())
|
|
{
|
|
if(detailsNode.isElement())
|
|
{
|
|
if(detailsNode.nodeName() == "id")
|
|
{
|
|
// The node data is a URL of which album id is the string following the last /
|
|
// like <id>http://www.picasaweb.google.com/.../AlbumID<id>
|
|
TQString albumIdUrl = detailsNode.toElement().text();
|
|
int index = albumIdUrl.findRev("/");
|
|
int length = albumIdUrl.length();
|
|
TQString album_id = albumIdUrl.right(length - index - 1);
|
|
fps.id = album_id;
|
|
}
|
|
|
|
if(detailsNode.nodeName() == "title")
|
|
{
|
|
album_title = "Not fetched";
|
|
|
|
if(detailsNode.toElement().attribute("type")=="text")
|
|
album_title = detailsNode.toElement().text();
|
|
|
|
//this is what is obtained from data.
|
|
fps.title = album_title;
|
|
}
|
|
|
|
if(detailsNode.nodeName()=="gphoto:name")
|
|
{
|
|
TQString name = detailsNode.toElement().text();
|
|
}
|
|
}
|
|
|
|
detailsNode = detailsNode.nextSibling();
|
|
}
|
|
|
|
m_albumsList->append(fps);
|
|
}
|
|
|
|
node = node.nextSibling();
|
|
}
|
|
|
|
if (!success)
|
|
{
|
|
emit signalGetAlbumsListFailed(i18n("Failed to fetch photoSets List"));
|
|
m_albumsList = NULL;
|
|
}
|
|
else
|
|
{
|
|
emit signalGetAlbumsListSucceeded();
|
|
}
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseListPhotos(const TQByteArray &data)
|
|
{
|
|
TQDomDocument doc( "getPhotosList" );
|
|
if ( !doc.setContent( data ) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
TQDomElement docElem = doc.documentElement();
|
|
TQDomNode node = docElem.firstChild();
|
|
//TQDomElement e;
|
|
// TODO
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseCreateAlbum(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString errorString;
|
|
TQString response(data);
|
|
TQDomDocument doc( "AddPhoto Response" );
|
|
// parse the new album name
|
|
TQDomElement docElem = doc.documentElement();
|
|
TQString title, photo_id, album_id, photoURI;
|
|
TQDomNode node = docElem.firstChild(); //this should mean <entry>
|
|
TQDomElement e;
|
|
|
|
while( !node.isNull() )
|
|
{
|
|
if ( node.isElement())
|
|
{
|
|
TQString node_name = node.nodeName();
|
|
TQString node_value = node.toElement().text();
|
|
if(node_name == "title")
|
|
{
|
|
success = true;
|
|
title = node_value;
|
|
}
|
|
else if (node_name == "id")
|
|
photoURI = node_value;
|
|
else if(node_name == "gphoto:id")
|
|
photo_id = node_value;
|
|
else if(node_name == "gphoto:albumid")
|
|
album_id = node_value;
|
|
}
|
|
|
|
node = node.nextSibling();
|
|
}
|
|
|
|
// Raise a popup informing success
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseAddTag(const TQByteArray &data)
|
|
{
|
|
TQString str(data);
|
|
remaining_tags_count -= 1;
|
|
emit signalBusy( false );
|
|
m_buffer.resize(0);
|
|
|
|
if (remaining_tags_count == 0)
|
|
emit signalAddPhotoSucceeded();
|
|
}
|
|
|
|
void PicasawebTalker::parseResponseAddPhoto(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString line;
|
|
TQString str(data);
|
|
success = 1;
|
|
TQDomDocument doc( "AddPhoto Response" );
|
|
|
|
if ( !doc.setContent( data ) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
TQDomElement docElem = doc.documentElement();
|
|
TQString title, photo_id, album_id, photoURI;
|
|
TQDomNode node = docElem.firstChild(); //this should mean <entry>
|
|
TQDomElement e;
|
|
|
|
while( !node.isNull() )
|
|
{
|
|
if ( node.isElement())
|
|
{
|
|
TQString node_name = node.nodeName();
|
|
TQString node_value = node.toElement().text();
|
|
if(node_name == "title")
|
|
{
|
|
success = true;
|
|
title = node_value;
|
|
}
|
|
else if (node_name == "id")
|
|
photoURI = node_value;
|
|
else if(node_name == "gphoto:id")
|
|
photo_id = node_value;
|
|
else if(node_name == "gphoto:albumid")
|
|
album_id = node_value;
|
|
}
|
|
|
|
node = node.nextSibling();
|
|
}
|
|
|
|
if (!success)
|
|
{
|
|
emit signalAddPhotoFailed(i18n("Failed to upload photo"));
|
|
}
|
|
else
|
|
{
|
|
// Update the tags information from the tags_map
|
|
TQStringList tags = tags_map[title];
|
|
remaining_tags_count = tags.count();
|
|
|
|
if (tags.count() == 0)
|
|
emit signalAddPhotoSucceeded();
|
|
|
|
for ( TQStringList::Iterator it = tags.begin(); it != tags.end(); ++it )
|
|
{
|
|
TQString photoURI= TQString("http://picasaweb.google.com/data/feed/api/user/"
|
|
"%1/albumid/%2/photoid/%3").arg(m_username).arg(album_id).arg(photo_id);
|
|
addPhotoTag( photoURI, *it);
|
|
}
|
|
}
|
|
}
|
|
|
|
void PicasawebTalker::parseResponsePhotoProperty(const TQByteArray &data)
|
|
{
|
|
bool success = false;
|
|
TQString line;
|
|
TQDomDocument doc( "Photos Properties" );
|
|
|
|
if ( !doc.setContent( data ) )
|
|
{
|
|
return;
|
|
}
|
|
|
|
TQDomElement docElem = doc.documentElement();
|
|
TQDomNode node = docElem.firstChild();
|
|
TQDomElement e;
|
|
|
|
while( !node.isNull() )
|
|
{
|
|
if ( node.isElement() && node.nodeName() == "photoid" )
|
|
{
|
|
e = node.toElement(); // try to convert the node to an element.
|
|
TQDomNode details=e.firstChild();
|
|
success=true;
|
|
}
|
|
|
|
if ( node.isElement() && node.nodeName() == "err" )
|
|
{
|
|
kdDebug()<<"Checking Error in response"<<endl;
|
|
TQString code=node.toElement().attribute("code");
|
|
kdDebug()<<"Error code="<<code<<endl;
|
|
kdDebug()<<"Msg="<<node.toElement().attribute("msg")<<endl;
|
|
emit signalError(code);
|
|
}
|
|
node = node.nextSibling();
|
|
}
|
|
|
|
kdDebug()<<"GetToken finished"<<endl;
|
|
if (!success)
|
|
{
|
|
emit signalAddPhotoFailed(i18n("Failed to query photo information"));
|
|
}
|
|
else
|
|
{
|
|
//emit signalAddPhotoSucceeded();
|
|
}
|
|
}
|
|
|
|
} // KIPIPicasawebExportPlugin
|