Python Django:必须使用对象pk或slug调用通用详细视图

Python Django:必须使用对象pk或slug调用通用详细视图,python,django,Python,Django,提交与此视图关联的表单时出现此错误。不确定到底是什么问题,考虑到我有一个结构非常相似的表单,它工作得很好 #views.py class Facture_Creer(SuccessMessageMixin, CreateView): model = Facture template_name = "facturation/nouvelle_facture.html" form_class= FormulaireFacture # permet de retour

提交与此视图关联的表单时出现此错误。不确定到底是什么问题,考虑到我有一个结构非常相似的表单,它工作得很好

#views.py
class Facture_Creer(SuccessMessageMixin, CreateView):
    model = Facture
    template_name = "facturation/nouvelle_facture.html"
    form_class= FormulaireFacture

    # permet de retourner a l'URL pointant vers le membre modifie
    def get_success_url(self):
        return reverse_lazy('facture_consulter',kwargs={'pk': self.get_object().id})

class Facture_Update(SuccessMessageMixin, UpdateView):
    model = Facture
    template_name = "facturation/nouvelle_facture.html"
    form_class= FormulaireFacture
    success_message = "Facture mise à jour avec succes"

    # permet de retourner a l'URL pointant vers le membre modifie
    def get_success_url(self):
        return reverse_lazy('facture_consulter',kwargs={'pk': self.get_object().id})

#urls.py
urlpatterns = patterns('',
    url(r'^$', TemplateView.as_view(template_name="facturation/index.html")),
    url(r'^facture/$', FactureView.as_view()),
    url(r'^facture/(?P<id>\d+)', FactureView.as_view(), name='facture_consulter'),
    url(r'^facture/ajouter/$', Facture_Creer.as_view(), name='facture_creer'),
    url(r'^facture/modifier/(?P<pk>\d+)/$', Facture_Update.as_view(), name='facture_update'),
    url(r'^membre/ajouter/$', Membre_Creer.as_view(), name='membre_creer'),
    url(r'^membre/modifier/(?P<pk>\d+)/$', Membre_Update.as_view(), name='membre_update'),
    #url(r'membre/(?P<pk>\d+)/supprimer/$', Membre_Supp.as_view(), name='membre_delete')
)

