web-dev-qa-db-fra.com

Django Vue basée sur les classes: Comment puis-je passer des paramètres supplémentaires à la méthode as_view?

J'ai une vue personnalisée basée sur les classes

# myapp/views.py
from Django.views.generic import *

class MyView(DetailView):
    template_name = 'detail.html'
    model = MyModel

    def get_object(self, queryset=None):
        return queryset.get(slug=self.slug)

Je veux passer le paramètre slug (ou d'autres paramètres à la vue) comme ceci

MyView.as_view(slug='hello_world')

Dois-je remplacer des méthodes pour pouvoir le faire?

87
Rudolf Olah

Chaque paramètre transmis à la méthode as_view Est une variable d'instance de la classe View. Cela signifie que pour ajouter slug en tant que paramètre, vous devez le créer en tant que variable d'instance dans votre sous-classe:

# myapp/views.py
from Django.views.generic import DetailView

class MyView(DetailView):
    template_name = 'detail.html'
    model = MyModel
    # additional parameters
    slug = None

    def get_object(self, queryset=None):
        return queryset.get(slug=self.slug)

Cela devrait faire fonctionner MyView.as_view(slug='hello_world').

Si vous passez les variables à l'aide de mots-clés, utilisez les suggestions de M. Erikkson: https://stackoverflow.com/a/11494666/99

82
Rudolf Olah

Si votre urlconf ressemble à ceci:

url(r'^(?P<slug>[a-zA-Z0-9-]+)/$', MyView.as_view(), name = 'my_named_view')

alors le slug sera disponible dans vos fonctions de vue (comme 'get_queryset') comme ceci:

self.kwargs['slug']
107
Daniel Eriksson

Il est à noter que vous n'avez pas besoin de remplacer get_object() pour rechercher un objet basé sur un slug passé en tant que mot clé arg. Vous pouvez utiliser les attributs d'un SingleObjectMixinhttps://docs.djangoproject.com/fr/1.5/ref/class-based-views/mixins-single-object/#singleobjectmixin

# views.py
class MyView(DetailView):
    model = MyModel
    slug_field = 'slug_field_name'
    slug_url_kwarg = 'model_slug'
    context_object_name = 'my_model'

# urls.py
url(r'^(?P<model_slug>[\w-]+)/$', MyView.as_view(), name = 'my_named_view')

# mymodel_detail.html
{{ my_model.slug_field_name }}

(tous les deux slug_field et slug_url_kwarg défaut à 'slug')

18
Fush

Si vous souhaitez ajouter un objet au contexte du modèle, vous pouvez remplacer get_context_data et ajouter à son contexte. La demande fait également partie de self au cas où vous auriez besoin de request.user.

def get_context_data(self, **kwargs):
        context = super(MyTemplateView, self).get_context_data(**kwargs)
        if 'slug' in self.kwargs:
            context['object'] = get_object_or_404(MyObject, slug=self.kwargs['slug'])
            context['objects'] = get_objects_by_user(self.request.user)

        return context
13
Aleck Landgraf

Vous pouvez transmettre des paramètres depuis urls.py https://docs.djangoproject.com/fr/1.7/topics/http/urls/#passing-extra-options-to-view-functions

Cela fonctionne également pour les vues génériques. Exemple:

url(r'^$', views.SectionView.as_view(), { 'pk': 'homepage', 'another_param':'?'}, name='main_page'),

Dans ce cas, les paramètres transmis à la vue ne doivent pas nécessairement être des variables d'instance de la classe View. En utilisant cette méthode, vous n'avez pas besoin de coder en dur le nom de page par défaut dans le modèle YourView, mais vous pouvez simplement le transmettre en tant que paramètre à partir de urlconf.

10
Yaroslav Nikitenko

Comme indiqué par Yaroslav Nikitenko , si vous ne souhaitez pas coder en dur une nouvelle variable d'instance dans la classe View, vous pouvez passer des options supplémentaires pour afficher des fonctions à partir de urls.py comme ça:

url(r'^$', YourView.as_view(), {'slug': 'hello_world'}, name='page_name')

Je voulais juste ajouter comment l'utiliser à partir de la vue. Vous pouvez implémenter l'une des méthodes suivantes:

# If slug is optional
def the_function(self, request, slug=None):
    # use slug here

# if slug is an optional param among others
def the_function(self, request, **kwargs):
    slug = kwargs.get("slug", None)
    other_param = kwargs.get("other_param", None)

# If slug is required
def the_function(self, request, slug):
    # use slug here
7
Emile Bergeron