# -*- coding: iso-8859-15 -*-


# Glasnost
# By: Odile Bénassy <obenassy@entrouvert.com>
#     Romain Chantereau <rchantereau@entrouvert.com>
#     Nicolas Clapiès <nclapies@easter-eggs.org>
#     Pierre-Antoine Dejace <padejace@entrouvert.be>
#     Thierry Dulieu <tdulieu@easter-eggs.com>
#     Florent Monnier <monnier@codelutin.com>
#     Cédric Musso <cmusso@easter-eggs.org>
#     Frédéric Péters <fpeters@entrouvert.be>
#     Benjamin Poussin <poussin@codelutin.com>
#     Emmanuel Raviart <eraviart@entrouvert.com>
#     Sébastien Régnier <regnier@codelutin.com>
#     Emmanuel Saracco <esaracco@easter-eggs.com>
#
# Copyright (C) 2000, 2001 Easter-eggs & Emmanuel Raviart
# Copyright (C) 2002 Odile Bénassy, Code Lutin, Thierry Dulieu, Easter-eggs,
#     Entr'ouvert, Frédéric Péters, Benjamin Poussin, Emmanuel Raviart,
#     Emmanuel Saracco & Théridion
# Copyright (C) 2003 Odile Bénassy, Romain Chantereau, Nicolas Clapiès,
#     Code Lutin, Pierre-Antoine Dejace, Thierry Dulieu, Easter-eggs,
#     Entr'ouvert, Florent Monnier, Cédric Musso, Ouvaton, Frédéric Péters,
#     Benjamin Poussin, Rodolphe Quiédeville, Emmanuel Raviart, Sébastien
#     Régnier, Emmanuel Saracco, Théridion & Vecam
#
# 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., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.


__doc__ = """Glasnost Upload Files Common Models"""

__version__ = '$Revision$'[11:-2]


import faults
from ObjectsCommon import AdminCommon, ObjectCommon, ObjectsCommonMixin
import slots
import tools_new as commonTools


class AdminUploadFilesCommon(AdminCommon):
    serverRole = 'uploadfiles'


