From e4019dad8f938c9361e053b91b04468f7e92e544 Mon Sep 17 00:00:00 2001 From: Nikolay Shirokov Date: Thu, 29 May 2025 23:07:00 +0700 Subject: [PATCH 1/4] feat: add models --- apps/books/models.py | 88 +++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 87 insertions(+), 1 deletion(-) diff --git a/apps/books/models.py b/apps/books/models.py index 6b20219..58dae13 100644 --- a/apps/books/models.py +++ b/apps/books/models.py @@ -1 +1,87 @@ -# Create your models here. +from django.db import models +from django.contrib.auth import get_user_model + +User = get_user_model() + + +class Publisher(models.Model): + name = models.CharField(max_length=255, verbose_name="Название издательства") + website = models.URLField(max_length=255, blank=True, verbose_name="Сайт издательства") + + class Meta: + verbose_name = "Издательство" + verbose_name_plural = "Издательства" + + def __str__(self): + return self.name + + +class Author(models.Model): + first_name = models.CharField(max_length=100, verbose_name="Имя автора") + last_name = models.CharField(max_length=100, verbose_name="Фамилия автора") + bio = models.TextField(verbose_name="Биография") + + class Meta: + verbose_name = "Автор" + verbose_name_plural = "Авторы" + + def __str__(self): + return f"{self.first_name} {self.last_name}" + + +class Tag(models.Model): + name = models.CharField(max_length=100, unique=True, verbose_name="Название тега") + slug = models.SlugField(max_length=100, unique=True, verbose_name="URL-имя") + color = models.CharField(max_length=20, verbose_name='цвет') + + class Meta: + verbose_name = 'Тег' + verbose_name_plural = "Теги" + + def __str__(self): + return self.name + + +class Book(models.Model): + author = models.ManyToManyField(Author, related_name='books', verbose_name='Авторы') + publisher = models.ForeignKey(Publisher, + on_delete=models.CASCADE, + related_name='books', + verbose_name='Издательство') + title = models.CharField(max_length=255, verbose_name="Название книги") + description = models.TextField(verbose_name="Описание книги") + publication_date = models.DateField(verbose_name="Дата публикации") + isbn = models.CharField(max_length=20, verbose_name="ISBN") + pages = models.IntegerField(verbose_name="Количество страниц") + cover_image = models.URLField(max_length=255, verbose_name="Обложка книги") + language = models.CharField(max_length=50, verbose_name="Язык") + tags = models.ManyToManyField(Tag, related_name='books', verbose_name='Теги') + parsed_at = models.DateTimeField(auto_now_add=True, verbose_name='Дата парсинга') + + class Meta: + verbose_name = "Книга" + verbose_name_plural = "Книги" + + def __str__(self): + return self.title + + +class Comment(models.Model): + user = models.ForeignKey( + User, + on_delete=models.CASCADE, + related_name='comments', + verbose_name='Пользователь' + ) + book = models.ForeignKey( + Book, + on_delete=models.CASCADE, + related_name='comments', + verbose_name='Книга' + ) + text = models.TextField(verbose_name='Комментарий') + created_at = models.DateTimeField(auto_now_add=True, verbose_name='Дата создания') + + class Meta: + verbose_name = "Комментарий" + verbose_name_plural = "Комментарии" From c20f26f04bc35af68245b2749e8f35cdadbfab61 Mon Sep 17 00:00:00 2001 From: Nikolay Shirokov Date: Thu, 29 May 2025 23:07:00 +0700 Subject: [PATCH 2/4] feat: add models --- apps/books/models.py | 89 +++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 88 insertions(+), 1 deletion(-) diff --git a/apps/books/models.py b/apps/books/models.py index 6b20219..dfe76d2 100644 --- a/apps/books/models.py +++ b/apps/books/models.py @@ -1 +1,88 @@ -# Create your models here. +from django.db import models +from django.contrib.auth import get_user_model + +User = get_user_model() + + +class Publisher(models.Model): + name = models.CharField(max_length=255, verbose_name="Название издательства") + website = models.URLField( + max_length=255, blank=True, verbose_name="Сайт издательства" + ) + + class Meta: + verbose_name = "Издательство" + verbose_name_plural = "Издательства" + + def __str__(self): + return self.name + + +class Author(models.Model): + first_name = models.CharField(max_length=100, verbose_name="Имя автора") + last_name = models.CharField(max_length=100, verbose_name="Фамилия автора") + bio = models.TextField(verbose_name="Биография") + + class Meta: + verbose_name = "Автор" + verbose_name_plural = "Авторы" + + def __str__(self): + return f"{self.first_name} {self.last_name}" + + +class Tag(models.Model): + name = models.CharField(max_length=100, unique=True, verbose_name="Название тега") + slug = models.SlugField(max_length=100, unique=True, verbose_name="URL-имя") + color = models.CharField(max_length=20, verbose_name="цвет") + + class Meta: + verbose_name = "Тег" + verbose_name_plural = "Теги" + + def __str__(self): + return self.name + + +class Book(models.Model): + author = models.ManyToManyField(Author, related_name="books", verbose_name="Авторы") + publisher = models.ForeignKey( + Publisher, + on_delete=models.CASCADE, + related_name="books", + verbose_name="Издательство", + ) + title = models.CharField(max_length=255, verbose_name="Название книги") + description = models.TextField(verbose_name="Описание книги") + publication_date = models.DateField(verbose_name="Дата публикации") + isbn = models.CharField(max_length=20, verbose_name="ISBN") + pages = models.IntegerField(verbose_name="Количество страниц") + cover_image = models.URLField(max_length=255, verbose_name="Обложка книги") + language = models.CharField(max_length=50, verbose_name="Язык") + tags = models.ManyToManyField(Tag, related_name="books", verbose_name="Теги") + parsed_at = models.DateTimeField(auto_now_add=True, verbose_name="Дата парсинга") + + class Meta: + verbose_name = "Книга" + verbose_name_plural = "Книги" + + def __str__(self): + return self.title + + +class Comment(models.Model): + user = models.ForeignKey( + User, + on_delete=models.CASCADE, + related_name="comments", + verbose_name="Пользователь", + ) + book = models.ForeignKey( + Book, on_delete=models.CASCADE, related_name="comments", verbose_name="Книга" + ) + text = models.TextField(verbose_name="Комментарий") + created_at = models.DateTimeField(auto_now_add=True, verbose_name="Дата создания") + + class Meta: + verbose_name = "Комментарий" + verbose_name_plural = "Комментарии" From ab00a4d2d73783e867da468eea9bd55a54579cd3 Mon Sep 17 00:00:00 2001 From: Nikolay Shirokov Date: Thu, 29 May 2025 23:51:50 +0700 Subject: [PATCH 3/4] style: format models.py with ruff --- apps/books/models.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/apps/books/models.py b/apps/books/models.py index 31870a3..f08255f 100644 --- a/apps/books/models.py +++ b/apps/books/models.py @@ -10,7 +10,6 @@ class Publisher(models.Model): max_length=255, blank=True, verbose_name="Сайт издательства" ) - class Meta: verbose_name = "Издательство" verbose_name_plural = "Издательства" @@ -63,7 +62,6 @@ class Book(models.Model): tags = models.ManyToManyField(Tag, related_name="books", verbose_name="Теги") parsed_at = models.DateTimeField(auto_now_add=True, verbose_name="Дата парсинга") - class Meta: verbose_name = "Книга" verbose_name_plural = "Книги" @@ -87,4 +85,4 @@ class Comment(models.Model): class Meta: verbose_name = "Комментарий" - verbose_name_plural = "Комментарии" \ No newline at end of file + verbose_name_plural = "Комментарии" From 03ae8b59646177bd3895eb216bd44bfbfb3b1a1d Mon Sep 17 00:00:00 2001 From: Nikolay Shirokov Date: Thu, 5 Jun 2025 23:06:24 +0700 Subject: [PATCH 4/4] fix:Changes applied --- apps/books/models.py | 108 +++++++++++++++++++++++++++++++++---------- config/settings.py | 7 +-- requirements.txt | Bin 474 -> 518 bytes 3 files changed, 84 insertions(+), 31 deletions(-) diff --git a/apps/books/models.py b/apps/books/models.py index f08255f..620dd50 100644 --- a/apps/books/models.py +++ b/apps/books/models.py @@ -1,13 +1,19 @@ from django.db import models from django.contrib.auth import get_user_model +from django_extensions.db.models import TimeStampedModel User = get_user_model() class Publisher(models.Model): - name = models.CharField(max_length=255, verbose_name="Название издательства") + name = models.CharField( + "Название издательства", + max_length=255, + ) website = models.URLField( - max_length=255, blank=True, verbose_name="Сайт издательства" + "Сайт издательства", + max_length=255, + blank=True, ) class Meta: @@ -19,9 +25,18 @@ def __str__(self): class Author(models.Model): - first_name = models.CharField(max_length=100, verbose_name="Имя автора") - last_name = models.CharField(max_length=100, verbose_name="Фамилия автора") - bio = models.TextField(verbose_name="Биография") + first_name = models.CharField( + "Имя автора", + max_length=100, + ) + last_name = models.CharField( + "Фамилия автора", + max_length=100, + ) + bio = models.TextField( + "Биография", + blank=True, + ) class Meta: verbose_name = "Автор" @@ -32,9 +47,20 @@ def __str__(self): class Tag(models.Model): - name = models.CharField(max_length=100, unique=True, verbose_name="Название тега") - slug = models.SlugField(max_length=100, unique=True, verbose_name="URL-имя") - color = models.CharField(max_length=20, verbose_name="Цвет") + name = models.CharField( + "Название тега", + max_length=100, + unique=True, + ) + slug = models.SlugField( + "URL-имя", + max_length=100, + unique=True, + ) + color = models.CharField( + "Цвет", + max_length=20, + ) class Meta: verbose_name = "Тег" @@ -44,23 +70,50 @@ def __str__(self): return self.name -class Book(models.Model): - author = models.ManyToManyField(Author, related_name="books", verbose_name="Авторы") +class Book(TimeStampedModel): + title = models.CharField( + "Название книги", + max_length=255, + ) + description = models.TextField( + "Описание книги", + ) + published_at = models.DateField( + "Дата публикации", + ) + isbn_code = models.CharField( + "ISBN", + max_length=20, + unique=True, + ) + total_pages = models.IntegerField( + "Количество страниц", + ) + cover_image = models.URLField( + "Обложка книги", + max_length=255, + ) + language = models.CharField( + "Язык", + max_length=50, + ) + + author = models.ManyToManyField( + Author, + verbose_name="Авторы", + related_name="books", + ) publisher = models.ForeignKey( Publisher, + verbose_name="Издательство", on_delete=models.CASCADE, related_name="books", - verbose_name="Издательство", ) - title = models.CharField(max_length=255, verbose_name="Название книги") - description = models.TextField(verbose_name="Описание книги") - publication_date = models.DateField(verbose_name="Дата публикации") - isbn = models.CharField(max_length=20, verbose_name="ISBN") - pages = models.IntegerField(verbose_name="Количество страниц") - cover_image = models.URLField(max_length=255, verbose_name="Обложка книги") - language = models.CharField(max_length=50, verbose_name="Язык") - tags = models.ManyToManyField(Tag, related_name="books", verbose_name="Теги") - parsed_at = models.DateTimeField(auto_now_add=True, verbose_name="Дата парсинга") + tags = models.ManyToManyField( + Tag, + verbose_name="Теги", + related_name="books", + ) class Meta: verbose_name = "Книга" @@ -70,18 +123,23 @@ def __str__(self): return self.title -class Comment(models.Model): +class Comment(TimeStampedModel): + text = models.TextField( + "Комментарий", + ) + user = models.ForeignKey( User, + verbose_name="Пользователь", on_delete=models.CASCADE, related_name="comments", - verbose_name="Пользователь", ) book = models.ForeignKey( - Book, on_delete=models.CASCADE, related_name="comments", verbose_name="Книга" + Book, + verbose_name="Книга", + on_delete=models.CASCADE, + related_name="comments", ) - text = models.TextField(verbose_name="Комментарий") - created_at = models.DateTimeField(auto_now_add=True, verbose_name="Дата создания") class Meta: verbose_name = "Комментарий" diff --git a/config/settings.py b/config/settings.py index 507d928..525ed9b 100644 --- a/config/settings.py +++ b/config/settings.py @@ -15,7 +15,6 @@ # Build paths inside the project like this: BASE_DIR / 'subdir'. BASE_DIR = Path(__file__).resolve().parent.parent - # Quick-start development settings - unsuitable for production # See https://docs.djangoproject.com/en/5.2/howto/deployment/checklist/ @@ -27,7 +26,6 @@ ALLOWED_HOSTS = [] - # Application definition INSTALLED_APPS = [ @@ -38,6 +36,7 @@ "django.contrib.messages", "django.contrib.staticfiles", "apps.books.apps.BooksConfig", + "django_extensions", ] MIDDLEWARE = [ @@ -69,7 +68,6 @@ WSGI_APPLICATION = "config.wsgi.application" - # Database # https://docs.djangoproject.com/en/5.2/ref/settings/#databases @@ -80,7 +78,6 @@ } } - # Password validation # https://docs.djangoproject.com/en/5.2/ref/settings/#auth-password-validators @@ -99,7 +96,6 @@ }, ] - # Internationalization # https://docs.djangoproject.com/en/5.2/topics/i18n/ LANGUAGE_CODE = "en" @@ -111,7 +107,6 @@ USE_I18N = True USE_TZ = True - # Static files (CSS, JavaScript, Images) # https://docs.djangoproject.com/en/5.2/howto/static-files/ diff --git a/requirements.txt b/requirements.txt index 1e8c9b53d987bd95bf64ea4946b0fda2879cf20e..05b906a9637a338960133555086b4cc51a46e390 100644 GIT binary patch delta 52 zcmcb`+{Uuu7NbrILl#3KLmopqLq3BpLn=cBLkW<~V<=|G1d4!YTOc%H&|@%U003U< B3mgCd delta 7 OcmZo;xy8KU79#))+ye6e