Re: [sqlalchemy] Clarification about performance and relation()

2010-03-26 Thread masetto
Excuse me,

After your valuable advice, i've modified my code and i've removed the
manual setting of the foreign key (which was completely wrong). But now
i've another problem, maybe due to another misunderstanding.
(I've moved all my ORM classes within the same module now).

I am parsing an xml where i can found something like:

definition id=1
   ..
  platform Windows XP/platform
  ..
/definition

definition id=2
   ..
  platform Linux/platform
  ..
/definition

definition id=3
  ..
  platform Windows 7/platform
  platform Windows XP/platform
  platform Windows Vista/platform
 ..
/definition

When a single platform is associated to a definition (1:1), i expect the
following table layout:

table_platform:

id | platform| definitionId_fk

1   Windows XP1
2   Linux   2

When N platforms are associated to the same definition (N:1), i expect the
following table layout:

id | platform| definitionId_fk

3   Windows 7  3
4   Windows XP   3
5   Windows Vista3
5   Solaris   4

For the first case, everything works fine and i got exactly what i am
expecting but, for the second case i got:

id | platform| definitionId_fk

3   Windows 7  None
4   Windows XP   None
5   Windows Vista3

Maybe it's a stupid problem but i can't figure it out at the moment :/

Code:
...
for definitions in ovalXML._childrenMap['definitions']:
for definition in definitions.getchildren():
defInst = ORM_Classes.DefinitionClass(definition)
...
if subElem1.tag == mainNS + platform:
platf = ORM_Classes.PlatformClass()

platf.setPlatform(str(subElem1))

defInst.PlatformRel = [platf]

session.add(defInst)
session.add(platf)

#i perform a commit every 1000 definitions as you suggested :)

DefinitionClass:

class DefinitionClass(Base):
__tablename__ = 'definitions'

defId = Column(Integer, primary_key=True)
...
version = Column(String)

PlatformRel = relation(PlatformClass, backref=definitions)

def __init__(self, node):
self.version = node.get(version)
...

PlatformClass:

class PlatformClass(Base):
__tablename__ = 'platform'

platformId = Column(Integer, primary_key=True)
platform = Column(String)

platformId_fk = Column('definitionId_fk', Integer,
ForeignKey('definitions.defId'))

def setPlatform(self, node):
self.platform = node

What can i do || correct to get the expected result?

Thanks for your patience.
---
Masetto



On Thu, Mar 25, 2010 at 4:56 PM, Michael Bayer mike...@zzzcomputing.comwrote:

 the relationship between two tables requires both the ForeignKey to be
 present as well as the relationship()  (relation() in 0.5) function to be
 present in the mapping.


 masetto wrote:
  From 30 mins to 2mins... shame :P
 
  Thanks Micheal !
 
  Forgive me, what about the other question about foreign keys?
 
 
  On Thu, Mar 25, 2010 at 3:43 PM, Michael Bayer
  mike...@zzzcomputing.comwrote:
 
  masetto wrote:
   Hi all,
  
   i am writing a python script which parse an xml file (python lxml) and
   import it into a sqlite db, and it works.
   The xml file size is about 30Mb and the import operation takes about
  15
   minutes (do you think is too much? is there something i can do to
  speed
  up
   the process?)
  
   This is a piece of the import function:
  
   ...
   for definition in definitions.getchildren(): #iterate for every xml
   children
   node
   defInst = SQLTableBuilder_Definition.DefinitionClass(definition)
  #read
   and write on db some attribute of the node
   ...
   if subbaElem1.tag == mainNS + platform: #another loop iterate
  for
   every sub-node of the definition node
   platf = SQLTableBuilder_Platform.PlatformClass()
   platf.setPlatform(str(subbaElem1))
   platf.platformId_fk = defInst.defId
  
   session.add(platf)
   session.commit()
...
session.add(defInst)
session.commit()
 
 
  don't commit on every node and on every sub-node.  Just commit once
  every
  1000 new objects or so.   will save a ton of processing.
 
 
 
  
   where DefinitionClass contains the attributes declaration
  (primary_key,
   column(string), etc.) and a Foreign Key.
   There is a relation between the definition table and the platform
  table
   (one
   or more platforms - Operating System - can be associated to a single
   definition) so,
   in the platform table, i've added the following: platformId_fk =
   Column('definitionId_fk', Integer, ForeignKey('definitions.defId'))
  
   All my ORM-Classes are declared within n different classes within n
   different

Re: [sqlalchemy] Clarification about performance and relation()

2010-03-26 Thread masetto
First of all, thanks for your answer :)

