/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
/***************************************************************************
 *            camel-kolab-imapx-server.c
 *
 *  2011-12-02, 17:05:41
 *  Copyright 2011, Christian Hilberg
 *  <hilberg@unix-ag.org>
 ****************************************************************************/

/*
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with main.c; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor Boston, MA 02110-1301,  USA
 */

/*----------------------------------------------------------------------------*/

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <string.h>

#include <libekolabutil/kolab-util-error.h>

#include "camel-kolab-imapx-store.h"
#include "camel-kolab-imapx-server.h"

/*----------------------------------------------------------------------------*/

#define CAMEL_KOLAB_IMAPX_SERVER_PRIVATE(obj)  (G_TYPE_INSTANCE_GET_PRIVATE ((obj), CAMEL_TYPE_KOLAB_IMAPX_SERVER, CamelKolabIMAPXServerPrivate))

G_DEFINE_TYPE (CamelKolabIMAPXServer, camel_kolab_imapx_server, CAMEL_TYPE_IMAPX_EXTD_SERVER)

/*----------------------------------------------------------------------------*/
/* object init */

static void
camel_kolab_imapx_server_init (CamelKolabIMAPXServer *self)
{
	g_assert (CAMEL_IS_KOLAB_IMAPX_SERVER (self));
}

static void
camel_kolab_imapx_server_constructed (GObject *object)
{
	g_assert (CAMEL_IS_KOLAB_IMAPX_SERVER (object));

	G_OBJECT_CLASS (camel_kolab_imapx_server_parent_class)->constructed (object);
}


static void
camel_kolab_imapx_server_dispose (GObject *object)
{
	g_assert (CAMEL_IS_KOLAB_IMAPX_SERVER (object));

	G_OBJECT_CLASS (camel_kolab_imapx_server_parent_class)->dispose (object);
}

static void
camel_kolab_imapx_server_finalize (GObject *object)
{
	g_assert (CAMEL_IS_KOLAB_IMAPX_SERVER (object));

	G_OBJECT_CLASS (camel_kolab_imapx_server_parent_class)->finalize (object);
}

/*----------------------------------------------------------------------------*/
/* local statics */

/*----------------------------------------------------------------------------*/
/* class functions */

/*----------------------------------------------------------------------------*/
/* class init */

static void
camel_kolab_imapx_server_class_init (CamelKolabIMAPXServerClass *klass)
{
	GObjectClass *object_class = G_OBJECT_CLASS (klass);

	object_class->constructed = camel_kolab_imapx_server_constructed;
	object_class->dispose = camel_kolab_imapx_server_dispose;
	object_class->finalize = camel_kolab_imapx_server_finalize;
}

/*----------------------------------------------------------------------------*/
/* API functions */

CamelKolabIMAPXServer*
camel_kolab_imapx_server_new (CamelKolabIMAPXStore *store)
{
	CamelKolabIMAPXServer *self = NULL;
	CamelIMAPXServer *is = NULL;
	CamelService *service = NULL;
	CamelSession *session = NULL;

	g_assert (CAMEL_IS_KOLAB_IMAPX_STORE (store));

	service = CAMEL_SERVICE (store);
	session = camel_service_get_session (service);

	self = g_object_new (CAMEL_TYPE_KOLAB_IMAPX_SERVER, NULL);

	is = CAMEL_IMAPX_SERVER (self);

	is->session = g_object_ref (session);
	is->store = CAMEL_STORE (store);

	return self;
}

#if 0
/* CAUTION -- TESTING purposes only! The server response may
 *            become too long to properly handle it!
 *
 *            The CamelKolabImapxMetadata has been moved to
 *            CamelKolabIMAPXStore - to resurrect this function,
 *            it needs to be moved over to CamelKolabIMAPXStore
 */
gboolean
camel_kolab_imapx_server_retrieve_all_folder_types (CamelKolabIMAPXServer *self,
                                                    GCancellable *cancellable,
                                                    GError **err)
{
	CamelIMAPXExtdServer *eserver = NULL;
	CamelOfflineStore *ostore = NULL;
	CamelImapxMetadataSpec *spec = NULL;
	camel_imapx_metadata_proto_t proto = CAMEL_IMAPX_METADATA_PROTO_INVAL;
	GError *tmp_err = NULL;

	g_assert (CAMEL_IS_KOLAB_IMAPX_SERVER (self));
	/* cancellable may be NULL */
	g_return_val_if_fail (err == NULL || *err == NULL, FALSE);

	/* check whether we're online */
	ostore = CAMEL_OFFLINE_STORE (CAMEL_IMAPX_SERVER (self)->store);
	if (! camel_offline_store_get_online (ostore)) {
		/* TODO turn this into proper GError */
		g_warning ("%s: must be online to complete this operation",
		           __func__);
		return FALSE;
	}

	/* TODO check whether we're authenticated */
	g_debug ("%s: implement authenticated check", __func__);

	eserver = CAMEL_IMAPX_EXTD_SERVER (self);

	proto = camel_imapx_extd_server_metadata_get_proto (eserver);
	spec = camel_imapx_metadata_spec_new (proto,
	                                      "*",
	                                      "/vendor/kolab/folder-type",
	                                      "value",
	                                      &tmp_err);
	if (spec == NULL) {
		g_propagate_error (err, tmp_err);
		return FALSE;
	}

	/* fetch annotations from server, do not resect the data
	 * from CamelIMAPXExtdServer as yet
	 */
	(void)camel_imapx_extd_server_get_metadata (eserver,
	                                            spec,
	                                            FALSE,
	                                            cancellable,
	                                            &tmp_err);
	camel_imapx_metadata_spec_free (spec);
	if (tmp_err != NULL) {
		g_propagate_error (err, tmp_err);
		return FALSE;
	}

	return TRUE;
}
#endif

/*----------------------------------------------------------------------------*/