class UploadFileCommon(ObjectCommon):
    comment = None
    comment_kind_balloonHelp = N_("Optional summary of the file's content, or comment.")
    comment_kindName = 'String'

    creationTime = None
    creationTime_kindName = 'CreationTime'

    data = None
    data_kind_balloonHelp = N_('Click on the button to select the file to upload. '\
            'You may rename it first, as its name will be the default name '\
            'proposed to users who will download it.')
    data_kind_useCustomStorage = 1
    data_kind_isRequired = 1
    data_kindName = 'Data'

    dataFileName = None
    dataFileName_kind_isTranslatable = 0
    dataFileName_kindName = 'String'

    dataType = None
    dataType_kind_isTranslatable = 0
    dataType_kindName = 'String'

    modificationTime = None
    modificationTime_kindName = 'ModificationTime'

    properties = None
    properties_kind_importExport = 'from-server-only'
    properties_kind_label = N_('Extra')
    properties_kindName = 'Properties'

    values = None

    readersSet = None
    readersSet_kindName = 'ReadersSet'

    serverRole = 'uploadfiles'

    size = None
    size_kind_importExport = 'from-server-only'
    size_kind_useCustomStorage = 1
    size_kindName = 'Integer'

    title = None
    title_kind_balloonHelp = N_('Enter a meaningful [title->files-help] for the file.')
    title_kind_isRequired = 1
    title_kindName = 'String'

    writersSet = None
    writersSet_kindName = 'WritersSet'

    def getLabel(self):
        label = self.getTitle()
        if label is None:
            return ''
        return label

    def getOrderedLayoutSlotNames(self, parentSlot = None):
        slotNames = ObjectCommon.getOrderedLayoutSlotNames(
            self, parentSlot = parentSlot)
        slotNames += [
            'title', 'dataType', 'dataFileName', 'data', 'size', 'width', 
            'height', 'comment', 'creationTime', 'modificationTime', 
            'writersSet', 'readersSet']
        return slotNames

    def getTitle(self):
        return self.title

    def isType(self, type):
        return self.dataType and self.dataType.startswith(type)

    def importFromXmlRpc(self, dataImport, parentSlot = None):
        # The slots 'properties' must be imported first,
        # because it is needed to compute the slotNames list.
        if dataImport.has_key('__noneSlotNames__'):
            noneSlotNames = dataImport['__noneSlotNames__']
        else:
            noneSlotNames = []
        for slotName in ['properties']:
            if dataImport.has_key(slotName):
                exportedValue = dataImport[slotName]
            elif slotName in noneSlotNames:
                exportedValue = None
            else:
                continue
            slot = self.getSlot(slotName, parentSlot = parentSlot)
            kind = slot.getKind()
            if not kind.isImportable():
                continue
            slot.setValue(kind.importValueFromXmlRpc(slot, exportedValue))
        return ObjectCommon.importFromXmlRpc(
                self, dataImport, parentSlot = parentSlot)

    ### TODO: those methods could be moved to ObjectsCommon (?)
    def getDirectPropertyNames(self):
        if self.properties is None:
            return []
        return [property.name for property in self.properties]

    def getDirectPropertyValue(self, propertyName):
        if not self.hasDirectPropertyValue(propertyName):
            raise faults.MissingItem(propertyName)
        return self.values[propertyName]

    def getDirectPropertyValueKind(self, propertyName):
        if self.properties:
            for property in self.properties:
                if property.name == propertyName:
                    return property.kind
        return None

    def getPropertiesCount(self):
        return len(self.getPropertyNames())

    def getPropertyNames(self):
        if self.properties is None:
            return []
        return [property.name for property in self.properties]

    def getPropertySlot(self, propertyName, parentSlot = None):
        propertiesSlot = self.getSlot('properties', parentSlot = parentSlot)
        return slots.Property(propertyName, parent = propertiesSlot)

    def getPropertyValue(self, propertyName, propertyKind):
        return self.getDirectPropertyValue(propertyName)

    def getPropertyValueKind(self, propertyName):
        kind = self.getDirectPropertyValueKind(propertyName)
        if kind is not None:
            return kind
        raise Exception('Property "%s" of %s has no kind' % (
                propertyName, self))

    def getPropertyValueSlot(self, propertyName, parentSlot = None):
        if parentSlot is None:
            container = self
        else:
            container = None
        return slots.PropertyValue(
            propertyName, container = container, parent = parentSlot)

    def getSlot(self, attributeName, parentSlot = None):
        if attributeName in ObjectCommon.getSlotNames(
                self, parentSlot = parentSlot):
            return ObjectCommon.getSlot(
                    self, attributeName, parentSlot = parentSlot)
        return self.getPropertyValueSlot(
            attributeName, parentSlot = parentSlot)

    def getSlotNames(self, parentSlot = None):
        slotNames = ObjectCommon.getSlotNames(self, parentSlot = parentSlot)
        return slotNames + self.getPropertyNames()

    def hasDirectPropertyValue(self, propertyName):
        return self.values and self.values.has_key(propertyName)

    def setDirectPropertyValue(self, propertyName, value):
        if self.values is None:
            self.values = {}
        self.values[propertyName] = value

    def setDirectPropertyValueKind(self, propertyName, propertyKind):
        if self.properties is None:
            self.properties = []
        else:
            for i in range(len(self.properties)):
                if self.properties[i].name == propertyName:
                    if propertyKind is None:
                        del self.properties[i]
                        return
                    else:
                        property = self.properties[i]
                        property.kind = propertyKind
                        return
        if propertyKind is not None:
            property = commonTools.newThing('other', 'Property')
            property.kind = propertyKind
            property.name = propertyName
            self.properties.append(property)

    def setPropertyValue(self, propertyName, propertyKind, value):
        if self.values is None:
            self.values = {}
        if value == self.getInheritedPropertyValue(propertyName, propertyKind):
            if self.values.has_key(propertyName):
                del self.values[propertyName]
                if not self.values:
                    del self.values
        else:
            self.values[propertyName] = value




class UploadFilesCommonMixin(ObjectsCommonMixin):
    adminClassName = 'AdminUploadFiles'
    newObjectNameCapitalized = N_('New File')
    objectClassName = 'UploadFile'
    objectName = N_('file')
    objectNameCapitalized = N_('File')
    objectsName = N_('files')
    objectsNameCapitalized = N_('Files')
    serverRole = 'uploadfiles'

