#!/usr/bin/python

#
# Copyright (C) 2005 Red Hat, Inc.
#
# 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, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#

from gconfvisitor import *

"""Personalize from a prototype account"""
class PersonalizeVisitor(EvolutionAccountGConfVisitor):
    def __init__(self, username, friendly_name, mailbox_name, server_name, uidHostname, emailDomain):
        self.username = username;
        self.friendly_name = friendly_name;
        self.mailbox_name = mailbox_name
        self.server_name = server_name
        self.uidHostname = uidHostname
        self.emailDomain = emailDomain

    def personalizeHumanReadableName(self, nameText):
        # The general case isn't doable, but look for things of the form SOMEONE@SOMETHING and remap to our username; hopefully this should work for many cases:
        pat = re.compile(usernameRegex + "@(.*)")
        mo = pat.search(nameText)
        if mo:
            if self.emailDomain:
                return self.username + "@" + self.emailDomain
            else:
                return self.username + "@" + mo.group(2)            
        else:
            return nameText

    def personalizeAddrSpec(self, addrSpec):
        # Look for the form "username@host":
        pat = re.compile(usernameRegex + "@" + hostnameRegex)
        mo = pat.search(addrSpec)
        if mo:
            
            if self.emailDomain:
                domain = self.emailDomain
            else:
                domain = mo.group(2)
            
            return self.username + "@" + domain
        else:
            return addrSpec;

    def personalizeRelativeURI(self, relative_uri):
        # Look for the form "username@host":
        # FIXME: make more robust
        pat = re.compile(usernameRegex + "@" + hostnameRegex)
        mo = pat.search(relative_uri)
        if mo:
            return self.username + "@" + self.personalizeServerName(mo.group(2))
        else:
            return relative_uri;

    def personalizeBaseURI(self, baseURI):
        url = urlparse (baseURI);
        if url[0] == "file":
            # Expect something of the form "/PATH_TO_HOME_DIR/USERNAME/.evolution/PATH_BELOW_HOME_DIR
            path = url[2]
            newPath = self.personalizePath(path)
            return "file://"+newPath;
        else:
            # Nothing to be done:
            return baseURI;

    def personalizeURI(self, inputURI):
        # Expect something of the form "SCHEME://USERNAME@HOSTNAME/PATH"
        fullRegex = schemeRegex+"://"+usernameRegex+"@"+hostnameRegex+"/"+pathRegex
        pat = re.compile(fullRegex)
        mo = pat.search(inputURI)
        if mo:
            newURI = mo.group(1)+"://"+self.username+"@"+self.personalizeServerName(mo.group(3))+"/"+mo.group(4)
            return newURI
        else:                         
            return inputURI;

    def personalizeUID(self, inputUID):
        # Expect something of the form "numbers-and-dots@HOSTNAME"
        if self.uidHostname:
            pat = re.compile("([0-9\\.]*)@"+hostnameRegex)
            mo = pat.search(inputUID)
            if mo:
                newUID = mo.group(1)+"@"+self.uidHostname;
                return newUID
            
        return inputUID

    """Personalize an absolute path below the ~/.evolution directory"""
    def personalizePath(self,path):
        pat = re.compile("(.*)/"+usernameRegex+"/\\.evolution/(.*)")
        mo = pat.search(path)

        if mo:
            newPath=mo.group(1)+"/"+self.username+"/.evolution/"+mo.group(3)
        else:
            newPath=path
        
        return newPath

    def personalizeServerName(self, serverName):
        if self.server_name:
            return self.server_name
        else:
            return serverName;
        

    def personalizeEvolutionExchangeUrl(self, urlText):
        # FIXME: make this more robust and generic
        # Expect a string of this form: "exchange://USERNAME@EXCH-SERVER.EXAMPLE.COM/;pf_server=EXCH-SERVER.EXAMPLE.COM;owa_path=/exchange;mailbox=USERNAME;ad_limit=NUMBER;ad_server=AD-SERVER.EXAMPLE.COM"
        patternText = "exchange://"+usernameRegex+"@"+hostnameRegex+"/;pf_server="+hostnameRegex+";owa_path=([/A-Za-z0-9\\.]*);mailbox="+mailboxRegex+";ad_limit=([0-9]*);ad_server="+hostnameRegex;
        pat = re.compile(patternText);
        mo = pat.search(urlText);

        mailServer = self.personalizeServerName(mo.group(2))
        ldapServer = self.personalizeServerName(mo.group(7))

        if self.mailbox_name:
            mailbox = self.mailbox_name
        else:
            mailbox = self.username
        
        # Personalise the URI and the mailbox:
        newUrlText = "exchange://"+self.username+"@"+mailServer+"/;pf_server="+mailServer+";owa_path="+mo.group(4)+";mailbox="+mailbox+";ad_limit="+mo.group(6)+";ad_server="+ldapServer;

        #print urlText
        #print newUrlText
        return newUrlText

    def personalizeEvolutionCamelUrl(self, urlText):
        url = urlparse (urlText)
        urlScheme = url[0]
        if urlScheme=="exchange":
            return self.personalizeEvolutionExchangeUrl(urlText)
        elif urlScheme=="sendmail":
            return urlText # can't handle this one at present
        elif urlScheme=="spool":
            return urlText # can't handle this one at present
        elif urlScheme=="mbox":
            return urlText # can't handle this one at present
        else:
            # FIXME: make this more robust and generic
            # Expect a string of this form: "SCHEME://USERNAME@SERVER.COM/;VARIOUS-OPTIONS-HERE"
            #patternText = urlScheme + "://"+usernameRegex+"@"+hostnameRegex+"/(.*)"
            patternText = urlScheme + "://"+usernameRegex+"@"+"(.*)"
            pat = re.compile(patternText);
            mo = pat.search(urlText);
            
            # Personalise the URI and the mailbox:
            newUrlText = urlScheme + "://"+self.username+"@"+mo.group(2)
            
            return newUrlText

    class ImplMailAccountVisitor(MailAccountVisitor):
        def visitXml(self, outerVisitor, dom):
            # Attempt to personalise the human-readable name of this account:
            nameText = self.getAccountElement(dom).getAttribute("name")
            newNameText = outerVisitor.personalizeHumanReadableName(nameText)
            self.getAccountElement(dom).setAttribute("name", newNameText)
            
            uid = self.getAccountElement(dom).getAttribute("uid")
            self.getAccountElement(dom).setAttribute("uid", outerVisitor.personalizeUID(uid))

            
            # Personalize the URL:
            sourceUrlText = self.getSourceUrlText(dom)
            if sourceUrlText==None:
                return False
            
            self.setSourceUrlText(dom, outerVisitor.personalizeEvolutionCamelUrl(sourceUrlText))
            
            transportUrlText = self.getTransportUrlText(dom)
            if transportUrlText!=None:
                self.setTransportUrlText(dom, outerVisitor.personalizeEvolutionCamelUrl(transportUrlText))

            # Personalize the identity:
            nameElement = self.getIdentityNameElement(dom)
            addrSpecElement = self.getIdentityAddrSpecElement(dom)
            replytoElement = self.getIdentityReplyToElement(dom)

            addrSpec = outerVisitor.personalizeAddrSpec(getTextBelow(addrSpecElement))
                
            setTextBelow(nameElement, outerVisitor.friendly_name)
            setTextBelow(addrSpecElement, addrSpec)
            if replytoElement!=None:
                if getTextBelow(replytoElement)!=None:
                    setTextBelow(replytoElement, outerVisitor.personalizeRelativeURI(getTextBelow(replytoElement)))
        
            return True

    def implVisitGroup(self, groupElement):
        baseURI = groupElement.getAttribute("base_uri")
        groupElement.setAttribute("base_uri", self.personalizeBaseURI(baseURI))

        uid = groupElement.getAttribute("uid")
        groupElement.setAttribute("uid", self.personalizeUID(uid))

        # Attempt to personalise the human-readable name of this group of accounts:
        nameText = groupElement.getAttribute("name")
        newNameText = self.personalizeHumanReadableName(nameText)
        groupElement.setAttribute("name", newNameText)
        
        return True
        

    class ImplAddressbookSourceVisitor(AddressbookSourceVisitor):
        def visitGroup(self, outerVisitor, groupElement):
            return outerVisitor.implVisitGroup(groupElement)

        def visitSource(self, outerVisitor, groupElement, sourceElement):
            uid = sourceElement.getAttribute("uid")
            sourceElement.setAttribute("uid", outerVisitor.personalizeUID(uid))
            
            uri = sourceElement.getAttribute("uri")
            sourceElement.setAttribute("uri", outerVisitor.personalizeURI(uri))
            return True
        
    class ImplCalendarSourceVisitor(CalendarSourceVisitor):
        def visitGroup(self, outerVisitor, groupElement):
            return outerVisitor.implVisitGroup(groupElement)

        def visitSource(self, outerVisitor, groupElement, sourceElement):
            uid = sourceElement.getAttribute("uid")
            sourceElement.setAttribute("uid", outerVisitor.personalizeUID(uid))

            relative_uri = sourceElement.getAttribute("relative_uri")
            sourceElement.setAttribute("relative_uri", outerVisitor.personalizeRelativeURI(relative_uri))
            return True

    class ImplTasksSourceVisitor(TasksSourceVisitor):
        def visitGroup(self, outerVisitor, groupElement):
            return outerVisitor.implVisitGroup(groupElement)

        def visitSource(self, outerVisitor, groupElement, sourceElement):
            uid = sourceElement.getAttribute("uid")
            sourceElement.setAttribute("uid", outerVisitor.personalizeUID(uid))

            relative_uri = sourceElement.getAttribute("relative_uri")
            sourceElement.setAttribute("relative_uri", outerVisitor.personalizeRelativeURI(relative_uri))
            return True

if __name__ == '__main__':
    import os

    # load input:
    gconfEntries = GConfEntriesStdin()

    # grab configuration information from environment
    username = os.getenv("PERSONALIZE_USERNAME")
    friendlyName = os.getenv("PERSONALIZE_FULLNAME")
    mailboxName = os.getenv("PERSONALIZE_MAILBOXNAME")
    serverName = os.getenv("PERSONALIZE_SERVERNAME")
    uidHostname = os.getenv("PERSONALIZE_UIDHOST")
    emailDomain = os.getenv("PERSONALIZE_EMAILDOMAIN")

    if username==None:
        print >> sys.stderr, "You must set the PERSONALIZE_USERNAME environment variable"
        sys.exit(-1)

    if friendlyName==None:
        print >> sys.stderr, "You must set the PERSONALIZE_FULLNAME environment variable"
        sys.exit(-1)

    # process:
    gconfEntries.accept(PersonalizeVisitor(username, friendlyName, mailboxName, serverName, uidHostname, emailDomain))

    # output the result:
    print gconfEntries.dom.toxml()


syntax highlighted by Code2HTML, v. 0.9.1