/*
 * privacymanager.h
 * Copyright (C) 2006  Remko Troncon
 *
 * 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) 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.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <https://www.gnu.org/licenses/>.
 *
 */

#ifndef PSIPRIVACYMANAGER_H
#define PSIPRIVACYMANAGER_H

#include "privacymanager.h"
#include "xmpp_jid.h"

#include <QHash>
#include <QObject>
#include <QStringList>

class PrivacyList;
class PrivacyListItem;
class PrivacyListListener;
class PsiAccount;
class QString;

namespace XMPP {
class Task;
}

class PsiPrivacyManager : public PrivacyManager {
    Q_OBJECT

public:
    PsiPrivacyManager(PsiAccount *account, XMPP::Task *rootTask);
    virtual ~PsiPrivacyManager();

    void requestListNames();

    void changeDefaultList(const QString &name);
    void changeActiveList(const QString &name);
    void changeList(const PrivacyList &list);
    void getDefaultList();
    void requestList(const QString &name);

    // Convenience
    void block(const QString &);

protected:
    static QStringList blockedContacts(const PrivacyList &, bool *allBlocked);

    // Can these be private ?
protected slots:
    void receiveLists();
    void receiveList();
    void changeDefaultList_finished();
    void changeActiveList_finished();
    void changeList_finished();
    void getDefault_listsReceived(const QString &, const QString &, const QStringList &);
    void getDefault_listsError();
    void getDefault_listReceived(const PrivacyList &);
    void getDefault_listError();

    void block_getDefaultList_success(const PrivacyList &);
    void block_getDefaultList_error();

private:
    XMPP::Task *         rootTask_;
    PrivacyListListener *listener_;

    bool    getDefault_waiting_;
    QString getDefault_default_;

    QStringList block_targets_;
    bool        block_waiting_;

public:
    bool isAvailable() const;

    bool isContactBlocked(const XMPP::Jid &jid) const;
    void setContactBlocked(const XMPP::Jid &jid, bool blocked);

signals:
    void availabilityChanged();
    void listChanged(const QStringList &contacts);

    // void simulateContactOffline(const XMPP::Jid& contact);

private slots:
    void newListReceived(const PrivacyList &p);
    void newListsReceived(const QString &defaultList, const QString &activeList, const QStringList &lists);
    void newListsError();

    void accountStateChanged();

    void newChangeDefaultList_success();
    void newChangeDefaultList_error();
    void newChangeActiveList_success();
    void newChangeActiveList_error();

private slots:
    void privacyListChanged(const QString &name);

private:
    PsiAccount *                  account_;
    bool                          accountAvailable_;
    bool                          isAvailable_;
    QHash<QString, PrivacyList *> lists_;
    QHash<QString, bool>          isBlocked_;

    void invalidateBlockedListCache();
    void setIsAvailable(bool available);

    void            createBlockedList();
    PrivacyList *   blockedList() const;
    PrivacyListItem blockItemFor(const XMPP::Jid &jid) const;

    QStringList blockedContacts() const;

    QString blockedListName_, tmpActiveListName_;
    bool    isAuthorized(const XMPP::Jid &jid) const;
};

#endif // PSIPRIVACYMANAGER_H
