modeling-cvs Mailing List for Object-Relational Bridge for python (Page 29)
Status: Abandoned
Brought to you by:
sbigaret
You can subscribe to this list here.
| 2003 |
Jan
|
Feb
|
Mar
(54) |
Apr
(29) |
May
(94) |
Jun
(47) |
Jul
(156) |
Aug
(132) |
Sep
(40) |
Oct
(6) |
Nov
(18) |
Dec
(24) |
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| 2004 |
Jan
(18) |
Feb
(59) |
Mar
(7) |
Apr
|
May
(8) |
Jun
(2) |
Jul
(12) |
Aug
(15) |
Sep
(12) |
Oct
(6) |
Nov
(25) |
Dec
(1) |
| 2005 |
Jan
|
Feb
|
Mar
|
Apr
|
May
(1) |
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
| 2006 |
Jan
|
Feb
(27) |
Mar
|
Apr
(16) |
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
| 2009 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
(1) |
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
|
From: <sbi...@us...> - 2003-05-16 11:33:27
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/scripts
In directory sc8-pr-cvs1:/tmp/cvs-serv32227
Modified Files:
Tag: brch-0_9pre6-1-ModelMasons_base_generation_scheme
mdl_generate_python_code.py
Log Message:
Updated usage()
Index: mdl_generate_python_code.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/scripts/mdl_generate_python_code.py,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -C2 -d -r1.4 -r1.4.2.1
*** mdl_generate_python_code.py 20 Apr 2003 16:10:41 -0000 1.4
--- mdl_generate_python_code.py 16 May 2003 11:33:24 -0000 1.4.2.1
***************
*** 110,113 ****
--- 110,115 ----
Generation options:
-------------------
+ For an explanation on generation schemes, see below
+
-B --base-generation-scheme use the 'base' scheme
-C --compact-generation-scheme use the 'compact' scheme (default)
***************
*** 116,120 ****
--generation_scheme=<scheme> use <scheme> as the generation scheme
(either 'base' or 'compact')
!
""" % prgName
sys.stderr.write(_usage)
--- 118,135 ----
--generation_scheme=<scheme> use <scheme> as the generation scheme
(either 'base' or 'compact')
!
! 'compact' scheme: puts all generated file in the same directory (the package
! for the model). When re-generating the files, a file that
! already exists is NEVER overwritten
!
! 'base' scheme: adds a sub-module 'MDL' within the generated package. All files
! within MDL/ are ALWAYS overwritten when the python code is regenerated,
! while others (in the root package) are never overwritten if they exist.
! This is probably the one you want to use if your model changes often.
!
! Note: this can be used if and only if there is no entity sharing the same
! module with one of its (direct or indirect) subentities. If this is
! not the case, the generation will raise and indicate the problem.
!
""" % prgName
sys.stderr.write(_usage)
|
|
From: <sbi...@us...> - 2003-05-16 11:04:43
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons
In directory sc8-pr-cvs1:/tmp/cvs-serv21096a/ModelMasons
Modified Files:
Tag: brch-0_9pre6-1-ModelMasons_base_generation_scheme
PyModelMason.py
Log Message:
Added: check that the model is valid for the 'base' generation scheme + fixed: __init__ in MDL/ was not overwritten
Index: PyModelMason.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/PyModelMason.py,v
retrieving revision 1.8.2.1
retrieving revision 1.8.2.2
diff -C2 -d -r1.8.2.1 -r1.8.2.2
*** PyModelMason.py 21 Apr 2003 22:53:05 -0000 1.8.2.1
--- PyModelMason.py 16 May 2003 11:04:40 -0000 1.8.2.2
***************
*** 42,45 ****
--- 42,100 ----
from Python_bricks import init,init_base,model,base_module,module_base,module_compact,setup_tmpl
+ class InvalidModelError(Exception):
+ "Raised by checkModelIsValid()"
+ pass
+
+ def checkModelIsValid(model, generation_scheme):
+ """
+ Checks that the supplied model is valid for a given python-code generation
+ scheme:
+
+ - if 'generation_scheme' is 'compact', all models are valid,
+
+ - if 'generation_scheme' is 'base', the model is valid iff a class/entity does
+ not share the same module than any of its subclasses
+
+ Parameters:
+
+ model -- a instance of Modeling.Model.Model
+
+ generation_scheme -- either 'compact' or 'base'
+
+ Returns: None
+
+ Raises InvalidModelError if the model is invalid.
+
+ Note: this is NOT validation of the model itself (responsability of
+ Modeling.ModelValidation)
+
+ """
+ if generation_scheme=='compact': return
+ if generation_scheme=='base':
+
+ # Build ordered list of entities
+ oe=[]
+ entities=list(model.entities())
+ entities_processed=[]
+ for entity in [e for e in entities if not e.parentEntity()]:
+ oe.append(entity)
+ entities_processed.append(entity.name())
+ entities.remove(entity)
+ while entities:
+ es=[e for e in entities if e.parentEntity().name() in entities_processed]
+ for entity in es:
+ entities.remove(entity)
+ entities_processed.append(entity.name())
+ oe.append(entity)
+ # check every parent against it subentities
+ for e in oe:
+ parent_moduleName=e.moduleName()
+ subs=e.allSubEntities()
+ for sub in subs:
+ if sub.moduleName()==parent_moduleName:
+ raise InvalidModelError, "Model is invalid wrt the 'base' generation scheme: entity '%s' and its subentity '%s' share the same moduleName.\nEither correct this or use the 'compact' generation scheme"%(e.name(), sub.name())
+ else:
+ raise ValueError, "Invalid value for 'generation_scheme' (%s), should be either 'base' or 'compact'"%use_scheme
+
class PyModelMason(ModelMason):
def __init__(self, model, rootPath=None, verbose_mode=0,
***************
*** 63,66 ****
--- 118,122 ----
if generation_scheme not in ('compact', 'base'):
raise ValueError,"Parameter generation_scheme can be either 'compact' or 'base'"
+ checkModelIsValid(model, generation_scheme)
ModelMason.__init__(self, model, rootPath,
Modeling.ModelMasons.PyModelMason, 'Python_bricks',
***************
*** 144,148 ****
self.createFileFromTemplate(init_base.init_base(),
os.path.join(self.base_dir,"__init__.py"),
! overwrite=0)
create_model_files(self,
--- 200,204 ----
self.createFileFromTemplate(init_base.init_base(),
os.path.join(self.base_dir,"__init__.py"),
! overwrite=1)
create_model_files(self,
|
|
From: <sbi...@us...> - 2003-05-16 11:02:50
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks
In directory sc8-pr-cvs1:/tmp/cvs-serv20408/ModelMasons/Python_bricks
Modified Files:
Tag: brch-0_9pre6-1-ModelMasons_base_generation_scheme
init.tmpl init_base.tmpl module_base.tmpl
Log Message:
Added a timestamp in comment at beginning of file
Index: init.tmpl
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks/init.tmpl,v
retrieving revision 1.3.4.1
retrieving revision 1.3.4.2
diff -C2 -d -r1.3.4.1 -r1.3.4.2
*** init.tmpl 21 Apr 2003 22:53:05 -0000 1.3.4.1
--- init.tmpl 16 May 2003 11:02:47 -0000 1.3.4.2
***************
*** 1,3 ****
--- 1,5 ----
## This template will build the __init__.py file
+ #import time
+ # Generated by mdl_generate_python_code.py / time.strftime("%Y/%m/%d %H:%M")
#set $model_name = str($model().name())
# Load the model
Index: init_base.tmpl
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks/Attic/init_base.tmpl,v
retrieving revision 1.1.2.1
retrieving revision 1.1.2.2
diff -C2 -d -r1.1.2.1 -r1.1.2.2
*** init_base.tmpl 21 Apr 2003 22:53:05 -0000 1.1.2.1
--- init_base.tmpl 16 May 2003 11:02:47 -0000 1.1.2.2
***************
*** 1,4 ****
--- 1,6 ----
## This template will build the __init__.py file in the 'base_dir' package
## (see ModelMasons.PyModelMason)
+ # WARNING: Any changes made here will be OVERWRITTEN next time the package
+ # is regenerated
#for entities in $entitiesSet:
import $(entities[0].moduleName())
Index: module_base.tmpl
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks/module_base.tmpl,v
retrieving revision 1.1.2.1
retrieving revision 1.1.2.2
diff -C2 -d -r1.1.2.1 -r1.1.2.2
*** module_base.tmpl 21 Apr 2003 22:53:05 -0000 1.1.2.1
--- module_base.tmpl 16 May 2003 11:02:47 -0000 1.1.2.2
***************
*** 1,4 ****
--- 1,6 ----
## This template will build the module
+ #import time
import $(base_dir)
+ # Generated by mdl_generate_python_code.py / time.strftime("%Y/%m/%d %H:%M")
from Modeling.Validation import ValidationException
from mx.DateTime import DateTimeFrom
|
|
From: <sbi...@us...> - 2003-05-16 11:01:28
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks
In directory sc8-pr-cvs1:/tmp/cvs-serv19810/ModelMasons/Python_bricks
Modified Files:
Tag: brch-0_9pre6-1-ModelMasons_base_generation_scheme
base_module.tmpl
Log Message:
Added a timestamp in comment at beginning of file
Index: base_module.tmpl
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelMasons/Python_bricks/base_module.tmpl,v
retrieving revision 1.1.2.1
retrieving revision 1.1.2.2
diff -C2 -d -r1.1.2.1 -r1.1.2.2
*** base_module.tmpl 21 Apr 2003 22:53:05 -0000 1.1.2.1
--- base_module.tmpl 16 May 2003 11:01:25 -0000 1.1.2.2
***************
*** 1,3 ****
--- 1,5 ----
## This template will build the <module>Base.py module
+ #import time
+ # Generated by mdl_generate_python_code.py / $(time.strftime("%Y/%m/%d %H:%M"))
# DO NOT MODIFY THIS FILE -- IT WILL BE OVERWRITTEN
# Instead, modify $(model.packageName).$(entities[0].moduleName())
|
|
From: <sbi...@us...> - 2003-05-16 10:46:27
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv14251
Modified Files:
Tag: brch-0_9pre6-1-ModelMasons_base_generation_scheme
Model.py Entity.py Attribute.py Relationship.py
Log Message:
Applied some changes made in 0.9pre7: added field 'comment' in Model, Entity, Attribute and Relationship
Index: Model.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Model.py,v
retrieving revision 1.3
retrieving revision 1.3.4.1
diff -C2 -d -r1.3 -r1.3.4.1
*** Model.py 10 Jan 2003 10:45:44 -0000 1.3
--- Model.py 16 May 2003 10:46:22 -0000 1.3.4.1
***************
*** 55,59 ****
_connectionDictionary={}
_packageName=''
!
def __init__(self, aName=''):
"Initializes a model. A name **must** be provided."
--- 55,60 ----
_connectionDictionary={}
_packageName=''
! _comment=''
!
def __init__(self, aName=''):
"Initializes a model. A name **must** be provided."
***************
*** 95,98 ****
--- 96,103 ----
anEntity._setModel(self)
+ def comment(self):
+ "Returns the comment field"
+ return self._comment
+
def connectionDictionary(self):
"Returns the connection dictionary"
***************
*** 191,194 ****
--- 196,203 ----
self._adaptorName=adaptorName
+ def setComment(self, aComment):
+ "Sets the comment field"
+ self._comment=aComment
+
def setConnectionDictionary(self, aConnectionDictionary):
"Sets the connection dictionary"
***************
*** 315,320 ****
'connectionDictionary': ('string',
self.setConnectionDictionary,
! self.connectionDictionary)
!
}
--- 324,331 ----
'connectionDictionary': ('string',
self.setConnectionDictionary,
! self.connectionDictionary),
! 'comment': ('string',
! self.setComment,
! self.comment),
}
Index: Entity.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Entity.py,v
retrieving revision 1.10
retrieving revision 1.10.4.1
diff -C2 -d -r1.10 -r1.10.4.1
*** Entity.py 17 Mar 2003 10:27:09 -0000 1.10
--- Entity.py 16 May 2003 10:46:22 -0000 1.10.4.1
***************
*** 145,148 ****
--- 145,149 ----
_attrsUsedForLocking=()
_moduleName=None
+ _comment=''
def __init__(self, name='', aModel=None):
***************
*** 158,161 ****
--- 159,163 ----
self._attrsUsedForLocking=()
self._className=None
+ self._comment=''
self._externalName=''
self._model=None
***************
*** 358,361 ****
--- 360,367 ----
if rel.isClassProperty()])
+ def comment(self):
+ "Returns the comment field"
+ return self._comment
+
def definedKeys(self):
"""
***************
*** 838,841 ****
--- 844,851 ----
self._className=aName
+ def setComment(self, aComment):
+ "Sets the comment field"
+ self._comment=aComment
+
def setExternalName(self, externalName):
"Sets the external name"
***************
*** 1378,1381 ****
--- 1388,1394 ----
self.setClassName,
self.className ),
+ 'comment': ( 'string',
+ self.setComment,
+ self.comment),
'externalName': ( 'string',
self.setExternalName,
Index: Attribute.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Attribute.py,v
retrieving revision 1.11
retrieving revision 1.11.4.1
diff -C2 -d -r1.11 -r1.11.4.1
*** Attribute.py 17 Mar 2003 11:15:11 -0000 1.11
--- Attribute.py 16 May 2003 10:46:22 -0000 1.11.4.1
***************
*** 100,103 ****
--- 100,104 ----
_columnName=''
_width=0
+ _comment=''
def __init__(self, aName='', anEntity=None):
***************
*** 111,114 ****
--- 112,116 ----
self._allowsNone=1
self._columnName=''
+ self._comment=''
self._defaultValue=None
self._definition=''
***************
*** 165,168 ****
--- 167,174 ----
return self._columnName
+ def comment(self):
+ "Returns the comment field"
+ return self._comment
+
def defaultValue(self):
"Returns the default value associated to this attribute"
***************
*** 323,326 ****
--- 329,336 ----
self._columnName=columnName
+ def setComment(self, aComment):
+ "Sets the comment field"
+ self._comment=aComment
+
def convertStringToAttributeType(self, aValue):
"""
***************
*** 595,598 ****
--- 605,611 ----
self.setColumnName,
self.columnName),
+ 'comment' : ( 'string',
+ self.setComment,
+ self.comment),
'displayLabel' : ('string',
self.setDisplayLabel,
***************
*** 638,642 ****
subList=('name',
'columnName', 'precision', 'scale', 'width', 'externalType', #DB
! 'displayLabel', 'isClassProperty', 'isRequired',
'defaultValue', 'type', )
dict=self.fullPropertySet()
--- 651,655 ----
subList=('name',
'columnName', 'precision', 'scale', 'width', 'externalType', #DB
! 'comment', 'displayLabel', 'isClassProperty', 'isRequired',
'defaultValue', 'type', )
dict=self.fullPropertySet()
***************
*** 647,651 ****
def flattenedPropertySet(self):
subList=('name', 'displayLabel', 'isClassProperty', 'definition',
! 'isFlattened', )
dict=self.fullPropertySet()
deleteKeys=filter(lambda k, list=subList: k not in list, dict.keys())
--- 660,664 ----
def flattenedPropertySet(self):
subList=('name', 'displayLabel', 'isClassProperty', 'definition',
! 'isFlattened', 'comment')
dict=self.fullPropertySet()
deleteKeys=filter(lambda k, list=subList: k not in list, dict.keys())
Index: Relationship.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Relationship.py,v
retrieving revision 1.7
retrieving revision 1.7.4.1
diff -C2 -d -r1.7 -r1.7.4.1
*** Relationship.py 10 Feb 2003 12:12:15 -0000 1.7
--- Relationship.py 16 May 2003 10:46:22 -0000 1.7.4.1
***************
*** 69,72 ****
--- 69,73 ----
#
_isClassProperty=1
+ _comment=''
__implements__=(RelationshipInterface, XMLCapabilityInterface)
***************
*** 76,79 ****
--- 77,81 ----
self._deleteRule = DELETE_NULLIFY
self._displayLabel = ''
+ self._comment = ''
self._entity = None
self._isClassProperty = 1
***************
*** 83,86 ****
--- 85,92 ----
return
+ def comment(self):
+ "Returns the comment field"
+ return self._comment
+
def entity(self):
"Return the relationship's source entity"
***************
*** 146,149 ****
--- 152,159 ----
return self._name
+ def setComment(self, aComment):
+ "Sets the comment field"
+ self._comment=aComment
+
def setDeleteRule(self, rule):
"""
***************
*** 280,283 ****
--- 290,296 ----
"-"
return {
+ 'comment' : ('string',
+ self.setComment,
+ self.comment),
'name' : ('string',
lambda self=None,p=None: None,
|
|
From: <sbi...@us...> - 2003-05-15 17:45:01
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/tests
In directory sc8-pr-cvs1:/tmp/cvs-serv25871/tests
Added Files:
Tag: brch-0_9pre7-1-PyModel
test_PyModel.py
Log Message:
Added PyModel.py and tests
--- NEW FILE: test_PyModel.py ---
#! /usr/bin/env python
#-----------------------------------------------------------------------------
#
# Modeling Framework: an Object-Relational Bridge for python
# (c) 2001, 2002, 2003 Sebastien Bigaret
#
# This file is part of the Modeling Framework.
#
# The Modeling Framework 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.
#
# The Modeling Framework 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 the Modeling Framework; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
#
#-----------------------------------------------------------------------------
"""
Tests for PyModel
"""
import unittest
if __name__ == "__main__":
import utils, sys
utils.fixpath()
from Modeling.PyModel import *
class TestPyModel(unittest.TestCase):
"""
Tests for PyModel
"""
def checkEntitiesProperties(self, entities):
"""
For each entity in 'entities', check that its attributes and
relationships entity() points to it. Also check that the relationships'
destination entity is not None.
See in particular the comment in updateComponent() for an explanation
"""
for e in entities:
for a in e.attributes():
self.assertEqual(a.entity(), e)
for r in e.relationships():
self.assertEqual(r.entity(), e)
self.failUnless(r.destinationEntity(),'%s.%s.destinationEntity() is None'%(e.name(),r.name()))
def setUp(self):
self.model = Model('StoreEmployees',adaptorName='Postgresql')
self.model.version='0.1'
Entity.defaults['properties'] = [
APrimaryKey('id', isClassProperty=0, isRequired=1, doc='Default PK')
]
AString.defaults['width'] = 20
def test_01_attr(self):
"[PyModel] entity w/ attributes and default pk"
model = self.model
model.entities = [
Entity('Employee',
properties=[ AString('lastName', isRequired=1, usedForLocking=1),
AString('firstName', isRequired=1, width=50,
usedForLocking=1),
] ),
]
model.build()
emp=model.component.entityNamed('Employee')
self.checkEntitiesProperties((emp,))
self.assertEqual(emp.attributeNamed('lastName').width(), 20)
self.assertEqual(emp.attributeNamed('firstName').width(), 50)
self.assertEqual(emp.attributeNamed('firstName').isRequired(), 1)
self.assertEqual(emp.primaryKeyAttributeNames(), ['id']) # default PK
self.failIf(emp.primaryKeyAttributes()[0].isClassProperty())
self.assertEqual(emp.primaryKeyAttributes()[0].defaultValue(), None)
def test_02_pk(self):
"[PyModel] entity w/ pk"
model = self.model
model.entities = [
Entity('Employee',
properties=[ APrimaryKey('ID', isClassProperty=1, isRequired=1,
doc='SalesClerk PK') ] ), ]
model.build()
emp=model.component.entityNamed('Employee')
self.checkEntitiesProperties((emp,))
self.assertEqual(emp.primaryKeyAttributeNames(), ['ID'])
self.failUnless(emp.primaryKeyAttributes()[0].isClassProperty())
self.assertEqual(emp.primaryKeyAttributes()[0].defaultValue(), 0)
def test_03_attrs_and_inheritance(self):
"[PyModel] attrs_and_inheritance"
model = self.model
model.entities = [
Entity('Employee',
properties=[ AString('lastName', isRequired=1, usedForLocking=1),
AString('firstName', isRequired=1, width=50,
usedForLocking=1),
] ),
Entity('SalesClerk', parent='Employee',
properties=[ APrimaryKey('id', isClassProperty=1, isRequired=1,
# NB: avec ID & Rels c'est une erreur!
doc='SalesClerk PK'),
AString('firstName', isRequired=1, width=5,
usedForLocking=1),
] ),
Entity('Executive', parent='Employee',
properties=[ AString('officeLocation', width=5), ] ),
]
model.build()
emp=model.component.entityNamed('Employee')
sc=model.component.entityNamed('SalesClerk')
ex=model.component.entityNamed('Executive')
self.checkEntitiesProperties((emp,sc,ex))
self.assertEqual(emp.primaryKeyAttributeNames(), ['id'])
self.assertEqual(emp.primaryKeyAttributeNames(), ['id']) # PK overriden
self.assertEqual(emp.primaryKeyAttributeNames(), ['id'])
self.failIf(emp.primaryKeyAttributes()[0].isClassProperty())
self.failIf(ex.primaryKeyAttributes()[0].isClassProperty())
self.failUnless(sc.primaryKeyAttributes()[0].isClassProperty())
# Propagation of attributes
self.failIf([a for a in emp.attributesNames()
if a not in sc.attributesNames()])
self.failIf([a for a in emp.attributesNames()
if a not in ex.attributesNames()])
self.assertEqual(len(sc.attributes()),3)
self.assertEqual(len(ex.attributes()),4)
#
self.assertEqual(emp.attributeNamed('firstName').width(), 50)
self.assertEqual(sc.attributeNamed('firstName').width(), 5)
self.assertEqual(emp.attributeNamed('id').entity(), emp)
self.assertEqual(sc.attributeNamed('id').entity(), sc)
self.assertEqual(ex.attributeNamed('id').entity(), ex)
def test_04_fully_qualified_relationships_no_inverse(self):
"[PyModel] fully_qualified_relationships"
model = self.model
model.entities = [
Entity('Employee',
properties=[ AForeignKey('fkStore'),
RToOne('toStore', 'Store',src='fkStore',dst='id'),
RToMany('toMarks', 'Mark',src='id',dst='fkEmployee'),
] ),
Entity('SalesClerk', parent='Employee'),
Entity('Mark', properties=[ AForeignKey('fkEmployee') ]),
Entity('Store'),
]
model.build()
emp=model.component.entityNamed('Employee')
sc=model.component.entityNamed('SalesClerk')
store=model.component.entityNamed('Store')
mark=model.component.entityNamed('Mark')
self.checkEntitiesProperties((emp,sc,store,mark))
self.assertEqual(len(sc.relationships()), 2)
def check(self, toStore, toMarks, store, mark):
self.failUnless(toStore.isToOne())
self.failUnless(toMarks.isToMany())
self.assertEqual(toStore.destinationEntity(), store)
self.assertEqual(toMarks.destinationEntity(), mark)
toStore=emp.propertyNamed('toStore')
toMarks=emp.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
toStore=sc.propertyNamed('toStore')
toMarks=sc.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
def test_05_unqualified_relationships_no_inverse(self):
"[PyModel] unqualified_relationships_no_inverse"
model = self.model
model.entities = [
Entity('Employee',
properties=[
RToMany('toMarks', 'Mark'),
RToOne('toStore', 'Store'),
] ),
Entity('SalesClerk', parent='Employee'),
Entity('Mark'),
Entity('Store'),
]
model.build()
emp=model.component.entityNamed('Employee')
sc=model.component.entityNamed('SalesClerk')
store=model.component.entityNamed('Store')
mark=model.component.entityNamed('Mark')
self.checkEntitiesProperties((emp,sc,store,mark))
self.assertEqual(len(sc.relationships()), 2)
# Check that each entity has the expected number of attributes
self.assertEqual(len(emp.attributes()), 2) # id + fk
self.assertEqual(len(sc.attributes()), 2) # id + fk
self.assertEqual(len(store.attributes()), 1) # id
self.assertEqual(len(mark.attributes()), 2) # id + fk
self.failUnless(emp.attributeNamed('fkStore'))
self.failUnless(sc.attributeNamed('fkStore'))
self.failUnless(mark.attributeNamed('fkEmployee'))
def check(self, toStore, toMarks, store, mark):
self.failUnless(toStore.isToOne())
self.failUnless(toMarks.isToMany())
self.assertEqual(toStore.destinationEntity(), store)
self.assertEqual(toMarks.destinationEntity(), mark)
# check the parent
toStore=emp.propertyNamed('toStore')
toMarks=emp.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
self.failIf(emp.propertyNamed('fkStore') not in toStore.sourceAttributes())
self.failIf(store.propertyNamed('id') not in toStore.destinationAttributes())
self.failIf(emp.propertyNamed('id') not in toMarks.sourceAttributes())
self.failIf(mark.propertyNamed('fkEmployee') not in toMarks.destinationAttributes())
# Also check the sub-entity
toStore=sc.propertyNamed('toStore')
toMarks=sc.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
self.failIf(sc.propertyNamed('fkStore') not in toStore.sourceAttributes())
self.failIf(store.propertyNamed('id') not in toStore.destinationAttributes())
self.failIf(sc.propertyNamed('id') not in toMarks.sourceAttributes())
self.failIf(mark.propertyNamed('fkEmployee') not in toMarks.destinationAttributes())
# test_06 qualified & unqualified
# model = self.model
# model.entities = [
# Entity('Employee',
# properties=[ AForeignKey('fkStore'),
# #RToOne('toStore', 'Store',src='fkStore',dst='id'),
# RToMany('toMarks', 'Mark',src='id',dst='fkEmployee'),
# ] ),
# Entity('SalesClerk', parent='Employee'),
# Entity('Mark',
# properties=[ AForeignKey('fkEmployee'),
# #RToOne('toEmployee','Employee',inverse='toMarks')
# ]
# ),
# Entity('Store',
# properties=[RToMany('toEmployees','Employee')#,src='id',dst='fkStore')
# ]#,inverse='toStore')]
# ),
# # NB: quid si inverse='ghjgh'? --> TBD test!
# ]
def check_model(self, model):
model.build()
emp=model.component.entityNamed('Employee')
sc=model.component.entityNamed('SalesClerk')
store=model.component.entityNamed('Store')
mark=model.component.entityNamed('Mark')
self.checkEntitiesProperties((emp,sc,store,mark))
self.assertEqual(len(sc.relationships()), 2)
def check(self, toStore, toMarks, store, mark):
self.failUnless(toStore.isToOne())
self.failUnless(toMarks.isToMany())
self.assertEqual(toStore.destinationEntity(), store)
self.assertEqual(toMarks.destinationEntity(), mark)
toStore=emp.propertyNamed('toStore')
toMarks=emp.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
toStore=sc.propertyNamed('toStore')
toMarks=sc.propertyNamed('toMarks')
check(self, toStore, toMarks, store, mark)
#### JUSQU'ICI on est pareil que test_04
self.failUnless(mark.relationshipNamed('toEmployee').inverseRelationship()==emp.propertyNamed('toMarks'))
self.failUnless(store.relationshipNamed('toEmployees').inverseRelationship()==emp.propertyNamed('toStore'))
def test_07_relationships_with_inverse(self):
"[PyModel] qualified_relationships_with_inverse"
model = self.model
model.entities = [
Entity('Employee',
properties=[ AForeignKey('fkStore'),
RToOne('toStore', 'Store',src='fkStore',dst='id'),
RToMany('toMarks', 'Mark',src='id',dst='fkEmployee'),
] ),
Entity('SalesClerk', parent='Employee'),
Entity('Mark',
properties=[ AForeignKey('fkEmployee'),
RToOne('toEmployee','Employee',inverse='toMarks')
]
),
Entity('Store',
properties=[RToMany('toEmployees','Employee',inverse='toStore',
)#src='id',dst='fkStore')
]#,inverse='toStore')]
),
# NB: quid si inverse='ghjgh'? --> TBD test!
]
self.check_model(self.model)
#
self.setUp()
self.model.entities = [
Entity('Employee',
properties=[ RToOne('toStore', 'Store'),#,src='fkStore',dst='id'),
RToMany('toMarks', 'Mark'),#,src='id',dst='fkEmployee'),
] ),
Entity('SalesClerk', parent='Employee'),
Entity('Mark',
properties=[ RToOne('toEmployee','Employee',inverse='toMarks') ]
),
Entity('Store',
properties=[RToMany('toEmployees','Employee',inverse='toStore',)]
),
]
self.check_model(self.model)
# Automatic creation of source + destination key
self.setUp()
self.model.entities = [
Entity('Employee',
properties=[ RToOne('toStore', 'Store',src='fkStore',dst='id'),
RToMany('toMarks', 'Mark',src='id',dst='fkEmployee'),
] ),
Entity('SalesClerk', parent='Employee'),
Entity('Mark',
properties=[ RToOne('toEmployee','Employee',inverse='toMarks') ]
),
Entity('Store',
properties=[RToMany('toEmployees','Employee',inverse='toStore',)]
),
]
#self.check_model(self.model)
def test_08_qualified_relationships_with_inverse(self):
"[PyModel] unqualified_relationships_with_inverse"
model = self.model
model.entities = [
Entity('Employee'),
Entity('SalesClerk', parent='Employee'),
Entity('Mark'),
Entity('Store'),
]
model.associations = [
Association('Employee', 'Store'),
Association('Mark', 'Employee'),
]
self.check_model(self.model)
def test_suite():
suite = unittest.TestSuite()
suite.addTest(unittest.makeSuite(TestPyModel, "test_08"))
return suite
if __name__ == "__main__":
verbose='-V' in sys.argv and 'Y' or ('-v' in sys.argv and 1 or 0)
errs = utils.run_suite(test_suite(), verbosity=verbose)
sys.exit(errs and 1 or 0)
## TBD: test init/build sur elements, p.ex. RToOne + cardinality, etc.
|
|
From: <sbi...@us...> - 2003-05-15 17:45:01
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv25871
Added Files:
Tag: brch-0_9pre7-1-PyModel
PyModel.py
Log Message:
Added PyModel.py and tests
--- NEW FILE: PyModel.py ---
#-----------------------------------------------------------------------------
#
# Modeling Framework: an Object-Relational Bridge for python
# (c) 2001, 2002, 2003 Sebastien Bigaret
#
# This file is part of the Modeling Framework.
#
# The Modeling Framework 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.
#
# The Modeling Framework 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 the Modeling Framework; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
#
#-----------------------------------------------------------------------------
"""
Pythonic Description of an OO-RDBM Model
Rules:
- a model is an object of type Model
- a model may specify a list of entities, each of type Entity
- an entity may specify a list of properties, that are either of type Attribute
or \of type Relation
- all references to attributes, relations, entities, models, is by their "name"
i.e. not by their columnName or className, etc, as the case may be
- whenever deemed useful, defaults are used
- note that the default "type" for an attribute is int
(not string -- seems more logical to me)
- delete rule values are in lowercase
New Changes to note:
parentEntity -> parent
Entity only exposes a properties[] (that holds all attributes and relations)
default for Model.adaptorName is None
added doc attribute on all description classes
Previous changes:
defaults class dictionary variable, for all model description classes
deleteRule -> delete
multiplicityLowerBound and miltiplicity upperBound -> multiplicity
parentEntity -> isAlso
default for displayLabel is value of name (not of columnName)
Entity only has attributes[] (that may also be relations)
"""
##
import Modeling
from Entity import externalNameForInternalName
from utils import isListOrTuple
identity=lambda x: x
def debug(msg):
print msg
def error(msg):
raise RuntimeError, msg
class MP:
def __init__(self, method, *args):
self.method=method
self.param=args
class BaseDescription:
''' Base description class (should not be exported to client code) '''
VERSION='0.1'
defaults = {}
def update(self):
pass
## NB pourrait servir a mettre une derniere fois a jour le component
## en fct. de self.__dict__ filtr'e par self.__class__.defaults.keys()
## ++ ?? peut-etre ajouter un truc du genre 'ignore' dans les defaults
def build(self, model):
pass
def requiredField(self, field):
''' make test more useful '''
if not field:
raise ValueError, 'Required field'
return field
def defaultedField(self, field, defaultValue):
if field:
return field
else:
return defaultValue
def clone(self, descriptionObject):
''' return an independant copy of object '''
return descriptionObject
def toXML(self):
return '<later/>'
#def __str__(self):
# return '<%s instance at %s>'%(str(self.__class__), hex(id(self)))
##
class Model(BaseDescription):
''' Describes a Model '''
defaults={ 'packageName': MP(identity, 'name'),
'adaptorName': '',
'connDict': { 'host': '', 'database': '',
'user': '', 'password': '' },
'entities': [],
'associations': [],
'doc': '',
}
def __init__(self, name, **kw):
self.name=self.requiredField(name)
self.entities=list(kw.get('entities', []))
from Model import Model as MModel
self.component=MModel(name)
updateComponent(self, kw, Model.defaults, name,
ignore=('entities','associations'))
def entityNamed(self, name):
for e in self.entities:
if e.name==name:
return e
return None
def validate(self):
''' validate this model instance '''
pass
def generatePython(self,entityName=None):
''' generate code for model, or only for entityName if specified '''
pass
def generateDBSchema(self,entityName=None):
''' Generate SQL only '''
pass
def createDBSchema(self,entityName=None):
''' drops and recreates from scratch '''
pass
def updateDBSchema(self,mode,entityName=None):
'''
operate on existing tables (and defined by this schema), employing mode:
- check: only report differences between model and existent DB
- incremental: only add/modify columns in existing tables
- clean: add/modify new columns/tables, and drop obsolete ones
Note: renaming of columns or tables?
'''
pass
def addEntity(self, entityDescObj):
''' add entity to model '''
pass
def removeEntity(self, name):
''' remove entity from model '''
pass
def build_associations(self):
""" """
debug('Processing associations')
for assoc in self.associations:
assoc.build(self)
def build(self):
# Check version
if getattr(self, 'version', None)!=BaseDescription.VERSION:
raise ValueError, 'Incompatible versions'
# Build ordered list of entities
self.ordered_entities=oe=[]
entities=list(self.entities)
entities_processed=[]
for entity in [e for e in entities if not e.parent]:
oe.append(entity)
entities_processed.append(entity.name)
entities.remove(entity)
while entities:
print [e.name for e in entities], entities_processed
es=[e for e in entities if e.parent in entities_processed]
for entity in es:
entities.remove(entity)
entities_processed.append(entity.name)
oe.append(entity)
# Build defaults, parent, attributes
for entity in self.ordered_entities:
entity.prebuild_with_defaults(model=self)
entity.prebuild_with_parent_properties(model=self)
# Build Associations
self.build_associations()
for entity in self.ordered_entities:
# propagates changes made by Associations
entity.prebuild_with_parent_properties(model=self)
# Build attributes
for entity in self.ordered_entities:
entity.build_attributes(model=self)
self.component.addEntity(entity.component)
# Check inheritance
for entity in self.ordered_entities:
if entity.parent:
superEntity=self.component.entityNamed(entity.parent)
superEntity.addSubEntity(entity.component)
# model / build phase 2
for entity in self.ordered_entities:
entity.build_preprocess_relationships_and_inverse(self)
for entity in self.ordered_entities:
entity.build_toOne_relationships(self)
for entity in self.ordered_entities:
entity.build_toMany_relationships(self)
##
class Entity(BaseDescription):
''' Describes an Entity '''
defaults={ 'className': MP(identity, 'name'),
'externalName': MP(externalNameForInternalName, 'name'),
'moduleName': MP(identity, 'name'),
'typeName': '',
'isAbstract': 0,
'isReadOnly': 0,
'properties': [],
'parent': '',
'doc': None,
}
def __init__(self, name, **kw):
self.name=self.requiredField(name)
#self.properties=kw.get('properties', ())
from Entity import Entity as MEntity
self.component=MEntity(name)
updateComponent(self, kw, Entity.defaults, name,
ignore=('parent','properties'))
def addAttribute(self, attributeDescObj, model):
''' add attribute to model '''
debug('Entity.addAttribute e: %s / attr: %s'%(self.name,
attributeDescObj.name))
# check it does not already exist
a=self.attributeNamed(attributeDescObj.name)
if a:
debug(' Found it -- ignoring / .entity()=%s'%a.component.entity())
return
# continue
self.properties.append(attributeDescObj)
attributeDescObj.build(model, self) # bizarre, plutot build(entity, model)
self.component.addAttribute(attributeDescObj.component)
self.processAttributes(model)
self.propagate_attribute(attributeDescObj, model)
def attFKName(self, destEntityName):
n='fk'+destEntityName
count=1
while self.propertyNamed(n):
n='fk'+destEntityName+str(count)
count+=1
return n
def attributeNamed(self, name):
for prop in [r for r in self.properties if isinstance(r, Attribute)]:
if prop.name==name: return prop
return None
def removeAttribute(self, attributeDescObj):
''' remove attribute from model '''
pass
def addRelation(self, relationDescObj):
''' add relation to model '''
pass
def attributes(self):
"-"
return [r for r in self.properties if isinstance(r, Attribute)]
def propertyNamed(self, name):
a=self.attributeNamed(name)
if a: return a
else: return self.relationshipNamed(name)
def relationshipNamed(self, name):
"-"
for r in self.relationships():
if r.name==name:
return r
return None
def relationships(self):
"-"
return [r for r in self.properties if isinstance(r, BaseRelation)]
def removeRelation(self, relationDescObj):
''' remove relation from model '''
pass
def inheritFrom(self, entityDescObj):
''' add to this entity all other atts & rels defined in entityDescObj '''
pass
def primaryKey(self):
""" Returns the entity's PK """
for prop in self.properties:
if isinstance(prop, APrimaryKey):
return prop
return 0
def propagate_attribute(self, attributeDescObj, model):
debug('Entity.propagate_attribute e: %s / attr: %s'%(self.name, attributeDescObj.name))
for e in [ee.name() for ee in self.component.subEntities()]:
entity=model.entityNamed(e)
#if not entity.component.attributeNamed(attributeDescObj.name):
entity.addAttribute(attributeDescObj.clone(), model)
def processAttributes(self, model):
# Process attributes and look for PKs & attributes usedForLocking
pks=[]
usedForLocking=[]
for prop in self.attributes():
prop.build(model, self)
if isinstance(prop, APrimaryKey):
pks.append(prop.component)
if prop.usedForLocking:
usedForLocking.append(prop.component)
self.component.setPrimaryKeyAttributes(pks)
self.component.setAttributesUsedForLocking(usedForLocking)
def prebuild_with_defaults(self, model):
"Phase 1"
debug('Entity.build/1: %s'%self.name)
# check defaults properties
if Entity.defaults.get('properties'):
# Update properties iff:
# - they are not already present
# - we do not add a PK if one is already defined
self_prop_names=[prop.name for prop in self.properties]
for dprop in Entity.defaults['properties']:
if dprop.name not in self_prop_names:
if not ( self.primaryKey() and isinstance(dprop, APrimaryKey) ):
self.properties.append(dprop.clone())
def prebuild_with_parent_properties(self, model):
""" Builds a Modeling.Entity / Phase 2 """
debug('Entity.build/2: %s'%self.name)
# Check inheritance
if self.parent:
parent=model.entityNamed(self.parent)
if not parent:
raise ValueError, "Unable to find parent '%s' for entity '%s'"%(self.parent, self.name)
# Update the properties
self_prop_names=[prop.name for prop in self.properties]
for pprop in parent.properties:
if pprop.name in self_prop_names:
# Overriden property, shouldnt be changed
continue
clone=pprop.clone()
clone.propagated_by=self.parent
self.properties.append(clone)
def build_attributes(self, model):
""" Builds a Modeling.Entity / Phase 3 """
debug('Entity.build/3: %s'%self.name)
## ATTRIBUTES
# Add all attributes
for prop in self.attributes():
prop.build(model, self)
self.component.addAttribute(prop.component)
debug('build_attributes %s.%s: %s'%(self.name,prop.name,prop.component.entity()))
self.processAttributes(model)
def build_preprocess_relationships_and_inverse(self, model):
""" Builds a Modeling.Entity / Phase 4 """
if self.parent: return
debug('Entity.build/4: %s'%self.name)
for r in self.relationships():
destEntity=model.entityNamed(r.destination)
if not destEntity:
raise ValueError, 'Relation %s.%s: cannot find destination entity %s'%(self.name,r.name,r.destination)
if getattr(r, 'inverse',None):
self.forward_rel_info(r, model)
def forward_rel_info(self, rel, model):
''' '''
debug('forward_rel_info %s.%s'%(self.name,rel.name))
def check_or_make_equal(x,y):
if x and y:
assert x == y
return x and (x,x) or (y,y)
for e in self.component.allSubEntities():
r=model.entityNamed(e.name()).relationshipNamed(rel.name)
r.inverse=''
rel.src,r.src=check_or_make_equal(rel.src,r.src)
rel.dst,r.dst=check_or_make_equal(rel.dst,r.dst)
if rel.inverse:
invr=model.entityNamed(rel.destination).relationshipNamed(rel.inverse)
if invr.inverse: assert invr.inverse==rel.name
else: invr.inverse=rel.name
rel.src,invr.dst=check_or_make_equal(rel.src,invr.dst)
rel.dst,invr.src=check_or_make_equal(rel.dst,invr.src)
def build_toOne_relationships(self, model):
toOneRels=[r for r in self.properties if isinstance(r, RToOne)]
for prop in toOneRels:
# Note: we build() AFTER we add the relationship, or
# relationship.component.entity==None and then it's impossible to
# add a join to such a MRelationship
self.component.addRelationship(prop.component)
prop.build(model, self)
def build_toMany_relationships(self, model):
toManyRels=[r for r in self.properties if isinstance(r, RToMany)]
for prop in toManyRels:
# Note: we build() AFTER we add the relationship, or
# relationship.component.entity==None and then it's impossible to
# add a join to such a MRelationship
self.component.addRelationship(prop.component)
prop.build(model, self)
def _void_void(self, model):
# We need to have two phases: building relationships requires that all
# attributes of all entities are previously initalized and built.
## RELATIONS
toOneRels=[r for r in self.properties if isinstance(r, RToOne)]
toManyRels={}
[toManyRels.setdefault(k,v) for k,v in [(r.name,r) for r in self.properties
if isinstance(r, RToMany)]]
# process inverse
#for r in toOneRels+toManyRels
## TBD: ici il faut encore 2 phases: 1. traiter toutes les toOnes,
## puis 2. toutes les toManys, ou alors 1. traiter les inverses, 2. traiter
## les relations.
## La 2eme solution implique plus de tests dans le build des relations
## (si inverse mais pas encore traitee, chercher/creer la fk et sinon
## recuperer la bonne avec le bon nom...
# toOne
#print toManyRels
for prop in toOneRels:
# Note: we build() AFTER we add the relationship, or
# relationship.component.entity==None and then it's impossible to
# add a join to such a MRelationship
self.component.addRelationship(prop.component)
prop.build(model, self)
# toMany
for prop in toManyRels.values():
self.component.addRelationship(prop.component)
prop.build(model, self)
## TBD: RETURN les entites modifiees pour update et propagation!
## ex. updateAfterChanges()
## pourrait tester l'existant avec entity.propertyNamed
##
class Attribute(BaseDescription):
''' Describes an Attribute '''
defaults={ 'columnName': MP(externalNameForInternalName, 'name'),
#'key': 0,
'usedForLocking': 0,
'type': 'int',
'externalType': 'INTEGER',
'isClassProperty': 1,
'isRequired': 0,
'precision': 0,
'width': 0,
'scale': 0,
'defaultValue': None,
'displayLabel': '',
'doc': None,
}
def __init__(self, name, **kw):
self.name=self.requiredField(name)
from Attribute import Attribute as MAttribute
self.component=MAttribute(name)
updateComponent(self, kw, Attribute.defaults, name,
ignore='usedForLocking')
def build(self, model, entity):
pass
def clone(self):
d=self.__dict__.copy()
try: del d['component']
except: pass
clone=apply(self.__class__, (), d)
return clone
class AInteger(Attribute):
defaults={ 'type': 'int',
'externalType': 'INTEGER',
'defaultValue': 0,
}
def __init__(self, name, **kw):
apply(Attribute.__init__.im_func, (self, name), kw)
updateComponent(self, kw, AInteger.defaults, name,
ignore='usedForLocking')
class AString(Attribute):
defaults={ 'type': 'string',
'externalType': 'VARCHAR',
'width': 255,
'defaultValue': '',
}
def __init__(self, name, **kw):
apply(Attribute.__init__.im_func, (self, name), kw)
updateComponent(self, kw, AString.defaults, name,
ignore='usedForLocking')
# http://www.onlamp.com/pub/a/onlamp/2001/09/13/aboutSQL.html
#
# SQL Wisdom #7) The data type is invariably different -- even if it has the
# same name -- in another database. Always check the documentation.
class AFloat(Attribute):
defaults={ 'type': 'float',
'externalType': 'NUMERIC',
'precision': 15,
'scale': 5,
'defaultValue': 0.0,
}
def __init__(self, name, **kw):
apply(Attribute.__init__.im_func, (self, name), kw)
updateComponent(self, kw, AFloat.defaults, name,
ignore='usedForLocking')
class ADateTime(Attribute):
defaults={ 'type': 'DateTime',
'externalType': 'TIMESTAMP',
'defaultValue': None,
}
def __init__(self, name, **kw):
apply(Attribute.__init__.im_func, (self, name), kw)
updateComponent(self, kw, ADateTime.defaults, name,
ignore='usedForLocking')
class APrimaryKey(AInteger):
defaults={ 'isClassProperty': 0,
'isRequired': 1,
'defaultValue': MP(lambda i: (i and [0] or [None])[0],
'isClassProperty'),
'doc': 'Primary Key',
}
def __init__(self, name='id', **kw):
apply(AInteger.__init__.im_func, (self, name), kw)
updateComponent(self, kw, APrimaryKey.defaults, name,
ignore='usedForLocking')
class AForeignKey(AInteger):
defaults={ 'isClassProperty': 0,
'isRequired': 0,
'defaultValue': None,
'doc': 'Foreign Key',
}
def __init__(self, name='id', **kw):
apply(AInteger.__init__.im_func, (self, name), kw)
updateComponent(self, kw, AForeignKey.defaults, name,
ignore='usedForLocking')
##
def xor(a,b):
return not not ((a and not b) or (not a and b))
class BaseRelation(BaseDescription):
''' Describes a Relation '''
defaults={ 'delete': 0,
#'key': 0,
#'destinationEntity': '',
##'usedForLocking': 0,
'isClassProperty': 1,
'multiplicity': [0,1],
'joinSemantic': 0,
'src': '',
'dst': '',
'displayLabel': '',
'doc': '',
'inverse': '',
}
# Additinal attr. for self.: src_dst_specified
def __init__(self, name, destination, **kw):
self.name=self.requiredField(name)
self.destination=self.requiredField(destination)
from Relationship import SimpleRelationship as MRelationship
self.component=MRelationship(name)
updateComponent(self,kw,BaseRelation.defaults,name,
ignore=('src', 'dst', 'multiplicity', 'src_dst_specified', 'inverse'))
if xor(self.src, self.dst):
raise ValueError, "Parameters src and dst should be both specified"
def clone(self):
d=self.__dict__.copy()
try: del d['component'] # we do not want to copy this
except: pass
try: del d['src_dst_specified']
except: pass
clone=apply(self.__class__, (), d)
return clone
class RToOne(BaseRelation):
defaults={ 'multiplicity': [0,1],
'joinSemantic': 0,
}
propagated_by=None
def __init__(self, name, destination, **kw):
apply(BaseRelation.__init__.im_func, (self, name, destination), kw)
updateComponent(self, kw, RToOne.defaults, name,
ignore=('src', 'dst', 'multiplicity', 'src_dst_specified', 'inverse'))
def build(self, model, entity):
debug('(build toOne) Relation %s.%s'%(entity.name,self.name))
self.src_dst_specified=not not self.src
destEntity=model.entityNamed(self.destination)
destMEntity=destEntity.component
#print model.component.entitiesNames()
# Check multiplicity
lowB=int(self.multiplicity[0])
uppB=int(self.multiplicity[1])
err=''
if lowB not in (0,1): err+='Lower bound must be 0 or 1. '
if uppB not in (0,1): err+='Upper bound must be 0 or 1. '
if err:
raise ValueError, 'Relation %s.%s: %s'%(entity.component.name(),
self.component.name(), err)
self.component.setMultiplicity(lowB, uppB)
# Process src & dst attributes
if not self.src_dst_specified:
destinationMAttribute=destMEntity.primaryKeyAttributes()[0]
if not self.propagated_by:
sourceAttribute=AForeignKey(entity.attFKName(destEntity.name))
else:
# The attribute has already been propagated, find & re-use it
mparent=model.entityNamed(self.propagated_by).component
mparent_destAttr=mparent.relationshipNamed(self.name).sourceAttributes()
fkName=mparent_destAttr[0].name()
sourceAttribute=entity.attributeNamed(fkName)
if not sourceAttribute:
error('Could not find src.attr. %s.%s for relationship %s.%s with %s inheriting from parent=%s (propagated_by=%s).\nThis should not happen, please report to <mod...@li...> along with your model'%(entity.name,fkName,entity.name,self.name,entity.name,entity.parent, self.propagated_by))
entity.addAttribute(sourceAttribute, model)
sourceMAttribute=sourceAttribute.component
self.src=sourceAttribute.name
self.dst=destinationMAttribute.name()
entity.forward_rel_info(self, model)
else: # src & dst specified
sourceMAttribute=entity.component.attributeNamed(self.src)
if not sourceMAttribute:
raise ValueError, 'Relation %s.%s: unable to find source attribute %s.%s'%(entity.component.name(), self.component.name(), entity.name, self.src)
destinationMAttribute=destMEntity.attributeNamed(self.dst)
# check destinationAttribute
if not destinationMAttribute:
if self.dst:
err_msg='Relation %s.%s: unable to find destination attribute %s.%s'%(entity.name, self.name, self.destination, self.dst)
else:
err_msg='Relation %s.%s: unable to find destination attribute: no primary key declared for entity %s'%(entity.name, self.name, self.destination)
raise ValueError, err_msg
# src and dest are set, ok
from Join import Join as MJoin
j=MJoin(sourceMAttribute, destinationMAttribute)
self.component.addJoin(j)
#if not self.component.destinationEntity(): import pdb ; pdb.set_trace()
class RToMany(BaseRelation):
defaults={ 'multiplicity': [0,None],
'joinSemantic': 0,
}
propagated_by=None
def __init__(self, name, destination, **kw):
apply(BaseRelation.__init__.im_func, (self, name, destination), kw)
updateComponent(self, kw, RToMany.defaults, name, ignore=('src', 'dst', 'multiplicity','inverse'))
def build(self, model, entity):
self.src_dst_specified=not not self.src
debug('(build toMany) Relation %s.%s(%s->%s)'%(entity.name,self.name,
self.src, self.dst))
#print model.component.entitiesNames()
destEntity=model.entityNamed(self.destination)
destMEntity=destEntity.component
# Check multiplicity
lowB=int(self.multiplicity[0])
uppB=self.multiplicity[1]
err=''
if uppB in (0,1): err+='Invalid value for upper bound of a toMany rel.'
if err:
raise ValueError, 'Relation %s.%s: %s'%(entity.component.name(),
self.component.name(), err)
self.component.setMultiplicity(lowB, uppB)
# Process src & dst attributes
if not self.src_dst_specified:
sourceMAttribute=entity.component.primaryKeyAttributes()[0]
if not self.propagated_by:
destinationAttribute=AForeignKey(destEntity.attFKName(entity.name))
else:
# The attribute has already been propagated, find it
mparent=model.entityNamed(self.propagated_by).component
mparent_destAttr=mparent.relationshipNamed(self.name).destinationAttributes()
fkName=mparent_destAttr[0].name()
destinationAttribute=destEntity.attributeNamed(fkName)
if not destinationAttribute:
error('Could not find dest.attr. %s.%s for relationship %s.%s with %s inheriting from parent=%s (propagated_by=%s).\nThis should not happen, please report to <mod...@li...> along with your model'%(destEntity.name,fkName,entity.name,self.name,entity.name,entity.parent, self.propagated_by))
destEntity.addAttribute(destinationAttribute, model)
destinationMAttribute=destinationAttribute.component
self.src=sourceMAttribute.name()
self.dst=destinationMAttribute.name()
entity.forward_rel_info(self, model)
else: # src and dst specified
sourceMAttribute=entity.component.attributeNamed(self.src)
destinationMAttribute=destMEntity.attributeNamed(self.dst)
if not destinationMAttribute:
raise ValueError, 'Relation %s.%s: unable to find destination attribute %s.%s'%(entity.component.name(), self.component.name(), self.destination, self.dst)
# Check source attribute
if not sourceMAttribute:
if self.src:
err_msg='Relation %s.%s: unable to find source attribute %s.%s'%(entity.name, self.name, entity.name, self.src)
else:
err_msg='Relation %s.%s: unable to find source attribute: no primary key declared for entity %s'%(entity.name, self.name, entity.name)
raise ValueError, err_msg
# src and dest are set
from Join import Join as MJoin
j=MJoin(sourceMAttribute, destinationMAttribute)
self.component.addJoin(j)
#if not self.component.destinationEntity(): import pdb ; pdb.set_trace()
class Association(BaseDescription):
''' Describes a Relation between 2 entities '''
# TBD a placer dans les prop. de Entity
# ex. Relation('Employee', 'Address', ([0,None],cascade), ([0,1],deny))
# --> soit ca
# --> soit tout a la main
# --> soit dans les Entity, RToOne, RToMany:
# - avec seulement destEntity
# - avec destEntity et inverse=
def __init__(self, src, dst,
multiplicity=[0,1], invMultiplicity=[0,None],
srcProps={}, dstProps={}):
if multiplicity[1]>1:
raise ValueError, 'invalid mult'
if not (invMultiplicity[1] in (None, '*', -1) or invMultiplicity[0]>1):
raise ValueError, 'invalid invMult'
self.src=src
self.dst=dst
## TBD 1: inverser src/dst si multiplicities sont inversees
## TBD 2: possibilite d'ajout des srcKey/dstKey
self.multiplicity=multiplicity
self.invMultiplicity=invMultiplicity
self.srcProps=srcProps
self.dstProps=dstProps
def build(self, model):
srcE=model.entityNamed(self.src)
if not srcE:
raise ValueError, 'Association: Unable to find source entity %s'%self.src
dstE=model.entityNamed(self.dst)
if not dstE:
raise ValueError, 'Association: Unable to find destination entity %s'%self.dst
dstAtt=dstE.primaryKey()
if not dstAtt:
dstAtt=APrimaryKey()
dstE.properties.append(srcAtt)
# FK: create it (TBD: unless ajout dstKey cf __init__)
srcAtt=AForeignKey(srcE.attFKName(dstE.name))
srcE.properties.append(srcAtt)
# Relationships
srcRelName='to'+dstE.name # TBD: build it appropriately!
dstRelName='to'+srcE.name+'s' # TBD: build it appropriately!
srcRel=RToOne(srcRelName, dstE.name, ## TBD: +properties
src=srcAtt.name, dst=dstAtt.name)
dstRel=RToMany(dstRelName, srcE.name, ## TBD: +properties
src=dstAtt.name, dst=srcAtt.name)
srcE.properties.append(srcRel)
dstE.properties.append(dstRel)
##
def updateComponent(object, kw, defaults, name, ignore=()):
"""
Parameters:
component --
kw -- NB: kw is not modified
defaults --
name --
"""
def copy(v):
if isListOrTuple(v):
return list(v)
#return list(v)
if type(v) is type({}): return v.copy()
#if hasattr(v, 'clone') and callable(v.clone):
# print '###Cloning'
# return v.clone() # props
else:
return v
if type(ignore) is type(''): ignore=[ignore]
ignore=list(ignore) ; ignore.extend(['name','propagated_by'])
_kw=defaults.copy()
# We need to clone the defaults['properties'], such as in Entity.defaults:
# when this is not done, Entities.default is reused as is in
# different entities; e.g. each default attr. is assigned
# to different entities, which in turn manipulate and change that attr.
# and its component --> a test like in
# test_PyModel.checkEntitiesProperties() then fails.
clone_or_self=lambda p: (hasattr(p, 'clone') and callable(p.clone)) and p.clone() or p
if _kw.get('properties'):
_kw['properties']=map(clone_or_self, _kw['properties'])
_kw.update(kw) ; kw=_kw
kw['name']=name
for k,v in kw.items():
# On ajoute tout a l'objet aussi, ca sert pdt le build
setattr(object,k,copy(v))
if k in ignore: continue
if isinstance(v,MP):
l=[kw[n] for n in v.param]
v=apply(v.method, l)
else:
v=copy(v)
#try: print k, ': ', v
#except: import pdb ; pdb.set_trace()
object.component.takeStoredValueForKey(v,k)
##
|
|
From: <sbi...@us...> - 2003-05-15 17:44:23
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv25464
Modified Files:
Tag: brch-0_9pre7-1-PyModel
Entity.py Model.py Attribute.py Relationship.py
Log Message:
Added: handleTakeStoredValueForUnboundKey(): used by PyModel e.g. when assigning 'doc' the value should go to the object's field 'comment'
Index: Entity.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Entity.py,v
retrieving revision 1.11
retrieving revision 1.11.2.1
diff -C2 -d -r1.11 -r1.11.2.1
*** Entity.py 22 Apr 2003 09:31:56 -0000 1.11
--- Entity.py 15 May 2003 17:44:19 -0000 1.11.2.1
***************
*** 33,36 ****
--- 33,37 ----
from XMLutils import *
from EntityClassDescription import EntityClassDescription
+ from KeyValueCoding import KeyValueCoding
from Model import ModelError
from Attribute import Attribute
***************
*** 115,119 ****
from Persistent import Persistent
! class Entity(XMLCapability, Persistent):
"""
Describes an entity
--- 116,120 ----
from Persistent import Persistent
! class Entity(XMLCapability, Persistent, KeyValueCoding):
"""
Describes an entity
***************
*** 1415,1420 ****
##
! ## Validation of an Entity
! ## -
##
--- 1416,1430 ----
##
! ## KeyValueCoding error handling
! ##
! def handleAssignementForUnboundKey(self, value, key):
! if key=='doc': self.setComment(value)
! else:
! raise AttributeError, key
! handleTakeStoredValueForUnboundKey=handleAssignementForUnboundKey
!
! ##
! ## TBD Validation of an Entity
! ##
##
Index: Model.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Model.py,v
retrieving revision 1.4
retrieving revision 1.4.2.1
diff -C2 -d -r1.4 -r1.4.2.1
*** Model.py 22 Apr 2003 09:31:56 -0000 1.4
--- Model.py 15 May 2003 17:44:20 -0000 1.4.2.1
***************
*** 40,44 ****
from utils import isaValidName
from XMLutils import *
!
import types
--- 40,44 ----
from utils import isaValidName
from XMLutils import *
! from KeyValueCoding import KeyValueCoding
import types
***************
*** 49,53 ****
from Persistent import Persistent
! class Model(Persistent, XMLCapability):
"Describes a model"
_is_a_model = 1
--- 49,53 ----
from Persistent import Persistent
! class Model(Persistent, XMLCapability, KeyValueCoding):
"Describes a model"
_is_a_model = 1
***************
*** 330,333 ****
--- 330,343 ----
}
+ ##
+ ## KeyValueCoding error handling
+ ##
+ def handleAssignementForUnboundKey(self, value, key):
+ if key=='connDict': self.setConnectionDictionary(value)
+ elif key=='doc': self.setComment(value)
+ else:
+ raise AttributeError, key
+ handleTakeStoredValueForUnboundKey=handleAssignementForUnboundKey
+
# Validation
#
Index: Attribute.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Attribute.py,v
retrieving revision 1.12
retrieving revision 1.12.2.1
diff -C2 -d -r1.12 -r1.12.2.1
*** Attribute.py 22 Apr 2003 09:31:56 -0000 1.12
--- Attribute.py 15 May 2003 17:44:20 -0000 1.12.2.1
***************
*** 37,40 ****
--- 37,41 ----
from XMLutils import *
from Model import ModelError
+ from KeyValueCoding import KeyValueCoding
import Validation
from Modeling.utils import capitalizeFirstLetter
***************
*** 85,89 ****
from Persistent import Persistent
! class Attribute(Persistent, XMLCapability):
"Describes an attribute"
# + public/private _TBD
--- 86,90 ----
from Persistent import Persistent
! class Attribute(Persistent, XMLCapability, KeyValueCoding):
"Describes an attribute"
# + public/private _TBD
***************
*** 678,679 ****
--- 679,688 ----
raise 'Unimplemented'
+ ##
+ ## KeyValueCoding error handling
+ ##
+ def handleAssignementForUnboundKey(self, value, key):
+ if key=='doc': self.setComment(value)
+ else:
+ raise AttributeError, key
+ handleTakeStoredValueForUnboundKey=handleAssignementForUnboundKey
Index: Relationship.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/Relationship.py,v
retrieving revision 1.8
retrieving revision 1.8.2.1
diff -C2 -d -r1.8 -r1.8.2.1
*** Relationship.py 22 Apr 2003 09:31:56 -0000 1.8
--- Relationship.py 15 May 2003 17:44:20 -0000 1.8.2.1
***************
*** 32,35 ****
--- 32,36 ----
from Join import Join
from utils import isaValidName, toBoolean
+ from KeyValueCoding import KeyValueCoding
from XMLutils import *
import Validation
***************
*** 64,68 ****
! class Relationship(Persistent, XMLCapability):
"See interfaces.Relationship for detail"
--- 65,69 ----
! class Relationship(Persistent, XMLCapability, KeyValueCoding):
"See interfaces.Relationship for detail"
***************
*** 205,213 ****
upperBound -- must be a strictly positive integer, or -1 for a non
! constrained to-many relationship. Special value '*' is
! equivalent to -1.
"""
! if upperBound=='*': upperBound=-1
assert(int(upperBound)>0 or int(upperBound)==-1)
self._multUpper=int(upperBound)
--- 206,214 ----
upperBound -- must be a strictly positive integer, or -1 for a non
! constrained to-many relationship. Special values '*'
! and None are equivalent to -1.
"""
! if upperBound in ('*', None): upperBound=-1
assert(int(upperBound)>0 or int(upperBound)==-1)
self._multUpper=int(upperBound)
***************
*** 339,342 ****
--- 340,344 ----
self._propagatesPK = 0
self._ownsDestination = 0
+ print 'RELATIONSHIP INIT %s'%aName
return
***************
*** 802,805 ****
--- 804,817 ----
return d
+ ##
+ ## KeyValueCoding error handling
+ ##
+ def handleAssignementForUnboundKey(self, value, key):
+ if key=='doc': self.setComment(value)
+ elif key=='delete': self.setDeleteRule(value)
+ else:
+ raise AttributeError, key
+ handleTakeStoredValueForUnboundKey=handleAssignementForUnboundKey
+
class FlattenedRelationship(Relationship):
***************
*** 1162,1166 ****
return d
-
# Validation
#
--- 1174,1177 ----
|
|
From: <sbi...@us...> - 2003-05-10 17:41:20
|
Update of /cvsroot/modeling/ProjectModeling/Modeling In directory sc8-pr-cvs1:/tmp/cvs-serv10438 Removed Files: MANIFEST Log Message: Removed deprecated file --- MANIFEST DELETED --- |
|
From: <sbi...@us...> - 2003-05-10 17:38:27
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv8975/Modeling
Modified Files:
CHANGES
Log Message:
Fixed in public release 0.9pre7.1 (and tagged as 0.9pre7): The script
mdl_compile_model.py was not included in the 0.9pre7 tarball.
Index: CHANGES
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/CHANGES,v
retrieving revision 1.101
retrieving revision 1.102
diff -C2 -d -r1.101 -r1.102
*** CHANGES 7 May 2003 11:22:06 -0000 1.101
--- CHANGES 10 May 2003 17:38:24 -0000 1.102
***************
*** 13,16 ****
--- 13,21 ----
password). See tests/Postgresql.cfg for an example.
+ 0.9-pre-7.1 (2003/05/08)
+ -----------
+
+ * Forgot to include mdl_compile_model.py
+
0.9-pre-7 (2003/05/06)
---------
|
|
From: <sbi...@us...> - 2003-05-10 17:38:27
|
Update of /cvsroot/modeling/ProjectModeling In directory sc8-pr-cvs1:/tmp/cvs-serv8975 Modified Files: MANIFEST.in Log Message: Fixed in public release 0.9pre7.1 (and tagged as 0.9pre7): The script mdl_compile_model.py was not included in the 0.9pre7 tarball. Index: MANIFEST.in =================================================================== RCS file: /cvsroot/modeling/ProjectModeling/MANIFEST.in,v retrieving revision 1.5 retrieving revision 1.6 diff -C2 -d -r1.5 -r1.6 *** MANIFEST.in 4 Feb 2003 08:12:05 -0000 1.5 --- MANIFEST.in 10 May 2003 17:38:23 -0000 1.6 *************** *** 12,15 **** --- 12,16 ---- include Modeling/scripts/mdl_generate_python_code.py include Modeling/scripts/mdl_validate_model.py + include Modeling/scripts/mdl_compile_model.py include Modeling/tests/README |
|
From: <sbi...@us...> - 2003-05-07 11:28:48
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/doc/UserGuide
In directory sc8-pr-cvs1:/tmp/cvs-serv24374/doc/UserGuide
Modified Files:
EnvironmentVariables.tex
Log Message:
Fixed typos
Index: EnvironmentVariables.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/UserGuide/EnvironmentVariables.tex,v
retrieving revision 1.5
retrieving revision 1.6
diff -C2 -d -r1.5 -r1.6
*** EnvironmentVariables.tex 7 May 2003 11:22:07 -0000 1.5
--- EnvironmentVariables.tex 7 May 2003 11:28:45 -0000 1.6
***************
*** 4,8 ****
\begin{tableiii}{p{1cm}p{11cm}|p{3cm}}{code}{Name}{Description}{Possible values}
! \lineiii{MDL_DB_CONNECTIONS}{}{}
\lineiii{}{It happens that a model can be written in different places:
in an xml file, in a python file, and even in a pickle when you use
--- 4,8 ----
\begin{tableiii}{p{1cm}p{11cm}|p{3cm}}{code}{Name}{Description}{Possible values}
! \lineiii{MDL_DB_CONNECTIONS_CFG}{}{}
\lineiii{}{It happens that a model can be written in different places:
in an xml file, in a python file, and even in a pickle when you use
|
|
From: <sbi...@us...> - 2003-05-07 11:28:48
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv24374
Modified Files:
ModelSet.py
Log Message:
Fixed typos
Index: ModelSet.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelSet.py,v
retrieving revision 1.6
retrieving revision 1.7
diff -C2 -d -r1.6 -r1.7
*** ModelSet.py 7 May 2003 11:22:07 -0000 1.6
--- ModelSet.py 7 May 2003 11:28:45 -0000 1.7
***************
*** 105,109 ****
A sample configuration file is like::
! [DEFAULTS]
host: localhost
--- 105,109 ----
A sample configuration file is like::
! [DEFAULT]
host: localhost
***************
*** 150,154 ****
try: options.remove('adaptor')
except ValueError: pass
! for key in options: ##### TBD ++ section [Default]
defaults[key]=cp.get(model.name(), key)
model.setConnectionDictionary(defaults)
--- 150,154 ----
try: options.remove('adaptor')
except ValueError: pass
! for key in options:
defaults[key]=cp.get(model.name(), key)
model.setConnectionDictionary(defaults)
|
|
From: <sbi...@us...> - 2003-05-07 11:27:13
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/tests
In directory sc8-pr-cvs1:/tmp/cvs-serv22893
Modified Files:
README test_EditingContext_Global.py
test_EditingContext_Global_Inheritance.py
test_EditingContext_ParentChild.py utils.py
Added Files:
Postgresql.cfg MySQL.cfg
Removed Files:
test.cfg
Log Message:
Updated the cfg. files for tests, now that ModelSet module got
updateModelWithCFG() [RFE #726839]. File test.cfg is replaced by 2 files:
Postgresql.cfg and MySQL.cfg
--- NEW FILE: Postgresql.cfg ---
# This file is used to initalize the model's connection dictionary and
# adaptor's name when the tests are run for Postgresql
# Change this to reflect your own configuration
[DEFAULT]
adaptor: Postgresql
host: localhost
user: postgres
password:
[AuthorBooks]
[StoreEmployees]
--- NEW FILE: MySQL.cfg ---
# This file is used to initalize the model's connection dictionary and
# adaptor's name when the tests are run for MySQL
# Change this to reflect your own configuration
[DEFAULT]
adaptor: MySQL
host: localhost
user: root
password:
[AuthorBooks]
[StoreEmployees]
Index: README
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/README,v
retrieving revision 1.7
retrieving revision 1.8
diff -C2 -d -r1.7 -r1.8
*** README 20 Feb 2003 15:19:28 -0000 1.7
--- README 7 May 2003 11:27:10 -0000 1.8
***************
*** 12,17 ****
# Remaining tests require:
# - that a PostgreSQL and/or MySQL database server is running somewhere
! # - you modify the file ./test.cfg to reflect you own PostgreSQL/MySQL
! # installation
# - two different (***) databases (may be empty) with names: "AUTHOR_BOOKS" &
# "STORE_EMPLOYEES"
--- 12,17 ----
# Remaining tests require:
# - that a PostgreSQL and/or MySQL database server is running somewhere
! # - you modify either ./Postgresql.cfg or MySQL.cfg to reflect you own
! # PostgreSQL/MySQL installation
# - two different (***) databases (may be empty) with names: "AUTHOR_BOOKS" &
# "STORE_EMPLOYEES"
Index: test_EditingContext_Global.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/test_EditingContext_Global.py,v
retrieving revision 1.19
retrieving revision 1.20
diff -C2 -d -r1.19 -r1.20
*** test_EditingContext_Global.py 27 Mar 2003 11:47:57 -0000 1.19
--- test_EditingContext_Global.py 7 May 2003 11:27:10 -0000 1.20
***************
*** 37,41 ****
import unittest, sys
import utils
- from utils import parseConfigFile_and_updateModel
if __name__ == "__main__":
utils.fixpath()
--- 37,40 ----
***************
*** 1017,1021 ****
verbose=0
! databaseAdaptorName='Postgresql'
def main(args):
--- 1016,1020 ----
verbose=0
! database_cfg='Postgresql.cfg'
def main(args):
***************
*** 1024,1028 ****
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, databaseAdaptorName
profile=0; reinitDB_flag=0
--- 1023,1027 ----
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, database_cfg
profile=0; reinitDB_flag=0
***************
*** 1034,1038 ****
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! databaseAdaptorName=v
continue
if k=='-r': reinitDB_flag=1; continue
--- 1033,1037 ----
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! database_cfg='%s.cfg'%v
continue
if k=='-r': reinitDB_flag=1; continue
***************
*** 1041,1048 ****
author_books_model=ModelSet.defaultModelSet().modelNamed('AuthorBooks')
! parseConfigFile_and_updateModel(author_books_model, databaseAdaptorName)
# MySQL specifics: change TIMESTAMP to DATETIME
! if databaseAdaptorName=='MySQL':
author_books_model.entityNamed('Writer').attributeNamed('birthday').setExternalType('DATETIME')
--- 1040,1048 ----
author_books_model=ModelSet.defaultModelSet().modelNamed('AuthorBooks')
! # Initialization of model's caracs.
! ModelSet.updateModelWithCFG(author_books_model, database_cfg)
# MySQL specifics: change TIMESTAMP to DATETIME
! if database_cfg=='MySQL.cfg':
author_books_model.entityNamed('Writer').attributeNamed('birthday').setExternalType('DATETIME')
Index: test_EditingContext_Global_Inheritance.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/test_EditingContext_Global_Inheritance.py,v
retrieving revision 1.8
retrieving revision 1.9
diff -C2 -d -r1.8 -r1.9
*** test_EditingContext_Global_Inheritance.py 10 Feb 2003 22:04:19 -0000 1.8
--- test_EditingContext_Global_Inheritance.py 7 May 2003 11:27:10 -0000 1.9
***************
*** 37,41 ****
import unittest, sys
import utils
- from utils import parseConfigFile_and_updateModel
if __name__ == "__main__":
utils.fixpath()
--- 37,40 ----
***************
*** 396,400 ****
verbose=0
! databaseAdaptorName='Postgresql'
def main(args):
--- 395,399 ----
verbose=0
! database_cfg='Postgresql.cfg'
def main(args):
***************
*** 403,407 ****
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, databaseAdaptorName
profile=0; reinitDB_flag=0
for k, v in options:
--- 402,406 ----
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, database_cfg
profile=0; reinitDB_flag=0
for k, v in options:
***************
*** 412,416 ****
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! databaseAdaptorName=v
continue
if k=='-r': reinitDB_flag=1; continue
--- 411,415 ----
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! database_cfg='%s.cfg'%v
continue
if k=='-r': reinitDB_flag=1; continue
***************
*** 418,422 ****
# Initialization of model's caracs.
! parseConfigFile_and_updateModel(ModelSet.defaultModelSet().modelNamed('StoreEmployees'), databaseAdaptorName)
if reinitDB_flag: reinitDB(); return
--- 417,422 ----
# Initialization of model's caracs.
! model=ModelSet.defaultModelSet().modelNamed('StoreEmployees')
! ModelSet.updateModelWithCFG(model, database_cfg)
if reinitDB_flag: reinitDB(); return
Index: test_EditingContext_ParentChild.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/test_EditingContext_ParentChild.py,v
retrieving revision 1.6
retrieving revision 1.7
diff -C2 -d -r1.6 -r1.7
*** test_EditingContext_ParentChild.py 14 Mar 2003 11:40:13 -0000 1.6
--- test_EditingContext_ParentChild.py 7 May 2003 11:27:10 -0000 1.7
***************
*** 15,19 ****
import unittest, sys
import utils
- from utils import parseConfigFile_and_updateModel
if __name__ == "__main__":
utils.fixpath()
--- 15,18 ----
***************
*** 509,513 ****
verbose=0
! databaseAdaptorName='Postgresql'
def main(args):
--- 508,512 ----
verbose=0
! database_cfg='Postgresql.cfg'
def main(args):
***************
*** 516,520 ****
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, databaseAdaptorName
profile=0; reinitDB_flag=0
--- 515,519 ----
options, args = getopt.getopt(sys.argv[1:], 'vVprd:')
#except: usage(me, 1)
! global verbose, database_cfg
profile=0; reinitDB_flag=0
***************
*** 526,530 ****
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! databaseAdaptorName=v
continue
if k=='-r': reinitDB_flag=1; continue
--- 525,529 ----
if k=='-d':
if v not in ('Postgresql', 'MySQL'): usage(me, 1)
! database_cfg='%s.cfg'%v
continue
if k=='-r': reinitDB_flag=1; continue
***************
*** 533,541 ****
author_books_model=ModelSet.defaultModelSet().modelNamed('AuthorBooks')
! parseConfigFile_and_updateModel(author_books_model, databaseAdaptorName)
! parseConfigFile_and_updateModel(ModelSet.defaultModelSet().modelNamed('StoreEmployees'), databaseAdaptorName)
# MySQL specifics: change TIMESTAMP to DATETIME
! if databaseAdaptorName=='MySQL':
author_books_model.entityNamed('Writer').attributeNamed('birthday').setExternalType('DATETIME')
--- 532,542 ----
author_books_model=ModelSet.defaultModelSet().modelNamed('AuthorBooks')
! store_employee_model=ModelSet.defaultModelSet().modelNamed('StoreEmployees')
! # Initialization of model's caracs.
! ModelSet.updateModelWithCFG(author_books_model, database_cfg)
! ModelSet.updateModelWithCFG(store_employee_model, database_cfg)
# MySQL specifics: change TIMESTAMP to DATETIME
! if database_cfg=='MySQL.cfg':
author_books_model.entityNamed('Writer').attributeNamed('birthday').setExternalType('DATETIME')
Index: utils.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/utils.py,v
retrieving revision 1.6
retrieving revision 1.7
diff -C2 -d -r1.6 -r1.7
*** utils.py 10 Jan 2003 10:45:45 -0000 1.6
--- utils.py 7 May 2003 11:27:10 -0000 1.7
***************
*** 67,88 ****
% (len(result.errors), len(result.failures)))
return newerrs
-
-
- def parseConfigFile_and_updateModel(model, dbAdaptorName):
- """
- Parse 'test.cfg' and change the model's connection dictionary according to
- the options the configuration file sets.
-
- This should only be triggered after the model has been loaded, e.g. after
- one of the modules in the corresponding package has been loaded.
- """
- from ConfigParser import ConfigParser
- import os
- defaults=model.connectionDictionary()
- cp=ConfigParser()
- cp.read('test.cfg')
- for key in defaults.keys():
- if cp.has_option(dbAdaptorName, key):
- defaults[key]=cp.get(dbAdaptorName, key)
- model.setConnectionDictionary(defaults)
- model.setAdaptorName(dbAdaptorName)
--- 67,68 ----
--- test.cfg DELETED ---
|
|
From: <sbi...@us...> - 2003-05-07 11:27:13
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/tests/testPackages/StoreEmployees
In directory sc8-pr-cvs1:/tmp/cvs-serv22893/testPackages/StoreEmployees
Modified Files:
model_StoreEmployees.py model_StoreEmployees.xml
Log Message:
Updated the cfg. files for tests, now that ModelSet module got
updateModelWithCFG() [RFE #726839]. File test.cfg is replaced by 2 files:
Postgresql.cfg and MySQL.cfg
Index: model_StoreEmployees.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/testPackages/StoreEmployees/model_StoreEmployees.py,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** model_StoreEmployees.py 29 Aug 2002 11:14:27 -0000 1.4
--- model_StoreEmployees.py 7 May 2003 11:27:10 -0000 1.5
***************
*** 1,4 ****
model_src="""<?xml version='1.0' encoding='iso-8859-1'?>
! <model name='StoreEmployees' packageName='StoreEmployees' adaptorName='Postgresql' connectionDictionary="{'database': 'STORE_EMPLOYEES', 'user': 'big', 'password': '', 'host': 'bidibule'}">
<entity isReadOnly='0' isAbstract='0' name='Store' parentEntity='' moduleName='Store' className='Store' typeName='' externalName='STORE'>
<primaryKey attributeName='id'/>
--- 1,4 ----
model_src="""<?xml version='1.0' encoding='iso-8859-1'?>
! <model name='StoreEmployees' packageName='StoreEmployees' adaptorName='' connectionDictionary="{'database': 'STORE_EMPLOYEES', 'user': '', 'password': '', 'host': ''}">
<entity isReadOnly='0' isAbstract='0' name='Store' parentEntity='' moduleName='Store' className='Store' typeName='' externalName='STORE'>
<primaryKey attributeName='id'/>
Index: model_StoreEmployees.xml
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/testPackages/StoreEmployees/model_StoreEmployees.xml,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** model_StoreEmployees.xml 29 Aug 2002 11:14:29 -0000 1.4
--- model_StoreEmployees.xml 7 May 2003 11:27:11 -0000 1.5
***************
*** 1,4 ****
<?xml version='1.0' encoding='iso-8859-1'?>
! <model name='StoreEmployees' packageName='StoreEmployees' adaptorName='Postgresql' connectionDictionary="{'database': 'STORE_EMPLOYEES', 'user': 'big', 'password': '', 'host': 'bidibule'}">
<entity isReadOnly='0' isAbstract='0' name='Store' parentEntity='' moduleName='Store' className='Store' typeName='' externalName='STORE'>
<primaryKey attributeName='id'/>
--- 1,4 ----
<?xml version='1.0' encoding='iso-8859-1'?>
! <model name='StoreEmployees' packageName='StoreEmployees' adaptorName='' connectionDictionary="{'database': 'STORE_EMPLOYEES', 'user': '', 'password': '', 'host': ''}">
<entity isReadOnly='0' isAbstract='0' name='Store' parentEntity='' moduleName='Store' className='Store' typeName='' externalName='STORE'>
<primaryKey attributeName='id'/>
|
|
From: <sbi...@us...> - 2003-05-07 11:27:13
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/tests/testPackages/AuthorBooks
In directory sc8-pr-cvs1:/tmp/cvs-serv22893/testPackages/AuthorBooks
Modified Files:
model_AuthorBooks.xml
Log Message:
Updated the cfg. files for tests, now that ModelSet module got
updateModelWithCFG() [RFE #726839]. File test.cfg is replaced by 2 files:
Postgresql.cfg and MySQL.cfg
Index: model_AuthorBooks.xml
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/tests/testPackages/AuthorBooks/model_AuthorBooks.xml,v
retrieving revision 1.5
retrieving revision 1.6
diff -C2 -d -r1.5 -r1.6
*** model_AuthorBooks.xml 27 Mar 2003 11:47:57 -0000 1.5
--- model_AuthorBooks.xml 7 May 2003 11:27:10 -0000 1.6
***************
*** 1,5 ****
<?xml version='1.0' encoding='iso-8859-1'?>
<!-- <!DOCTYPE model SYSTEM "mdl_model.dtd"> -->
! <model name='AuthorBooks' packageName='AuthorBooks' adaptorName='Postgresql' connectionDictionary="{'database': 'AUTHOR_BOOKS', 'user': 'postgres', 'password': '', 'host': 'localhost'}">
<entity isReadOnly='0' externalName='WRITER' name='Writer' parentEntity='' className='Writer' typeName='Writer' isAbstract='0'>
<primaryKey attributeName='id'/>
--- 1,5 ----
<?xml version='1.0' encoding='iso-8859-1'?>
<!-- <!DOCTYPE model SYSTEM "mdl_model.dtd"> -->
! <model name='AuthorBooks' packageName='AuthorBooks' adaptorName='' connectionDictionary="{'database': 'AUTHOR_BOOKS', 'user': '', 'password': '', 'host': ''}">
<entity isReadOnly='0' externalName='WRITER' name='Writer' parentEntity='' className='Writer' typeName='Writer' isAbstract='0'>
<primaryKey attributeName='id'/>
|
|
From: <sbi...@us...> - 2003-05-07 11:22:10
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/doc/UserGuide
In directory sc8-pr-cvs1:/tmp/cvs-serv22018/doc/UserGuide
Modified Files:
EnvironmentVariables.tex
Log Message:
RFE #726839: Added environment variable MDL_DB_CONNECTIONS_CFG; it
points to a single ini-file which centralizes the sensitive
informations contained in each model's database connection dictionary
(username, password). See tests/Postgresql.cfg for an example.
Index: EnvironmentVariables.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/UserGuide/EnvironmentVariables.tex,v
retrieving revision 1.4
retrieving revision 1.5
diff -C2 -d -r1.4 -r1.5
*** EnvironmentVariables.tex 10 Mar 2003 17:02:50 -0000 1.4
--- EnvironmentVariables.tex 7 May 2003 11:22:07 -0000 1.5
***************
*** 4,9 ****
\begin{tableiii}{p{1cm}p{11cm}|p{3cm}}{code}{Name}{Description}{Possible values}
! \lineiii{MDL_ENABLE_DATABASE_LOGGING}{}{}
\lineiii{}{DatabaseAdaptors for Postgresql and MySQL use a common logging
mechanism, whose methods are located in module \module{Modeling.logging}. This
--- 4,38 ----
\begin{tableiii}{p{1cm}p{11cm}|p{3cm}}{code}{Name}{Description}{Possible values}
! \lineiii{MDL_DB_CONNECTIONS}{}{}
! \lineiii{}{It happens that a model can be written in different places:
! in an xml file, in a python file, and even in a pickle when you use
! \code{mdl_compile_model.py}. The consequence is that the connection
! dictionary itself for each model, containing the user and its password,
! is written two or three times in the filesystems. For security and
! administrative reasons, one would prefer that this sensitive information
! should be written in a single place.\newline
! ~\newline
! This environment variable allows you to externalize the connection
! dictionaries of all your models in a single file; you'll typically
! remove the user and password from your models, and add these
! informations to a single file, say
! \file{/full/path/to/db_conn_dicts.cfg}, in a dedicated section for each
! model, like this:\newline
! \begin{center}
! \code{[aModelName]~~~~}\newline
! \code{user: a_username}\newline
! \code{password: passwd}\end{center}
! Then, simply assign to the env. variable \code{MDL_DB_CONNECTIONS_CFG}
! the full path to your \file{db_conn_dicts.cfg}, and your models'
! connection dictionaries will automatically be updated when they are
! loaded.\newline Last, every parameter normally assigned to a connection
! dictionary can be defined in this file, such as: \code{host},
! \code{port}, etc. An extra field can be specified, \code{adaptor}, which
! overrides the adaptor's name in your model (example value:
! \code{Postgresql}, \code{MySQL}).\newline See also python documentation
! for \module{ConfigParser}.}{full path to an ini-file}
! \hline
+ \lineiii{MDL_ENABLE_DATABASE_LOGGING}{}{}
\lineiii{}{DatabaseAdaptors for Postgresql and MySQL use a common logging
mechanism, whose methods are located in module \module{Modeling.logging}. This
***************
*** 12,16 ****
--- 41,47 ----
the \code{sys.stderr}. To disable it, just unset this variable, or set it to
the empty string.}{e.g. '1', 'YES' (plus the empty string for de-activation)}
+
\hline
+
\lineiii{MDL_PERMANENT_DB_CONNECTION}{}{}
\lineiii{}{By default, the database connection is closed each time the last
|
|
From: <sbi...@us...> - 2003-05-07 11:22:10
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv22018
Modified Files:
CHANGES ModelSet.py
Log Message:
RFE #726839: Added environment variable MDL_DB_CONNECTIONS_CFG; it
points to a single ini-file which centralizes the sensitive
informations contained in each model's database connection dictionary
(username, password). See tests/Postgresql.cfg for an example.
Index: CHANGES
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/CHANGES,v
retrieving revision 1.100
retrieving revision 1.101
diff -C2 -d -r1.100 -r1.101
*** CHANGES 6 May 2003 13:52:00 -0000 1.100
--- CHANGES 7 May 2003 11:22:06 -0000 1.101
***************
*** 8,11 ****
--- 8,16 ----
--------------------------------------------------------
+ * RFE #726839: Added environment variable MDL_DB_CONNECTIONS_CFG; it points
+ to a single ini-file which centralizes the sensitive informations
+ contained in each model's database connection dictionary (username,
+ password). See tests/Postgresql.cfg for an example.
+
0.9-pre-7 (2003/05/06)
---------
Index: ModelSet.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/ModelSet.py,v
retrieving revision 1.5
retrieving revision 1.6
diff -C2 -d -r1.5 -r1.6
*** ModelSet.py 28 Feb 2003 23:21:26 -0000 1.5
--- ModelSet.py 7 May 2003 11:22:07 -0000 1.6
***************
*** 56,60 ****
import types
! from logging import error
try:
--- 56,60 ----
import types
! from logging import error, warn
try:
***************
*** 98,101 ****
--- 98,161 ----
setDefaultModelGroup=setDefaultModelSet
+ def updateModelWithCFG(model, cfg_path):
+ """
+ Updates the model's connection dictionary and adaptorName with the values
+ in file 'cfg_path'.
+
+ A sample configuration file is like::
+
+ [DEFAULTS]
+ host: localhost
+
+ [ModelName_1]
+ user: user_1
+ password: pwd_1
+
+ [ModelName_2]
+ adaptor: MySQL
+ user: user_2
+ password: pwd_2
+
+ The special field 'adaptor', if present, changes the adaptorName of the
+ model.
+
+ Raises IOError if file 'cfg_path' cannot be found.
+
+ See also: ModelSet.addModel()
+
+ Parameters:
+
+ model -- the model whose conn.dict. should be updated
+
+ cfg_path -- the full path to the configuration file
+
+ """
+ from ConfigParser import ConfigParser
+ import os
+ defaults=model.connectionDictionary()
+ cp=ConfigParser()
+ try:
+ cp.readfp(open(cfg_path))
+ except IOError:
+ import traceback, cStringIO, sys
+ exc_raised=sys.exc_info()[:2]
+ err_msg="Unable to open file '%s' pointed by env. variable MDL_DB_CONNECTIONS_CFG"%cfg_path
+ exc=cStringIO.StringIO()
+ traceback.print_exception(exc_raised[0], exc_raised[1], None, file=exc)
+ err_msg+="\nOriginal exception was: %s"%exc.getvalue()
+ raise IOError, err_msg
+
+ try: options=cp.options(model.name())
+ except: return
+ try: options.remove('adaptor')
+ except ValueError: pass
+ for key in options: ##### TBD ++ section [Default]
+ defaults[key]=cp.get(model.name(), key)
+ model.setConnectionDictionary(defaults)
+ try:
+ model.setAdaptorName(cp.get(model.name(), 'adaptor'))
+ except:
+ pass
+
class ModelSet(Persistent):
"""Holds a set of Modeling.Models that can co-exist at runtime
***************
*** 114,118 ****
def addModel(self, aModel):
! "..."
#assert
# Check model name
--- 174,189 ----
def addModel(self, aModel):
! """
! Add a model to the model set. In order to be successfully added the model
! should not have the same name than one of the models already added to the
! ModelSet, nor should it hold an entity whose name is already used within
! the ModelSet.
!
! Raises ModelError if the insertion of aModel fails.
!
! If the environment variable 'MDL_DB_CONNECTIONS_CFG' is set, the file
! it points to is used to update aModel's connection dictionary (and
! possibly its adaptorName as well). See updateModelWithCFG() for details.
! """
#assert
# Check model name
***************
*** 129,132 ****
--- 200,209 ----
aModel._setModelSet(self)
+ # MDL_DB_CONNECTIONS_CFG
+ import os
+ cfg_path=os.environ.get('MDL_DB_CONNECTIONS_CFG')
+ if cfg_path:
+ updateModelWithCFG(aModel, cfg_path)
+
# XML Import/Export facilities
def addModelFromXML(self, xmlSource):
|
|
From: <sbi...@us...> - 2003-05-06 16:29:52
|
Update of /cvsroot/modeling/ZModeling
In directory sc8-pr-cvs1:/tmp/cvs-serv27997
Modified Files:
CHANGES INSTALL README
Log Message:
Updated & added informations about the products (README,INSTALL)
Index: CHANGES
===================================================================
RCS file: /cvsroot/modeling/ZModeling/CHANGES,v
retrieving revision 1.16
retrieving revision 1.17
diff -C2 -d -r1.16 -r1.17
*** CHANGES 22 Apr 2003 09:35:16 -0000 1.16
--- CHANGES 6 May 2003 16:29:48 -0000 1.17
***************
*** 1,5 ****
-*- text -*-
! Current release is: 0.9-pre-6
* Updated ZModelizationTool: a field 'comment' was added for Model, Entity,
--- 1,10 ----
-*- text -*-
! Current release is: 0.9-pre-7
!
! 0.9-pre-7 (2003/05/06)
! ---------
!
! * mdl_validate_model.py: added '-Q' + slightly change the usage (see --help)
* Updated ZModelizationTool: a field 'comment' was added for Model, Entity,
Index: INSTALL
===================================================================
RCS file: /cvsroot/modeling/ZModeling/INSTALL,v
retrieving revision 1.1.1.1
retrieving revision 1.2
diff -C2 -d -r1.1.1.1 -r1.2
*** INSTALL 30 Jul 2002 15:34:59 -0000 1.1.1.1
--- INSTALL 6 May 2003 16:29:48 -0000 1.2
***************
*** 1,2 ****
ZModelizationTool:
! drop it into a Zope's Products/ directory, then create an instance
--- 1,3 ----
ZModelizationTool:
! drop it into a Zope's Products/ directory, then create an instance in the
! Zope Management Interface (ZMI).
Index: README
===================================================================
RCS file: /cvsroot/modeling/ZModeling/README,v
retrieving revision 1.1.1.1
retrieving revision 1.2
diff -C2 -d -r1.1.1.1 -r1.2
*** README 30 Jul 2002 15:34:59 -0000 1.1.1.1
--- README 6 May 2003 16:29:48 -0000 1.2
***************
*** 1 ****
! For dependencies and general informations, see ProjectModeling/
--- 1,30 ----
! This directory contains Zope products based on the Modeling framework:
!
! ZModelizationTool:
! ------------------
! The ZModelization is a tool to help you design a model.
!
! It lets you create and edit the model through a web interface, that is
! to say that every single element being part of the xml-model can be
! modified through easy-to-use web forms. It has some niceties, such as
! the possibility to create a relationship and its inverse along with
! the foreign key if needed in a single operation, or the ability to
! create in a single click a sub-entity having all of its parent's
! attributes and relationships.
!
! Last, you may validate the model, generate the database schemas and
! the python code for your model, just by a few mouse clicks.
!
! ZEditingContextSessioning:
! --------------------------
!
! Adds a new method to Zope session objects: defaultEditingContext(), which
! delivers a specific EditingContext in each session.
!
!
! The two other products, ZModelManager and ZClassDescriptionManager are for
! debugging purposes only and should probably not be used unless you're
! debugging the framework itself. Note that it is possible that they are
! out-of-sync with the current version of the framework.
!
! For dependencies and general informations, see the Modeling framework.
|
|
From: <sbi...@us...> - 2003-05-06 16:29:52
|
Update of /cvsroot/modeling/ZModeling/ZEditingContextSessioning In directory sc8-pr-cvs1:/tmp/cvs-serv27997/ZEditingContextSessioning Modified Files: README.txt Log Message: Updated & added informations about the products (README,INSTALL) Index: README.txt =================================================================== RCS file: /cvsroot/modeling/ZModeling/ZEditingContextSessioning/README.txt,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** README.txt 9 Mar 2003 20:46:39 -0000 1.1 --- README.txt 6 May 2003 16:29:48 -0000 1.2 *************** *** 8,9 **** --- 8,21 ---- there can be some time between the moment where the session expires and the actual unregistration/destruction of its EC. + + Installation + ------------ + + Simply drop ZEditingContextSessioning/ into a Zope's Products/ directory and + restart zope. + + Documentation + ------------- + + The current documentation can be found in the User's Guide at: + http://modeling.sourceforge.net/UserGuide/framework-integration-hints.html |
|
From: <sbi...@us...> - 2003-05-06 16:29:52
|
Update of /cvsroot/modeling/ZModeling/ZModelizationTool In directory sc8-pr-cvs1:/tmp/cvs-serv27997/ZModelizationTool Added Files: INSTALL README Log Message: Updated & added informations about the products (README,INSTALL) --- NEW FILE: INSTALL --- ZModelizationTool: drop this directory into a Zope's Products/ directory, then create an instance in the Zope Management Interface (ZMI). --- NEW FILE: README --- The ZModelization is a tool to help you design a model. It lets you create and edit the model through a web interface, that is to say that every single element being part of the xml-model can be modified through easy-to-use web forms. It has some niceties, such as the possibility to create a relationship and its inverse along with the foreign key if needed in a single operation, or the ability to create in a single click a sub-entity having all of its parent's attributes and relationships. Last, you may validate the model, generate the database schemas and the python code for your model, just by a few mouse clicks. Documentation ------------- The current documentation can be found in the User's Guide: http://modeling.sourceforge.net/UserGuide/define-model.html |
|
From: <sbi...@us...> - 2003-05-06 13:52:06
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/doc/HomePage
In directory sc8-pr-cvs1:/tmp/cvs-serv11584/Modeling/doc/HomePage
Modified Files:
documentation.tex downloads.tex main.tex
Log Message:
Release 0.9-pre-7
Index: documentation.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/HomePage/documentation.tex,v
retrieving revision 1.3
retrieving revision 1.4
diff -C2 -d -r1.3 -r1.4
*** documentation.tex 23 Feb 2003 14:38:54 -0000 1.3
--- documentation.tex 6 May 2003 13:52:01 -0000 1.4
***************
*** 37,40 ****
--- 37,42 ----
\end{enumerate}
+
+ %% end
\input{www/menu-inline-end}
\end{document}
Index: downloads.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/HomePage/downloads.tex,v
retrieving revision 1.7
retrieving revision 1.8
diff -C2 -d -r1.7 -r1.8
*** downloads.tex 14 Mar 2003 09:42:57 -0000 1.7
--- downloads.tex 6 May 2003 13:52:01 -0000 1.8
***************
*** 10,14 ****
\begin{enumerate}
! \item[\bf Current version: 0.9-pre-4 (Second release candidate for 0.9)]
Download it here:\begin{rawhtml}<a
--- 10,14 ----
\begin{enumerate}
! \item[\bf Current version: 0.9-pre-7]
Download it here:\begin{rawhtml}<a
Index: main.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/HomePage/main.tex,v
retrieving revision 1.12
retrieving revision 1.13
diff -C2 -d -r1.12 -r1.13
*** main.tex 14 Mar 2003 09:42:57 -0000 1.12
--- main.tex 6 May 2003 13:52:01 -0000 1.13
***************
*** 7,11 ****
% Increment the release number whenever significant changes are made.
% The author and/or editor can define 'significant' however they like.
! %\release{0.9-pre-4}
% At minimum, give your name and an email address. You can include a
--- 7,11 ----
% Increment the release number whenever significant changes are made.
% The author and/or editor can define 'significant' however they like.
! %\release{0.9-pre-7}
% At minimum, give your name and an email address. You can include a
***************
*** 13,17 ****
\author{S\'ebastien Bigaret}
\email{sbi...@us...}
! \date{March 14, 2003}
%\date{\today}
--- 13,17 ----
\author{S\'ebastien Bigaret}
\email{sbi...@us...}
! \date{May 06, 2003}
%\date{\today}
|
|
From: <sbi...@us...> - 2003-05-06 13:52:05
|
Update of /cvsroot/modeling/ProjectModeling/Modeling/doc
In directory sc8-pr-cvs1:/tmp/cvs-serv11584/Modeling/doc
Modified Files:
UserGuide.tex
Log Message:
Release 0.9-pre-7
Index: UserGuide.tex
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/doc/UserGuide.tex,v
retrieving revision 1.18
retrieving revision 1.19
diff -C2 -d -r1.18 -r1.19
*** UserGuide.tex 14 Mar 2003 09:42:57 -0000 1.18
--- UserGuide.tex 6 May 2003 13:52:01 -0000 1.19
***************
*** 12,19 ****
% the rest is at your discretion.
\authoraddress{Email: \email{sbi...@us...}}
! \date{March 14, 2003}
%\date{\today}
! \release{0.9-pre-4}
! %\setreleaseinfo{pre-4}
\setshortversion{0.9}
--- 12,19 ----
% the rest is at your discretion.
\authoraddress{Email: \email{sbi...@us...}}
! \date{May 06, 2003}
%\date{\today}
! \release{0.9-pre-7}
! %\setreleaseinfo{pre-7}
\setshortversion{0.9}
|
|
From: <sbi...@us...> - 2003-05-06 13:52:05
|
Update of /cvsroot/modeling/ProjectModeling/Modeling
In directory sc8-pr-cvs1:/tmp/cvs-serv11584/Modeling
Modified Files:
CHANGES TODO
Log Message:
Release 0.9-pre-7
Index: CHANGES
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/CHANGES,v
retrieving revision 1.99
retrieving revision 1.100
diff -C2 -d -r1.99 -r1.100
*** CHANGES 6 May 2003 12:20:31 -0000 1.99
--- CHANGES 6 May 2003 13:52:00 -0000 1.100
***************
*** 3,11 ****
Module Modeling
---------------
! Current release is: 0.9-pre-6 / See also: TODO, INSTALL and doc/
* ** Distributed under the GNU General Public License **
--------------------------------------------------------
* Fixed DatabaseChannel.fetchObject(): it was not MT-safe wrt Database
snapshots' caching in some circumstances (see comments in the code for
--- 3,14 ----
Module Modeling
---------------
! Current release is: 0.9-pre-7 / See also: TODO, INSTALL and doc/
* ** Distributed under the GNU General Public License **
--------------------------------------------------------
+ 0.9-pre-7 (2003/05/06)
+ ---------
+
* Fixed DatabaseChannel.fetchObject(): it was not MT-safe wrt Database
snapshots' caching in some circumstances (see comments in the code for
***************
*** 28,32 ****
0.9-pre-6 (2003/04/22) Project milestone -- no public release
! --------- Preparing 0.9 - ETA: 2003/04/28
* ModelMasons: added a new generation scheme. The existing one is named
--- 31,35 ----
0.9-pre-6 (2003/04/22) Project milestone -- no public release
! ---------
* ModelMasons: added a new generation scheme. The existing one is named
Index: TODO
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/Modeling/TODO,v
retrieving revision 1.9
retrieving revision 1.10
diff -C2 -d -r1.9 -r1.10
*** TODO 17 Mar 2003 11:19:14 -0000 1.9
--- TODO 6 May 2003 13:52:00 -0000 1.10
***************
*** 296,297 ****
--- 296,304 ----
seperate module.
+ * KeyValueCoding:
+
+ - takeValuesFromDictionary unused in the framework -> should be used in
+ DatabaseContext.initializeObject()
+
+ - voir aussi autre chose (??) entre KVC et (Entity)ClassDescription
+
\ No newline at end of file
|
|
From: <sbi...@us...> - 2003-05-06 13:52:05
|
Update of /cvsroot/modeling/ProjectModeling
In directory sc8-pr-cvs1:/tmp/cvs-serv11584
Modified Files:
setup.py
Log Message:
Release 0.9-pre-7
Index: setup.py
===================================================================
RCS file: /cvsroot/modeling/ProjectModeling/setup.py,v
retrieving revision 1.23
retrieving revision 1.24
diff -C2 -d -r1.23 -r1.24
*** setup.py 25 Apr 2003 18:13:32 -0000 1.23
--- setup.py 6 May 2003 13:52:00 -0000 1.24
***************
*** 46,50 ****
setup(name="ModelingCore",
! version="0.9-pre-6",
licence ="GNU General Public License",
description=short_description,
--- 46,50 ----
setup(name="ModelingCore",
! version="0.9-pre-7",
licence ="GNU General Public License",
description=short_description,
|