Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django user HiddenInput vs. saving directly in views with Class Based Views

Please this as a consideration question. Maybe somebody will use one of the solutions below.

I have a couple of models which contain a ForeignKey(User) field. My class-based create views are derived from the generic CreateView.

There are two options to save the associated user when adding a new object:

  1. Saving the form in the views by overriding the form_valid method; this doesn't expose user_id (and other not mentioned here data that should not be exposed)

    class CreateOfferView(CreateView):
    
        model = Offer
        form_class = SomeModelFormWithUserFieldExcluded
    
        def form_valid(self, form):
            instance = form.save(commit=False)
            instance.user = self.request.user
            instance.save()
    
  2. Saving the form with user id stored (and exposed) in a hidden field. Here's the tricky part. There are more models with user field... so when creating a form I need to fill the user field with initial (currently logged in) user and also I need to make that field hidden. For this purpose I've used my OwnFormMixin

    class OwnFormMixin(object):
    
        def get_form(self, form_class):
            form = super(OwnFormMixin, self).get_form(form_class)
            form.fields['user'].widget = forms.HiddenInput()
    
        def get_initial(self):
            initial = super(OwnFormMixin, self).get_initial()
            initial['user'] = self.request.user.pk
            #I could also do this in get_form() with form.fields['user'].initial
    
    class CreateOfferView(OwnFormMixin, CreateView):
        model = Offer
        form_class = SomeModelFormWithAllFields
    

There are more CreateXXXView using the OwnFormMixin..

How do you save your user data in the forms?

Hidden vs. saving directly in your views? What are pros/cons?

like image 305
Robert Avatar asked Nov 03 '22 23:11

Robert


1 Answers

Unless you're allowing users to modify that ForeignKeyField, there's no reason to include it in a form — I'd go with your first solution of using exclude to keep the user field out of your ModelForm, and setting the user from request.user. In fact, the Django documentation now has an example along these exact lines.

You have the advantage of not having to secure against manipulation of the user_id parameter, not exposing your internal user IDs and not having to worry about the different Create vs. Update cases. A slight disadvantage is that if you ever need the ability to change an object's associated User you'll need to start again.

like image 68
supervacuo Avatar answered Nov 08 '22 10:11

supervacuo