Creating tables with pylons and SQLAlchemy - python

I'm using SQLAlchemy and I can create tables that I have defined in /model/__init__.py but I have defined my classes, tables and their mappings in other files found in the /model directory.
For example I have a profile class and a profile table which are defined and mapped in /model/profile.py
To create the tables I run:
paster setup-app development.ini
But my problem is that the tables that I have defined in /model/__init__.py are created properly but the table definitions found in /model/profile.py are not created. How can I execute the table definitions found in the /model/profile.py so that all my tables can be created?
Thanks for the help!

I ran into the same problem with my first real Pylons project. The solution that worked for me was this:
Define tables and classes in your profile.py file
In your __init__.py add from profile import * after your def init_model
I then added all of my mapper definitions afterwards. Keeping them all in the init file solved some problems I was having relating between tables defined in different files.
Also, I've since created projects using the declarative method and didn't need to define the mapping in the init file.

Just import your other table's modules in your init.py, and use metadata object from models.meta in other files. Pylons default setup_app function creates all tables found in metadata object from model.meta after importing it.

If you are using declarative style, be sure to use Base.meta for tables generation.

Related

Create various tables from some Model with Flask-Sqlalchemy

From the docs, I can see how to create the Models necessary to later create the Tables.
What I want is to create various tables, each with different __tablename__ att., but all of them with the same properties, thus the need for just one Model class which will serve as a model for all the tables.
I looked into the db.metadata option, but the docs state that it is designed for read-only purpose.
EDIT1:
To create a table from a model, I create
class Sample(db.Model):
//code here
then to create the table from the model, a script is run which executes
manage.py migrate
manage.py update
What would be the correct way to create the mentioned tables on runtime?
EDIT2:
Having found a question on SO similar to mine, I tried the accepted answer, which proposes the use of type to create the tables, but that doesn't seem to work as expected.
In my app/my_model.py file I have the model which at first inherited from db.Model, but later removed that following the example in the mentioned question. In my app/routes.py, when I run type(name.title(), (MyModel, db.Model), { '__tablename__' : name }) and print the given object, I get <class 'app.routes.name'>, as opposed to the expected <class 'flask_sqlalchemy.Name'>.
I posted a separate question because the doubt is broader than what the existing question covers, I think.
Thanks in advance!
I think I managed to make it work (a test which creates the table and then checks if the table exists in the db passes! Although the print statement still prints the unexpected message).
I had to
inherit from db.Model when defining MyModel in app/my_model.py.
set __abstract__ = True.
The type command is now: type(name.title(), (MyModel, db.Model), { '__tablename__' : name }).
Now I am dealing with data insertion, since I have to find a way to specify to which table it should go. Class xxx is not mapped error... But that's another problem! (For which if anyone has any comments, will be more than thankful!).
Thanks to everyone who helped!

How to add new tables to flask-sqlalchemy database after database init?

I have launched this project and it uses Flask-SQLAlchemy and already has some classes (tables). Now I added few more tables - classes that inherit db.Model. And when I run application, I get this error:
sqlalchemy.exc.InvalidRequestError: Table 'table_name' is already defined for this MetaData instance. Specify 'extend_existing=True' to redefine options and columns on an existing Table object.`
I also opened and inspected the database file, but there is no such table created, so error seams a bit misleading.
How to achieve that newly defined classes be created as tables in database?
The problem was in Python cache files. I deleted all __pycache__ folders that I found in my project directory and it helped.

Django: If I added new tables to database, how can I query them?

Django: If I added new tables to database, how can I query them?
Do I need to create the relevant models first? Or django creates it by itself?
More specifically, I installed another django app, it created several database tables in database, and now I want to get some specific data from them? What are the correct approaches? Thank you very much!
I suppose another django app has all model files needed to access those tables, you should just try importing those packages and use this app's models.
Django doen't follow convention over configuration philosophy. you have to explicitly create the backing model for the table and in the meta tell it about the table name...

In Django, how to create tables from an SQL file when syncdb is run

How do I make syncdb execute SQL queries (for table creation) defined by me, rather then generating tables automatically.
I'm looking for this solution as some particular models in my app represent SQL-table-views for a legacy-database table.
So, I've created their SQL-views in my django-DB like this:
CREATE VIEW legacy_series AS SELECT * FROM legacy.series;
I have a reverse engineered model that represents the above view/legacytable. But whenever I run syncdb, I have to create all the views first by running sql scripts, otherwise syncdb simply creates tables for them (if a view is not found).
How do I make syncdb run the above mentioned SQL?
There are 2 possible approaches I know of to adapt your models to a legacy database table (without using views that is):
1) Run python manage.py inspectdb within your project. This will generate models for existing database tables, you can then continue to work with those.
2) Modify your tables with some specific settings. First of all you define the table name in your model by setting the db_table option in your meta options. Secondly you define for each field the column name to match your legacy database by setting the db_column option. Note there are other db_ options listed you possibly could use to match your legacy database.
If you really want the views approach an (ugly) workaround is possible, you can define custom sql commands per application model. This file is found in "application"/sql/"model".sql . Django will call this sql's after it created all tables. You can try to specify DROP statements for the generated tables followed by your view create statement in this file. Note that this will be a bit tricky for the tables with foreign keys as django guarantees no order of execution of these files (so stuffing all statements in one .sql will be the easiest way I think, I've never tried this before).
You could use unmanaged models for your reverse-engineered models, and initial SQL scripts for creating your views.
EDIT:
A bit more detailed answer. When you use unmanaged models, syncdb will not create your database tables for you, so you have to take care of it yourself. An important point is the table name, and how django maps Model classes to table names, I suggest you read the doc on that point.
Basically, your Series model will look like that :
class Series(models.Model):
# model fields...
...
class Meta:
managed = False
db_table = "legacy_series"
Then, you can put your SQL commands, in the yourapp/sql/series.sql file :
### yourapp/sql/series.sql
CREATE VIEW legacy_series AS SELECT * FROM legacy.series;
You can then syncdb as usual, and start using your legacy models.

Sqlalchemy file organization

Does anyone has any insight on organizing sqlalchemy based projects? I have many tables and classes with foreign keys, and relations. What is everyone doing in terms of separating classes, tables, and mappers ? I am relatively new to the framework, so any help would be appreciated.
Example:
classA.py # table definition and class A definition
classB.py # table definition and class B definition
### model.py
import classA,classB
map(classA.classA,clasSA.table)
map(classB.classB,clasSB.table)
Including mappers inside classA, and classB works, but poses cross import issues when building relations.. Maybe I am missing something :)
Take a look at Pylons project including SA setup.
meta.py includes engine and metadata objects
models package includes declerative classes (no mapper needed). Inside that package, structure your classes by relavance into modules.
Maybe a good example would be reddit source code:)
There are two features in SQLAlchemy design to avoid cross imports when defining relations:
backref argument of relation() allows you to define backward relation.
Using strings (model class and their fields names). Unfortunately this works for declarative only, which is not your case.
See this chapter in tutorial for more information.

Categories