#24317: Deprecate field.rel, replace it with real field instances
-------------------------------------+-------------------------------------
Reporter: Anssi Kääriäinen | Owner: nobody
Type: | Status: new
Cleanup/optimization |
Component: Database layer | Version: master
(models, ORM) |
Severity: Normal | Resolution:
Keywords: | Triage Stage: Accepted
Has patch: 0 | Needs documentation: 0
Needs tests: 0 | Patch needs improvement: 0
Easy pickings: 0 | UI/UX: 0
-------------------------------------+-------------------------------------
Comment (by Asif Saifuddin Auvi):
Replying to [comment:17 Gabriel Canto de Souza]:
> I also had a huge difficulty sorting out the fields of
._meta.get_fields() , what I was trying to achieve was get ONLY the
reverse fields (because in our context every relationship is
bidirectional, and everything is generic/auto generated)
>
> This gets really complicated with m2m that contain through tables,
because not only you get the reverse m2m remote_field, but also the m2o
relationship with the through table, so no only you have to figure out
these are reverse, but group both the m2m and m2o that revert to the same
relationship.
>
> This is the code I managed to come up with to get only the reverse rels:
>
>
> {{{#!python
>
> #I'm sure there's a better way of doing this
> #This is the documented way of getting reverse fields, but it also gets
ManyToOne rel with the through table of forward m2m rels, so we have to
filter them
> reverse_fields = [f for f in opts.get_fields() if f.auto_created and
not f.concrete]
> reverse_m2m = [f for f in reverse_fields if f.__class__.__name__ ==
'ManyToManyRel' and f.on_delete == None and not
getattr(model,f.field.name,False)]
> #Also filtering the ManyToOne rel with the through table of the reverse
m2m rels, because we need to differentiate them from reverse ManyToOne
with other models(not through)
> reverse_m2m_through = [f for f in reverse_fields if
f.__class__.__name__ == 'ManyToOneRel' and f.related_model in [f.through
for f in reverse_m2m if getattr(f,'through',False)]]
> forward_m2m = [f.remote_field for f in opts.get_fields() if not
f.auto_created and f.many_to_many]
> #Filtering the ManyToOne rels with the through table of forwards m2m
rels, same logic as above
> forward_m2m_through = [f for f in reverse_fields if
f.__class__.__name__ == 'ManyToOneRel' and f.related_model in [f.through
for f in forward_m2m if getattr(f,'through',False)]]
> reverse_fields_final = itertools.chain(reverse_m2m, [f for f in
reverse_fields if f not in itertools.chain(reverse_m2m,
reverse_m2m_through, forward_m2m, forward_m2m_through)])
> }}}
>
> I propose to add a new attribute ''is_reverse = True/False'' to
facilitate this, of course this solution works in my context point of
view, there might be a better approach to this
>
I am preparing a Draft DEP for addressing ORM relations API related issues
here https://github.com/django/deps/pull/39
It's still work in progress but you certainly add your thoughts/feedbacks.
--
Ticket URL: <https://code.djangoproject.com/ticket/24317#comment:18>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
--
You received this message because you are subscribed to the Google Groups
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/django-updates/066.937d03212669ef5a5d01a60ec7cac286%40djangoproject.com.
For more options, visit https://groups.google.com/d/optout.