[Zope] SECURITY ROLES and < DTML-IN>

Brian Lloyd Brian@digicool.com
Mon, 17 Jul 2000 11:26:40 -0400


This message is in MIME format. Since your mail reader does not understand
this format, some or all of this message may not be legible.

------ =_NextPart_000_01BFF003.679CAD30
Content-Type: text/plain

> I am having trouble rendering a <DTML IN> in ZOPE 2.2.0 to any user
> regardless of roles.
> 
> I have allocated the proper rights to all objects used and 
> nothing happens.
> The <IN> will not let any user view its contents.

Theodore - 

I bet you're running into the same problem as the 
folks using the ODBC adaptor. I've attached the post 
I made addressing this a few minutes ago.

If this fixes your problem, could you send a note to 
the zope-list and let the folks there know that the fix 
works for the Oracle DA too? (I'm going out of town today, 
so I won't be able to forward it if you only reply to me)

Thanks!

> Hi guys - 
> 
> For those of you (I've mostly heard ODBC adapter users) 
> having authorization problems with your SQL methods, heres
> the scoop:
> 
> Database connections use one of two classes in the 
> framework for wrapping up result data returned from 
> queries. One of those classes (that understands results 
> in RDB format) was missing a required security assertion. 
> 
> The results returned by the ODBC adapter were bitten by 
> this - probably there are other adapters that could 
> be affected.
> 
> I've attached a patch file for the file:
> lib/python/Shared/DC/ZRDB/RDB.py
> 
> ...as well as an updated version of the whole file (since 
> I know a lot of you will be on Windows w/o patch :) Either 
> patch or replace the file and restart Zope to fix the 
> problem.
> 
> This is also checked in for a 2.2.1 release that will 
> probably happen after a few weeks when enough people 
> have upgraded to shake out any other problems.
> 


Brian Lloyd        brian@digicool.com
Software Engineer  540.371.6909              
Digital Creations  http://www.digicool.com 





------ =_NextPart_000_01BFF003.679CAD30
Content-Type: application/octet-stream;
	name="RDB.py"
Content-Transfer-Encoding: quoted-printable
Content-Disposition: attachment;
	filename="RDB.py"

########################################################################=
######=0A=
# =0A=
# Zope Public License (ZPL) Version 1.0=0A=
# -------------------------------------=0A=
# =0A=
# Copyright (c) Digital Creations.  All rights reserved.=0A=
# =0A=
# This license has been certified as Open Source(tm).=0A=
# =0A=
# Redistribution and use in source and binary forms, with or without=0A=
# modification, are permitted provided that the following conditions =
are=0A=
# met:=0A=
# =0A=
# 1. Redistributions in source code must retain the above copyright=0A=
#    notice, this list of conditions, and the following disclaimer.=0A=
# =0A=
# 2. Redistributions in binary form must reproduce the above =
copyright=0A=
#    notice, this list of conditions, and the following disclaimer =
in=0A=
#    the documentation and/or other materials provided with the=0A=
#    distribution.=0A=
# =0A=
# 3. Digital Creations requests that attribution be given to Zope=0A=
#    in any manner possible. Zope includes a "Powered by Zope"=0A=
#    button that is installed by default. While it is not a license=0A=
#    violation to remove this button, it is requested that the=0A=
#    attribution remain. A significant investment has been put=0A=
#    into Zope, and this effort will continue if the Zope community=0A=
#    continues to grow. This is one way to assure that growth.=0A=
# =0A=
# 4. All advertising materials and documentation mentioning=0A=
#    features derived from or use of this software must display=0A=
#    the following acknowledgement:=0A=
# =0A=
#      "This product includes software developed by Digital =
Creations=0A=
#      for use in the Z Object Publishing Environment=0A=
#      (http://www.zope.org/)."=0A=
# =0A=
#    In the event that the product being advertised includes an=0A=
#    intact Zope distribution (with copyright and license included)=0A=
#    then this clause is waived.=0A=
# =0A=
# 5. Names associated with Zope or Digital Creations must not be used =
to=0A=
#    endorse or promote products derived from this software without=0A=
#    prior written permission from Digital Creations.=0A=
# =0A=
# 6. Modified redistributions of any form whatsoever must retain=0A=
#    the following acknowledgment:=0A=
# =0A=
#      "This product includes software developed by Digital =
Creations=0A=
#      for use in the Z Object Publishing Environment=0A=
#      (http://www.zope.org/)."=0A=
# =0A=
#    Intact (re-)distributions of any official Zope release do not=0A=
#    require an external acknowledgement.=0A=
# =0A=
# 7. Modifications are encouraged but must be packaged separately as=0A=
#    patches to official Zope releases.  Distributions that do not=0A=
#    clearly separate the patches from the original work must be =
clearly=0A=
#    labeled as unofficial distributions.  Modifications which do =
not=0A=
#    carry the name Zope may be packaged in any form, as long as =
they=0A=
#    conform to all of the clauses above.=0A=
# =0A=
# =0A=
# Disclaimer=0A=
# =0A=
#   THIS SOFTWARE IS PROVIDED BY DIGITAL CREATIONS ``AS IS'' AND ANY=0A=
#   EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, =
THE=0A=
#   IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A =
PARTICULAR=0A=
#   PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL DIGITAL CREATIONS OR =
ITS=0A=
#   CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,=0A=
#   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT=0A=
#   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF=0A=
#   USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED =
AND=0A=
#   ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT =
LIABILITY,=0A=
#   OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY =
OUT=0A=
#   OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY =
OF=0A=
#   SUCH DAMAGE.=0A=
# =0A=
# =0A=
# This software consists of contributions made by Digital Creations =
and=0A=
# many individuals on behalf of Digital Creations.  Specific=0A=
# attributions are listed in the accompanying credits file.=0A=
# =0A=
########################################################################=
######=0A=
__doc__=3D'''Class for reading RDB files=0A=
=0A=
=0A=
$Id: RDB.py,v 1.24.32.2 2000/07/17 15:03:55 brian Exp $'''=0A=
__version__=3D'$Revision: 1.24.32.2 $'[11:-2]=0A=
=0A=
import regex, regsub=0A=
from string import split, strip, lower, upper, atof, atoi, atol, find, =
join=0A=
import DateTime=0A=
from Missing import MV=0A=
from array import array=0A=
from Record import Record=0A=
from Acquisition import Implicit=0A=
import ExtensionClass=0A=
=0A=
def parse_text(s):=0A=
    if find(s,'\\') < 0 and (find(s,'\\t') < 0 and find(s,'\\n') < 0): =
return s=0A=
    r=3D[]=0A=
    for x in split(s,'\\\\'):=0A=
        x=3Djoin(split(x,'\\n'),'\n')=0A=
        r.append(join(split(x,'\\t'),'\t'))=0A=
    return join(r,'\\')=0A=
=0A=
=0A=
Parsers=3D{'n': atof,=0A=
         'i': atoi,=0A=
         'l': atol,=0A=
         'd': DateTime.DateTime,=0A=
         't': parse_text,=0A=
         }=0A=
=0A=
class SQLAlias(ExtensionClass.Base):=0A=
    def __init__(self, name): self._n=3Dname=0A=
    def __of__(self, parent): return getattr(parent, self._n)=0A=
 =0A=
class NoBrains: pass=0A=
=0A=
class DatabaseResults:=0A=
    """Class for reading RDB files=0A=
    """=0A=
    _index=3DNone=0A=
=0A=
    # We need to allow access to not-explicitly-protected=0A=
    # individual record objects contained in the result.=0A=
    __allow_access_to_unprotected_subobjects__=3D1=0A=
=0A=
    def __init__(self,file,brains=3DNoBrains, parent=3DNone, =
zbrains=3DNone):=0A=
=0A=
        self._file=3Dfile=0A=
        readline=3Dfile.readline=0A=
        line=3Dreadline()=0A=
        self._parent=3Dparent=0A=
        if zbrains is None: zbrains=3DNoBrains=0A=
=0A=
        comment_pattern=3Dregex.compile('#')=0A=
        while line and comment_pattern.match(line) >=3D 0: =
line=3Dreadline()=0A=
=0A=
        line=3Dline[:-1]=0A=
        if line and line[-1:] in '\r\n': line=3Dline[:-1]=0A=
        self._names=3Dnames=3Dsplit(line,'\t')=0A=
        if not names: raise ValueError, 'No column names'=0A=
=0A=
        aliases=3D[]=0A=
        self._schema=3Dschema=3D{}=0A=
        i=3D0=0A=
        for name in names:=0A=
            name=3Dstrip(name)=0A=
            if not name:=0A=
                raise ValueError, 'Empty column name, %s' % name=0A=
            if schema.has_key(name):=0A=
                raise ValueError, 'Duplicate column name, %s' % name=0A=
            schema[name]=3Di=0A=
            n=3Dlower(name)=0A=
            if n !=3D name: aliases.append((n, SQLAlias(name)))=0A=
            n=3Dupper(name)=0A=
            if n !=3D name: aliases.append((n, SQLAlias(name)))=0A=
            i=3Di+1=0A=
=0A=
        self._nv=3Dnv=3Dlen(names)=0A=
        line=3Dreadline()=0A=
        line=3Dline[:-1]=0A=
        if line[-1:] in '\r\n': line=3Dline[:-1]=0A=
        =0A=
        self._defs=3Ddefs=3Dsplit(line,'\t')=0A=
        if not defs: raise ValueError, 'No column definitions'=0A=
        if len(defs) !=3D nv:=0A=
            raise ValueError, (=0A=
                """The number of column names and the number of =
column=0A=
                definitions are different.""")=0A=
        =0A=
        i=3D0=0A=
        self._parsers=3Dparsers=3D[]=0A=
        defre=3Dregex.compile('\([0-9]*\)\([a-zA-Z]\)?')=0A=
        self._data_dictionary=3Ddd=3D{}=0A=
        self.__items__=3Ditems=3D[]=0A=
        for _def in defs:=0A=
            _def=3Dstrip(_def)=0A=
            if not _def:=0A=
                raise ValueError, ('Empty column definition for %s' % =
names[i])=0A=
            if defre.match(_def) < 0:=0A=
                raise ValueError, (=0A=
                    'Invalid column definition for, %s, for %s'=0A=
                    % _def, names[i])=0A=
            type=3Dlower(defre.group(2))=0A=
            width=3Ddefre.group(1)=0A=
            if width: width=3Datoi(width)=0A=
            else: width=3D8=0A=
=0A=
            try: parser=3DParsers[type]=0A=
            except: parser=3Dstr=0A=
=0A=
            name=3Dnames[i]=0A=
            d=3D{'name': name, 'type': type, 'width': width, 'parser': =
parser}=0A=
            items.append(d)=0A=
            dd[name]=3Dd=0A=
            =0A=
            parsers.append((i,parser))=0A=
            i=3Di+1=0A=
=0A=
        # Create a record class to hold the records.=0A=
        names=3Dtuple(names)=0A=
=0A=
        class r(Record, Implicit, brains, zbrains):=0A=
            'Result record class'               =0A=
=0A=
        r.__record_schema__=3Dschema=0A=
        for k in filter(lambda k: k[:2]=3D=3D'__', =
Record.__dict__.keys()):=0A=
            setattr(r,k,getattr(Record,k))=0A=
=0A=
        # Add SQL Aliases=0A=
        d=3Dr.__dict__=0A=
        for k, v in aliases:=0A=
            if not hasattr(r,k): d[k]=3Dv=0A=
=0A=
        if hasattr(brains, '__init__'):=0A=
            binit=3Dbrains.__init__=0A=
            if hasattr(binit,'im_func'): binit=3Dbinit.im_func=0A=
            def __init__(self, data, parent, binit=3Dbinit):=0A=
                Record.__init__(self,data)=0A=
                binit(self.__of__(parent))=0A=
=0A=
            r.__dict__['__init__']=3D__init__=0A=
                    =0A=
=0A=
        self._class=3Dr=0A=
=0A=
        # OK, we've read meta data, now get line indexes=0A=
=0A=
        p=3Dfile.tell()=0A=
        save=3Dself._lines=3Darray('i')=0A=
        save=3Dsave.append=0A=
        l=3Dreadline()=0A=
        while l:=0A=
            save(p)=0A=
            p=3Dp+len(l)=0A=
            l=3Dreadline()=0A=
=0A=
    def _searchable_result_columns(self): return self.__items__=0A=
    def names(self): return self._names=0A=
    def data_dictionary(self): return self._data_dictionary=0A=
=0A=
    def __len__(self): return len(self._lines)=0A=
=0A=
    def __getitem__(self,index):=0A=
        if index=3D=3Dself._index: return self._row=0A=
        file=3Dself._file=0A=
        file.seek(self._lines[index])=0A=
        line=3Dfile.readline()=0A=
        line=3Dline[:-1]=0A=
        if line and line[-1:] in '\r\n': line=3Dline[:-1]=0A=
        fields=3Dsplit(line,'\t')=0A=
        l=3Dlen(fields)=0A=
        nv=3Dself._nv=0A=
        if l !=3D nv:=0A=
            if l < nv:=0A=
                fields=3Dfields+['']*(nv-l)=0A=
            else:=0A=
                raise ValueError, (=0A=
                    """The number of items in record %s is invalid=0A=
                    <pre>%s\n%s\n%s\n%s</pre>=0A=
                    """ =0A=
                    % (index, ('=3D'*40), line, ('=3D'*40), fields))=0A=
        for i, parser in self._parsers:=0A=
            try: v=3Dparser(fields[i])=0A=
            except:=0A=
                if fields[i]:=0A=
                    raise ValueError, (=0A=
                        """Invalid value, %s, for %s in record %s"""=0A=
                        % (fields[i], self._names[i], index))=0A=
                else: v=3DMV=0A=
            fields[i]=3Dv=0A=
=0A=
        parent=3Dself._parent=0A=
        fields=3Dself._class(fields, parent)=0A=
        self._index=3Dindex=0A=
        self._row=3Dfields=0A=
        if parent is None: return fields=0A=
        return fields.__of__(parent)=0A=
=0A=
File=3DDatabaseResults=0A=

------ =_NextPart_000_01BFF003.679CAD30
Content-Type: application/octet-stream;
	name="RDB.py.patch"
Content-Transfer-Encoding: quoted-printable
Content-Disposition: attachment;
	filename="RDB.py.patch"

Index: RDB.py=0A=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=0A=
RCS file: /cvs-repository/Zope2/lib/python/Shared/DC/ZRDB/RDB.py,v=0A=
retrieving revision 1.24.32.1=0A=
retrieving revision 1.24.32.2=0A=
diff -c -r1.24.32.1 -r1.24.32.2=0A=
*** RDB.py	2000/07/12 17:38:03	1.24.32.1=0A=
--- RDB.py	2000/07/17 15:03:55	1.24.32.2=0A=
***************=0A=
*** 85,92 ****=0A=
  __doc__=3D'''Class for reading RDB files=0A=
  =0A=
  =0A=
! $Id: RDB.py,v 1.24.32.1 2000/07/12 17:38:03 brian Exp $'''=0A=
! __version__=3D'$Revision: 1.24.32.1 $'[11:-2]=0A=
  =0A=
  import regex, regsub=0A=
  from string import split, strip, lower, upper, atof, atoi, atol, =
find, join=0A=
--- 85,92 ----=0A=
  __doc__=3D'''Class for reading RDB files=0A=
  =0A=
  =0A=
! $Id: RDB.py,v 1.24.32.2 2000/07/17 15:03:55 brian Exp $'''=0A=
! __version__=3D'$Revision: 1.24.32.2 $'[11:-2]=0A=
  =0A=
  import regex, regsub=0A=
  from string import split, strip, lower, upper, atof, atoi, atol, =
find, join=0A=
***************=0A=
*** 123,128 ****=0A=
--- 123,132 ----=0A=
      """Class for reading RDB files=0A=
      """=0A=
      _index=3DNone=0A=
+ =0A=
+     # We need to allow access to not-explicitly-protected=0A=
+     # individual record objects contained in the result.=0A=
+     __allow_access_to_unprotected_subobjects__=3D1=0A=
  =0A=
      def __init__(self,file,brains=3DNoBrains, parent=3DNone, =
zbrains=3DNone):=0A=
  =0A=

------ =_NextPart_000_01BFF003.679CAD30--