/*
 *  Copyright (C) 2007-2008 CMM Sigma Andrzej Chmielowiec 
<cmmsigma@cmmsigma.eu>
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License version 2
 *  as published by the Free Software Foundation.
 *
 *  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.
 */

// QtPop3.h: interface for the QtPop3 class.
//
//////////////////////////////////////////////////////////////////////

#ifndef QTPOP3_H
#define QTPOP3_H

#include "QtTelnet.h"	// Added by ClassView
#include <QQueue>
#include "MessageStructs.h"

//////////////////////////////////////////////////////////////////////
// class QtPop3
//////////////////////////////////////////////////////////////////////

class QtPop3 : public QObject  
{
	Q_OBJECT

protected:
	enum Pop3State
	{
		DISCONNECTED,
		CONNECTED,
		USER,
		PASSWORD,
		STAT,
		LIST,
		UIDL,
		RETR,
		COMPLETED,
		NOMESSAGES,
	};

	static bool equal(const QString &s1, const QString &s2);
	static bool contains(const QString &text, const QString token);

	struct ValName
	{
		QString name;
		QString value;

		void clear();
		void trim();
	};

	class ValNameList : public QList<ValName>
	{
	public:
		bool containsName(const QString name);
		bool getValue(const QString name, QString &value);
	};


public:
	void setLocalWriteMode(bool local);
	void setMessageLimit(int bytes);
	void setDownloadPath(QString path);
	void setLeaveOnServer(bool leaveOnServer = true);
	void receiveAll();
	QtPop3(QObject *parent = 0);
	virtual ~QtPop3();
	void setServer(const QString host);
	void setUserPassword(const QString user, const QString password);

signals:
	void errorOccured(const QString &error);
	void newMessages(const QStringList &messages);
	void newMessagesCount(const int &count);
	void noNewMessages();
	void messageReceived(const MessageItem &msg);


protected slots:
	void telnetMessage(const QStringList &lines);
	void telnetConnectionError(const QString &error);
	void telnetConnected();

protected:
	void getValues(const QStringList &lines, int &index, QString &name, QStringList &values, ValNameList &sub);
	bool decodeMultipart(QStringList &lines, int &index, MessageItem &msg, QString boundary, QString parentBoundary);
	bool parseMessage(MessageItem &msg, QStringList *lines = NULL);
	bool collectResponse(const QStringList &lines);
	int toInt(QString text);
	void send(QString data, bool multiPart = false);
	int mBytesLimit;
	void readStoredIDs();
	void writeStoredIDs();
	void updateStoredList();
	QString toString(int value);

	bool saveMessage();
	void getNextMessage();
	QString mDownloadPath;
	bool mLeaveOnServer;
	bool checkResponse(const QStringList &lines, int &value);
	void processReceiving(const QStringList &lines);
	QtTelnet *mTelnet;
	Pop3State mState;
	QString mUser;
	QString mPassword;
	QString mHost;
	QStringList mReceivedUIDList;
	QString mMessage;
	QStringList mResponse;
	bool mMultiPartResponse;
	bool mNextMultiPartResponse;
	bool mWriteLocal;
	QQueue<QString> mToReceive;
	QStringList serverUIDL;
	QStringList receivedUIDL;
	QHash<QString, QString> index2UID;
};

#endif
