Package Products :: Package ZenRelations :: Module ToOneRelationship |
[hide private]
[frames] | no frames]

# Source Code for Module Products.ZenRelations.ToOneRelationship

      1  ###########################################################################
      2  #
      3  # This program is part of Zenoss Core, an open source monitoring platform.
      4  # Copyright (C) 2007, Zenoss Inc.
      5  #
      6  # This program is free software; you can redistribute it and/or modify it
      7  # under the terms of the GNU General Public License version 2 as published by
      8  # the Free Software Foundation.
      9  #
     10  # For complete information please visit: http://www.zenoss.com/oss/
     11  #
     12  ###########################################################################
     13
     14  __doc__="""ToOneRelationship
     15
     16  ToOneRelationship is a class used on a RelationshipManager
     17  to give it toOne management Functions.
     18  """
     19
     20  import logging
     21  log = logging.getLogger("zen.Relations")
     22
     23
     24  # Base classes for ToOneRelationship
     25  from RelationshipBase import RelationshipBase
     26
     27  from Globals import InitializeClass
     28  from Globals import DTMLFile
     29  from AccessControl import ClassSecurityInfo
     30  from App.Dialogs import MessageDialog
     31  from Acquisition import aq_base
     32
     33  from zExceptions import NotFound
     34  from Products.ZenRelations.Exceptions import *
     35  from Products.ZenUtils.Utils import unused, getObjByPath
     36
     37 -def manage_addToOneRelationship(context, id, REQUEST = None):
     38      """ToOneRelationship Factory"""
     39      r =  ToOneRelationship(id)
     40      context._setObject(id, r)
     41      if REQUEST:
     42          REQUEST['RESPONSE'].redirect(context.absolute_url()+'/manage_main')
     43
     44
     45
     46  addToOneRelationship = DTMLFile('dtml/addToOneRelationship',globals())
     47
     48
     49 -class ToOneRelationship(RelationshipBase):
     50      """ToOneRelationship represents a to one Relationship
     51      on a RelationshipManager"""
     52
     53      meta_type = 'ToOneRelationship'
     54
     55      security = ClassSecurityInfo()
     56
     57
     58 -    def __init__(self, id):
     59          self.id = id
     60          self.obj = None
     61
     62
     63 -    def __call__(self):
     64          """return the related object when a ToOne relation is called"""
     65          # Disabling relationship checking code.
     66          # http://dev.zenoss.org/trac/ticket/5391
     67          #self.checkRelation(True)
     68          return self.obj
     69
     70
     71 -    def hasobject(self, obj):
     72          """does this relation point to the object passed"""
     73          return self.obj == obj
     74
     75
     76 -    def _add(self, obj):
     77          """add a to one side of a relationship
     78          if a relationship already exists clear it"""
     79          if obj == self.obj: raise RelationshipExistsError
     80          self._remoteRemove()
     81          self.obj = aq_base(obj)
     82          self.__primary_parent__._p_changed = True
     83
     84
     85 -    def _remove(self,obj=None):
     86          """remove the to one side of a relationship"""
     87          if obj == None or obj == self.obj:
     88              self.obj = None
     89              self.__primary_parent__._p_changed = True
     90          else:
     91              raise ObjectNotFound( "object %s was not found on %s" % (obj, self))
     92
     93
     94 -    def _remoteRemove(self, obj=None):
     95          """clear the remote side of this relationship"""
     96          if self.obj:
     97              if obj != None and obj != self.obj:
     98                  raise ObjectNotFound(
     99                          "object %s was not found on %s it has object %s" %
    100                          (obj.getPrimaryId(), self.getPrimaryId(),
    101                          self.obj.getPrimaryId()))
    102              remoteRel = getattr(aq_base(self.obj), self.remoteName())
    103              remoteRel._remove(self.__primary_parent__)
    104
    105
    106      security.declareProtected('View', 'getRelatedId')
    107 -    def getRelatedId(self):
    108          '''return the id of the our related object'''
    109          if self.obj:
    110              return self.obj.id
    111          else:
    112              return None
    113
    114
    115 -    def _getCopy(self, container):
    116          """
    117          Create ToOne copy. If this is the one side of one to many
    118          we set our side of the relation to point towards the related
    119          object (maintain the relationship across the copy).
    120          """
    121          rel = self.__class__(self.id)
    122          rel.__primary_parent__ = container
    123          rel = rel.__of__(container)
    124          if (self.remoteTypeName() == "ToMany" and self.obj):
    125              rel.addRelation(self.obj)
    126          return rel
    127
    128
    129 -    def manage_afterAdd(self, item, container):
    130          """Don't do anything here because we have on containment"""
    131          pass
    132
    133
    134 -    def manage_afterClone(self, item):
    135          """Don't do anything here because we have on containment"""
    136          pass
    137
    138
    139 -    def manage_workspace(self, REQUEST):
    140          """ZMI function to return the workspace of the related object"""
    141          if self.obj:
    142              objurl = self.obj.getPrimaryUrlPath()
    143              REQUEST['RESPONSE'].redirect(objurl+'/manage_workspace')
    144          else:
    145              return MessageDialog(
    146                  title = "No Relationship Error",
    147                  message = "This relationship does not currently point" \
    148                              " to an object",
    149                  action = "manage_main")
    150
    151
    152 -    def manage_main(self, REQUEST=None):
    153          """ZMI function to redirect to parent relationship manager"""
    154          REQUEST['RESPONSE'].redirect(
    155              self.getPrimaryParent().getPrimaryUrlPath()+'/manage_workspace')
    156
    157
    158      #FIXME - please make me go away, I'm so ugly!
    159      security.declareProtected('View', 'getPrimaryLink')
    160 -    def getPrimaryLink(self):
    161          """get the link tag of a related object"""
    162          link = ""
    163          if self.obj:
    164              if not self.obj.checkRemotePerm("View", self.obj):
    165                  link = self.obj.id
    166              else:
    167                  link = "<a href='%s'>%s</a>" % (self.obj.getPrimaryUrlPath(),
    168                                              self.obj.id)
    169          return link
    170
    171
    172 -    def getPrimaryHref(self):
    173          """Return the primary URL for our related object.
    174          """
    175          return self.obj.getPrimaryUrlPath()
    176
    177
    178 -    def exportXml(self,ofile,ignorerels=[]):
    179          """return an xml representation of a ToOneRelationship
    180          <toone id='cricket'>
    181              /Monitors/Cricket/crk0.srv.hcvlny.cv.net
    182          </toone>"""
    183          from RelSchema import ToManyCont
    184          if not self.obj or self.remoteType()==ToManyCont: return
    185          ofile.write("<toone id='%s' objid='%s'/>\n" % (
    186                      self.id, self.obj.getPrimaryId()))
    187
    188
    189 -    def checkRelation(self, repair=False):
    190          """Check to make sure that relationship bidirectionality is ok.
    191          """
    192          if not self.obj: return
    193          log.debug("checking relation: %s", self.id)
    194
    195          try:
    196              ppath = self.obj.getPrimaryPath()
    197              getObjByPath(self, ppath)
    198          except (KeyError, NotFound):
    199              log.error("object %s in relation %s has been deleted " \
    200                           "from its primary path",
    201                           self.obj.getPrimaryId(), self.getPrimaryId())
    202              if repair:
    203                  log.warn("removing object %s from relation %s",
    204                           self.obj.getPrimaryId(), self.getPrimaryId())
    205                  self.obj = None
    206
    207          if not self.obj: return
    208
    209          rname = self.remoteName()
    210          rrel = getattr(self.obj, rname)
    211          parobj = self.getPrimaryParent()
    212          if not rrel.hasobject(parobj):
    213              log.error("remote relation %s doesn't point back to %s",
    214                        rrel.getPrimaryId(), self.getPrimaryId())
    215              if repair:
    216                  log.warn("reconnecting relation %s to relation %s",
    217                          rrel.getPrimaryId(), self.getPrimaryId())
    218                  rrel._add(parobj)
    219
    220
    221  InitializeClass(ToOneRelationship)
    222