Установка владельца объекта с общим представлением create_object в django
Можно ли использовать представление create_object для создания нового объекта и автоматически присваивать request.user в качестве внешнего ключа?
P.E:
class Post(models.Model):
text = models.TextField()
author = models.ForeignKey(User)
Я хочу использовать create_object и заполнять автора request.user.
Ответы
Ответ 1
Во многих отношениях все решения для этого будут больше проблем, чем они того стоят. Это можно назвать взломом. Возможно, обновление django оставит вас высоко и сухо, если они изменят способ реализации create_update. Для простоты я предполагаю, что вы пытаетесь установить пользователя по умолчанию, а не молча заставить пользователя быть зарегистрированным пользователем.
Записать обработчик контекста:
from django.views.generic.create_update import get_model_and_form_class
def form_user_default(request):
if request.method == 'GET':
model, custom_form = get_model_and_form_class(Post,None)
custom_form.author = request.user
return {'form':custom_form}
else: return {}
Что это будет делать, это переопределить объект формы, который create_update переходит к шаблону. То, что это технически делает, - это повторное создание формы после того, как это сделал по умолчанию.
Затем в вашем URL conf:
url(r'pattern_to_match', 'django.views.generic.create_update.create_object', kwargs={'context_processors':form_user_default})
Опять же, мне пришлось углубиться в исходный код, чтобы выяснить, как это сделать. Лучше всего попытаться написать собственное представление (но включить как можно больше пользовательских объектов Django). Нет никакого "простого дефолтного" способа сделать это, потому что в парадигмах django более тесно привязаны к слою модели, чем к представлениям, и только представления имеют знания объекта запроса.
Ответ 2
Возможно, вы захотите рассмотреть закрытие.
from django.forms import ModelForm
from django.views.generic.create_update import create_object, update_object
def make_foo_form(request):
class FooForm(ModelForm):
class Meta:
model = Foo
fields = ['foo', 'bar']
def save(self, commit=True):
f = super(FooForm, self).save(commit=False)
if not f.pk: f.user = request.user
if commit: f.save()
return f
return FooForm
def create_foo(request):
FooForm = make_foo_form(request)
return create_object(form_class=FooForm)
Здесь есть некоторая неэффективность, так как вам нужно создать объект ModelForm для каждого запроса, но это позволяет вам вводить функциональность в общий вид.
Вам нужно решить, стоит ли добавлять сложность для создания формы, чтобы упростить ее на стороне представления.
Преимущество здесь заключается в том, что это также работает с случаем обновления практически без особых усилий:
def update_foo(request, object_id):
FooForm = make_foo_form(request)
return update_object(form_class=FooForm, object_id=object_id)
Очевидно, вы можете использовать этот подход и для более сложных случаев.
Ответ 3
Если пользователь аутентифицирован, их пользовательский объект является объектом request.user
.
Я не знаком с create_object... Я все еще новичок в django и только что начал с ним свой первый настоящий проект.
Обратите внимание, что вы должны проверить, чтобы пользователь вошел в систему, прежде чем использовать это. Это можно сделать с помощью request.user.is_authenticated()
.
Ответ 4
Невозможно подключиться к сохранению объекта при использовании текущих общих представлений Django. Когда они переписаны как классы, вы сможете подклассифицировать представление и вставить его в нужное место, не переписывая весь вид.
По этой причине я уже использую свои собственные общие представления на основе классов.
Ответ 5
Я бы предложил создать обертку для create_object, как это предлагает автор
http://www.b-list.org/weblog/2006/nov/16/django-tips-get-most-out-generic-views/
в представлении вы получите доступ к информации о пользователе.
После этого вам нужно будет использовать extra_context, чтобы передать пользователя шаблону. Наконец, в шаблоне вы можете добавить скрытое поле с информацией о пользователе. Я не пробовал, но об этом уже давно думаю. Надеюсь, это решение вам подходит!
;) приветствия!