Skip to content
This repository has been archived by the owner on Feb 20, 2023. It is now read-only.

Commit

Permalink
Fix up zope.app for new location of zope.traversing.
Browse files Browse the repository at this point in the history
(also sneaked in some minor cosmetics regarding zapi/ztapi)
  • Loading branch information
philikon committed Apr 5, 2006
1 parent bc187ef commit d8e864d
Showing 1 changed file with 106 additions and 0 deletions.
106 changes: 106 additions & 0 deletions __init__.py
@@ -0,0 +1,106 @@
##############################################################################
#
# Copyright (c) 2002 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE.
#
##############################################################################
"""Dependable Framework.
$Id$
"""
__docformat__ = 'restructuredtext'

from zope.interface import implements
from zope.traversing.api import getParent, canonicalPath, getPath

from zope.app.dependable.interfaces import IDependable
from zope.app.annotation.interfaces import IAnnotations

class PathSetAnnotation(object):
"""Abstract base class for annotations that are sets of paths.
To make this into a concrete class, a subclass must set the class
attribute `key` to a unique annotation key. A subclass may also
choose to rename the methods.
"""

def __init__(self, context):
self.context = context
try:
parent = getParent(self.context)
except TypeError:
parent = None
if parent is not None:
try:
pp = getPath(parent)
except TypeError:
pp = ""
if not pp.endswith("/"):
pp += "/"
self.pp = pp # parentpath
else:
self.pp = ""
self.pplen = len(self.pp)

def addPath(self, path):
path = self._make_relative(path)
annotations = IAnnotations(self.context)
old = annotations.get(self.key, ())
fixed = map(self._make_relative, old)
if path not in fixed:
fixed.append(path)
new = tuple(fixed)
if new != old:
annotations[self.key] = new

def removePath(self, path):
path = self._make_relative(path)
annotations = IAnnotations(self.context)
old = annotations.get(self.key, ())
if old:
fixed = map(self._make_relative, old)
fixed = [loc for loc in fixed if loc != path]
new = tuple(fixed)
if new != old:
if new:
annotations[self.key] = new
else:
del annotations[self.key]

def getPaths(self):
annotations = IAnnotations(self.context)
locs = annotations.get(self.key, ())
return tuple(map(self._make_absolute, locs))

def _make_relative(self, path):
if path.startswith("/") and self.pp:
path = canonicalPath(path)
if path.startswith(self.pp):
path = path[self.pplen:]
while path.startswith("/"):
path = path[1:]
return path

def _make_absolute(self, path):
if not path.startswith("/") and self.pp:
path = self.pp + path
return path


class Dependable(PathSetAnnotation):
"""See `IDependable`."""

implements(IDependable)

key = "zope.app.dependable.Dependents"

addDependent = PathSetAnnotation.addPath
removeDependent = PathSetAnnotation.removePath
dependents = PathSetAnnotation.getPaths

0 comments on commit d8e864d

Please sign in to comment.