Django - Как отфильтровать купленную книгу по пользователю - PullRequest
0 голосов
/ 21 апреля 2019

Я создал модель, в которой пользователю разрешено приобретать книгу.Приобретаемая книга уже была распознана, но когда пользователь посещает содержимое книги, возникает следующая ошибка: get () возвратил более одной книги Purchase_Book - вернул 2!

Я уже пытался настроить кодыно безрезультатно.

Вот мои модели и их связь друг с другом.

class Book(models.Model):
      # some book info

      def __str__(self):
          return self.title

      def get_absolute_url(self):
         return reverse('book-detail', kwargs={'slug': self.slug})

      @property
      def pages(self):
          return self.page_set.all()

содержание книги

class Page(models.Model):
    # some pdf files to upload

    def __str__(self):
        return self.slug

    def get_absolute_url(self):
        return reverse('page-detail',
                   kwargs={
                       'book_slug': self.book.slug,
                       'page_slug': self.slug
                   })

модели для фильтрации пользователей, которые могут получить доступ к содержанию книги.

class Purchase_Book(models.Model):
    description = models.CharField(max_length=50, null=True)
    selected_Book = models.ManyToManyField(Book)

    def __str__(self):
        return self.description

class Customer(models.Model):
       user = models.OneToOneField(User, on_delete=models.CASCADE)
       service_Type = models.ForeignKey(Purchase_Book, on_delete=models.CASCADE, null=True)

      def __str__(self):
         return self.user.email

Вот мой последний views.py, где я фильтрую пользователя, которыймогу получить доступ к содержанию книги.

class PageDetailView(NeverCacheMixin, LoginRequiredMixin, generic.View):

def get(self, request, book_slug, page_slug, *args, **kwargs):
    book = get_object_or_404(Book, slug=book_slug)
    page = get_object_or_404(Page, slug=page_slug)
    purchased = get_object_or_404(Purchase_Book)
    user_membership = get_object_or_404(Customer, user=request.user)
    user_membership_type = user_membership.service_Type.selected_Book

    user_allowed = purchased.selected_Book.all()

    context = {'object': None}
    if user_allowed.filter(selected_Book=user_membership_type).exists():
        context = {'object': page}
    return render(request, "catalog/page_detail.html", context)

Я все еще новичок.Я надеюсь, что кто-то может помочь мне.

1 Ответ

2 голосов
/ 21 апреля 2019

Я думаю, что ошибка для следующей строки:

purchased = get_object_or_404(Purchase_Book)

Будет выдано сообщение об ошибке, если будет создано несколько купленных книг. В идеале вам нужно предоставить условие (или параметр) для получения реального объекта, то есть get_object_or_404(Purchase_Book, pk=1).

Кстати, вы можете удалить эту строку и получить купленные книги для конкретного клиента, например:

user_membership = get_object_or_404(Customer, user=request.user)
purchased = user_membership.service_Type

Кроме того, я не думаю, что следующие строки вообще необходимы (объяснение в комментариях к коду):

user_membership_type = user_membership.service_Type.selected_Book  # getting current user books

user_allowed = purchased.selected_Book.all()  # getting current user books

context = {'object': None}
if user_allowed.filter(selected_Book=user_membership_type).exists():  # comparing books ? Why? You can remove that, because you are already getting current user books. 
# if there is a relation between page and user, you should put logic for that here instead of current one

Обновление

Что-то вроде этого должно работать:

if purchased.selected_Book.filter(pk=page.book.pk).exists()
   context = {'object': page}
...