Take the 2-minute tour ×

I'm building an app that puts together the hardware of a computer. This is my first time working with django. Say I have the following models:

class Memory(models.Model):
    partNum = models.CharField()
    capacity = models.CharField()

class Computer(models.Model):
    name = models.CharField()
    memory = models.ManyToManyField(Memory)
    # also has cpus, hard drives, and motherboard, but focus on memory for now

One memory object can belong to many computer objects, and one computer object can have many memory objects - hense Many-To-Many. However, computers require the same exact memory sticks installed if using more than one.

Yet django's manytomany field (by default?) only allows one instance of a memory-computer relationship, it must me unique. Any way around this?

If I try, in the admin page, to add many of the same memory objects to a computer, it says "Computer-memory relationship with this Computer and Memory already exists". If I try adding more than once the same memory object to a server object in the manage.py shell, it appears that only one memory object was added. If I try to manually edit the database to have a duplicate entry, I get an error saying that the entry already exists. I see that in the database structure, some sorta "unique together" index thingy is enforcing is enforcing this. If I altered the table to remove that clause, would that solve my problem? Probably not unless the django manager is more stupid than expected.

What are my options? Write my own intermediary models and use the through construct? But then I won't get to use the cool filter_horizontal widget! Rewrite my Computer model to have a Foreign Key field plus a field for the number of memory object? But then I won't get the ManyToMany API facilities. Help!

share|improve this question

2 Answers 2

up vote 3 down vote accepted

Edit: sorry, I did not read your post well enough, about not wanting to use 'through'.

One way to circumvent the problem, would be to use the "through" parameter, in which you can manually specify an intermediate model to use for the many-to-many relationship. In this way, you should still have (most of) the many-to-many facilities that Django provides.

The intermediate model could then have count (which I would find easier to manage than having multiple relations):

class Memory(models.Model):
    partNum = models.CharField()
    capacity = models.CharField()

class Computer(models.Model):
    name = models.CharField()
    memory = models.ManyToManyField(Memory, through='ComputerMemory')

class ComputerMemory(models.Model):
    memory = models.ForeignKey(Memory)
    computer = models.ForeignKey(Computer)
    count = models.IntegerField()

For further information, take a look in the Django documentation: https://docs.djangoproject.com/en/dev/topics/db/models/#intermediary-manytomany

share|improve this answer
Thank you. This is the best compromise I guess. –  Dan Mantyla Dec 14 '12 at 22:17

No this is not a compromise, Even if you dont create another table for the through thing, than also django will create it to remember exactly which memory is associated with each computer, so better is that you do it yourself...and this also allows you to get other fields in there that are required for a specific computer with a specific memory

share|improve this answer
I disagree. Why can't django just allow non-unique m2m relationships? –  Dan Mantyla Dec 17 '12 at 17:34
Ok...If you ask for that...just tell me...how will it it than keep track that which is related to what?? It has to store that information somewhere na....So it uses this technique –  Saransh Mohapatra Dec 19 '12 at 4:42
And if your not comfortable with this method....you could very well use your custom SQL –  Saransh Mohapatra Dec 19 '12 at 4:42
There would just be duplicate rows in the intermediate table, just like how I'm doing it now by specifying my own table with the through property (which I'm paying for now because I have to use Inlines instead of regular admin models, which has much more functionality). And, no, I don't think custom SQL could be used because, when the table is created, some sorta UNIQUE property is specified which doesn't allow for multiple rows. –  Dan Mantyla Dec 20 '12 at 18:06

Your Answer


