using System;
using System.Collections;
using System.Xml;
using System.IO;
using System.Collections.Specialized;
using System.Runtime.InteropServices;
using Gtk;
using GLib;
using Novell.CASA.DataEngines.Common;
using Novell.CASA.DataEngines.GK;


namespace Novell.CASA.DataEngines
{

   /*
    * This class is implementation of Data engine for Gnome-Keyring.
    */

    class GKEngine : DataEngine
    {
       public GKEngine()
       {

       }

       public XmlNode Aggregate()
       {
            XmlDocument doc = new XmlDocument();
           
            XmlNode rootElem = doc.CreateElement(ConstStrings.CCF_GKTAG);
            doc.AppendChild(rootElem);
            XmlElement keyringElem;

            ArrayList itemList;
            ArrayList attrList;
            ItemInfo itemInfo;
            KeyringInfo keyringInfo;
            int itemId;
            ArrayList keyringList = GnomeKeyring.GKGetKeyrings();
            IEnumerator kEtor = keyringList.GetEnumerator();
            IEnumerator iEtor;
           
            while(kEtor.MoveNext())
            {
                string keyring = (string)(kEtor.Current);

                keyringElem = doc.CreateElement(ConstStrings.CCF_GKKEYRING);
                XmlAttribute idAttr = doc.CreateAttribute(ConstStrings.CCF_ID);
                idAttr.Value = keyring;
                keyringElem.SetAttributeNode(idAttr);

                keyringInfo = GnomeKeyring.GKGetKeyringInfo(keyring);

                itemList = GnomeKeyring.GKGetItems(keyring);
                iEtor = itemList.GetEnumerator();
                while(iEtor.MoveNext())
                {
                    itemId = (int)iEtor.Current;
                    itemInfo = GnomeKeyring.GKGetItemInfo(keyring,itemId);
                    attrList = GnomeKeyring.GKGetAttributeList(keyring,itemId);

                    XmlElement secretElem = doc.CreateElement(ConstStrings.CCF_SECRET);
                    XmlAttribute secIdAttr = doc.CreateAttribute(ConstStrings.CCF_ID);
                    secIdAttr.Value = itemInfo.displayName + ":" + itemId;
                   
                    secretElem.SetAttributeNode(secIdAttr);

                    XmlAttribute typeAttr = doc.CreateAttribute(ConstStrings.CCF_TYPE);
                    typeAttr.Value = itemInfo.itemType.ToString();
                    secretElem.SetAttributeNode(typeAttr);

                    XmlElement keyElem = doc.CreateElement(ConstStrings.CCF_KEY);
                    XmlAttribute keyIdAttr = doc.CreateAttribute(ConstStrings.CCF_ID);
                    keyIdAttr.Value = "GKPassword";
                    keyElem.SetAttributeNode(keyIdAttr);

                    XmlElement valueElem = doc.CreateElement(ConstStrings.CCF_VALUE);
                    valueElem.InnerText = itemInfo.secret;
                    keyElem.AppendChild(valueElem);
                    secretElem.AppendChild(keyElem);
                    
                    IEnumerator attrEtor = (IEnumerator)(attrList.GetEnumerator());
                    while(attrEtor.MoveNext())
                    {
                        Novell.CASA.DataEngines.GK.Attribute attr = (Novell.CASA.DataEngines.GK.Attribute)(attrEtor.Current);
                        keyElem = doc.CreateElement(ConstStrings.CCF_KEY);
                        keyIdAttr = doc.CreateAttribute(ConstStrings.CCF_ID);
                        keyIdAttr.Value = attr.key;
                        keyElem.SetAttributeNode(keyIdAttr);

                        valueElem = doc.CreateElement(ConstStrings.CCF_VALUE);
                        valueElem.InnerText = attr.value;
                        keyElem.AppendChild(valueElem);
                        secretElem.AppendChild(keyElem);
                    }
                    
                    keyringElem.AppendChild(secretElem);
                    XmlElement timeElem = doc.CreateElement(ConstStrings.CCF_TIME);

                    XmlElement itemCreatedTimeElem = doc.CreateElement(ConstStrings.CCF_CRTIME);
                    itemCreatedTimeElem.InnerText = itemInfo.mTime.ToString();
                    timeElem.AppendChild(itemCreatedTimeElem);

                    XmlElement itemModifiedTimeElem = doc.CreateElement(ConstStrings.CCF_MDTIME);
                    itemModifiedTimeElem.InnerText = itemInfo.cTime.ToString();
                    timeElem.AppendChild(itemModifiedTimeElem);

                    secretElem.AppendChild(timeElem);
                }
                XmlElement keyringTimeElem = doc.CreateElement(ConstStrings.CCF_TIME);

                XmlElement createdTimeElem = doc.CreateElement(ConstStrings.CCF_CRTIME);
                createdTimeElem.InnerText = keyringInfo.mTime.ToString();
                keyringTimeElem.AppendChild(createdTimeElem);

                XmlElement modifiedTimeElem = doc.CreateElement(ConstStrings.CCF_MDTIME);
                modifiedTimeElem.InnerText = keyringInfo.cTime.ToString();
                keyringTimeElem.AppendChild(modifiedTimeElem);

                keyringElem.AppendChild(keyringTimeElem);

                XmlElement lockElem = doc.CreateElement(ConstStrings.CCF_LOCK);

                XmlAttribute lockStatusAttr = doc.CreateAttribute(ConstStrings.CCF_LOCKSTATUS);
                if( keyringInfo.isLocked == 1 )
                    lockStatusAttr.Value = "locked";
                else
                    lockStatusAttr.Value = "unlocked";
                lockElem.SetAttributeNode(lockStatusAttr);

                XmlAttribute lockOnIdleAttr = doc.CreateAttribute(ConstStrings.CCF_LOCKHAND);
                if( keyringInfo.lockOnIdle == 1)
                    lockOnIdleAttr.Value = "true";
                else
                    lockOnIdleAttr.Value = "false";
                lockElem.SetAttributeNode(lockOnIdleAttr);

                XmlAttribute lockTimeoutAttr = doc.CreateAttribute(ConstStrings.CCF_LOCKTIME);
                lockTimeoutAttr.Value = keyringInfo.lockTimeout.ToString();
                lockElem.SetAttributeNode(lockTimeoutAttr);

                keyringElem.AppendChild(lockElem);
                rootElem.AppendChild(keyringElem);
            }
#if TEST
            XmlTextWriter writer = new XmlTextWriter("./gk.xml",null);
            writer.Formatting = Formatting.Indented;
            doc.Save(writer);
            writer.Close();
#endif

            return doc.ChildNodes[0];
        }
        public  int SetSecret(XmlNode secret)
        {
            return ConstStrings.CASA_SUCCESS;
        }

        public  int GetSecret(XmlNode secret)
        {
            return ConstStrings.CASA_SUCCESS;
        }
        public  int Remove(XmlNode secret)
        {
            return ConstStrings.CASA_SUCCESS;
        }

    }
}