#   defInst.PlatformRel = [platf]# change this to
platf.definitions = defInst

I don't have any definitions attribute within the PlatformClass, i suppose
you mean the foreign key, isnt'it?
That is

platf.platformId_fk = defInst

However, this results in another error:

sqlalchemy.exc.InterfaceError: (InterfaceError) Error binding parameter 1 -
probably unsupported type. u'INSERT INTO platform (platform,
definitionId_fk) VALUES (?, ?)' ['Microsoft Windows 2000',
ORM_Classes.DefinitionClass object at 0x8f5278c]

I've played a little with it, then i've moved the relation() from
DefinitionClass to PlatformClass:

class PlatformClass(Base):
__tablename__ = 'platform'

platformId = Column(Integer, primary_key=True)
platform = Column(String)

platformId_fk = Column('definitionId_fk', Integer,
ForeignKey('definitions.defId'))
PlatformRel = relation(DefinitionClass, backref=platform)

and then:

platf.PlatformRel = defInst

Now i got the expected data! It WORKS :P Thanks Werner!

But, i need to understand.. why now it's working?

From the doc:

We are also free... to define the
relationship()http://www.sqlalchemy.org/docs/reference/orm/mapping.html#sqlalchemy.orm.relationshiponly
on one class and not the other. It is also possible to define two
separate 
relationship()http://www.sqlalchemy.org/docs/reference/orm/mapping.html#sqlalchemy.orm.relationshipconstructs
for either direction, which is generally safe for many-to-one and
one-to-many relationships, but not for many-to-many relationships.

Maybe i don't have well understood the role of the relation()/relationship()
function but, shouldn't be the same thing to define the relation() within
the DefinitionClass? I've only changed the location of the relation() and
now it works.
Can you kindly better explain me the role of the relationship() function?

Mmm... please correct me if i'm wrong:

- The relationship between the User and Address classes is defined
separately using the
relationship()http://www.sqlalchemy.org/docs/reference/orm/mapping.html#sqlalchemy.orm.relationshipfunction
OK, and is the only way to define a relation between two tables.

- If i put relationship() in both classes i got a *bidirectional*relationship

- Because of the *placement* of the foreign key, from Address to User it is
*many to one*...   !!! Oh, is this the point, right? If, in the same class,
i define a foreign key AND a relationship() i create a many to one relation
with the linked table

- ..., and from User to Address it is *one to many* - This is valid only
in the bidirectional case or it's automatic when i declare somewhere
foreign key + relationship() ?

- Initially i've defined the foreign key in the PlatformClass and the
relation() in the DefinitionClass. Which type of relation i've created in
that way?

Thanks again!


On Fri, Mar 26, 2010 at 4:50 PM, werner wbru...@free.fr wrote:

 Hi Masetto,

 On 26/03/2010 16:01, masetto wrote:
 

  Maybe it's a stupid problem but i can't figure it out at the moment :/

 Code:
 ...
 for definitions in ovalXML._childrenMap['definitions']:
for definition in definitions.getchildren():
defInst = ORM_Classes.DefinitionClass(definition)

session.add(defInst)  # I think this line should be here,
 you have it further down

...
if subElem1.tag == mainNS + platform:
platf = ORM_Classes.PlatformClass()
platf.setPlatform(str(subElem1))

 #defInst.PlatformRel = [platf]# change this to

   platf.definitions = defInst

 Werner

 --
 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.comsqlalchemy%2bunsubscr...@googlegroups.com
 .
 For more options, visit this group at
 http://groups.google.com/group/sqlalchemy?hl=en.



