############################################################################### ## ## ## ALEXANDRIA DIGITAL LIBRARY ## ## University of California at Santa Barbara ## ## ## ## ------------------------------------------------------------------------- ## ## ## ## Copyright (c) 2004 by the Regents of the University of California ## ## All rights reserved ## ## ## ## Redistribution and use in source and binary forms, with or without ## ## modification, are permitted provided that the following conditions are ## ## met: ## ## ## ## 1. Redistributions of source code must retain the above copyright ## ## notice, this list of conditions, and the following disclaimer. ## ## ## ## 2. Redistributions in binary form must reproduce the above copyright ## ## notice, this list of conditions, and the following disclaimer in ## ## the documentation and/or other materials provided with the ## ## distribution. ## ## ## ## 3. All advertising materials mentioning features or use of this ## ## software must display the following acknowledgement: This product ## ## includes software developed by the Alexandria Digital Library, ## ## University of California at Santa Barbara, and its contributors. ## ## ## ## 4. Neither the name of the University nor the names of its ## ## contributors may be used to endorse or promote products derived ## ## from this software without specific prior written permission. ## ## ## ## THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS "AS IS" AND ANY ## ## EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED ## ## WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE, ARE ## ## DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ## ## ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL ## ## DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS ## ## OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) ## ## HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, ## ## STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ## ## ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ## ## POSSIBILITY OF SUCH DAMAGE. ## ## ## ############################################################################### # $Header: /export/home/gjanee/bucket99/paradigms/RCS/Relational_String.py,v 1.1 2004/02/25 18:50:32 gjanee Exp $ # SYNOPSIS # # Relational_String (table, idColumn, relationColumn, targetColumn, # cardinality, prefix="", relationTable=None, # relationTableIdColumn=None, relationTableRelationColumn=None) # # table # A table to query, e.g., "holding_relations". # # idColumn # The table's item identifier column (i.e., the column to # be selected), e.g., "holding_id". # # relationColumn # The column that holds relation names or relation foreign # keys, e.g., "relation". # # targetColumn # The target identifier column (i.e., the column against # which the constraint is to be placed), e.g., # "target_holding_id". # # cardinality # A Cardinality object representing the cardinality of # 'table' with respect to 'relation' and 'targetColumn'. # # prefix # The prefix to be removed from target identifiers in # constraints, when present. The prefix typically # corresponds to the collection name and delimiting colon # (e.g., "adl_catalog:"), thus allowing relational # constraints that specify global ADL identifiers (as they # do by definition) to match against internal, # collection-local identifiers. Defaults to the empty # string. # # relationTable # Optionally, the name of an auxiliary table that holds # relation names, e.g., "relation". # # relationTableIdColumn # If 'relationTable' is not None, the auxiliary relation # table's column that holds relation IDs. # # relationTableRelationColumn # If 'relationTable' is not None, the auxiliary relation # table's column that holds relation names. # # DESCRIPTION # # Translates a relational constraint to a pair of equality tests. # In this version of the paradigm, item identifiers are treated as # strings; in Relational_Integer, they are treated as integers. # # Given a relational constraint (B, R, TI) where B is a relational # bucket, R is a relation, and TI is the ADL identifier of a # target item, this paradigm removes the prefix 'prefix' from TI, # yielding TI-local, and returns the query: # # SELECT idColumn FROM table # WHERE relationColumn = 'R' AND targetColumn = 'TI-local' # # If an auxiliary relation table is specified, the relation is # obtained by an INNER JOIN, as in: # # SELECT A.idColumn FROM table A, relationTable B # WHERE B.relationTableIdColumn = A.relationColumn AND # B.relationTableRelationColumn = 'R' AND # A.targetColumn = 'TI-local' # # In either case, if the target identifier TI does not have # 'prefix' as a prefix, the query # # SELECT idColumn FROM table # WHERE 1 = 0 # # is returned. # # Exceptions thrown: # # none # # AUTHOR # # Greg Janee # gjanee@alexandria.ucsb.edu # # HISTORY # # $Log: Relational_String.py,v $ # Revision 1.1 2004/02/25 18:50:32 gjanee # Initial revision # import types import edu.ucsb.adl.middleware M = edu.ucsb.adl.middleware import UniversalTranslator UT = UniversalTranslator class Relational_String (UT.Paradigm): def __init__ (self, table, idColumn, relationColumn, targetColumn, cardinality, prefix="", relationTable=None, relationTableIdColumn=None, relationTableRelationColumn=None): UT.assertType(table, types.StringType) UT.assertType(idColumn, types.StringType) UT.assertType(relationColumn, types.StringType) UT.assertType(targetColumn, types.StringType) UT.assertType(cardinality, UT.Cardinality) UT.assertType(prefix, types.StringType) UT.assertPolytype(relationTable, [types.StringType, types.NoneType]) if isinstance(relationTable, types.StringType): UT.assertType(relationTableIdColumn, types.StringType) UT.assertType(relationTableRelationColumn, types.StringType) else: UT.assertType(relationTableIdColumn, types.NoneType) UT.assertType(relationTableRelationColumn, types.NoneType) self.table = table self.idColumn = idColumn self.relationColumn = relationColumn self.targetColumn = targetColumn self.cardinality = cardinality self.prefix = prefix self.relationTable = relationTable self.relationTableIdColumn = relationTableIdColumn self.relationTableRelationColumn = relationTableRelationColumn def translateBucketAtomic (self, constraint, vocabularies): UT.assertType(constraint, M.Query.RelationalConstraint) target = constraint.getTargetIdentifier() if target[:len(self.prefix)] != self.prefix: return UT.constantFalseQuery(self.table, self.idColumn, self.cardinality) target = target[len(self.prefix):] table = UT.TableRef(self.table) froms = [UT.MainFrom(table, self.idColumn, self.cardinality)] if self.relationTable != None: relationTable = UT.TableRef(self.relationTable) froms += [UT.AuxiliaryFrom(relationTable, UT.Expression([relationTable, "." +\ self.relationTableIdColumn + " = ", table, "." +\ self.relationColumn]))] expression = UT.Expression([relationTable, "." +\ self.relationTableRelationColumn + " = '" +\ UT.protectQuotes(constraint.getOperator()) + "'"]) else: expression = UT.Expression([table, "." +\ self.relationColumn + " = '" +\ UT.protectQuotes(constraint.getOperator()) + "'"]) return UT.Select( froms, expression.combine("AND", UT.Expression([table, "." +\ self.targetColumn + " = '" + UT.protectQuotes(target) + "'"])))