ultrajohn
ultrajohn

Reputation: 2597

Get all related objects of an object in Django?

Let us say I have a model which contains related (foreign key) fields. Likewise, those Foreign Key fields may refer to models which may or may not contain related fields. Note that relational fields in Django may be one-to-one, many-to-one, or many-to-many.

Now, given an instance of a model, I want to recursively and dynamically get all instances of the models related to it, either directly or indirectly down the line. Conceptually, i want to perform a traversal of the related objects and return them.

Example:

class Model1{
   rfield1 = models.ForeignKey("Model2")
   rfield2 = models.ManyToManyField("Model3")
   normalfield1 = models.Charfield(max_length=50)
}
class Model2{
   sfield = models.ForeignKey("Model3")
   normalfield = models.CharField(max_length=50)
}
class Model3{
   normalfield = models.CharField(max_length=50)
}

Let's say, I have an instance of model Model1 model1, and I want to get objects directly related to it i.e. all Model2 and Model3 objects, and also those which are indirectly related i.e. all Model3 objects related to the Model2 objects retrieved previously. I also want to consider the case of a One-to-One field where the related field is defined on the OTHER MODEL.

Also, note that it might not be the case that I know the model of an instance I'm currently working on. Let's say in the previous example, I may not now that model1 is an instance of Model1 model. So I want to perform all these dynamically.

In order to this, I think I need a way to get all related fields of an object.

  1. How to get all the related fields of an object?
  2. And how should I use them to get the actual related objects?

Or is there a way to better to do this? Thank you very much!

UPDATE:

I already know how to perform 1, and 2 basically follows directly from 1. :) Update later.

Upvotes: 1

Views: 3858

Answers (1)

cchristelis
cchristelis

Reputation: 2015

If you have model1 getting all it's many to many field names (etc) is easy since this is well know and these are all stored in the meta's 'local_many_to_many' list:

[field.name for field in model1._meta.local_many_to_many]

The foreign keys are a bit more tricky since they are stored with all other fields in the meta's 'local_fields' list. Hence we need to make sure that it has a relation of sorts. This can be done as follows:

[field.name for field in model1._meta.local_fields if field.rel]

This method has requires no knowledge of your models. Also further interrogation can be done on the field object if the name is not enough.

Upvotes: 1

Related Questions