urlpatterns += staticfiles_urlpatterns()
#views.py
类别制作(Successessagexin,CreateView):
模型=断裂
template_name=“factouring/nouvelle_factory.html”
form_class=公式制作
#重新调用一个URL指针来修改内存
def get_success_url(自我):
返回reverse_lazy('facture_consulter',kwargs={'pk':self.get_object().id})
类别制作更新(Successessagexin,UpdateView):
模型=断裂
template_name=“factouring/nouvelle_factory.html”
form_class=公式制作
成功消息=“制造成功”
#重新调用一个URL指针来修改内存
def get_success_url(自我):
返回reverse_lazy('facture_consulter',kwargs={'pk':self.get_object().id})
#url.py
urlpatterns=模式(“”,
url(r'^$',TemplateView.as_view(template_name=“facturition/index.html”),
url(r'^facture/$,FactureView.as_view()),
url(r'^facture/(?P\d+),FactureView.as\u view(),name='facture\u consulter'),
url(r“^facture/ajouter/$”,facture\u Creer.as\u view(),name='facture\u Creer'),
url(r“^facture/modifier/(?P\d+)/$”,facture\u Update.as\u view(),name='facture\u Update'),
url(r“^membre/ajouter/$”,membre_Creer.as_view(),name='membre_Creer'),
url(r“^membre/modifier/(?P\d+)/$”,membre_Update.as_view(),name='membre_Update'),
#url(r'membre/(?P\d+)/supprimer/$”,membre_Supp.as_view(),name='membre_delete')
)
urlpatterns+=静态文件\u urlpatterns()

您需要传递一个对象标识符(pk或slug),以便您的视图知道它们在操作哪个对象

以您的
url.py
为例:

url(r'^facture/ajouter/$', Facture_Creer.as_view(), name='facture_creer'),
url(r'^facture/modifier/(?P<pk>\d+)/$', Facture_Update.as_view(), name='facture_update'),
url(r'^facture/ajour/$,facture\u Creer.as\u view(),name='facture\u Creer'),
url(r“^facture/modifier/(?P\d+)/$”,facture\u Update.as\u view(),name='facture\u Update'),
查看第二个如何具有
(?p\d+)/
?这就是将pk传递给UpdateView,以便它知道要使用哪个对象。因此,如果您转到
facture/modifier/5/
,那么UpdateView将修改pk为5的对象


如果不想在url中传递pk或slug,则需要重写该方法并以另一种方式获取对象。Url。

正如Alex所建议的:对于默认的Django行为,您必须在Url模式中使用“pk”


如果希望将主键“pk”的对象标识符更改为其他名称,可以定义。这是从Django 1.4开始提供的。

更新:在Django 2.0.2中,将其更改为:

url(r'^facture/modifier/<int:pk>/$', Facture_Update.as_view(), name='facture_update'),
url(r'^facture/modifier/$,facture\u Update.as\u view(),name='facture\u Update'),

嘿,我使用了新的
path()
函数,下面是我的工作示例,我相信这会有所帮助:

views.py:

from django.views.generic.detail import DetailView

class ContentAmpView(DetailView):

    model = Content
    template_name = 'content_amp.html'  # Defaults to content_detail.html
URL.py:

from django.urls import path

from .views import ContentAmpView

# My pk is a string so using a slug converter here intead of int
urlpatterns = [
    path('<slug:pk>/amp', ContentAmpView.as_view(), name='content-amp'),
]
从django.url导入路径
从.views导入ContentAmpView
#我的pk是一个字符串,所以在这里使用段塞转换器intead of int
URL模式=[
路径('/amp',ContentAmpView.as_view(),name='content-amp'),
]
模板/内容\u amp.html

<!doctype html>
<html amp lang="en">
<head>
    <meta charset="utf-8">
    <script async src="https://cdn.ampproject.org/v0.js"></script>
    <title>Hello, AMPs</title>
    <link rel="canonical" href="http://example.ampproject.org/article-metadata.html">
    <meta name="viewport" content="width=device-width,minimum-scale=1,initial-scale=1">
    <script type="application/ld+json">
      {
        "@context": "http://schema.org",
        "@type": "NewsArticle",
        "headline": "Open-source framework for publishing content",
        "datePublished": "2015-10-07T12:02:41Z",
        "image": [
          "logo.jpg"
        ]
      }

    </script>
    <style amp-boilerplate>
        body{-webkit-animation:-amp-start 8s steps(1,end) 0s 1 normal both;-moz-animation:-amp-start 8s steps(1,end) 0s 1 normal both;-ms-animation:-amp-start 8s steps(1,end) 0s 1 normal both;animation:-amp-start 8s steps(1,end) 0s 1 normal both}@-webkit-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-moz-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-ms-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-o-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}
    </style>
    <noscript>
        <style amp-boilerplate>body{-webkit-animation:none;-moz-animation:none;-ms-animation:none;animation:none}
        </style>
    </noscript>
</head>
<body>
<h1>Welcome to AMP - {{ object.pk }}</h1>
<p>{{ object.titles.main }}</p>
<p>Reporter: {{ object.reporter }}</p>
<p>Date: {{ object.created_at|date }}</p>
</body>
</html>

你好,AMPs
{
“@context”:”http://schema.org",
“@type”:“新闻文章”,
“标题”:“发布内容的开源框架”,
“发布日期”:“2015-10-07T12:02:41Z”,
“图像”:[
“logo.jpg”
]
}
body{-webkit动画:-amp start 8s steps(1,end)0s1 normal tweet;-moz动画:-amp start 8s steps(1,end)0s1 normal tweet;-ms动画:-amp start 8s steps(1,end)0s1 normal tweet}@-webkit关键帧-amp start{从{可见性:隐藏}到{可见性:可见}}@-moz关键帧-amp start{from{visibility:hidden}to{visibility:visible}-ms关键帧-amp start{from{visibility:hidden}to{visibility:visible}}-o-关键帧-amp start{from{visibility:hidden}to{visibility:visible}@keyframes amp start{from{visibility:hidden}to{visibility:visible}}}
body{-webkit动画:无;-moz动画:无;-ms动画:无;动画:无}
欢迎使用AMP-{{object.pk}
{{object.titles.main}

记者:{{object.Reporter}

日期:{{object.created|u at|Date}


还请注意,在我的
设置.py
中,在
模板下,我有
'APP_DIRS':True
。路径上有更多信息。

如Robin所说,如果您想要自定义pk名称,可以使用
pk_url_kwarg

但作为补充,必须使用对象pk或slug中的slug调用问题通用细节视图

因此,如果您想创建自定义slug字段(无需使用pk或slug名称)。您可以在DetailView类中重写
slug\u字段
slug\u url\u kwarg

如果您希望url作为Slug字段,这里只是另一个示例

型号.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
视图.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
url.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
urlpatterns=[
路径(“”,ListPost.as_view()),
路径(“/”,DetailPost.as_view()),
]

我正在使用Django 2.2.12版

下面是另一个例子,这对我来说很好:

型号.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
视图.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
url.py

class Post(models.Model):
    title = models.CharField(max_length=255)
    url = models.SlugField()
    body = models.TextField()
    image = models.ImageField(upload_to='blog/', blank=True, null=True)
class ListPost(ListView):
    model = Post
    template_name = 'blog/list.html'
    paginate_by = 2
    context_object_name = 'posts'

class DetailPost(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    slug_field = 'url'
    slug_url_kwarg = 'url'
urlpatterns = [
    path('', ListPost.as_view()),
    path('<slug:url>/', DetailPost.as_view()),
]
from django.db import models

class Book(models.Model):
    title = models.CharField(max_length=256)
    author = models.CharField(max_length=256)
    pages = models.IntegerField()
    price = models.FloatField()
from django.views.generic import ListView,DetailView
from testapp.models import Book

class BookListView(ListView):
    model=Book

class BookDetailView(DetailView):
    model=Book
from django.contrib import admin
from django.urls import path
from testapp import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('', views.BookListView.as_view()),
    path('<slug:pk>/', views.BookDetailView.as_view()),
]
来自django.contrib导入管理
从django.url导入路径
从testapp导入视图
URL模式=[
路径('admin/',admin.site.url),
路径(“”,views.BookListView.as_view()),
路径('/',views.BookDetailView.as_view()),
]

有道理。问题似乎出在def get_success_url(self)上:返回reverse_lazy('facture_consulter',kwargs={'pk':self.get_object().id})部分。你知道从CreateView中取出保存对象的方法吗?不管怎样,找到了。谢谢你的快速回答