On Sep 14, 2010, at 5:03 PM, A.M. wrote:

> Hello,
> 
> I have a schema like this:
> 
> Image
> *id
> *name
> 
> Metadatakey
> *id
> *exifkey
> *name
> 
> Metadata
> *id
> *image_id -> Image
> *metadatakey_id -> Metadatakey
> *value

Thanks to Michael Bayer, I was able to put together the image metadata model I 
posted on some months ago. 

I added an association_proxy to make the db schema more transparent which works 
well when reading (as per this example 
http://stackoverflow.com/questions/780774/sqlalchemy-dictionary-of-tags), but 
when setting an attribute through the association proxy, it seems like I would 
need access to the current session to make the determination of whether or not 
the metadatakey exists (and grab it).

Is it OK practice to use the session in the _metadataCreator method? Is there a 
better way to accomplish this? The last line of the source code below 
demonstrates what I wish to accomplish. Thanks.

-M

-----------------------------------

from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.types import Integer,Unicode
from sqlalchemy.orm import relationship,scoped_session,backref
from sqlalchemy.orm.session import sessionmaker
from sqlalchemy.schema import Column,ForeignKey
from sqlalchemy.orm.collections import attribute_mapped_collection
from sqlalchemy.engine import create_engine
from sqlalchemy.ext.associationproxy import association_proxy

Base = declarative_base()

class Image(Base):
   __tablename__ = 'image'
   id = Column(Integer,primary_key=True)
   metadatadict = relationship('MetadataValue',
                               
collection_class=attribute_mapped_collection('key'),
                               primaryjoin='Image.id==MetadataValue.image_id')

   def _metadataCreator(key,value):
       #-----------> get existing MetadataName for this key here, but how?
       return MetadataValue(namekey=key,value=value)

   metadatas = 
association_proxy('metadatadict','value',creator=_metadataCreator)

class MetadataName(Base):
   __tablename__ = 'metadataname'
   id = Column(Integer,primary_key=True)
   namekey = Column(Unicode,nullable=False,unique=True)

class MetadataValue(Base):
   __tablename__ = 'metadatavalue'
   id = Column(Integer,primary_key=True)
   image_id = Column(Integer,ForeignKey(Image.id),nullable=False)
   image = relationship(Image,
                        primaryjoin='MetadataValue.image_id==Image.id')
   metadataname_id = Column(Integer,ForeignKey(MetadataName.id),nullable=False)
   metadataname = relationship(MetadataName,
                                
primaryjoin='MetadataValue.metadataname_id==MetadataName.id')
   value = Column(Unicode,nullable=False)

   @property
   def key(self):
       return self.metadataname.namekey

engine = create_engine('postgresql://localhost/test',echo=True)
session = scoped_session(sessionmaker(autocommit=False,bind=engine))

Base.metadata.drop_all(engine)
Base.metadata.create_all(engine)

metadataname1 = MetadataName(namekey=u'MIMEType')
metadataname2 = MetadataName(namekey=u'PixelWidth')
img1 = Image()
metadatavalue1 = 
MetadataValue(image=img1,value=u'image/png',metadataname=metadataname1)

session.add_all([metadataname1,img1,metadatavalue1,metadataname2])

session.flush()

#BEGIN TEST AREA
print img1.metadatas['MIMEType']
img1.metadatas['PixelWidth'] = u'300'


-- 
You received this message because you are subscribed to the Google Groups 
"sqlalchemy" group.
To post to this group, send email to sqlalch...@googlegroups.com.
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en.

Reply via email to