Найти - Пользователи
Полная версия: несколько форм Django
Начало » Django » несколько форм Django
1 2
infoforfoi
Вопрос элементарный, но не смог победить.

2 таблицы UserProfile (Пользователь) и Estates (Товар пользователя)
views.py
    estates_obj = Estates.objects.filter(userprofile__user__username__exact=username)[0]
if request.method == 'POST':
form = EstatesForm(data=request.POST, files=request.FILES, instance=estates_obj)
if form.is_valid():
form.save()
return HttpResponseRedirect('')
else:
form = EstatesForm(instance=estates_obj)

Так все работает, если выводить только одну редактируемую форму пользователя.
Как сделать, чтобы выводило все редактируемые формы?
Спасибо
FishHook
Для вопросов по Django есть отдельный форум
FishHook
Точно так же как с одной формой

class UserForm(forms.ModelForm):
    class Meta:
        model = User
        fields = ["username", "email"]
 
class UserProfileForm(forms.ModelForm):
    class Meta:
        model = UserProfile
 
#in views.py
def add_user(request):
    ...
    if request.method == "POST":
        uform = UserForm(data = request.POST)
        pform = UserProfileForm(data = request.POST)
        if uform.is_valid() and pform.is_valid():
            user = uform.save()
            profile = pform.save(commit = False)
            profile.user = user
            profile.save()
            ....
    ...

#in template
<form method="post">
    {{ uform.as_p }}
    {{ pform.as_p }}
    <input type="submit" ...>
</form> 
infoforfoi
Это мое первое сообщение извини, если не туда вписал, впредь буду внимательнее
Спасибо за ответ, но…

Может не совсем понятно объяснился.
Пользователь 1, у него много Товара, т.е. форма тоже одна, но для каждого Товара отдельная
estates_obj = Estates.objects.filter
(userprofile__user__username__exact=username) # тут убираем [0]
for n in estates_obj:
# где-то тут должен быть цикл, но это пока выше моего понимания
if request.method == 'POST':

подсказывают формсетом, но сколько не читал, пока не вникну как
FishHook
Если я правильно понял, то у тебя случай, когда нужно использовать формсеты.
infoforfoi
дошел до:

forms.py
class EstatesForm(ModelForm):
    class Meta:
      model = Estates
      fields = ('type_estate', 'cost', 'bargain', )
      
class BaseEstatesFormSet(BaseModelFormSet):
    def __init__(self, *args, **kwargs):
        super(BaseEstatesFormSet, self).__init__(*args, **kwargs)
        self.queryset = Estates.objects.all()
        
EstatesFormSet = modelformset_factory(Estates, form=EstatesForm, formset=BaseEstatesFormSet, extra=1)

views.py
    if request.method == 'POST':
        formset = EstatesFormSet(data=request.POST, files=request.FILES)
        if formset.is_valid():
            for n in formset.save(commit=False):
                formset.save()
            return HttpResponseRedirect('')
    else:
        formset = EstatesFormSet() 

templates.py
{{ formset }}

Выдает список форм с возможностью редактирования их, но пока все формы заполнены данными только одной записи

пытаюсь заполнить каждую форму Товара одного Пользователя разными записями из таблицы Товары
(т.е. на всякий, еще раз: Пользователь видит на странице, все свои Товары, в виде редактируемых форм)

        formset = EstatesFormSet(data=request.POST, files=request.FILES)
for form in formset:
if form.is_valid():
form.save()
return HttpResponseRedirect('')

        if formset.is_valid():
for n in formset.save():
n.userprofile__user__username__exact = request.username
n.save()

сложно строить логику, когда объекты не до конца изучены
может подскажите, один шаг до завершения этого проекта

в учебнике это выглядит, так:
>>> for form in formset:
.... print form.as_table()
как это реализовать не в shell, а в views?
buddha
Я пока отвечал сайт лёг.

Всё верно. Используй formset.

Будет так в твоём случае:
from django.forms.models import  modelformset_factory
# ...                           остальные импорты
def show_edit_estates(request):
    model_formset = modelformset_factory(Estates) # тут еще интересные параметры exclude, fields, can_delete, can_order
    if request.POST:
        formset = model_formset(request.POST, request.FILES, queryset=Estates.objects.filter(userprofile__user__username__exact=username))
        if formset.is_valid():                          # если не указать queryset, по умолчанию будет Estates.objects.all()
            estates_objects = formset.save(commit=False) # если не нужно менять ничего в объекте просто formset.save()
            for obj in estates_objects: # если какое то поле хочешь поменять вручную
                obj.some_field = 'adqwqe' # точно так же, как и с одиночной формой
                obj.save
                return HttpResponseRedirect('')
    else:
        formset = model_formset(queryset=Estates.objects.filter(userprofile__user__username__exact=username))
        return render(request, 'template.html', dict(formset=formset))

В шаблоне template.html:
<form action="{% url edit_estates %}" method="POST">{% csrf_token %}
            {{ formset.management_form }} {# обязательно выводить этот аргумент!!! #}
            {% for form in formset %}
                <div class="well">
                    {{ form }} {# тут уже как с обычной формой работай #}
                    <br>
                </div>
            {% endfor %}
            <input type="submit" class="btn" value="SAVE">
        </form>

За подробным описанием работы и возможностей
https://docs.djangoproject.com/en/1.4/topics/forms/formsets/

https://docs.djangoproject.com/en/1.4/topics/forms/modelforms/#model-formsets

Отпишись, что получилось. Сам не так давно подобное делал.
infoforfoi
Не знаю как тебя благодарить. Решил делать проект на Джанго, все просто супер, но логика требует опыта. Кстати, читал ту же документацию на русском, на английском она более полная.

Вывод форм происходит именно так как и хотелось бы.
+ Сохраняет введенные данные в новую форму из extra=1
- Но формы с имеющимися данными пока не перезаписывает.

Еще вопрос, как связать с forms.py, BaseEstatesFormSet, чтобы была возможность редактирования?
model_formset = modelformset_factory(Estates, EstatesFormSet) # что-то типа такого должно быть?

Редактирую django-profiles
infoforfoi
Вот оно решение:
    model_formset = modelformset_factory(Estates, form=EstatesForm) 
    if request.POST:
        formset = model_formset(request.POST, request.FILES, queryset=Estates.objects.filter(userprofile__user__username__exact=username)) 
        if formset.is_valid():
            estates_objects = formset.save(commit=False) 
            for obj in estates_objects:
                obj.save()
                return HttpResponseRedirect('')
    else:
        formset = model_formset(queryset=Estates.objects.filter(userprofile__user__username__exact=username))
        return render(request, template_name, dict(formset=formset)) 
infoforfoi
А как в новой форме из из extra=1, задать в поле Пользователя - текущего?

так понимаю, задается где-то здесь:
            estates_objects = formset.save(commit=False)
            for obj in estates_objects:
                obj.userprofile = request.user.username # тут вроде как
                obj.save()
                return HttpResponseRedirect('')

есть такие параметры:
def profile_detail(request, username, public_profile_field=None, form_class=None, success_url=None,
                   template_name='profiles/profile_detail.html',
                   extra_context=None):
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Powered by DjangoBB