2015-04-19 2 views
-1

С помощью следующего кода я могу получить Dict полей в списке:Как получить поля модели и их отношения в django?

from django.db import connection 

table_info = [] 
tables = connection.introspection.table_names() 
seen_models = connection.introspection.installed_models(tables) 
for model in seen_models: 
    table = model._meta.db_table 
    columns = [field.column for field in model._meta.fields] 
    table_info.append((table, columns)) 

Из выше я могу получить JSON закодированный файл, как:

["account_profile",["id","avatar","owner_id","forums","forum_threads","lct_discussion","organization_id","created_at","updated_at"]] 

Примечание owner_id является соответствующий элемент, я хотел бы вытащить все связанные элементы и создать вложенные массивы в результате. Я не уверен, как я могу изменить приведенный выше код, чтобы достичь этого. Любая рекомендация?

+0

Вы проверили [django-report-builder] (https://github.com/burke-software/django-report-builder)? Я не знаю, подходит ли оно вашим потребностям, но это полезный инструмент. – aumo

+0

Проверено, но мне не нравится пользовательский интерфейс. Я хотел бы что-то, что хорошо сочетается с моим дизайном интерфейса администратора и не выглядит совершенно другим. Я чувствую, что это не так просто. –

ответ

0

Я решил так:

table_info = [] 
    tables = connection.introspection.table_names() 
    seen_models = connection.introspection.installed_models(tables) 
    for model in seen_models: 
     table = model._meta.db_table 
     columns = [field.column for field in model._meta.fields] 

     # Identify a related field item: 
     # Use this to get the related table details 
     # Loop the table details and append the columns to the main table columns 
     # Results to a nested list with depth of 1 
     for field in model._meta.fields: 
      if field.get_internal_type() == "ForeignKey": 
       related_obj = field.rel.to 
       related_table = related_obj._meta.db_table 
       columns.append((related_table, [x.column for x in related_obj._meta.fields])) 

     table_info.append((table, columns)) 

Примечание: Я не хочу, чтобы сделать это рекурсивно, чтобы избежать круговую связь, как упомянуто @ahumeau. Это хорошо работает для моих нужд. Это дает мне глубину 1, то есть не смотрит дальше первого элемента.

0

Вы можете использовать Field.is_relation, чтобы проверить, является ли поле отношением к другой модели, и проверьте поля Field.related_model так же, как вы здесь.

Я думаю, что лучшим решением было бы написать рекурсивную функцию, но остерегайтесь круговых отношений между моделями.