Login

multiple model form with image

Author:
lawgon
Posted:
November 14, 2007
Language:
Python
Version:
.96
Score:
0 (after 2 ratings)

You have two models, one of which also has an image field. You want to get the data into a form and edit it. This also requires showing the url of the image, if there is one, on the form. This is a complete working example. No big deal, but for newbies, a complete working example could be valuable.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
Models:

class Delegate(models.Model):
    username = models.ForeignKey(User,
                                                        verbose_name=_("User Name"),unique=True)
    resume = models.TextField(_("Resume"),blank=True,null=True)
    location = models.TextField(_("City/Organisation"),blank=True,null=True)
    occupation = models.ForeignKey(Occupation,blank=True,null=True,
                                                                verbose_name = _("Occupation"))
    photo = ImageField(_("Photo"),upload_to="delphotos/",
                                                                    blank=True,null=True)
    class Admin:
        pass
    def __unicode__(self):
            return _(u"Username: %s") %(self.username)

View:

class Edituserform(forms.Form):
    def __init__(self, *args, **kwargs):
            super(Edituserform, self).__init__(*args, **kwargs)
            # Generate choices
            self.fields['occupation'].choices = [(chld.id, 
            chld.name) for chld in Occupation.objects.all()]
 
    first_name = forms.CharField(max_length=30,
                                            label=_("First Name or Initials"),
                                            required=False)
    last_name = forms.CharField(max_length=30,
                                            label=_("Last Name"),
                                            required=False)
    occupation = forms.ChoiceField(label=_("Occupation"),
                                            choices=(),
                                            required=False)
    photo = forms.ImageField(label=_("Photo"),
                                            required=False)
    resume = forms.CharField(max_length=1000,
                                            label=_("Resume"),
                                            widget=forms.Textarea,
                                            required=False)
    location = forms.CharField(max_length=1000,
                                            label=_("City/Organisation"),
                                            widget=forms.Textarea,
                                            required=False)
    pass1 = forms.CharField(max_length=50,widget=forms.PasswordInput,
                                            label=_("Enter New Password"),
                                            required=False)
    pass2 = forms.CharField(max_length=50,widget=forms.PasswordInput,
                                            label=_("Enter New Password Again"),
                                            required=False)
    # Hidden fields to store the url of photo for display
    flname = forms.CharField(max_length=250,widget=forms.HiddenInput,
                                            label='',
                                            required=False)
    flurl = forms.CharField(max_length=250,widget=forms.HiddenInput,
                                            label='',
                                            required=False)
    def clean_pass2(self):
        if self.cleaned_data['pass1'] != self.cleaned_data['pass2']:
                raise forms.ValidationError('Passwords do not match')
        else:
            if len(self.cleaned_data['pass1']) < 6 and len(self.cleaned_data['pass1']) >0:
                raise forms.ValidationError('Password must be at\
            least 6 letters long')
            
            
@user_passes_test(lambda u: u.is_anonymous()==False ,login_url="/web/login/")    
def edituser(request):
    """view to edit a user's profile - this is saved in User and Delegate
        """
    if request.POST:
        form = Edituserform(request.POST,request.FILES)
        if form.is_valid():
                fm = form.cleaned_data
                newuser = User.objects.get(pk=request.user.id)
                newuser.first_name = fm['first_name']
                newuser.last_name = fm['last_name']
                if fm.get('pass1') and fm.get('pass2'):
                    newuser.set_password(fm['pass1'])
                newuser.save()
                changed = False
                newdel,created = Delegate.objects.get_or_create(username=request.user)
                newdel.resume = fm['resume']
                changed = True
                newdel.occupation_id= int(fm['occupation'])
                changed = True
                newdel.location = fm['location']
                changed = True
                newdel.save()
                if request.FILES:
                    # Delete the old photo
                    pat = settings.MEDIA_ROOT+request.POST['flname']
                    try:
                        os.unlink(pat)
                    except:
                        pass
                    newdel.save_photo_file(request.FILES['photo']['filename'],
                                                                request.FILES['photo']['content'])
                return HttpResponseRedirect("/web/" )
    else:
        try:
            id = request.user.id
            usr = User.objects.get(pk=id)
            data = {
                            'username': usr.username,
                            'first_name':usr.first_name,
                            'last_name': usr.last_name
                            }
            a = Delegate.objects.get(username=request.user)
            data['resume'] = a.resume
            data['occupation'] = a.occupation.id
            data['location'] = a.location
            pat = settings.MEDIA_ROOT+a.photo
            filedt = open(pat,'r')
            filedata = {
                                'photo':  {'filename': a.get_photo_url(),'content': filedt.read()}
                                    }
            try:
                data['flname'] = a.photo
                data['flurl'] = a.get_photo_url()
            except:
                pass
            form = Edituserform(data,filedata)
        except:
            form = Edituserform(data)
    return render_to_response("web/edituser.html",
                              {'form':form,
                               'request':request,
                               })

Template:

{% extends "base.html" %}
{% load i18n %}
{% block centercontent %}
<h2>{% trans "Edit  profile for user:" %} {{ form.data.username }}</h2>
<p>{% trans "Edit your profile here. You can also change your password if you want" %}</p>
<p>{% if form.errors %} Please correct the errors below {% endif %}</p>
<form enctype="multipart/form-data" method="POST" action=".">
<dl>
{% for field in form %}

    <dt>{{ field.label_tag }}</dt>

{% ifequal field.name 'photo' %}
    <a href="{{ form.data.flurl }}">{{ form.data.flname }}</a></dd>
{% endifequal %}
    <dd>{{ field }}</dd>
    {% if field.help_text %}<dd>{{ field.help_text }}</dd>{% endif %}
    {% if field.errors %}<dd>{{ field.errors }}</dd>{% endif %}
{% endfor %}
</dl>
<input type="submit" name="Register" value="{% trans "Submit" %}"></p>
</form>
{% endblock %}

More like this

  1. Template tag - list punctuation for a list of items by shapiromatron 3 months, 1 week ago
  2. JSONRequestMiddleware adds a .json() method to your HttpRequests by cdcarter 3 months, 2 weeks ago
  3. Serializer factory with Django Rest Framework by julio 10 months, 1 week ago
  4. Image compression before saving the new model / work with JPG, PNG by Schleidens 11 months ago
  5. Help text hyperlinks by sa2812 11 months, 3 weeks ago

Comments

Please login first before commenting.