-- 
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.



[sqlalchemy] Clarification about performance and relation()

2010-03-25 Thread masetto
Hi all,

i am writing a python script which parse an xml file (python lxml) and
import it into a sqlite db, and it works.
The xml file size is about 30Mb and the import operation takes about 15
minutes (do you think is too much? is there something i can do to speed up
the process?)

This is a piece of the import function:

...
for definition in definitions.getchildren(): #iterate for every xml children
node
defInst = SQLTableBuilder_Definition.DefinitionClass(definition) #read
and write on db some attribute of the node
...
if subbaElem1.tag == mainNS + platform: #another loop iterate for
every sub-node of the definition node
platf = SQLTableBuilder_Platform.PlatformClass()
platf.setPlatform(str(subbaElem1))
platf.platformId_fk = defInst.defId

session.add(platf)
session.commit()
 ...
 session.add(defInst)
 session.commit()

where DefinitionClass contains the attributes declaration (primary_key,
column(string), etc.) and a Foreign Key.
There is a relation between the definition table and the platform table (one
or more platforms - Operating System - can be associated to a single
definition) so,
in the platform table, i've added the following: platformId_fk =
Column('definitionId_fk', Integer, ForeignKey('definitions.defId'))

All my ORM-Classes are declared within n different classes within n
different python modules so, i've included the needed imports everytime i
needed it.
And i suppose this is a problem, at least for me, sometime, because when i
try to add: PlatformRel =
relation(SQLTableBuilder_Definition.DefinitionClass, backref=platform)
within my platformClass, i got: 'list' object has no attribute
'_sa_instance_state' :/

