Code Monkey home page Code Monkey logo

Comments (10)

gasman avatar gasman commented on July 1, 2024 2

Finally completed in #62!

from django-modelcluster.

alexgleason avatar alexgleason commented on July 1, 2024 1

I wrote a quick guide and explanation on how to implement M2M's using what's currently available. https://gist.github.com/alexgleason/09b1802b004babd74e96

from django-modelcluster.

dgaus avatar dgaus commented on July 1, 2024

This is affecting us us well, does anyone have any ideas on how to properly implement support for m2m relations?

from django-modelcluster.

jsma avatar jsma commented on July 1, 2024

@gasman Can you comment on this? Is the crux of the issue that modelcluster just wasn't designed to work with M2M's? Or is modelcluster accidentally overstepping its bounds when a Page has an M2M with a non-modelcluster model? If the latter, can you point the community in the right direction so we can help resolve this?

from django-modelcluster.

gasman avatar gasman commented on July 1, 2024

@jsma It's the first one I'm afraid - modelcluster isn't (currently) designed to work with M2M relations. I'm sure M2M support could be implemented, but it hasn't been a high priority up to now, because it's generally possible to work around it by defining your own 'through' models.

from django-modelcluster.

caioariede avatar caioariede commented on July 1, 2024

Hi guys,

I'm having a hard time trying to understand this line:
https://github.com/torchbox/django-modelcluster/blob/master/modelcluster/forms.py#L265

  • Why the call to save_m2m only happens when commit=False?
  • Why not call save_m2m only when commit=True?

The last one seems to solve the problem with many-to-many relationships, but I'm not aware of the side effects of this change.

from django-modelcluster.

gasman avatar gasman commented on July 1, 2024

@caioariede When commit=True, Django's own save method deals with saving m2m relations, so we don't have to do it in our own code. In fact, save_m2m is not even defined in that situation: https://github.com/django/django/blob/master/django/forms/models.py#L449-L456

from django-modelcluster.

caioariede avatar caioariede commented on July 1, 2024

So what's the purpose of calling it manually? I read the comment but didn't get it.

from django-modelcluster.

gasman avatar gasman commented on July 1, 2024

The overall principle of django-modelcluster is that you can assign relations between objects (e.g. band.members = [john, paul, george, ringo]) and have it store those in memory, so that you can query those relations without them existing in the database. Django on its own does not support this - if you assign a relation like that, it will immediately try to write those objects to the database.

When you call form.save(commit=False), you are telling Django "copy the form data to the model, without saving it to the database". This creates a problem if the form data contains M2M relations, because Django can only represent those relations by saving them to the database. To work around this, Django just copies the plain (non-relation) fields to the model, and generates a save_m2m method that you can call later, when you're ready to write your data back to the database.

With django-modelcluster, we don't need this workaround - we can write the relation data back to the model immediately on form.save(commit=False), because the relations will be stored in memory, not written back to the database. So, in this piece of code, django-modelcluster is effectively saying "Take the actions that Django has postponed to the save_m2m method, and perform them now, because we know that we can safely do them without writing to the database".

from django-modelcluster.

arlyon avatar arlyon commented on July 1, 2024

I'm currently having a similar issue. Adding a manytomany to an existing element in the db works fine, but when trying to create a new one with wagtail Line 230 in forms.py causes an error, for example: "<Team: Red>" needs to have a value for field "team" before this many-to-many relationship can be used.", the many-to-many in question being the "players" field.

I have no idea where "team" comes from, since I haven't defined it in my model anywhere, however if I comment out line 230, create a Team, and then uncomment it, I can edit the page and add players to the team just fine.

Here's some example code.

class Sport(Page):
    description = RichTextField()
    content_panels = Page.content_panels + [
        FieldPanel('description', classname="full"),
    ]

class Team(Page):
    team_game = models.ForeignKey(Sport, related_name='roster_game', on_delete=models.PROTECT) # the sport they play
    players = models.ManyToManyField(User, blank=True) # linked to users, many users on a team
    level = models.TextField() # the skill level of the team

    content_panels = Page.content_panels + [
        FieldPanel('roster_game', classname="full"),
        FieldPanel('players'),
        FieldPanel('level')
    ]

# practice

class Practice(Page):
    practice_team = models.ForeignKey(Team, on_delete=models.PROTECT) # the team that is playing
    times = models.TextField() # practice times
    location = models.TextField() # practice location

    content_panels = Page.content_panels + [
        FieldPanel('practice_team', classname="full"),
        FieldPanel('times'),
        FieldPanel('location')

    ]

from django-modelcluster.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.