в Django я по прежнему новичок, но что-то стараюсь понять и запомнить.
стояла задача расширить профиль пользователя дополнительными полями, статей на эту тему пресс и малелькая тележка, но не получалось, то у кого-то на сайте парсер html сильно злой и код надо было переписывать, у кого-то были ошибки в примерах и т.п.
но как-то оно получилось, попробую собрать все мысли в кучу в эту статью.
Многие знают о django-registration и вот от автора этого замечательного приложения существует django-profiles котором я и воспользовался.
устанавливаем django-profiles
в models.py создадим модель профиля, которая наследуется от штатной User и добавим в ней нужное нам поле
...
...
class UserProfile(models.Model):
# поле для связки со встроенной моделью пользователя Django
user = models.ForeignKey(User, unique=True)
# наше новое поле
about = models.TextField(blank=True)
Далее в settings.py надо указать кто будет новым AUTH_PROFILE_MODULE
где list это ваше приложение в котором расположена модель расширяющая пользователя
в принципе на этом можно закончить, ибо обращаться теперь можно к
только нужно обратить внимание что надо пользоваться не context а RequestContext
и указать это в
TEMPLATE_CONTEXT_PROCESSORS файла settings.py
...
'django.contrib.auth.context_processors.auth',
...
)
но мы идём дальше
Теперь нам надо подключить django-profiles для просмотра\редактирования профиля
в файле urls.py
подключаем
(r'^profiles/', include('profiles.urls')),
...
в settings.py также подключим приложение
...
'profiles',
)
теперь создадим таблицы в базе
приложение profiles использует вот такие шаблоны
profiles/edit_profile.html
profiles/profile_detail.html
profiles/profile_list.html
по названию понятно что к чему
для начала отредактируем edit_profile.html
сохраняем, теперь можно обратиться к /profiles/edit/ то должно открыться форма редактирования профиля.
бывают ситуации, что в профиле есть какие-то поля, что запрещено редактировать пользователю, реализуется это довольно просто
создаём класс формы, наследуемой от общей формы, в котором перечисляем, то что нам исключить от вывода пользователю
forms.py
from django.forms import ModelForm
from PROJ.apps.APP.models import UserProfile
.........
class ProfileForm(forms.ModelForm):
class Meta:
model = UserProfile
exclude = ('user','last_name',)
from PROJ.apps.APP.models import UserProfile
проект и приложение где расположена расширенная модель
теперь в urls.py надо указать, что страницу редактирования профиля надо открывать с нужной нам формой
........
('^profiles/edit', 'profiles.views.edit_profile', {'form_class': ProfileForm,}),
(r'^profiles/', include('profiles.urls')),
.......
Должно получиться примерно так.. проверяем на странице редактирования профиля (/profiles/edit/).
Теперь сделаем страницу отображения профиля profile/profile_detail.html
вывести можно что угодно из профиля вот так
где address2 это дополнительное поле
список пользователей с профилями можно вывести вот так
profiles/profile_list.html
{% block content %}
<h1>Список пользователей</h1>
<br/><br/>
{% for p in object_list %}
<a href="{% url profiles_profile_detail p.user %}">{{ p.user }}</a>
{% endfor %}
{% endblock %}
Теперь задача такая, сейчас профиль и пользователь живут почти своей жизнью, при регистрации пользователя профиль сам не создаётся это мы сейчас и решим сигналами.
в models.py добавим
from bucket.signals import create_profile
# When model instance is saved, trigger creation of corresponding profile
signals.post_save.connect(create_profile, sender=User)
создадим файл, если он не создан signals.py:
"""When user is created also create a matching profile."""
from PROJ.apps.APP.models import UserProfile
if created:
UserProfile(user = instance).save()
# Do additional stuff here if needed, e.g.
# create other required related records
вот и всё, при регистрации нового пользователя автоматически будет создаваться к нему профиль, если у вас уже сейчас много пользователей, то создать для каждого профиль можно вот так
from django.contrib.auth.models import User
from bucket.models import Profile
users = User.objects.all()
for u in users:
try:
p = u.get_profile()
except p.DoesNotExist:
Profile(user = u).save()
ещё коснусь вопроса редактирования своего email в профиль, пока ещё не совсем разобрался с этим.
пока есть только пример, делается это анналогично через forms.py
def __init__(self, *args, **kwargs):
super(ProfileForm, self).__init__(*args, **kwargs)
try:
self.fields['email'].initial = self.instance.user.email
# self.fields['first_name'].initial = self.instance.user.first_name
# self.fields['last_name'].initial = self.instance.user.last_name
except User.DoesNotExist:
pass
email = forms.EmailField(label="Primary email",help_text='')
class Meta:
model = Profile
exclude = ('user',)
def save(self, *args, **kwargs):
"""
Update the primary email address on the related User object as well.
"""
u = self.instance.user
u.email = self.cleaned_data['email']
u.save()
profile = super(ProfileForm, self).save(*args,**kwargs)
return profile
надеюсь вернусь к этому вопросу


