Reputation: 725
I've been trying to map an object to a database using SQLAlchemy but have run into a snag.
Edit: Basically changed a whole bunch of stuff.
Version info if handy: [OS: Mac OSX 10.5.8 | Python: 2.6.4 | SQLAlchemy: 0.5.8]
The class I'm going to map:
class Student(object):
def __init__(self, id, name):
self.id = id
self.name = name
def __repr__(self):
return str(self)
def __str__(self):
return "%s %s" %(self.id, self.name)
Background:
Now, I've got a function that reads in the necessary information from a text database into these objects. The function more or less works and I can easily access the information from the objects.
Before the SQLAlchemy code runs, the function will read in the necessary info and store it into the Class. There is a dictionary called students
which stores this as such:
students = {}
students[id] = Student(<all the info from the various "reader" functions>)
Afterwards, there is an "allocation" algorithm that will allocate projects to student. It does that well enough. The allocated_project
remains as None
if a student is unsuccessful in getting a project.
SQLAlchemy bit:
So after all this happens, I'd like to map my object to a database table.
from sqlalchemy import *
from sqlalchemy.orm import *
engine = create_engine('sqlite:///:memory:', echo=False)
metadata = MetaData()
students_table = Table('studs', metadata,
Column('id', Integer, primary_key=True),
Column('name', String)
)
metadata.create_all(engine)
mapper(Student, students_table)
Now after that, I was curious to see if I could print out all the students from my students dictionary.
for student in students.itervalues():
print student
What do I get but an error. This error only takes place if try to print as I am, after calling the mapper
:
Traceback (most recent call last):
File "~/FYP_Tests/FYP_Tests.py", line 140, in <module>
print student
File "~/FYP_Tests/Parties.py", line 30, in __str__
return "%s %s" %(self.id, self.name)
File "/opt/local/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/site-packages/SQLAlchemy-0.5.8-py2.6.egg/sqlalchemy/orm/attributes.py", line 158, in __get__
return self.impl.get(instance_state(instance), instance_dict(instance))
AttributeError: 'NoneType' object has no attribute 'get'
I'm at a loss as to how to resolve this issue, if it is an issue. If more information is required, please ask and I will provide it.
Questions:
mapper
change anything about the original Class/dictionary? get
works with dictionaries?Upvotes: 6
Views: 9593
Reputation: 33250
You are creating Student
instances before mapping class which modifies class to SQLAlchemy needs. So your instance is not properly initialized. Just put the lines creating Student
instances after calling mapper(Student, students_table)
and everything will work as expected.
Upvotes: 3
Reputation: 43527
It looks like you might have a name shadowing conflict where Column('id'...)
hides Student.id. Changing Student.__init__.id
to Student._init__.sid
would be a quick test to confirm or refute this conjecture.
There is mention of this connection in the third code block of the SQLAlchemy tutorial on mappings.
For example, replacing your first code snippet with this fragement:
class Student(object):
def __init__(self, name, id):
self.sid = id
self.name = name
# and so on
Obviously other references to Student.id
would have to change as well.
Upvotes: 1