views:

189

answers:

2

I want to set the BooleanField inuse to True when I save the ModelForm (I'm using a form outside of the admin area) and I'm unsure how to do it.

Models:

class Location(models.Model):
    place = models.CharField(max_length=100)
    inuse = models.BooleanField()

class Booking(models.Model):
    name = models.CharField(max_length=100, verbose_name="Your name*:")
    place = models.ManyToManyField(Location, blank=True, null=True)

Forms:

class BookingForm(ModelForm):

    class Meta:
        model = Booking

        def save(self, commit=True):
            booking = super(BookingForm, self).save(commit=False)
            if commit:
                booking.save()
                self.save_m2m()
                for location in booking.place.all():
                    location.inuse = True
                    print location #nothing prints
                    location.save()

View:

def booking(request):
    form = BookingForm()
    if request.method == 'POST':
        form = BookingForm(request.POST)
        if form.is_valid():
            form.save()
        else:
            form = form

        return render_to_response('bookingform.html', {
                'form': form,
            })

Updated to latest (see Manoj Govindan's answer). It is still not updating inuse to True on submit / save.

+2  A: 
class BookingForm(ModelForm):

    class Meta:
        model = Booking

    def save(self, commit=True):
        booking = super(BookingForm, self).save(commit=False)
        booking.inuse = True
        if commit:
            booking.save()
Daniel Roseman
@Daniel: shouldn't it be `Location.inuse`? According to the OP `Booking` is a _form_.
Manoj Govindan
Looking promising but gives me...TypeError at /super(type, obj): obj must be an instance or subtype of type
Rob B
@Rob B: try replacing `booking = super(Booking, self).save(commit=False)` with `booking = super(BookingForm, self).save(commit=False)`
Manoj Govindan
@Manoj Govindan that solved my error message but looking in admin the Location value hasn't updated to true when I submit the form.
Rob B
@Rob B: is the underlying model of the form `Booking` or `Location`? Daniel's answer presumes that it is `Booking`; but I do not see such a model in your question.
Manoj Govindan
@everyone! The code is updated to show its current state
Rob B
I presume that `Booking` is a *model*, not a form, especially as it has model fields rather than form fields.
Daniel Roseman
@Daniel Roseman yes Booking is a model - there was a typo in the code above I've corrected. Thanks
Rob B
+2  A: 

Here is my stab at it:

class BookingForm(ModelForm):
    class Meta:
        model = Booking

    def save(self, commit=True):
        booking = super(BookingForm, self).save(commit=False)
        if commit:
            booking.save()  
            self.save_m2m()
            for location in booking.place.all():
                location.inuse = True
                location.save()

Update

Entire code I've used:

# models.py
class Location(models.Model):
    place = models.CharField(max_length=100)
    inuse = models.BooleanField()

class Booking(models.Model):
    name = models.CharField(max_length=100, verbose_name="Your name*:")
    place = models.ManyToManyField(Location, blank=True, null=True)

# forms.py
class BookingForm(ModelForm):
    class Meta:
        model = Booking

    def save(self, commit=True):
        booking = super(BookingForm, self).save(commit=False)
        if commit:
            booking.save()
            self.save_m2m()
            for location in booking.place.all():
                location.inuse = True
                location.save()

In [1]: from test_app.forms import BookingForm
In [2]: from test_app.models import Location

# I had already saved some `Location` instances.

In [3]: data = dict(name = 'MyCity', place = [p.id for p in Location.objects.all()])
In [4]: f = BookingForm(data)
In [5]: f.save()
In [6]: for each in Location.objects.all():
   ...:     print each.place, each.inuse
   ...:      
PlaceA True 
PlaceB True 
PlaceC True
Manoj Govindan
doesn't bring up any errors just doesn't update the location value to True on save
Rob B
I changed the code a bit. Can you try with a latest version?
Manoj Govindan
nope still no luck. Doesn't error but doesn't seem to do anything either
Rob B
Got it working. See above. The trick is to call `self.save_m2m()` explicitly to save the m2m objects.
Manoj Govindan
@Manoj Govindan inuse is not becoming True with the new code
Rob B
Strange. I tested it and it worked for me.
Manoj Govindan
can you paste in the entire model so I can compare? I've tripled checked and its not working
Rob B
@Rob: added entire code as well as shell snippet.
Manoj Govindan
@Manoj Govindan Thanks. Still no luck. Would my view affect anything?
Rob B
@Manoj Govindan updated my code to what I have currently
Rob B