diff options
Diffstat (limited to 'src/sync')
| -rw-r--r-- | src/sync/operasynchandler.cpp | 884 | ||||
| -rw-r--r-- | src/sync/operasynchandler.h | 142 | ||||
| -rw-r--r-- | src/sync/sync_host_type.ui | 7 | ||||
| -rw-r--r-- | src/sync/sync_opera_settings.ui | 70 | ||||
| -rw-r--r-- | src/sync/syncassistant.cpp | 2 | ||||
| -rw-r--r-- | src/sync/syncassistant.h | 1 | ||||
| -rw-r--r-- | src/sync/synccheckwidget.cpp | 5 | ||||
| -rw-r--r-- | src/sync/synchosttypewidget.cpp | 17 | ||||
| -rw-r--r-- | src/sync/syncmanager.cpp | 4 | ||||
| -rw-r--r-- | src/sync/syncoperasettingswidget.cpp | 60 | ||||
| -rw-r--r-- | src/sync/syncoperasettingswidget.h | 52 | 
11 files changed, 1239 insertions, 5 deletions
| diff --git a/src/sync/operasynchandler.cpp b/src/sync/operasynchandler.cpp new file mode 100644 index 00000000..cdddbe38 --- /dev/null +++ b/src/sync/operasynchandler.cpp @@ -0,0 +1,884 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2012 by Siteshwar Vashisht <siteshwar at gmail dot com> +* Copyright (C) 2011 by Andrea Diamantini <adjam7 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 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* 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. +* +* You should have received a copy of the GNU General Public License +* along with this program.  If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "operasynchandler.h" +#include "operasynchandler.moc" + +// Auto Includes +#include "rekonq.h" + +// Local Includes +#include "application.h" +#include "bookmarkmanager.h" + +// KDE Includes +#include <KStandardDirs> +#include <klocalizedstring.h> +#include <kbookmarkmanager.h> + + +#include <QList> +#include <QWebPage> +#include <QWebFrame> +#include <QWebElement> +#include <QUrl> +#include <QWebSettings> +#include <QNetworkAccessManager> +#include <QNetworkReply> +#include <QDomDocument> + + +OperaSyncHandler::OperaSyncHandler(QObject *parent) +    : SyncHandler(parent) +    , _mode(RECEIVE_CHANGES) +//    , _doLogin(false) +    , _isSyncing(false) +/*    , _reply(0) +    , _requestCount(0)*/ +{ +    kDebug() << "Creating Opera Bookmarks handler..."; +//    _webPage.settings()->setAttribute(QWebSettings::AutoLoadImages, false); +//    _webPage.settings()->setAttribute(QWebSettings::PrivateBrowsingEnabled, true); +//    connect(&_webPage, SIGNAL(loadFinished(bool)), this, SLOT(loadFinished(bool))); + +    webView = new QWebView(); +    webView->settings()->setAttribute(QWebSettings::AutoLoadImages, false); +    connect(webView, SIGNAL(loadFinished(bool)), this, SLOT(loadFinished(bool))); + +    qoauth = new QOAuth::Interface(); +    qoauth->setConsumerKey("test_desktop_key"); +    qoauth->setConsumerSecret("p2FlOFGr3XFm5gOwEKKDcg3CvA4pp0BC"); +} + + +void OperaSyncHandler::initialLoadAndCheck() +{ +    if (!ReKonfig::syncEnabled()) +    { +        _firstTimeSynced = false; +        return; +    } + +    // Bookmarks +    if (ReKonfig::syncBookmarks()) +    { +//        _mode = RECEIVE_CHANGES; +        _mode = SEND_CHANGES; +        startLogin(); +    } + +    if (ReKonfig::syncHistory()) +    { +        emit syncStatus(Rekonq::History, false, i18n("Not supported!")); +    } + +    if (ReKonfig::syncHistory()) +    { +        emit syncStatus(Rekonq::Passwords, false, i18n("Not supported!")); +    } +} + + +bool OperaSyncHandler::syncRelativeEnabled(bool check) +{ +    if (!ReKonfig::syncEnabled()) +        return false; + +    if (!_firstTimeSynced) +        return false; + +    return check; +} + + +// --------------------------------------------------------------------------------------- + + +void OperaSyncHandler::syncHistory() +{ +    kDebug() << "Syncing history not supported!"; +    emit syncStatus(Rekonq::History, false, i18n("Syncing history not supported!")); +    emit syncHistoryFinished(false); +} + + +void OperaSyncHandler::syncPasswords() +{ +    kDebug() << "Syncing passwords not supported!"; +    emit syncStatus(Rekonq::Passwords, false, i18n("Syncing passwords not supported!")); +    emit syncPasswordsFinished(false); +} + + +void OperaSyncHandler::syncBookmarks() +{ + +    if (_isSyncing) +    { +        kDebug() << "Sync already in progress!"; +        return; +    } +//    _mode = SEND_CHANGES; +//    startLogin(); +} + +void OperaSyncHandler::startLogin() +{ +    if (ReKonfig::syncUser().isEmpty() || ReKonfig::syncPass().isEmpty()) +    { +        kDebug() << "No username or password!"; +        emit syncStatus(Rekonq::Bookmarks, false, i18n("No username or password!")); +        emit syncBookmarksFinished(false); +        return; +    } + +    _isSyncing = true; + +    _doLogin = true; + +    kDebug() << "Loading login page..."; +//    _webPage.mainFrame()->load(QUrl("http://bookmarks.google.com/")); + + +    qoauth->setRequestTimeout(20000); +    qoauth->ignoreSslErrors(); +    QOAuth::ParamMap requestMap; +    requestMap.insert("oauth_callback", "oob"); + +    requestParam = qoauth->requestToken("https://auth.opera.com/service/oauth/request_token", QOAuth::POST, QOAuth::HMAC_SHA1, requestMap); +    qDebug() << qoauth->error(); +    qDebug() << requestParam; + +    requestToken = requestParam.value("oauth_token"); +    requestTokenSecret = requestParam.value("oauth_token_secret"); + +    qDebug() << requestToken; +    qDebug() << requestTokenSecret; + + +    qDebug() << QUrl("https://auth.opera.com/service/oauth/authorize?oauth_token=" + QString(requestToken) + "&oauth_callback=oob"); + +    webView->resize(400, 400); + +    webView->load(QUrl("https://auth.opera.com/service/oauth/authorize?oauth_token=" + QString(requestToken) + "&oauth_callback=oob" )); + +    webView->show(); + + +} + +//Loading a webpage finished, what action to take is decided based on url we have loaded. +void OperaSyncHandler::loadFinished(bool ok) +{ +    kDebug() << "Load Finished" << ok; +    if (!ok) +    { +        kDebug() << "Error loading: " << _webPage.mainFrame()->url(); +        emit syncStatus(Rekonq::Bookmarks, false, i18n( "Error loading: " + _webPage.mainFrame()->url().toEncoded())); + +        _isSyncing = false; +        return; +    } + +    qDebug() << webView->url(); +    QString path = webView->url().path(); + +    qDebug() << path; +    if (path == "/service/oauth/authorize") +    { +        QWebFrame *mainFrame = webView->page()->mainFrame(); +        QString html = mainFrame->toHtml(); + +        if (html.contains("login-form")) +        { +            qDebug() << "Login page"; +            QWebElement form = mainFrame->findFirstElement("#login-form"); +            if (form.isNull()) +            { +                qDebug() << "form is null"; +            } + +            QWebElement username = form.findFirst("#username"); +            QWebElement password = form.findFirst("#password"); +            QWebElement button = form.findFirst("input[name=\"grant\"]"); + +            qDebug() << username.isNull(); +            qDebug() << password.isNull(); +            qDebug() << button.isNull(); +            username.setAttribute("value", ReKonfig::syncUser()); +            password.setAttribute("value", ReKonfig::syncPass()); + +            qDebug() << button.toPlainText(); +            button.evaluateJavaScript("this.click();"); + +        } +        else if (html.contains("verifier")) +        { +            QWebElement authkey = mainFrame->findFirstElement("#verifier"); +            QByteArray verifier = authkey.toPlainText().toUtf8(); + +            qDebug() << verifier; +            authParams.insert("oauth_verifier", verifier); +            resultParam = qoauth->accessToken("https://auth.opera.com/service/oauth/access_token", QOAuth::POST, requestToken, requestTokenSecret, QOAuth::HMAC_SHA1, authParams); + +            qDebug() << qoauth->error(); +            qDebug() << resultParam; + +            authToken = resultParam.value("oauth_token"); +            authTokenSecret = resultParam.value("oauth_token_secret"); + + +            requestToken.clear(); +            requestTokenSecret.clear(); +            requestParam.clear(); +            resultParam.clear(); +            authParams.clear(); +            getBookmarks(); +        } + +    } +} + + + +void OperaSyncHandler::getBookmarks() +{ +    QOAuth::ParamMap requestMap; +    //requestMap.insert("oauth_nonce", "123"); +    requestMap.insert("api_output", "xml"); +    qDebug() << "Auth Token : " << authToken; +    qDebug() << "Auth Token Secret : " << authTokenSecret; + +    urlParams = qoauth->createParametersString("https://link.api.opera.com/rest/bookmark/descendants", QOAuth::GET, authToken, authTokenSecret, QOAuth::HMAC_SHA1, requestMap, QOAuth::ParseForInlineQuery); + +    QNetworkRequest request; + +    qDebug() << "URL Params: " << urlParams; +    QByteArray urlstr = "https://link.api.opera.com/rest/bookmark/descendants"; + +    urlstr.append(urlParams); +    kDebug() << urlstr; +    KIO::TransferJob *job = KIO::get(KUrl(urlstr), KIO::Reload, KIO::HideProgressInfo); + +    connect(job, SIGNAL(result(KJob*)), this, SLOT(resultSlot(KJob*))); +    connect(job, SIGNAL(data(KIO::Job*, QByteArray)), this, SLOT(dataSlot(KIO::Job*, QByteArray))); +} + +void OperaSyncHandler::dataSlot(KIO::Job* job, QByteArray data) +{ +    kDebug() << data; +    xmlData += data; +} + +void OperaSyncHandler::resultSlot(KJob* job) +{ +    if (job->error() != 0) +    { +        xmlData = ""; +        kDebug() << "Some error!"; +        return; +    } + +    kDebug() << "No Error!"; +    kDebug() << xmlData; + +    QDomDocument doc("bookmarks"); +    doc.setContent(xmlData); +    QDomNodeList responseList = doc.elementsByTagName("response"); + +    qDebug() << responseList.size(); +    KBookmarkGroup root = rApp->bookmarkManager()->rootGroup(); + +    if (_mode == RECEIVE_CHANGES) +    { +        if (responseList.size() > 0) +        { +            QDomNode item = responseList.at(0).firstChild(); + +            //        qDebug() << item.nodeName(); + +            while (!item.isNull()) +            { +                handleResource(item, root); +                item = item.nextSibling(); +            } +        } +    } +    else +    { +        if (responseList.size() > 0) +        { +            QDomNode item = responseList.at(0).firstChild(); + +            //        qDebug() << item.nodeName(); + +            while (!item.isNull()) +            { +                handleResource(item, root); +                item = item.nextSibling(); +            } +        } + +        //handleLocalGroup(root, responseList.at(0).toElement()); + +        QDomElement item = responseList.at(0).toElement(); +        KBookmark current = root.first(); + +        while(!current.isNull()) +        { +            if (current.isGroup()) +            { +                QString groupName = current.fullText(); +                QDomElement child = findOperaFolder(item, groupName); + +                if (child.isNull()) +                { +                    //Add Opera group here +                    kDebug() << "Add group " << groupName; +                    KJob *job = addBookmarkFolderOnServer(current.fullText()); +                    jobToGroupMap.insert(job, root); +                } +                else +                { +                    kDebug() << "Handling group " << groupName; +                    QDomElement grandChild = getChildElement(child, "children"); + +                    QString id = getChildString(child, "id"); + +                    kDebug() << grandChild.tagName() << id; + +                    if (grandChild.isNull()) +                    { +                        kDebug() << "Grand child is null"; +                        handleLocalGroup(current.toGroup(), grandChild, id); +                    } +                    else{ +                        //kDebug() << "Grand child " << getTitleFromResourceProperties(grandChild); +                        handleLocalGroup(current.toGroup(), grandChild, id); +                    } +                } +            } + +            else +            { +                KUrl url = current.url(); + +                QDomElement child = findOperaBookmark(item, url); + +                if (child.isNull()) +                { +                    //Add bookmark on server +                    kDebug() << "Add bookmark :" << url; +                    addBookmarkOnServer(current.fullText(), current.url().url()); +                } +                else +                { +                    kDebug() << "Bookmark exists :" << url; +                } +            } + +            current = root.next(current); +        } +    } + +    xmlData = ""; +} + +void OperaSyncHandler::bookmarkDataSlot(KIO::Job* job, QByteArray data) +{ +    kDebug() << data; +    //xmlData += data; +} + +void OperaSyncHandler::bookmarkResultSlot(KJob* job) +{ +    if (job->error() != 0) +    { +        kDebug() << "Some error!" << job->error(); +        return; +    } +} + +void OperaSyncHandler::bookmarkFolderDataSlot(KIO::Job* job, QByteArray data) +{ +    kDebug() << data; + +    QByteArray &value = jobToResponseMap[job]; +    value.append(data); +    //xmlData += data; +} + +void OperaSyncHandler::bookmarkFolderResultSlot(KJob* job) +{ +    if (job->error() != 0) +    { +        kDebug() << "Some error!"; +        return; +    } + +    QByteArray value = jobToResponseMap[job]; +    KBookmarkGroup root = jobToGroupMap[job]; + +    kDebug() << "Final value is " << value; +    QDomDocument doc("new bookmark"); +    doc.setContent(value); +    QDomNodeList responseList = doc.elementsByTagName("response"); + +    qDebug() << responseList.size(); + +    if (responseList.size() > 0) +    { +        QDomElement item = responseList.at(0).firstChildElement(); + +        QString parentId = getIdFromResource(item); +        kDebug() << "Resource id is : " << parentId; + +        handleLocalGroup(root, item, parentId); + +    } +} + +void OperaSyncHandler::handleBookmark(const QDomElement &item, KBookmarkGroup root) +{ +    QString url = getUrlFromResourceProperties(item); +    QString title = getTitleFromResourceProperties(item); +    QString id = getChildString(item, "id"); + +    KBookmark bookmark = findLocalBookmark(root, KUrl(url)); + +    if (bookmark.isNull()) +    { +        if (_mode == RECEIVE_CHANGES) +        { +            root.addBookmark(title, KUrl(url)); +            rApp->bookmarkManager()->manager()->emitChanged(root); +        } +        else +        { +            //Delete bookmark from server +            kDebug() << "Deleting bookmark from server : " << title; +            deleteResourceOnServer(id); +        } +    } + +} + +void OperaSyncHandler::handleBookmarkFolder(const QDomElement &item, KBookmarkGroup &root) +{ +    qDebug() << "Title : " << getTitleFromResourceProperties(item); + +    QDomNode child = item.firstChild(); + +    while (!child.isNull()) +    { +        QDomNode resource = child.firstChild(); + +        while (!resource.isNull()) +        { +            handleResource(resource, root); +            resource = resource.nextSibling(); +        } +        child = child.nextSibling(); +    } +} + +//Handle resource tag of xml replied from server +void OperaSyncHandler::handleResource(const QDomNode &item, KBookmarkGroup &root) +{ +    //        qDebug() << item.nodeName(); +    QDomElement element = item.toElement(); + +    QString itemType = getChildString(item, "item_type"); +    if (itemType == "bookmark") +    { +        handleBookmark(element, root); +    } +    else if (itemType == "bookmark_folder") +    { +        QString title = getTitleFromResourceProperties(item.toElement()); +        QString id = getChildString(item.toElement(), "id"); +        if (title == "Trash") return; + + +        KBookmarkGroup childGroup = findLocalGroup(root, title); +        kDebug() << childGroup.isNull(); + +        if (_mode == RECEIVE_CHANGES) +        { +            if (childGroup.isNull()) +            { +                childGroup = root.createNewFolder(title); +                rApp->bookmarkManager()->manager()->emitChanged(root); +            } + +            handleBookmarkFolder(element, childGroup); +        } +        else +        { +            if (childGroup.isNull()) +            { +                //Delete bookmark folder on server +                kDebug() << "Deleting bookmark folder from server : " << title; +                deleteResourceOnServer(id); +            } +            else +            { +                handleBookmarkFolder(element, childGroup); +            } +        } +    } +} + +/* +void OperaSyncHandler::handleLocalBookmark(const KBookmark &root, const QDomElement &item) +{ +    KUrl url = root.url(); + +    QDomElement child = findOperaBookmark(item, url); + +    if (child.isNull()) +    { +        //Delete bookmark on server +    } + +} +*/ + +void OperaSyncHandler::handleLocalGroup(const KBookmarkGroup &root, const QDomElement &item, QString parentId) +{ +    KBookmark current = root.first(); + +    kDebug() << "Handling " << parentId; +    while(!current.isNull()) +    { +        kDebug() << "Looping"; +        if (current.isGroup()) +        { +            QString groupName = current.fullText(); +            QDomElement child = findOperaFolder(item, groupName); + +            if (child.isNull()) +            { +                //Add Opera group here +                kDebug() << "Add group " << groupName; +                kDebug() << "Parent is " << item.text(); +                //QString parentId = getIdFromResource(item); +                kDebug() << "Parent id is " << parentId; +                KJob *job = addBookmarkFolderOnServer(current.fullText(), parentId); +                jobToGroupMap.insert(job, current.toGroup()); +            } +            else +            { +                kDebug() << "Handling group " << groupName; + +                QDomElement grandChild = getChildElement(child, "children"); + +                QString id = getChildString(child, "id"); + +                if (grandChild.isNull()) +                { +                    handleLocalGroup(current.toGroup(), grandChild, id); +                } +                else +                { +                    handleLocalGroup(current.toGroup(), grandChild, id); +                } + + +            } +        } +        else +        { +            KUrl url = current.url(); + +            QDomElement child = findOperaBookmark(item, url); + +            if (child.isNull()) +            { +                //Add bookmark on server +                kDebug() << "Add bookmark :" << url; +                kDebug() << "Parent is : " << item.text(); +                //QString parentId = getIdFromResource(item); +                kDebug() << "Parent id is " << parentId; +                addBookmarkOnServer(current.fullText(), current.url().url(), parentId); +            } +            else +            { +                kDebug() << "Bookmark exists :" << url; +            } +        } + +        current = root.next(current); +    } +} + +void OperaSyncHandler::addBookmarkOnServer(QString title, QString url, QString parent) +{ +    QOAuth::ParamMap requestMap; +    requestMap.insert("api_output", "xml"); +    requestMap.insert("api_method","create"); +    requestMap.insert("item_type","bookmark"); +    requestMap.insert("title", QUrl::toPercentEncoding(title.toUtf8())); +    requestMap.insert("uri", QUrl::toPercentEncoding(url.toUtf8())); + +    QByteArray requestUrl = "https://link.api.opera.com/rest/bookmark/"; + +    if (!parent.isNull()) +    { +        requestUrl.append(parent.toUtf8()); +    } + +    QByteArray postData = qoauth->createParametersString(requestUrl, QOAuth::POST, authToken, authTokenSecret, QOAuth::HMAC_SHA1, requestMap, QOAuth::ParseForRequestContent); + +    kDebug() << "Post data is : " << postData; + +    kDebug() << "Request Url is : " << requestUrl; + +    KIO::TransferJob *job = KIO::http_post( KUrl(requestUrl), postData, KIO::HideProgressInfo ); +    job->addMetaData("Content-Type", "application/x-www-form-urlencoded" ); + +    connect(job, SIGNAL(result(KJob*)), this, SLOT(bookmarkResultSlot(KJob*))); +    connect(job, SIGNAL(data(KIO::Job*, QByteArray)), this, SLOT(bookmarkDataSlot(KIO::Job*, QByteArray))); + +} + +KJob *OperaSyncHandler::addBookmarkFolderOnServer(QString title, QString parent) +{ +    QOAuth::ParamMap requestMap; +    requestMap.insert("api_output", "xml"); +    requestMap.insert("api_method","create"); +    requestMap.insert("item_type","bookmark_folder"); +    requestMap.insert("title", QUrl::toPercentEncoding(title.toUtf8())); + +    QByteArray requestUrl = "https://link.api.opera.com/rest/bookmark/"; +    if (!parent.isNull()) +    { +        requestUrl.append(parent.toUtf8()); +    } + +    QByteArray postData = qoauth->createParametersString(requestUrl, QOAuth::POST, authToken, authTokenSecret, QOAuth::HMAC_SHA1, requestMap, QOAuth::ParseForRequestContent); + +    kDebug() << "Post data is : " << postData; + +    kDebug() << "Request Url is : " << requestUrl; + +    KIO::TransferJob *job = KIO::http_post( KUrl(requestUrl), postData, KIO::HideProgressInfo ); +    job->addMetaData("Content-Type", "application/x-www-form-urlencoded" ); +    jobToResponseMap.insert(job, ""); + +    connect(job, SIGNAL(result(KJob*)), this, SLOT(bookmarkFolderResultSlot(KJob*))); +    connect(job, SIGNAL(data(KIO::Job*, QByteArray)), this, SLOT(bookmarkFolderDataSlot(KIO::Job*, QByteArray))); + +    return job; +} + +void OperaSyncHandler::deleteResourceOnServer(QString id) +{ +    QOAuth::ParamMap requestMap; +    requestMap.insert("api_method","delete"); + +    QByteArray requestUrl = "https://link.api.opera.com/rest/bookmark/"; + +    if (id.isEmpty()) +    { +        qDebug() << "Id is empty!"; +        return; +    } + +    requestUrl.append(id.toUtf8()); +    QByteArray postData = qoauth->createParametersString(requestUrl, QOAuth::POST, authToken, authTokenSecret, QOAuth::HMAC_SHA1, requestMap, QOAuth::ParseForRequestContent); + +    kDebug() << "Deleting Resource : " << id; +    kDebug() << "Post data is : " << postData; + +    kDebug() << "Request Url is : " << requestUrl; + +    KIO::TransferJob *job = KIO::http_post( KUrl(requestUrl), postData, KIO::HideProgressInfo ); +    job->addMetaData("Content-Type", "application/x-www-form-urlencoded" ); + +    connect(job, SIGNAL(result(KJob*)), this, SLOT(bookmarkResultSlot(KJob*))); +    connect(job, SIGNAL(data(KIO::Job*, QByteArray)), this, SLOT(bookmarkDataSlot(KIO::Job*, QByteArray))); + +} + +//Get url for a bookmark from xml element of Opera bookmarks +QString OperaSyncHandler::getUrlFromResourceProperties(const QDomElement &item) +{ +    if (item.tagName() != "resource")   return QString(); +    QDomNodeList propertiesList = item.elementsByTagName("properties"); + +    if (propertiesList.size() > 0) +    { +        QDomElement properties = propertiesList.at(0).toElement(); +        QDomNodeList uriList = properties.elementsByTagName("uri"); +        if (uriList.size() > 0) +            return uriList.at(0).toElement().text(); +    } + +    return QString(); +} + +//Get title for a bookmark or folder from xml element of Opera bookmarks +QString OperaSyncHandler::getTitleFromResourceProperties(const QDomElement &item) +{ +    if (item.tagName() != "resource")   return QString(); + +    QDomNodeList propertiesList = item.elementsByTagName("properties"); + +    if (propertiesList.size() > 0) +    { +        QDomElement properties = propertiesList.at(0).toElement(); +        QDomNodeList titleList = properties.elementsByTagName("title"); +        if (titleList.size() > 0) +            return titleList.at(0).toElement().text(); +    } + +    return QString(); +} + +//Get id for a bookmark or folder from xml element of Opera bookmarks +QString OperaSyncHandler::getIdFromResource(const QDomElement &item) +{ +    if (item.tagName() != "resource")   return QString(); + +    QDomNodeList idList = item.elementsByTagName("id"); + +    if (idList.size() > 0) +    { +        return idList.at(0).toElement().text(); +    } + +    return QString(); +} + +//Get value of a child element of a dom node +QString OperaSyncHandler::getChildString(const QDomNode &node, const QString &name) +{ +    QDomNodeList nodes = node.childNodes(); + +    for (int j=0; j<nodes.size(); ++j) +    { +        QDomElement element = nodes.at(j).toElement(); + +        if (nodes.at(j).nodeName() == name) +        { +            //kDebug() << "Url : " << element.text(); +            return element.text(); +        } +    } +    return NULL; +} + +//Get value of a child element of a dom node +QDomElement OperaSyncHandler::getChildElement(const QDomNode &node, const QString &name) +{ +    QDomNodeList nodes = node.childNodes(); + +    for (int j=0; j<nodes.size(); ++j) +    { +        QDomElement element = nodes.at(j).toElement(); + +        if (nodes.at(j).nodeName() == name) +        { +            //kDebug() << "Url : " << element.text(); +            return element; +        } +    } +    return QDomElement(); +} +//Find a bookmark group in a specifiec bookmark group of client +KBookmarkGroup OperaSyncHandler::findLocalGroup(const KBookmarkGroup &root, const QString &name) +{ +    KBookmark child = root.first(); + +    while (!child.isNull()) +    { +        kDebug() << child.fullText(); +        if (child.isGroup() && name == child.fullText()) +        { +            break; +        } +        child = root.next(child); +    } + +    return child.toGroup(); +} + +//Find a bookmark in a specifiec bookmark group of client +KBookmark OperaSyncHandler::findLocalBookmark(const KBookmarkGroup &root, const KUrl &url) +{ +    KBookmark child = root.first(); + +    kDebug() << "finding bookmark " << url << " in : " << root.text(); + +    while (!child.isNull()) +    { +        kDebug() << child.url(); +        if (!child.isGroup() && url == child.url()) +        { +            break; +        } +        child = root.next(child); +    } + +    return child; +} + +//Find bookmark folder in xml returned by server +QDomElement OperaSyncHandler::findOperaFolder(const QDomElement &root, const QString &name) +{ +    QDomElement current = root.firstChild().toElement(); + +    kDebug() << "Finding group " << name; +    while (!current.isNull()) +    { +//        kDebug() << "in " <<  getTitleFromResourceProperties(current); +        if ((getChildString(current, "item_type") == "bookmark_folder") && getTitleFromResourceProperties(current) == name) +            break; +        current = current.nextSibling().toElement(); +    } + +    return current; +} + +//Find bookmark in xml returned by server +QDomElement OperaSyncHandler::findOperaBookmark(const QDomElement &root, const KUrl &url) +{ +    QDomElement current = root.firstChild().toElement(); + +    kDebug() << "Finding bookmark " << url; +    while (!current.isNull()  ) +    { +//        kDebug() << "in " <<  getUrlFromResourceProperties(current); +        if ((getChildString(current, "item_type") == "bookmark") && KUrl(getUrlFromResourceProperties(current)) == url) +            break; +        current = current.nextSibling().toElement(); +    } + +    return current; +} diff --git a/src/sync/operasynchandler.h b/src/sync/operasynchandler.h new file mode 100644 index 00000000..5131425f --- /dev/null +++ b/src/sync/operasynchandler.h @@ -0,0 +1,142 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2012 by Siteshwar Vashisht <siteshwar at gmail dot com> +* Copyright (C) 2011 by Andrea Diamantini <adjam7 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 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* 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. +* +* You should have received a copy of the GNU General Public License +* along with this program.  If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef OPERA_SYNC_HANDLER_H +#define OPERA_SYNC_HANDLER_H + +#include <QWebPage> + +// Local Includes +#include "synchandler.h" + +// KDE Includes +#include <KUrl> +#include <KBookmarkGroup> +#include <KIO/Job> + +// Qt Includes +#include <QtOAuth/QtOAuth> + +// Forward Declarations +class QNetworkReply; +class BookmarkManager; +class QWebView; + +class OperaSyncHandler : public SyncHandler +{ +    Q_OBJECT + +public: +    OperaSyncHandler(QObject *parent = 0); + +    void syncHistory(); +    void syncBookmarks(); +    void syncPasswords(); + +    void initialLoadAndCheck(); + +private Q_SLOTS: +    void loadFinished(bool); +/*    void fetchingBookmarksFinished(); +    void updateBookmarkFinished(); +*/ +    void dataSlot(KIO::Job*, QByteArray); +    void resultSlot(KJob*); + +    void bookmarkDataSlot(KIO::Job*, QByteArray); +    void bookmarkResultSlot(KJob*); + +    void bookmarkFolderDataSlot(KIO::Job*, QByteArray); +    void bookmarkFolderResultSlot(KJob*); + +Q_SIGNALS: +    void syncBookmarksFinished(bool); +    void syncHistoryFinished(bool); +    void syncPasswordsFinished(bool); + +private: +    enum {SEND_CHANGES, RECEIVE_CHANGES} _mode; +    enum BookmarkType {BOOKMARK, BOOKMARK_FOLDER}; + +    bool syncRelativeEnabled(bool); +    void startLogin(); +    void getBookmarks(); +    void handleBookmark(const QDomElement &item, KBookmarkGroup root); +    void handleBookmarkFolder(const QDomElement &item, KBookmarkGroup &root); +    void handleResource(const QDomNode &item, KBookmarkGroup &root); + +//    void handleLocalBookmark(const KBookmarkGroup &root, const QDomElement &item); +    void handleLocalGroup(const KBookmarkGroup &root, const QDomElement &item, QString parentId); + +    void addBookmarkOnServer(QString, QString, QString parent = QString()); +    KJob *addBookmarkFolderOnServer(QString, QString parent = QString()); +    void deleteResourceOnServer(QString id); + +    static QString getUrlFromResourceProperties(const QDomElement &item); +    static QString getTitleFromResourceProperties(const QDomElement &item); +    static QString getIdFromResource(const QDomElement &item); +    static QString getChildString(const QDomNode &node, const QString &name); +    static QDomElement getChildElement(const QDomNode &node, const QString &name); + +    static KBookmarkGroup findLocalGroup(const KBookmarkGroup &root, const QString &name); +    static KBookmark findLocalBookmark(const KBookmarkGroup &root, const KUrl &url); + +    static QDomElement findOperaFolder(const QDomElement &root, const QString &name); +    static QDomElement findOperaBookmark(const QDomElement &root, const KUrl &url); + +/*    void checkToAddGB(const KBookmarkGroup &root, const QDomNodeList &); +    void checkToDeleteGB(BookmarkManager *, const QDomNodeList &); +    QString getChildElement(const QDomNode &node, QString name); +    void checkRequestCount();*/ + + +    //    QUrl _remoteBookmarksUrl; +    bool _doLogin; + +    QWebPage _webPage; +/*    QNetworkReply *_reply; +    QSet<KUrl> _bookmarksToAdd; +    QSet<QString> _bookmarksToDelete; +    unsigned int _requestCount;*/ + +    bool _isSyncing; + +    QOAuth::Interface *qoauth; +    QOAuth::ParamMap requestParam, resultParam, authParams; +    QByteArray requestToken, requestTokenSecret; +    QByteArray authToken, authTokenSecret; + +    QUrl url; +//    QSslSocket *socket; +    QByteArray urlParams; +    QWebView *webView; +    QByteArray xmlData; +    QMap<KJob*, QByteArray> jobToResponseMap; +    QMap<KJob*, KBookmarkGroup> jobToGroupMap; +}; + +#endif // OPERA_SYNC_HANDLER_H diff --git a/src/sync/sync_host_type.ui b/src/sync/sync_host_type.ui index ba96ab83..ed7e1cd9 100644 --- a/src/sync/sync_host_type.ui +++ b/src/sync/sync_host_type.ui @@ -32,6 +32,13 @@         </widget>        </item>        <item> +       <widget class="QRadioButton" name="operaRadioButton"> +        <property name="text"> +         <string>Opera Bookmarks</string> +        </property> +       </widget> +      </item> +      <item>         <widget class="QRadioButton" name="nullRadioButton">          <property name="text">           <string>/dev/null</string> diff --git a/src/sync/sync_opera_settings.ui b/src/sync/sync_opera_settings.ui new file mode 100644 index 00000000..5144c552 --- /dev/null +++ b/src/sync/sync_opera_settings.ui @@ -0,0 +1,70 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>SyncOperaSettings</class> + <widget class="QWidget" name="SyncOperaSettings"> +  <property name="geometry"> +   <rect> +    <x>0</x> +    <y>0</y> +    <width>400</width> +    <height>300</height> +   </rect> +  </property> +  <layout class="QVBoxLayout" name="verticalLayout"> +   <item> +    <widget class="QGroupBox" name="operaGroupBox"> +     <property name="title"> +      <string>Opera Account Settings</string> +     </property> +     <layout class="QFormLayout" name="formLayout"> +      <property name="fieldGrowthPolicy"> +       <enum>QFormLayout::ExpandingFieldsGrow</enum> +      </property> +      <item row="0" column="0"> +       <widget class="QLabel" name="label_2"> +        <property name="text"> +         <string>Username:</string> +        </property> +       </widget> +      </item> +      <item row="0" column="1"> +       <widget class="KLineEdit" name="kcfg_syncUser"/> +      </item> +      <item row="1" column="0"> +       <widget class="QLabel" name="label_3"> +        <property name="text"> +         <string>Password:</string> +        </property> +       </widget> +      </item> +      <item row="1" column="1"> +       <widget class="KLineEdit" name="kcfg_syncPass"/> +      </item> +     </layout> +    </widget> +   </item> +   <item> +    <spacer name="verticalSpacer"> +     <property name="orientation"> +      <enum>Qt::Vertical</enum> +     </property> +     <property name="sizeHint" stdset="0"> +      <size> +       <width>20</width> +       <height>124</height> +      </size> +     </property> +    </spacer> +   </item> +  </layout> + </widget> + <customwidgets> +  <customwidget> +   <class>KLineEdit</class> +   <extends>QLineEdit</extends> +   <header>klineedit.h</header> +  </customwidget> + </customwidgets> + <resources/> + <connections/> +</ui> diff --git a/src/sync/syncassistant.cpp b/src/sync/syncassistant.cpp index 651cad75..078ff375 100644 --- a/src/sync/syncassistant.cpp +++ b/src/sync/syncassistant.cpp @@ -35,6 +35,7 @@  #include "syncftpsettingswidget.h"  #include "syncgooglesettingswidget.h" +#include "syncoperasettingswidget.h"  SyncAssistant::SyncAssistant(QWidget *parent) @@ -46,5 +47,6 @@ SyncAssistant::SyncAssistant(QWidget *parent)      setPage(Page_Type, new SyncHostTypeWidget(this));      setPage(Page_FTP_Settings, new SyncFTPSettingsWidget(this));      setPage(Page_Google_Settings, new SyncGoogleSettingsWidget(this)); +    setPage(Page_Opera_Settings, new SyncOperaSettingsWidget(this));      setPage(Page_Check, new SyncCheckWidget(this));  } diff --git a/src/sync/syncassistant.h b/src/sync/syncassistant.h index e09db71a..263c918a 100644 --- a/src/sync/syncassistant.h +++ b/src/sync/syncassistant.h @@ -43,6 +43,7 @@ public:          Page_Type,          Page_FTP_Settings,          Page_Google_Settings, +        Page_Opera_Settings,          Page_Check      }; diff --git a/src/sync/synccheckwidget.cpp b/src/sync/synccheckwidget.cpp index 5fdf5cd7..7d44c580 100644 --- a/src/sync/synccheckwidget.cpp +++ b/src/sync/synccheckwidget.cpp @@ -65,6 +65,11 @@ void SyncCheckWidget::initializePage()          syncLabel->setText(i18n("Google"));          hostLabel->setText(ReKonfig::syncHost());      } +    else if (ReKonfig::syncType() == 2) +    { +        syncLabel->setText(i18n("Opera")); +        hostLabel->setText(ReKonfig::syncHost()); +    }      else      {          syncLabel->setText(i18n("No sync")); diff --git a/src/sync/synchosttypewidget.cpp b/src/sync/synchosttypewidget.cpp index d52baf34..73f9a7cb 100644 --- a/src/sync/synchosttypewidget.cpp +++ b/src/sync/synchosttypewidget.cpp @@ -42,8 +42,10 @@ SyncHostTypeWidget::SyncHostTypeWidget(QWidget *parent)      if (ReKonfig::syncType() == 0)          ftpRadioButton->setChecked(true); -    else if (ReKonfig::syncType() == 1) +    else if(ReKonfig::syncType() == 1)          googleRadioButton->setChecked(true); +    else if(ReKonfig::syncType() == 2) +        operaRadioButton->setChecked(true);      else          nullRadioButton->setChecked(true);  } @@ -57,14 +59,19 @@ int SyncHostTypeWidget::nextId() const          ReKonfig::setSyncType(0);          return SyncAssistant::Page_FTP_Settings;      } -    else if (googleRadioButton->isChecked()) +	else if (googleRadioButton->isChecked()) +	{ +		ReKonfig::setSyncType(1); +		return SyncAssistant::Page_Google_Settings; +	} +    else if (operaRadioButton->isChecked())      { -        ReKonfig::setSyncType(1); -        return SyncAssistant::Page_Google_Settings; +        ReKonfig::setSyncType(2); +        return SyncAssistant::Page_Opera_Settings;      }      else      { -        ReKonfig::setSyncType(2); +        ReKonfig::setSyncType(3);          return SyncAssistant::Page_Check;      } diff --git a/src/sync/syncmanager.cpp b/src/sync/syncmanager.cpp index aeb543d0..a4acb80b 100644 --- a/src/sync/syncmanager.cpp +++ b/src/sync/syncmanager.cpp @@ -39,6 +39,7 @@  #include "syncassistant.h"  #include "ftpsynchandler.h"  #include "googlesynchandler.h" +#include "operasynchandler.h"  // KDE Includes  #include <klocalizedstring.h> @@ -83,6 +84,9 @@ void SyncManager::loadSettings()          case 1:              _syncImplementation = new GoogleSyncHandler(this);              break; +        case 2: +            _syncImplementation = new OperaSyncHandler(this); +            break;          default:              kDebug() << "/dev/null";              return; diff --git a/src/sync/syncoperasettingswidget.cpp b/src/sync/syncoperasettingswidget.cpp new file mode 100644 index 00000000..0b5e3386 --- /dev/null +++ b/src/sync/syncoperasettingswidget.cpp @@ -0,0 +1,60 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* Copyright (C) 2012 by Siteshwar Vashisht <siteshwar at gmail dot com> +* Copyright (C) 2011 by Andrea Diamantini <adjam7 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 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* 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. +* +* You should have received a copy of the GNU General Public License +* along with this program.  If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "syncoperasettingswidget.h" +#include "syncoperasettingswidget.moc" + +// Auto Includes +#include "rekonq.h" + +// Local Includes +#include "syncassistant.h" + + +SyncOperaSettingsWidget::SyncOperaSettingsWidget(QWidget *parent) +    : QWizardPage(parent) +{ +    setupUi(this); +    kcfg_syncUser->setText(ReKonfig::syncUser()); +    kcfg_syncPass->setText(ReKonfig::syncPass()); + +    kcfg_syncPass->setPasswordMode(true); +} + + +int SyncOperaSettingsWidget::nextId() const +{ +    // save +    ReKonfig::setSyncHost("http://link.opera.com/"); +    ReKonfig::setSyncUser(kcfg_syncUser->text()); +    ReKonfig::setSyncPass(kcfg_syncPass->text()); + +    ReKonfig::setSyncHistory(false); +    ReKonfig::setSyncPasswords(false); + +    return SyncAssistant::Page_Check; +} diff --git a/src/sync/syncoperasettingswidget.h b/src/sync/syncoperasettingswidget.h new file mode 100644 index 00000000..5eb608d3 --- /dev/null +++ b/src/sync/syncoperasettingswidget.h @@ -0,0 +1,52 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2011 by Siteshwar Vashisht <siteshwar AT gmail.com>  +* Copyright (C) 2011 by Andrea Diamantini <adjam7 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 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* 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. +* +* You should have received a copy of the GNU General Public License +* along with this program.  If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef SYNC_OPERA_SETTINGS_WIDGET_H +#define SYNC_OPERA_SETTINGS_WIDGET_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// Ui Includes +#include "ui_sync_opera_settings.h" + +// Qt Includes +#include <QWizardPage> + + +class SyncOperaSettingsWidget : public QWizardPage, private Ui::SyncOperaSettings +{ +    Q_OBJECT + +public: +    SyncOperaSettingsWidget(QWidget *parent = 0); + +    int nextId() const; +}; + +#endif // SYNC_OPERA_SETTINGS_WIDGET_H | 
