Django map dynamically generated tables by another application

0

I will develop an application with Django where you will need to query data in a database that is powered by an ERP (desktop).

This ERP generates some movement tables by adding at the end of the table name the month and the year, as a kind of partitioning, eg financeiro0718 , financeiro0818 , financeiro0918 , etc.

These tables have the same column structure and data type, the difference is just the name. My intention is to have only one model mapping these tables so I do not get a huge amount of classes with repeated code in my project.

How can I map these tables in Django in a way that I can have a Financeiro and ORM can query the data in the corresponding tables?

    
asked by anonymous 02.10.2018 / 03:05

1 answer

2

You can explicitly name the table in the SQL database by filling in the db_table field in the metadata of a model. In a conventional declaration, the metadata stays within the nested class named "Meta" -

So one way to dynamically create multiple models, each pointing to a table, is to dynamically create those models with type calls, changing the required data - you can store those models in a dictionary, so you can access same at runtime.

If this is done in code top level - that is, executed when the models.py file is loaded, it will almost certainly work. It may work lazy, with models being created dynamically as they are needed too - but it might not, if Django does some ORM action at the time it loads the tables.

from django.db import model

class BaseFinanceiro(models.Model):
     # declare os campos normalmente
     class Meta:
          abstract = True

tabelas_extras = "financeiro0718 financeiro0818 financeiro0918 ...".split()
# acima, é só uma forma com menos digitação de criar uma lista

modelos = {}
for nome in tabelas_extras:
     meta = type('Meta', (), {'db_table': nome})
     modelos[nome] = type(nome, (BaseFinanceiro,), {'Meta': meta})

Of course I only used the "name" as a string because it was the example you gave - access can be even more straightforward if you use as a pair of "month, year" is a tuple in Python: models [9, 18] - or even a datetime.date object) - but then, of course, it depends on how you will access those templates in the rest of the code.     

02.10.2018 / 15:19