So, i've tried to manually set the foreign key, as you can see above. In
the documentation (http://www.sqlalchemy.org/docs/ormtutorial.html) i read:
 SQLAlchemy is automatically aware of many-to-one/one-to-many based on
foreign keys. Does this mean that what i've done is correct or i'm a little
confused? If i manually set a foreign key value, does sqlalchemy
understand that a relation between two tables exists?

Thanks for your attention.
---
Masetto

-- 
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.



Re: [sqlalchemy] Clarification about performance and relation()

2010-03-25 Thread masetto
From 30 mins to 2mins... shame :P

Thanks Micheal !

Forgive me, what about the other question about foreign keys?


On Thu, Mar 25, 2010 at 3:43 PM, Michael Bayer mike...@zzzcomputing.comwrote:

 masetto wrote:
  Hi all,
 
  i am writing a python script which parse an xml file (python lxml) and
  import it into a sqlite db, and it works.
  The xml file size is about 30Mb and the import operation takes about 15
  minutes (do you think is too much? is there something i can do to speed
 up
  the process?)
 
  This is a piece of the import function:
 
  ...
  for definition in definitions.getchildren(): #iterate for every xml
  children
  node
  defInst = SQLTableBuilder_Definition.DefinitionClass(definition)
 #read
  and write on db some attribute of the node
  ...
  if subbaElem1.tag == mainNS + platform: #another loop iterate for
  every sub-node of the definition node
  platf = SQLTableBuilder_Platform.PlatformClass()
  platf.setPlatform(str(subbaElem1))
  platf.platformId_fk = defInst.defId
 
  session.add(platf)
  session.commit()
   ...
   session.add(defInst)
   session.commit()


 don't commit on every node and on every sub-node.  Just commit once every
 1000 new objects or so.   will save a ton of processing.



 
  where DefinitionClass contains the attributes declaration (primary_key,
  column(string), etc.) and a Foreign Key.
  There is a relation between the definition table and the platform table
  (one
  or more platforms - Operating System - can be associated to a single
  definition) so,
  in the platform table, i've added the following: platformId_fk =
  Column('definitionId_fk', Integer, ForeignKey('definitions.defId'))
 
  All my ORM-Classes are declared within n different classes within n
  different python modules so, i've included the needed imports everytime i
  needed it.
  And i suppose this is a problem, at least for me, sometime, because when
 i
  try to add: PlatformRel =
  relation(SQLTableBuilder_Definition.DefinitionClass, backref=platform)
  within my platformClass, i got: 'list' object has no attribute
  '_sa_instance_state' :/
 
  So, i've tried to manually set the foreign key, as you can see above.
 In
  the documentation (http://www.sqlalchemy.org/docs/ormtutorial.html) i
  read:
   SQLAlchemy is automatically aware of many-to-one/one-to-many based on
  foreign keys. Does this mean that what i've done is correct or i'm a
  little
  confused? If i manually set a foreign key value, does sqlalchemy
  understand that a relation between two tables exists?
 
  Thanks for your attention.
  ---
  Masetto
 
  --
  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.comsqlalchemy%2bunsubscr...@googlegroups.com
 .
  For more options, visit this group at
  http://groups.google.com/group/sqlalchemy?hl=en.
 
 

 --
 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.comsqlalchemy%2bunsubscr...@googlegroups.com
 .
 For more options, visit this group at
 http://groups.google.com/group/sqlalchemy?hl=en.



-- 
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.



[sqlalchemy] Problem with Foreign Key

2010-03-18 Thread masetto
Hi all,

i am new to SQLAlchemy (simply wonderful!), and i'm writing some
python scripts to do some experiment.

I've written a SINGLE python module with two classes which define two
different tables (declarative_base) with a simple relationship and a
single Foreign Key and everything WORKS fine as expected. Cool! :P

Then, i've moved that two classes in two different python modules to
better organize my code but now i got the following error:
sqlalchemy.exc.NoReferencedTableError: Could not find table 'metadata'
with which to generate a foreign key

I understood the error message but i can't found a way to resolve this
issue, can you help me?

This is my directory layout:

test.py - the main python module
SQLTableBuilder_Definition.py - class that define a table called
Definition
SQLTableBuilder_Metadata.py - class that define a table called
Metadata

test.py:
...
engine = create_engine('sqlite:///test.db3', echo=True,
encoding='utf-8' )

import SQLTableBuilder_Metadata

metadata_table = SQLTableBuilder_Metadata.MetadataClass.__table__
metadata = SQLTableBuilder_Metadata.Base.metadata
metadata.create_all(engine)

import SQLTableBuilder_Definition
definitions_table =
SQLTableBuilder_Definition.DefinitionClass.__table__
metadata = SQLTableBuilder_Definition.Base.metadata
metadata.create_all(engine)  == My script explode here with the
following:

Traceback (most recent call last):
  File test.py, line 82, in module
metadata.create_all(engine)
...
sqlalchemy.exc.NoReferencedTableError: Could not find table
'metadata' with which to generate a foreign key


Session = sessionmaker(bind=engine)
Session.configure(bind=engine)
session = Session()

...
session.add(myObj)
...

SQLTableBuilder_Definition.py:

Base = declarative_base()

class DefinitionClass(Base):
__tablename__ = 'definitions'

defId = Column(Integer, primary_key=True)
Id = Column(String)
classType = Column(String)
version = Column(String)

metadataId = Column('metadataId', Integer,
ForeignKey('metadata.metadataId'))

def __init__(self, node):
self.Id = node.get(id)[len(IdName):]
self.version = node.get(version)
self.classType = node.get(class)

SQLTableBuilder_Metadata.py:
import SQLTableBuilder_Definition

Base = declarative_base()

class MetadataClass(Base):
__tablename__ = 'metadata'

metadataId = Column(Integer, primary_key=True)
title = Column(String)

defRef = relation(SQLTableBuilder_Definition.DefinitionClass,
backref=metadata)

def __init__(self, node):
self.title = node

If i remove relation and foreign key from the two classes, everything
works fine again.
I suppose that python can't find the metadata table (previously
created without error) from SQLTableBuilder_Definition.py, but how i
can point him in the right direction?

Thanks for your attention.

ps.
 print sqlalchemy.__version__
0.6beta1

-- 
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.



Re: [sqlalchemy] Problem with Foreign Key

2010-03-18 Thread masetto
Damn, your're right! Mea culpa :P
Thanks! Now it's working again



On Thu, Mar 18, 2010 at 6:27 PM, Michael Bayer mike...@zzzcomputing.comwrote:

 masetto wrote:
  Hi all,
 
  i am new to SQLAlchemy (simply wonderful!), and i'm writing some
  python scripts to do some experiment.
 
  I've written a SINGLE python module with two classes which define two
  different tables (declarative_base) with a simple relationship and a
  single Foreign Key and everything WORKS fine as expected. Cool! :P
 
  Then, i've moved that two classes in two different python modules to
  better organize my code but now i got the following error:
  sqlalchemy.exc.NoReferencedTableError: Could not find table 'metadata'
  with which to generate a foreign key
 
  I understood the error message but i can't found a way to resolve this
  issue, can you help me?
 
  This is my directory layout:'


 you need to share one declarative Base class for all of the classes that
 are related to each other, or alternatively at least a single MetaData
 for all tables that wish to reference foreign keys using strings.
 Anytime you specify options using strings to find something else, the
 relevant base has to be shared, i.e. declarative base if using strings
 in relation(), and MetaData if using strings in ForeignKey().







 
  test.py - the main python module
  SQLTableBuilder_Definition.py - class that define a table called
  Definition
  SQLTableBuilder_Metadata.py - class that define a table called
  Metadata
 
  test.py:
  ...
  engine = create_engine('sqlite:///test.db3', echo=True,
  encoding='utf-8' )
 
  import SQLTableBuilder_Metadata
 
  metadata_table = SQLTableBuilder_Metadata.MetadataClass.__table__
  metadata = SQLTableBuilder_Metadata.Base.metadata
  metadata.create_all(engine)
 
  import SQLTableBuilder_Definition
  definitions_table =
  SQLTableBuilder_Definition.DefinitionClass.__table__
  metadata = SQLTableBuilder_Definition.Base.metadata
  metadata.create_all(engine)  == My script explode here with the
  following:
 
  Traceback (most recent call last):
File test.py, line 82, in module
  metadata.create_all(engine)
  ...
  sqlalchemy.exc.NoReferencedTableError: Could not find table
  'metadata' with which to generate a foreign key
 
 
  Session = sessionmaker(bind=engine)
  Session.configure(bind=engine)
  session = Session()
 
  ...
  session.add(myObj)
  ...
 
  SQLTableBuilder_Definition.py:
 
  Base = declarative_base()
 
  class DefinitionClass(Base):
  __tablename__ = 'definitions'
 
  defId = Column(Integer, primary_key=True)
  Id = Column(String)
  classType = Column(String)
  version = Column(String)
 
  metadataId = Column('metadataId', Integer,
  ForeignKey('metadata.metadataId'))
 
  def __init__(self, node):
  self.Id = node.get(id)[len(IdName):]
  self.version = node.get(version)
  self.classType = node.get(class)
 
  SQLTableBuilder_Metadata.py:
  import SQLTableBuilder_Definition
 
  Base = declarative_base()
 
  class MetadataClass(Base):
  __tablename__ = 'metadata'
 
  metadataId = Column(Integer, primary_key=True)
  title = Column(String)
 
  defRef = relation(SQLTableBuilder_Definition.DefinitionClass,
  backref=metadata)
 
  def __init__(self, node):
  self.title = node
 
  If i remove relation and foreign key from the two classes, everything
  works fine again.
  I suppose that python can't find the metadata table (previously
  created without error) from SQLTableBuilder_Definition.py, but how i
  can point him in the right direction?
 
  Thanks for your attention.
 
  ps.
  print sqlalchemy.__version__
  0.6beta1
 
  --
  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.comsqlalchemy%2bunsubscr...@googlegroups.com
 .
  For more options, visit this group at
  http://groups.google.com/group/sqlalchemy?hl=en.
 
 

 --
 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.comsqlalchemy%2bunsubscr...@googlegroups.com
 .
 For more options, visit this group at
 http://groups.google.com/group/sqlalchemy?hl=en.



-- 
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.