Skip to content

Commit

Permalink
Adding solution
Browse files Browse the repository at this point in the history
Added solution for last few weeks
b-angelov committed Aug 3, 2024

Verified

This commit was created on GitHub.com and signed with GitHub’s verified signature. The key has expired.
1 parent 3d4a992 commit 93a83d1
Showing 219 changed files with 6,052 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import os
from decimal import Decimal

import django
from django.core.exceptions import ValidationError

# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models here
from main_app.models import Customer, Book, Product, DiscountedProduct, SpiderHero, FlashHero, Document

# Create queries within functions

if __name__ == '__main__':
pass
from django.contrib.postgres.search import SearchVector

# Create the first 'Document' object with a title and content.
document1 = Document.objects.create(
title="Django Framework 1",
content="Django is a high-level Python web framework for building web applications.",
)

# Create the second 'Document' object with a title and content.
document2 = Document.objects.create(
title="Django Framework 2",
content="Django framework provides tools for creating web pages, handling URL routing, and more.",
)

# Update the 'search_vector' field in the 'Document' model with search vectors.
Document.objects.update(search_vector=SearchVector('title', 'content'))

# Perform a full-text search for documents containing the words 'django' and 'web framework'.
results = Document.objects.filter(search_vector='django web framework')

# Print the search results.
for result in results:
print(f"Title: {result.title}")
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.contrib import admin

# Register your models here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# Generated by Django 5.0.4 on 2024-07-20 09:48

import django.core.validators
import main_app.validators
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='Customer',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100, validators=[main_app.validators.ValidName()])),
('age', models.PositiveIntegerField(validators=[django.core.validators.MinValueValidator(18, 'Age must be greater than or equal to 18')])),
('email', models.EmailField(error_messages={'invalid': 'Enter a valid email address'}, max_length=254)),
('phone_number', models.CharField(max_length=13, validators=[main_app.validators.CountryPhoneNumberValidator()])),
('website_url', models.URLField(error_messages={'invalid': 'Enter a valid URL'})),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
# Generated by Django 5.0.4 on 2024-07-20 10:16

import django.core.validators
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0001_initial'),
]

operations = [
migrations.CreateModel(
name='Book',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=100)),
('description', models.TextField()),
('genre', models.CharField(max_length=100)),
('created_at', models.DateTimeField(auto_now=True)),
('author', models.CharField(max_length=100, validators=[django.core.validators.MinLengthValidator(5, 'Author must be at least 5 characters long')])),
('isbn', models.CharField(max_length=20, unique=True, validators=[django.core.validators.MinLengthValidator(6, 'ISBN must be at least 6 characters long')])),
],
options={
'ordering': ['-created_at', 'title'],
'abstract': False,
},
),
migrations.CreateModel(
name='Movie',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=100)),
('description', models.TextField()),
('genre', models.CharField(max_length=100)),
('created_at', models.DateTimeField(auto_now=True)),
('director', models.CharField(max_length=100, validators=[django.core.validators.MinLengthValidator(8, 'Director must be at least 8 characters long')])),
],
options={
'verbose_name': 'Model Movie',
'verbose_name_plural': 'Models of type -Movie',
'ordering': ['-created_at', 'title'],
'abstract': False,
},
),
migrations.CreateModel(
name='Music',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=100)),
('description', models.TextField()),
('genre', models.CharField(max_length=100)),
('created_at', models.DateTimeField(auto_now=True)),
('artist', models.CharField(max_length=100, validators=[django.core.validators.MinLengthValidator(9, 'Artist must be at least 9 characters long')])),
],
options={
'verbose_name': 'Model Music',
'verbose_name_plural': 'Models of type - Music',
'ordering': ['-created_at', 'title'],
'abstract': False,
},
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Generated by Django 5.0.4 on 2024-07-20 10:19

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('main_app', '0002_book_movie_music'),
]

operations = [
migrations.AlterModelOptions(
name='movie',
options={'ordering': ['-created_at', 'title'], 'verbose_name': 'Model Movie', 'verbose_name_plural': 'Models of type - Movie'},
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Generated by Django 5.0.4 on 2024-07-20 10:21

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('main_app', '0003_alter_movie_options'),
]

operations = [
migrations.AlterModelOptions(
name='book',
options={'ordering': ['-created_at', 'title'], 'verbose_name': 'Model Book', 'verbose_name_plural': 'Models of type - Book'},
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# Generated by Django 5.0.4 on 2024-07-20 10:38

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0004_alter_book_options'),
]

operations = [
migrations.CreateModel(
name='Product',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('price', models.DecimalField(decimal_places=2, max_digits=10)),
],
),
migrations.CreateModel(
name='DiscountedProduct',
fields=[
],
options={
'proxy': True,
'indexes': [],
'constraints': [],
},
bases=('main_app.product',),
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
# Generated by Django 5.0.4 on 2024-07-20 12:44

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0005_product_discountedproduct'),
]

operations = [
migrations.CreateModel(
name='Hero',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('hero_title', models.CharField(max_length=100)),
],
options={
'abstract': False,
},
),
migrations.CreateModel(
name='FlashHero',
fields=[
],
options={
'proxy': True,
'indexes': [],
'constraints': [],
},
bases=('main_app.hero',),
),
migrations.CreateModel(
name='SpiderHero',
fields=[
],
options={
'proxy': True,
'indexes': [],
'constraints': [],
},
bases=('main_app.hero',),
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# Generated by Django 5.0.4 on 2024-07-20 12:55

import django.contrib.postgres.search
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0006_hero_flashhero_spiderhero'),
]

operations = [
migrations.CreateModel(
name='Document',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=200)),
('content', models.TextField()),
('search_vector', django.contrib.postgres.search.SearchVectorField(null=True)),
],
options={
'indexes': [models.Index(fields=['search_vector'], name='main_app_do_search__c97410_idx')],
},
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
from django.db import models


class RechargeEnergyMixin(models.Model):
def recharge_energy(self, amount: int):
# print(self.energy, amount)
self.energy += amount

class Meta:
abstract = True
Original file line number Diff line number Diff line change
@@ -0,0 +1,157 @@
from decimal import Decimal

from django.contrib.postgres.search import SearchVectorField
from django.core.validators import MinValueValidator, EmailValidator, URLValidator, MinLengthValidator
from django.db import models

from main_app.mixins import RechargeEnergyMixin
from main_app.validators import ValidName, CountryPhoneNumberValidator


# Create your models here.

class Customer(models.Model):

name = models.CharField(max_length=100, validators = [ValidName()])
age = models.PositiveIntegerField(validators = [MinValueValidator(18,"Age must be greater than or equal to 18")])
email = models.EmailField(error_messages={'invalid': 'Enter a valid email address'})
phone_number = models.CharField(max_length=13, validators=[CountryPhoneNumberValidator()])
website_url = models.URLField(error_messages={'invalid':"Enter a valid URL"})


class BaseMedia(models.Model):

class Meta:
abstract = True
ordering = ['-created_at','title']

title = models.CharField(max_length=100)
description = models.TextField()
genre = models.CharField(max_length=100)
created_at = models.DateTimeField(auto_now=True)

class Book(BaseMedia):
author = models.CharField(max_length=100, validators=[MinLengthValidator(5,"Author must be at least 5 characters long")])
isbn = models.CharField(max_length=20, unique=True, validators=[MinLengthValidator(6, "ISBN must be at least 6 characters long")])

class Meta(BaseMedia.Meta):
verbose_name = 'Model Book'
verbose_name_plural = 'Models of type - Book'


class Movie(BaseMedia):
director = models.CharField(max_length=100, validators=[MinLengthValidator(8, "Director must be at least 8 characters long")])

class Meta(BaseMedia.Meta):
verbose_name = 'Model Movie'
verbose_name_plural = 'Models of type - Movie'


class Music(BaseMedia):
artist = models.CharField(max_length=100, validators=[MinLengthValidator(9, "Artist must be at least 9 characters long")])

class Meta(BaseMedia.Meta):
verbose_name = 'Model Music'
verbose_name_plural = 'Models of type - Music'


class Product(models.Model):
name = models.CharField(max_length=100)
price = models.DecimalField(max_digits=10, decimal_places=2)

def calculate_tax(self):
return self.price * Decimal(0.08)

def calculate_shipping_cost(self, weight: Decimal):
return weight * Decimal(2.00)

def format_product_name(self):
return f"Product: {self.name}"



class DiscountedProduct(Product):

class Meta:
proxy = True

def calculate_price_without_discount(self):
return self.price * Decimal(1.20)

def calculate_tax(self):
return self.price * Decimal(0.05)

def calculate_shipping_cost(self, weight: Decimal):
return weight * Decimal(1.50)

def format_product_name(self):
return f'Discounted Product: {self.name}'


class Hero(RechargeEnergyMixin):
name = models.CharField(max_length=100)
hero_title = models.CharField(max_length=100)
energy = models.PositiveIntegerField()

@property
def energy(self):
return self.__energy

@energy.setter
def energy(self, value):
try:
energy = self.__energy
energy = value
if energy < 0:
raise ValueError('cannot decrease below zero')
self.__energy = energy
except AttributeError:
self.__energy = value
self.__energy = min(100, self.__energy)


class SpiderHero(Hero):

def swing_from_buildings(self):
try:
self.energy -= 80
except ValueError:
return f"{self.name} as Spider Hero is out of web shooter fluid"
self.energy = max(1,self.energy)
self.clean()
self.save()
return f"{self.name} as Spider Hero swings from buildings using web shooters"

class Meta:
proxy = True


class FlashHero(Hero):

def run_at_super_speed(self):
try:
self.energy -= 65
except ValueError:
return f"{self.name} as Flash Hero needs to recharge the speed force"
self.energy = max(1, self.energy)
self.clean()
self.save()
return f"{self.name} as Flash Hero runs at lightning speed, saving the day"

class Meta:
proxy=True


class Document(models.Model):
title = models.CharField(max_length=200)
content = models.TextField()
search_vector = SearchVectorField(null=True)

class Meta:
indexes = [
models.Index(fields=['search_vector'])
]




Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
from re import match

from django.core.exceptions import ValidationError
# from django.db import models
from django.core.validators import BaseValidator

class ValidName(BaseValidator):

def __init__(self, *args, **kwargs):
self.message = kwargs.get('message', "Name can only contain letters and spaces")
super().__init__(None, **kwargs)

def __call__(self, value):
if not isinstance(value, str) or not value.replace(' ','').isalpha():
raise ValidationError(self.message)


class CountryPhoneNumberValidator(BaseValidator):

def __init__(self, *args, **kwargs):
self.phone_code = kwargs.get('country_code','+359')
try:
del kwargs['country_code']
except:
pass
self.message = kwargs.get('message',f"Phone number must start with '{self.phone_code}' followed by 9 digits")
super().__init__(None,**kwargs)

def __call__(self, value):
pattern = fr'^\{self.phone_code}\d{{9}}$'
if not match(pattern, value):
raise ValidationError(self.message)
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
"""
Django settings for orm_skeleton project.
Generated by 'django-admin startproject' using Django 4.2.4.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/topics/settings/
For the full list of settings and their values, see
https://docs.djangoproject.com/en/4.2/ref/settings/
"""

from pathlib import Path

# 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/4.2/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = 'django-insecure-cd%2g!p_@ut(kc8)%bd9_*@)i@kff^orkvy=!c#i!l+ak98)%0'

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'main_app',
]

MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'orm_skeleton.urls'

TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates']
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]

WSGI_APPLICATION = 'orm_skeleton.wsgi.application'


# Database
# https://docs.djangoproject.com/en/4.2/ref/settings/#databases

# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': BASE_DIR / 'db.sqlite3',
# }
# }

DATABASES = {
"default": {
"ENGINE": "django.db.backends.postgresql",
"NAME": "advanced_django_model_techniques_exercise",
"USER": "postgres-user",
"PASSWORD": "password",
"HOST": "localhost",
"PORT": "5432",
}
}

# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
},
]


# Internationalization
# https://docs.djangoproject.com/en/4.2/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_TZ = True


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/4.2/howto/static-files/

STATIC_URL = 'static/'

# Default primary key field type
# https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
URL configuration for orm_skeleton project.
The `urlpatterns` list routes URLs to views. For more information please see:
https://docs.djangoproject.com/en/4.2/topics/http/urls/
Examples:
Function views
1. Add an import: from my_app import views
2. Add a URL to urlpatterns: path('', views.home, name='home')
Class-based views
1. Add an import: from other_app.views import Home
2. Add a URL to urlpatterns: path('', Home.as_view(), name='home')
Including another URLconf
1. Import the include() function: from django.urls import include, path
2. Add a URL to urlpatterns: path('blog/', include('blog.urls'))
"""
from django.contrib import admin
from django.urls import path

urlpatterns = [
path('admin/', admin.site.urls),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
WSGI config for orm_skeleton project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/wsgi/
"""

import os

from django.core.wsgi import get_wsgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_wsgi_application()
Binary file not shown.
42 changes: 42 additions & 0 deletions DataBases/PythonORM/advanced_django_model_techniques_lab/caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import os
import django
from django.core.exceptions import ValidationError


# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models here
from main_app.models import Restaurant

# Create queries within functions

if __name__ == '__main__':
pass
from main_app.models import Restaurant, RegularRestaurantReview, FoodCriticRestaurantReview
from django.core.exceptions import ValidationError

restaurant1 = Restaurant.objects.create(name="Restaurant A", location="123 Main St.",
description="A cozy restaurant", rating=4.88)
RegularRestaurantReview.objects.create(reviewer_name="Bob", restaurant=restaurant1,
review_content="Good experience overall.", rating=4)
RegularRestaurantReview.objects.create(reviewer_name="Aleks", restaurant=restaurant1,
review_content="Great food and service!", rating=5)

duplicate_review = RegularRestaurantReview(reviewer_name="Aleks", restaurant=restaurant1,
review_content="Another great meal!", rating=5)

try:
duplicate_review.full_clean()
duplicate_review.save()
except ValidationError as e:
print(f"Validation Error: {e}")

print("Regular Restaurant Review:")
print(f"Model Name: {RegularRestaurantReview._meta.verbose_name}")
print(f"Model Plural Name: {RegularRestaurantReview._meta.verbose_name_plural}")

print("Food Critic Restaurant Review:")
print(f"Model Name: {FoodCriticRestaurantReview._meta.verbose_name}")
print(f"Model Plural Name: {FoodCriticRestaurantReview._meta.verbose_name_plural}")
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.contrib import admin

# Register your models here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Generated by Django 5.0.4 on 2024-07-18 13:25

import django.core.validators
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='Restaurant',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100, validators=[django.core.validators.MinLengthValidator(2, 'Name must be at least 2 characters long.'), django.core.validators.MaxLengthValidator(100, 'Name cannot exceed 100 characters.')])),
('location', models.CharField(max_length=200, validators=[django.core.validators.MinLengthValidator(2, 'Location must be at least 2 characters long.'), django.core.validators.MaxLengthValidator(200, 'Location cannot exceed 200 characters.')])),
('description', models.TextField(blank=True, null=True)),
('rating', models.DecimalField(decimal_places=2, max_digits=3, validators=[django.core.validators.MinValueValidator(0.0, 'Rating must be at least 0.00.'), django.core.validators.MaxValueValidator(5.0, 'Rating cannot exceed 5.00.')])),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# Generated by Django 5.0.4 on 2024-07-19 12:08

import django.db.models.deletion
import main_app.validators
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0001_initial'),
]

operations = [
migrations.CreateModel(
name='Menu',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('description', models.TextField(validators=[main_app.validators.validate_menu_categories(limit_value=['Appetizers', 'Main Course', 'Desserts'], message='The menu must include each of the categories "Appetizers", "Main Course", "Desserts".')])),
('restaurant', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.restaurant')),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Generated by Django 5.0.4 on 2024-07-19 12:25

import django.core.validators
import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0002_menu'),
]

operations = [
migrations.CreateModel(
name='RestaurantReview',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('reviewer_name', models.CharField(max_length=100)),
('review_content', models.TextField(validators=[django.core.validators.MaxValueValidator(5)])),
('rating', models.PositiveIntegerField()),
('restaurant', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.restaurant')),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# Generated by Django 5.0.4 on 2024-07-19 12:26

import django.core.validators
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0003_restaurantreview'),
]

operations = [
migrations.AlterField(
model_name='restaurantreview',
name='rating',
field=models.PositiveIntegerField(validators=[django.core.validators.MaxValueValidator(5)]),
),
migrations.AlterField(
model_name='restaurantreview',
name='review_content',
field=models.TextField(),
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Generated by Django 5.0.4 on 2024-07-19 12:28

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('main_app', '0004_alter_restaurantreview_rating_and_more'),
]

operations = [
migrations.AlterModelOptions(
name='restaurantreview',
options={'ordering': ['-rating'], 'verbose_name': 'Restaurant Review', 'verbose_name_plural': 'Restaurant Reviews'},
),
migrations.AlterUniqueTogether(
name='restaurantreview',
unique_together={('reviewer_name', 'restaurant')},
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
# Generated by Django 5.0.4 on 2024-07-19 12:41

import django.core.validators
import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0005_alter_restaurantreview_options_and_more'),
]

operations = [
migrations.CreateModel(
name='FoodCriticRestaurantReview',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('reviewer_name', models.CharField(max_length=100)),
('review_content', models.TextField()),
('rating', models.PositiveIntegerField(validators=[django.core.validators.MaxValueValidator(5)])),
('food_critic_cuisine_area', models.CharField(max_length=100)),
('restaurant', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.restaurant')),
],
options={
'verbose_name': 'Food Critic Review',
'verbose_name_plural': 'Food Critic Reviews',
'ordering': ['-rating'],
'abstract': False,
'unique_together': {('reviewer_name', 'restaurant')},
},
),
migrations.CreateModel(
name='RegularRestaurantReview',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('reviewer_name', models.CharField(max_length=100)),
('review_content', models.TextField()),
('rating', models.PositiveIntegerField(validators=[django.core.validators.MaxValueValidator(5)])),
('restaurant', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.restaurant')),
],
options={
'verbose_name': 'Restaurant Review',
'verbose_name_plural': 'Restaurant Reviews',
'ordering': ['-rating'],
'abstract': False,
'unique_together': {('reviewer_name', 'restaurant')},
},
),
migrations.DeleteModel(
name='RestaurantReview',
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# Generated by Django 5.0.4 on 2024-07-19 12:56

import django.core.validators
import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0006_foodcriticrestaurantreview_regularrestaurantreview_and_more'),
]

operations = [
migrations.CreateModel(
name='MenuReview',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('reviewer_name', models.CharField(max_length=100)),
('review_content', models.TextField()),
('rating', models.PositiveIntegerField(validators=[django.core.validators.MaxValueValidator(5)])),
('menu', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.menu')),
],
options={
'verbose_name': 'Menu Review',
'verbose_name_plural': 'Menu Reviews',
'ordering': ['-rating'],
'indexes': [models.Index(fields=['menu'], name='main_app_menu_review_menu_id')],
'unique_together': {('reviewer_name', 'menu')},
},
),
]
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
from django.core.validators import MaxValueValidator
from django.db import models


class ReviewMixin(models.Model):
reviewer_name = models.CharField(max_length=100)
review_content = models.TextField()
rating = models.PositiveIntegerField(validators=[MaxValueValidator(5)])

class Meta:
abstract = True
ordering = ['-rating']
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
from django.core.validators import MinLengthValidator, MaxLengthValidator, MinValueValidator, MaxValueValidator
from django.db import models

from main_app.mixins import ReviewMixin
from main_app.validators import validate_menu_categories


# Create your models here.


class Restaurant(models.Model):
name = models.CharField(
max_length=100,
validators=[
MinLengthValidator(2, "Name must be at least 2 characters long."),
MaxLengthValidator(100, "Name cannot exceed 100 characters.")
]
)
location = models.CharField(
max_length=200,
validators=[
MinLengthValidator(2, "Location must be at least 2 characters long."),
MaxLengthValidator(200, "Location cannot exceed 200 characters.")
]
)
description = models.TextField(null=True, blank=True)
rating = models.DecimalField(max_digits=3, decimal_places=2,
validators=[
MinValueValidator(0.00, "Rating must be at least 0.00."),
MaxValueValidator(5.00, "Rating cannot exceed 5.00.")
])


class Menu(models.Model):
name = models.CharField(
max_length=100,
)
description = models.TextField(
validators=[validate_menu_categories(limit_value=["Appetizers", "Main Course","Desserts"],message='The menu must include each of the categories "Appetizers", "Main Course", "Desserts".')]
)
restaurant = models.ForeignKey(to='Restaurant', on_delete=models.CASCADE)


class RestaurantReview(ReviewMixin):
restaurant = models.ForeignKey(to='Restaurant', on_delete=models.CASCADE)

class Meta(ReviewMixin.Meta):
verbose_name = 'Restaurant Review'
verbose_name_plural = 'Restaurant Reviews'
unique_together = ['reviewer_name', 'restaurant']
abstract = True



class RegularRestaurantReview(RestaurantReview):
pass


class FoodCriticRestaurantReview(RestaurantReview):
food_critic_cuisine_area = models.CharField(max_length=100)

class Meta(RestaurantReview.Meta):
verbose_name = 'Food Critic Review'
verbose_name_plural = 'Food Critic Reviews'


class MenuReview(ReviewMixin):
menu = models.ForeignKey(to='Menu', on_delete=models.CASCADE)

class Meta(ReviewMixin.Meta):
verbose_name = 'Menu Review'
verbose_name_plural = 'Menu Reviews'
unique_together = ['reviewer_name', 'menu']
indexes = [models.Index(fields=('menu',), name='main_app_menu_review_menu_id')]

Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import django.core.validators
from django.core.exceptions import ValidationError
from django.core.validators import BaseValidator


class validate_menu_categories(BaseValidator):

def __init__(self, *args, **kwargs):
kwargs['limit_value'] = kwargs.get('limit_value', ["Appetizers", "Main Course","Desserts"])
kwargs['message'] = kwargs.get('message','The menu must include each of the categories "Appetizers", "Main Course", "Desserts".')
self.includes = kwargs['limit_value']
self.message = kwargs['message']
super().__init__(*args,**kwargs)

def __call__(self, value):
for dish in self.includes:
if dish not in value:
raise ValidationError(self.message)
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
22 changes: 22 additions & 0 deletions DataBases/PythonORM/advanced_django_model_techniques_lab/manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
"""
Django settings for orm_skeleton project.
Generated by 'django-admin startproject' using Django 4.2.4.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/topics/settings/
For the full list of settings and their values, see
https://docs.djangoproject.com/en/4.2/ref/settings/
"""

from pathlib import Path

# 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/4.2/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = 'django-insecure-cd%2g!p_@ut(kc8)%bd9_*@)i@kff^orkvy=!c#i!l+ak98)%0'

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'main_app',
]

MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'orm_skeleton.urls'

TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates']
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]

WSGI_APPLICATION = 'orm_skeleton.wsgi.application'


# Database
# https://docs.djangoproject.com/en/4.2/ref/settings/#databases

# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': BASE_DIR / 'db.sqlite3',
# }
# }

DATABASES = {
"default": {
"ENGINE": "django.db.backends.postgresql",
"NAME": "advanced_django_models_techniques_lab",
"USER": "postgres-user",
"PASSWORD": "password",
"HOST": "localhost",
"PORT": "5432",
}
}

# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
},
]


# Internationalization
# https://docs.djangoproject.com/en/4.2/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_TZ = True


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/4.2/howto/static-files/

STATIC_URL = 'static/'

# Default primary key field type
# https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
URL configuration for orm_skeleton project.
The `urlpatterns` list routes URLs to views. For more information please see:
https://docs.djangoproject.com/en/4.2/topics/http/urls/
Examples:
Function views
1. Add an import: from my_app import views
2. Add a URL to urlpatterns: path('', views.home, name='home')
Class-based views
1. Add an import: from other_app.views import Home
2. Add a URL to urlpatterns: path('', Home.as_view(), name='home')
Including another URLconf
1. Import the include() function: from django.urls import include, path
2. Add a URL to urlpatterns: path('blog/', include('blog.urls'))
"""
from django.contrib import admin
from django.urls import path

urlpatterns = [
path('admin/', admin.site.urls),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
WSGI config for orm_skeleton project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/wsgi/
"""

import os

from django.core.wsgi import get_wsgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_wsgi_application()
Binary file not shown.
63 changes: 63 additions & 0 deletions DataBases/PythonORM/advanced_queries_in_django_exercise/caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
import os
from datetime import date

import django


# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models here
from main_app.models import RealEstateListing, VideoGame, BillingInfo, Invoice, Programmer, Project, Technology, Task, \
Exercise

# Run and print your queries

if __name__ == '__main__':
Exercise.objects.all().delete()
# Create instances of Exercise
exercise1 = Exercise.objects.create(
name="Push-ups",
category="Strength",
difficulty_level=4,
duration_minutes=10,
repetitions=50,
)

exercise2 = Exercise.objects.create(
name="Running",
category="Cardio",
difficulty_level=7,
duration_minutes=20,
repetitions=0,
)

exercise3 = Exercise.objects.create(
name="Pull-ups",
category="Strength",
difficulty_level=13,
duration_minutes=35,
repetitions=20,
)

# Print the results
long_and_hard_exercises = Exercise.get_long_and_hard_exercises()
print("Long and hard exercises:")
for exercise in long_and_hard_exercises:
print('- ' + exercise.name)

short_and_easy_exercises = Exercise.get_short_and_easy_exercises()
print("Short and easy exercises:")
for exercise in short_and_easy_exercises:
print('- ' + exercise.name)

exercises_within_duration = Exercise.get_exercises_within_duration(20, 40)
print(f"Exercises within 20 - 40 minutes:")
for exercise in exercises_within_duration:
print('- ' + exercise.name)

exercises_with_difficulty_and_repetitions = Exercise.get_exercises_with_difficulty_and_repetitions(6, 15)
print(f"Exercises with difficulty 6+ and repetitions 15+:")
for exercise in exercises_with_difficulty_and_repetitions:
print('- ' + exercise.name)
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.contrib import admin

# Register your models here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
from decimal import Decimal

from django.db import models
from django.db.models import Count, Avg


class RealEstateListingManager(models.Manager):
def by_property_type(self, property_type: str):
return self.filter(property_type=property_type)

def in_price_range(self, min_price: Decimal, max_price: Decimal):
return self.filter(price__range=(min_price,max_price))

def with_bedrooms(self, bedrooms_count: int):
return self.filter(bedrooms=bedrooms_count)

def popular_locations(self):
return self.values('location').annotate(location_count=Count('id')).order_by('-location_count','location')[:2]


class VideoGameManager(models.Manager):
def games_by_genre(self, genre: str):
return self.filter(genre=genre)


def recently_released_games(self, year: int):
return self.filter(release_year__gte=year)


def highest_rated_game(self):
return self.all().order_by('-rating').first()


def lowest_rated_game(self):
return self.all().order_by('rating').first()


def average_rating(self):
return round(self.aggregate(avg_rating=Avg('rating'))['avg_rating'],1)



Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
# Generated by Django 5.0.4 on 2024-07-20 19:42

import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='BillingInfo',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('address', models.CharField(max_length=200)),
],
),
migrations.CreateModel(
name='Exercise',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('category', models.CharField(max_length=50)),
('difficulty_level', models.PositiveIntegerField()),
('duration_minutes', models.PositiveIntegerField()),
('repetitions', models.PositiveIntegerField()),
],
),
migrations.CreateModel(
name='Project',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('description', models.TextField()),
],
),
migrations.CreateModel(
name='RealEstateListing',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('property_type', models.CharField(choices=[('House', 'House'), ('Flat', 'Flat'), ('Villa', 'Villa'), ('Cottage', 'Cottage'), ('Studio', 'Studio')], max_length=100)),
('price', models.DecimalField(decimal_places=2, max_digits=10)),
('bedrooms', models.PositiveIntegerField()),
('location', models.CharField(max_length=100)),
],
),
migrations.CreateModel(
name='Task',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=200)),
('description', models.TextField()),
('priority', models.CharField(choices=[('Low', 'Low'), ('Medium', 'Medium'), ('High', 'High')], max_length=20)),
('is_completed', models.BooleanField(default=False)),
('creation_date', models.DateField()),
('completion_date', models.DateField()),
],
),
migrations.CreateModel(
name='Technology',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('description', models.TextField()),
],
),
migrations.CreateModel(
name='VideoGame',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=100)),
('genre', models.CharField(choices=[('Action', 'Action'), ('RPG', 'RPG'), ('Adventure', 'Adventure'), ('Sports', 'Sports'), ('Strategy', 'Strategy')], max_length=100)),
('release_year', models.PositiveIntegerField()),
('rating', models.DecimalField(decimal_places=1, max_digits=2)),
],
),
migrations.CreateModel(
name='Invoice',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('invoice_number', models.CharField(max_length=20, unique=True)),
('billing_info', models.OneToOneField(on_delete=django.db.models.deletion.CASCADE, to='main_app.billinginfo')),
],
),
migrations.CreateModel(
name='Programmer',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('projects', models.ManyToManyField(related_name='programmers', to='main_app.project')),
],
),
migrations.AddField(
model_name='project',
name='technologies_used',
field=models.ManyToManyField(related_name='projects', to='main_app.technology'),
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# Generated by Django 5.0.4 on 2024-07-21 10:22

import main_app.validators
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0001_initial'),
]

operations = [
migrations.AlterField(
model_name='videogame',
name='rating',
field=models.DecimalField(decimal_places=1, max_digits=2, validators=[main_app.validators.InRangeValidator(0.0, 10.0, 'The rating must be between 0.0 and 10.0')]),
),
migrations.AlterField(
model_name='videogame',
name='release_year',
field=models.PositiveIntegerField(validators=[main_app.validators.InRangeValidator(1990, 2023, 'The release year must be between 1990 and 2023')]),
),
]
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
from datetime import timedelta

from django.db import models
from django.db.models import F, Q, Min, Max

from main_app.managers import RealEstateListingManager, VideoGameManager
from main_app.validators import InRangeValidator


# Create your models here.


class RealEstateListing(models.Model):
PROPERTY_TYPE_CHOICES = [
('House', 'House'),
('Flat', 'Flat'),
('Villa', 'Villa'),
('Cottage', 'Cottage'),
('Studio', 'Studio'),
]

property_type = models.CharField(max_length=100, choices=PROPERTY_TYPE_CHOICES)
price = models.DecimalField(max_digits=10, decimal_places=2)
bedrooms = models.PositiveIntegerField()
location = models.CharField(max_length=100)

objects = RealEstateListingManager()


class VideoGame(models.Model):
GENRE_CHOICES = [
('Action', 'Action'),
('RPG', 'RPG'),
('Adventure', 'Adventure'),
('Sports', 'Sports'),
('Strategy', 'Strategy'),
]

title = models.CharField(max_length=100)
genre = models.CharField(max_length=100, choices=GENRE_CHOICES)
release_year = models.PositiveIntegerField(validators=[InRangeValidator(1990,2023, "The release year must be between 1990 and 2023")])
rating = models.DecimalField(max_digits=2,decimal_places=1, validators=[InRangeValidator(0.0,10.0,"The rating must be between 0.0 and 10.0")])

def __str__(self):
return self.title

objects = VideoGameManager()


class BillingInfo(models.Model):
address = models.CharField(max_length=200)


class Invoice(models.Model):
invoice_number = models.CharField(max_length=20, unique=True)
billing_info = models.OneToOneField(BillingInfo, on_delete=models.CASCADE)

@classmethod
def get_invoices_with_prefix(cls, prefix: str):
return cls.objects.filter(invoice_number__startswith=prefix)

@classmethod
def get_invoices_sorted_by_number(cls):
return cls.objects.all().order_by('invoice_number')

@classmethod
def get_invoice_with_billing_info(cls, invoice_number: str):
return cls.objects.get(invoice_number=invoice_number)




class Technology(models.Model):
name = models.CharField(max_length=100)
description = models.TextField()


class Project(models.Model):
name = models.CharField(max_length=100)
description = models.TextField()
technologies_used = models.ManyToManyField(Technology, related_name='projects')

def get_programmers_with_technologies(self):
return self.programmers.prefetch_related('projects__technologies_used')


class Programmer(models.Model):
name = models.CharField(max_length=100)
projects = models.ManyToManyField(Project, related_name='programmers')

def get_projects_with_technologies(self):
return self.projects.prefetch_related('technologies_used')


class Task(models.Model):
PRIORITIES = (
('Low', 'Low'),
('Medium', 'Medium'),
('High', 'High')
)

title = models.CharField(max_length=200)
description = models.TextField()
priority = models.CharField(max_length=20, choices=PRIORITIES)
is_completed = models.BooleanField(default=False)
creation_date = models.DateField()
completion_date = models.DateField()

@classmethod
def ongoing_high_priority_tasks(cls):
return cls.objects.filter(priority='High', is_completed=False, completion_date__gt=F('creation_date'))

@classmethod
def completed_mid_priority_tasks(cls):
return cls.objects.filter(priority='Medium', is_completed=True)

@classmethod
def search_tasks(cls, query: str):
return cls.objects.filter((Q(title__icontains=query) | Q(description__icontains=query)))

@classmethod
def recent_completed_tasks(cls, days: int):
return cls.objects.filter(is_completed=True, completion_date__gte=F('creation_date') - timedelta(days=days))




class Exercise(models.Model):
name = models.CharField(max_length=100)
category = models.CharField(max_length=50)
difficulty_level = models.PositiveIntegerField()
duration_minutes = models.PositiveIntegerField()
repetitions = models.PositiveIntegerField()


@classmethod
def get_long_and_hard_exercises(cls):
return cls.objects.filter(duration_minutes__gt=30, difficulty_level__gte=10)

@classmethod
def get_short_and_easy_exercises(cls):
return cls.objects.filter(duration_minutes__lt=15, difficulty_level__lt=5)

@classmethod
def get_exercises_within_duration(cls, min_duration: int, max_duration: int):
return cls.objects.filter(duration_minutes__gte=min_duration, duration_minutes__lte=max_duration)

@classmethod
def get_exercises_with_difficulty_and_repetitions(cls, min_difficulty: int, min_repetitions: int):
return cls.objects.filter((Q(difficulty_level__gte=min_difficulty) & Q(repetitions__gte=min_repetitions)))

Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
from decimal import Decimal

from django.core.exceptions import ValidationError
from django.core.validators import BaseValidator


class InRangeValidator(BaseValidator):

def __init__(self, min_value, max_value, message=None):
super().__init__(None, message)
self.min_value = min_value
self.max_value = max_value

def __call__(self, value):
if not self.min_value <= value <= self.max_value:
raise ValidationError(self.message)
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
22 changes: 22 additions & 0 deletions DataBases/PythonORM/advanced_queries_in_django_exercise/manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
Original file line number Diff line number Diff line change
@@ -0,0 +1,158 @@
"""
Django settings for orm_skeleton project.
Generated by 'django-admin startproject' using Django 4.2.4.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/topics/settings/
For the full list of settings and their values, see
https://docs.djangoproject.com/en/4.2/ref/settings/
"""

from pathlib import Path

# 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/4.2/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = 'django-insecure-cd%2g!p_@ut(kc8)%bd9_*@)i@kff^orkvy=!c#i!l+ak98)%0'

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'main_app',
]

MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'orm_skeleton.urls'

TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates']
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]

WSGI_APPLICATION = 'orm_skeleton.wsgi.application'


# Database
# https://docs.djangoproject.com/en/4.2/ref/settings/#databases

# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': BASE_DIR / 'db.sqlite3',
# }
# }

DATABASES = {
"default": {
"ENGINE": "django.db.backends.postgresql",
"NAME": "advanced_queries_in_django_exercise",
"USER": "postgres-user",
"PASSWORD": "password",
"HOST": "localhost",
"PORT": "5432",
}
}



# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
},
]


# Internationalization
# https://docs.djangoproject.com/en/4.2/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_TZ = True

LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'handlers': {
'console': {
'class': 'logging.StreamHandler',
},
},
'root': {
'handlers': ['console'],
'level': 'DEBUG', # Other levels CRITICAL, ERROR, WARNING, INFO, DEBUG
},
'loggers': {
'django.db.backends': { # responsible for the sql logs
'handlers': ['console'],
'level': 'DEBUG',
'propagate': False,
},
},
}


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/4.2/howto/static-files/

STATIC_URL = 'static/'

# Default primary key field type
# https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
URL configuration for orm_skeleton project.
The `urlpatterns` list routes URLs to views. For more information please see:
https://docs.djangoproject.com/en/4.2/topics/http/urls/
Examples:
Function views
1. Add an import: from my_app import views
2. Add a URL to urlpatterns: path('', views.home, name='home')
Class-based views
1. Add an import: from other_app.views import Home
2. Add a URL to urlpatterns: path('', Home.as_view(), name='home')
Including another URLconf
1. Import the include() function: from django.urls import include, path
2. Add a URL to urlpatterns: path('blog/', include('blog.urls'))
"""
from django.contrib import admin
from django.urls import path

urlpatterns = [
path('admin/', admin.site.urls),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
WSGI config for orm_skeleton project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/wsgi/
"""

import os

from django.core.wsgi import get_wsgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_wsgi_application()
Binary file not shown.
104 changes: 104 additions & 0 deletions DataBases/PythonORM/advanced_queries_in_django_lab/caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
import os
from decimal import Decimal

import django
from django.db.models import Sum, F, Q

# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models
from main_app.models import Product, Category, Customer, Order, OrderProduct


# Create and run queries
def add_records_to_database():
# Categories
food_category = Category.objects.create(name='Food')
drinks_category = (Category.objects.create(name='Drinks'))

# Food
product1 = Product.objects.create(name='Pizza', description='Delicious pizza with toppings', price=10.99, category=food_category, is_available=False)
product2 = Product.objects.create(name='Burger', description='Classic burger with cheese and fries', price=7.99, category=food_category, is_available=False)
product3 = Product.objects.create(name='Apples', description='A bag of juicy red apples', price=3.99, category=food_category, is_available=True)
product4 = Product.objects.create(name='Bread', description='A freshly baked loaf of bread', price=2.49, category=food_category, is_available=True)
product5 = Product.objects.create(name='Pasta and Sauce Bundle', description='Package containing pasta and a jar of pasta sauce', price=6.99, category=food_category, is_available=False)
product6 = Product.objects.create(name='Tomatoes', description='A bundle of ripe, red tomatoes', price=2.99, category=food_category, is_available=True)
product7 = Product.objects.create(name='Carton of Eggs', description='A carton containing a dozen fresh eggs', price=3.49, category=food_category, is_available=True)
product8 = Product.objects.create(name='Cheddar Cheese', description='A block of aged cheddar cheese', price=7.99, category=food_category, is_available=False)
product9 = Product.objects.create(name='Milk', description='A gallon of fresh cow milk', price=3.49, category=food_category, is_available=True)

# Drinks
product10 = Product.objects.create(name='Coca Cola', description='Refreshing cola drink', price=1.99, category=drinks_category, is_available=True)
product11 = Product.objects.create(name='Orange Juice', description='Freshly squeezed orange juice', price=2.49, category=drinks_category, is_available=False)
product12 = Product.objects.create(name='Bottled Water', description='A 12-pack of purified bottled water', price=4.99, category=drinks_category, is_available=True)
product13 = Product.objects.create(name='Orange Soda', description='A 6-pack of carbonated orange soda', price=5.49, category=drinks_category, is_available=True)
product14 = Product.objects.create(name='Bottled Green Tea', description='A bottled green tea', price=3.99, category=drinks_category, is_available=False)
product15 = Product.objects.create(name='Beer', description='A bottled craft beer', price=5.49, category=drinks_category, is_available=True)

# Customers
customer1 = Customer.objects.create(username='john_doe')
customer2 = Customer.objects.create(username='alex_alex')
customer3 = Customer.objects.create(username='peter132')
customer4 = Customer.objects.create(username='k.k.')
customer5 = Customer.objects.create(username='peter_smith')

# Orders
order1 = Order.objects.create(customer=customer1)
order_product1 = OrderProduct.objects.create(order=order1, product=product3, quantity=2)
order_product2 = OrderProduct.objects.create(order=order1, product=product6, quantity=1)
order_product3 = OrderProduct.objects.create(order=order1, product=product7, quantity=5)
order_product4 = OrderProduct.objects.create(order=order1, product=product13, quantity=1)

order2 = Order.objects.create(customer=customer3)
order_product5 = OrderProduct.objects.create(order=order2, product=product3, quantity=2)
order_product6 = OrderProduct.objects.create(order=order2, product=product9, quantity=1)

order3 = Order.objects.create(customer=customer1)
order_product5 = OrderProduct.objects.create(order=order3, product=product12, quantity=4)
order_product6 = OrderProduct.objects.create(order=order3, product=product7, quantity=3)
return "All data entered!"


# Run and print your queries
# print(add_records_to_database())

def product_quantity_ordered():
return '\n'.join(f'Quantity ordered of {product.name}: {product.total_ordered_quantity}' for product in Product.objects.annotate(total_ordered_quantity = Sum('orderproduct__quantity')).exclude(total_ordered_quantity=None).order_by('-total_ordered_quantity'))


def ordered_products_per_customer():
result = []
for order in Order.objects.prefetch_related('orderproduct_set__product__category').order_by('id'):
result.append(f'Order ID: {order.id}, Customer: {order.customer.username}')
for product in order.orderproduct_set.all():
result.append(f'- Product: {product.product.name}, Category: {product.product.category.name}')
return '\n'.join(result)


def filter_products():
return '\n'.join(
f'{product.name}: {product.price}lv.' for product in
Product.objects.filter(Q(is_available=True) & Q(price__gt=3.00)).order_by('-price','name')
)


def give_discount():
Product.objects.filter(is_available=True, price__gt=3.00).update(price=(F('price') * 0.70))
return '\n'.join(
f'{product.name}: {product.price}lv.' for product in \
Product.objects.filter(is_available=True).order_by('-price', 'name'))






if __name__ == '__main__':
Product.objects.all().delete()
Order.objects.all().delete()
Customer.objects.all().delete()
Category.objects.all().delete()
add_records_to_database()
print(give_discount())
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.contrib import admin

# Register your models here.
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from django.db import models


class ProductManager(models.Manager):

def available_products(self):
return self.filter(is_available=True)

def available_products_in_category(self, category_name: str):
return self.filter(category__name=category_name, is_available=True)

Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
# Generated by Django 5.0.4 on 2024-07-20 13:09

import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='Category',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
],
),
migrations.CreateModel(
name='Customer',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('username', models.CharField(max_length=50, unique=True)),
],
),
migrations.CreateModel(
name='Order',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('customer', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.customer')),
],
),
migrations.CreateModel(
name='Product',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('description', models.TextField(blank=True, null=True)),
('price', models.DecimalField(decimal_places=2, max_digits=10)),
('is_available', models.BooleanField(default=True)),
('category', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.category')),
],
),
migrations.CreateModel(
name='OrderProduct',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('quantity', models.PositiveIntegerField()),
('order', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.order')),
('product', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.product')),
],
),
migrations.AddField(
model_name='order',
name='products',
field=models.ManyToManyField(through='main_app.OrderProduct', to='main_app.product'),
),
]
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
from django.db import models

from main_app.managers import ProductManager


class Category(models.Model):
name = models.CharField(max_length=100)


class Product(models.Model):
name = models.CharField(max_length=100)
description = models.TextField(null=True, blank=True)
price = models.DecimalField(max_digits=10, decimal_places=2)
category = models.ForeignKey(Category, on_delete=models.CASCADE)
is_available = models.BooleanField(default=True)

def __str__(self):
return f"{self.category.name}: {self.name}"

objects = ProductManager()


class Customer(models.Model):
username = models.CharField(max_length=50, unique=True)


class Order(models.Model):
customer = models.ForeignKey(Customer, on_delete=models.CASCADE)
products = models.ManyToManyField(Product, through='OrderProduct')


class OrderProduct(models.Model):
order = models.ForeignKey(Order, on_delete=models.CASCADE)
product = models.ForeignKey(Product, on_delete=models.CASCADE)
quantity = models.PositiveIntegerField()
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
22 changes: 22 additions & 0 deletions DataBases/PythonORM/advanced_queries_in_django_lab/manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
"""
Django settings for orm_skeleton project.
Generated by 'django-admin startproject' using Django 4.2.4.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/topics/settings/
For the full list of settings and their values, see
https://docs.djangoproject.com/en/4.2/ref/settings/
"""

from pathlib import Path

# 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/4.2/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = 'django-insecure-cd%2g!p_@ut(kc8)%bd9_*@)i@kff^orkvy=!c#i!l+ak98)%0'

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'main_app',
]

MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'orm_skeleton.urls'

TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates']
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]

WSGI_APPLICATION = 'orm_skeleton.wsgi.application'


# Database
# https://docs.djangoproject.com/en/4.2/ref/settings/#databases

# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': BASE_DIR / 'db.sqlite3',
# }
# }

DATABASES = {
"default": {
"ENGINE": "django.db.backends.postgresql",
"NAME": "advanced_queries_in_django_lab",
"USER": "postgres-user",
"PASSWORD": "password",
"HOST": "localhost",
"PORT": "5432",
}
}


# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
},
]


# Internationalization
# https://docs.djangoproject.com/en/4.2/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_TZ = True


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/4.2/howto/static-files/

STATIC_URL = 'static/'

# Default primary key field type
# https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
URL configuration for orm_skeleton project.
The `urlpatterns` list routes URLs to views. For more information please see:
https://docs.djangoproject.com/en/4.2/topics/http/urls/
Examples:
Function views
1. Add an import: from my_app import views
2. Add a URL to urlpatterns: path('', views.home, name='home')
Class-based views
1. Add an import: from other_app.views import Home
2. Add a URL to urlpatterns: path('', Home.as_view(), name='home')
Including another URLconf
1. Import the include() function: from django.urls import include, path
2. Add a URL to urlpatterns: path('blog/', include('blog.urls'))
"""
from django.contrib import admin
from django.urls import path

urlpatterns = [
path('admin/', admin.site.urls),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
WSGI config for orm_skeleton project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/wsgi/
"""

import os

from django.core.wsgi import get_wsgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_wsgi_application()
Binary file not shown.
57 changes: 57 additions & 0 deletions DataBases/PythonORM/advanced_queries_in_django_lab/test_caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
from django.test import TestCase
from caller import give_discount
from main_app.models import Category, Product, Customer, Order, OrderProduct

class OrderedProductsPerCustomerTestCase(TestCase):
def setUp(self):
# Categories
food_category = Category.objects.create(name='Food')
drinks_category = (Category.objects.create(name='Drinks'))

# Food
product1 = Product.objects.create(name='Pizza', description='Delicious pizza with toppings', price=10.99,
category=food_category, is_available=False)
product2 = Product.objects.create(name='Burger', description='Classic burger with cheese and fries', price=7.99,
category=food_category, is_available=False)
product3 = Product.objects.create(name='Apples', description='A bag of juicy red apples', price=3.99,
category=food_category, is_available=True)
product4 = Product.objects.create(name='Bread', description='A freshly baked loaf of bread', price=2.49,
category=food_category, is_available=True)
product5 = Product.objects.create(name='Pasta and Sauce Bundle',
description='Package containing pasta and a jar of pasta sauce', price=6.99,
category=food_category, is_available=False)
product6 = Product.objects.create(name='Tomatoes', description='A bundle of ripe, red tomatoes', price=2.99,
category=food_category, is_available=True)
product7 = Product.objects.create(name='Carton of Eggs', description='A carton containing a dozen fresh eggs',
price=3.49, category=food_category, is_available=True)
product8 = Product.objects.create(name='Cheddar Cheese', description='A block of aged cheddar cheese',
price=7.99, category=food_category, is_available=False)
product9 = Product.objects.create(name='Milk', description='A gallon of fresh cow milk', price=3.49,
category=food_category, is_available=True)

# Drinks
product10 = Product.objects.create(name='Coca Cola', description='Refreshing cola drink', price=1.99,
category=drinks_category, is_available=True)
product11 = Product.objects.create(name='Orange Juice', description='Freshly squeezed orange juice', price=2.49,
category=drinks_category, is_available=False)
product12 = Product.objects.create(name='Bottled Water', description='A 12-pack of purified bottled water',
price=4.99, category=drinks_category, is_available=True)
product13 = Product.objects.create(name='Orange Soda', description='A 6-pack of carbonated orange soda',
price=5.49, category=drinks_category, is_available=True)
product14 = Product.objects.create(name='Bottled Green Tea', description='A bottled green tea', price=3.99,
category=drinks_category, is_available=False)
product15 = Product.objects.create(name='Beer', description='A bottled craft beer', price=5.49,
category=drinks_category, is_available=True)


def test_practice_test(self):
result = give_discount()
self.assertEqual(result.strip(), """Beer: 3.84lv.
Orange Soda: 3.84lv.
Bottled Water: 3.49lv.
Tomatoes: 2.99lv.
Apples: 2.79lv.
Bread: 2.49lv.
Carton of Eggs: 2.44lv.
Milk: 2.44lv.
Coca Cola: 1.99lv.""")
61 changes: 61 additions & 0 deletions DataBases/PythonORM/exam_prep_I/caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
import os
import django
from django.db.models import Q, Count, Avg, F

# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models here
from main_app.models import Director, Actor, Movie


# Create queries within functions
def get_directors(search_name=None, search_nationality=None):
search = dict(filter(lambda x: x[1],{
"full_name__icontains": search_name,
"nationality__icontains": search_nationality
}.items()))
return '\n'.join(f"Director: {d.full_name}, nationality: {d.nationality}, experience: {d.years_of_experience}" for d in Director.objects.filter(**search).order_by('full_name')) or ""




def get_top_director():
best_director = Director.objects.get_directors_by_movies_count().first()
return f"Top Director: {best_director.full_name}, movies: {best_director.movies_count}." if best_director else ""


def get_top_actor():
top_actor = Actor.objects.prefetch_related('movies').annotate(movies_starred=Count('movies')).annotate(average_rating=Avg('movies__rating')).order_by('-movies_starred', "full_name").first()
return f"Top Actor: {top_actor.full_name}, starring in movies: {', '.join(m.title for m in top_actor.movies.all())}, movies average rating: {top_actor.average_rating:.1f}" if top_actor and top_actor.movies.count() else ""



def get_actors_by_movies_count():
top_actors = Actor.objects.annotate(count_participations=Count('movie')).filter(count_participations__gt=0).order_by('-count_participations', 'full_name')[:3]
return '\n'.join(f"{a.full_name}, participated in {a.count_participations} movies" for a in top_actors) if top_actors else ""


def get_top_rated_awarded_movie():
top_movie = Movie.objects.select_related('starring_actor').prefetch_related("actors").filter(is_awarded=True).order_by('-rating','title').first()
return f"Top rated awarded movie: {top_movie.title}, rating: {top_movie.rating:.1f}. Starring actor: {top_movie.starring_actor.full_name if top_movie.starring_actor else 'N/A'}. Cast: {', '.join(a.full_name for a in top_movie.actors.all().order_by('full_name'))}." if top_movie else ""


def increase_rating():
updated = Movie.objects.filter(is_classic=True, rating__lte=9.9).update(rating=F('rating') + 0.1)
return f"Rating increased for {updated} movies." if updated else "No ratings increased."





if __name__ == '__main__':
pass
# print(Director.objects.get_directors_by_movies_count())
# print(get_directors(None, 'zear'))
# print(get_top_director())
# print(get_top_actor())
# print(get_actors_by_movies_count())
# print(get_top_rated_awarded_movie())
print(increase_rating())
Empty file.
30 changes: 30 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/admin.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
from django.contrib import admin

from main_app.models import Director, Actor, Movie


# Register your models here.

@admin.register(Director)
class DirectorAdmin(admin.ModelAdmin):
list_display = ['full_name', 'birth_date', 'nationality']
list_filter = ['years_of_experience' ]
search_fields = ['full_name', 'nationality' ]



@admin.register(Actor)
class ActorAdmin(admin.ModelAdmin):
list_display = ['full_name', 'birth_date', 'nationality']
list_filter = ['is_awarded']
search_fields = ['full_name']
readonly_fields = ['last_updated']


@admin.register(Movie)
class MovieAdmin(admin.ModelAdmin):
list_display = ['title', 'storyline', 'rating', 'director']
list_filter = ['is_awarded', 'is_classic', 'genre']
search_fields = ['title' , 'director__full_name']
readonly_fields = ['last_updated']
search_help_text = 'Search by movie\'s title or director\'s name'
6 changes: 6 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/apps.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
7 changes: 7 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/managers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
from django.db import models
from django.db.models import Count

class DirectorManager(models.Manager):

def get_directors_by_movies_count(self):
return self.all().annotate(movies_count=Count('movie')).order_by('-movies_count', 'full_name')
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
# Generated by Django 5.0.4 on 2024-08-02 12:39

import django.core.validators
import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='Actor',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('full_name', models.CharField(max_length=120, validators=[django.core.validators.MinLengthValidator(2)])),
('birth_date', models.DateField(default='1900-01-01')),
('nationality', models.CharField(default='Unknown', max_length=50)),
('is_awarded', models.BooleanField(default=False)),
('last_updated', models.DateTimeField(auto_now=True)),
],
),
migrations.CreateModel(
name='Director',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('full_name', models.CharField(max_length=120, validators=[django.core.validators.MinLengthValidator(2)])),
('birth_date', models.DateField(default='1900-01-01')),
('nationality', models.CharField(default='Unknown', max_length=50)),
('years_of_experience', models.SmallIntegerField(validators=[django.core.validators.MinValueValidator(0)])),
],
),
migrations.CreateModel(
name='Movie',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('title', models.CharField(max_length=150, validators=[django.core.validators.MinLengthValidator(5)])),
('release_date', models.DateField()),
('storyline', models.TextField(blank=True, null=True)),
('genre', models.CharField(choices=[('Action', 'Action'), ('Comedy', 'Comedy'), ('Drama', 'Drama'), ('Other', 'Other')], default='Other', max_length=6)),
('rating', models.DecimalField(decimal_places=1, default=0.0, max_digits=3, validators=[django.core.validators.MinValueValidator(0.0), django.core.validators.MaxValueValidator(10.0)])),
('is_classic', models.BooleanField(default=False)),
('is_awarded', models.BooleanField(default=False)),
('last_updated', models.DateTimeField(auto_now=True)),
('actors', models.ManyToManyField(to='main_app.actor')),
('director', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.director')),
('starring_actor', models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, related_name='movies', to='main_app.actor')),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# Generated by Django 5.0.4 on 2024-08-02 12:42

import django.core.validators
from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('main_app', '0001_initial'),
]

operations = [
migrations.AlterField(
model_name='director',
name='years_of_experience',
field=models.SmallIntegerField(default=0, validators=[django.core.validators.MinValueValidator(0)]),
),
]
Empty file.
54 changes: 54 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
from django.core.validators import MinLengthValidator, MinValueValidator, MaxValueValidator
from django.db import models

from main_app.managers import DirectorManager


# Create your models here.

class Director(models.Model):
full_name = models.CharField(max_length=120, validators=[MinLengthValidator(2)])
birth_date = models.DateField(default='1900-01-01')
nationality = models.CharField(max_length=50, default='Unknown')
years_of_experience = models.SmallIntegerField(validators=[MinValueValidator(0)], default=0)

def __str__(self):
return self.full_name

objects = DirectorManager()



class Actor(models.Model):
full_name = models.CharField(max_length=120, validators=[MinLengthValidator(2)])
birth_date = models.DateField(default='1900-01-01')
nationality = models.CharField(max_length=50, default='Unknown')
is_awarded = models.BooleanField(default=False)
last_updated = models.DateTimeField(auto_now=True)

def __str__(self):
return self.full_name


class Movie(models.Model):

class GenreChoices(models.TextChoices):
ACTION = 'Action','Action'
COMEDY = 'Comedy','Comedy'
DRAMA = 'Drama','Drama'
OTHER = 'Other','Other'

title = models.CharField(max_length=150, validators=[MinLengthValidator(5)])
release_date = models.DateField()
storyline = models.TextField(blank=True, null=True)
genre = models.CharField(max_length=6, default='Other', choices=GenreChoices)
rating = models.DecimalField(max_digits=3, decimal_places=1, validators=[MinValueValidator(0.0), MaxValueValidator(10.0)], default=0.0)
is_classic = models.BooleanField(default=False)
is_awarded = models.BooleanField(default=False)
last_updated = models.DateTimeField(auto_now=True)
director = models.ForeignKey(to='Director', on_delete=models.CASCADE)
starring_actor = models.ForeignKey(null=True, blank=True, to='Actor', on_delete=models.SET_NULL, related_name='movies')
actors = models.ManyToManyField(to='Actor')

def __str__(self):
return self.title
3 changes: 3 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/tests.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
3 changes: 3 additions & 0 deletions DataBases/PythonORM/exam_prep_I/main_app/views.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
22 changes: 22 additions & 0 deletions DataBases/PythonORM/exam_prep_I/manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
16 changes: 16 additions & 0 deletions DataBases/PythonORM/exam_prep_I/orm_skeleton/asgi.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
156 changes: 156 additions & 0 deletions DataBases/PythonORM/exam_prep_I/orm_skeleton/settings.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,156 @@
"""
Django settings for orm_skeleton project.
Generated by 'django-admin startproject' using Django 4.2.4.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/topics/settings/
For the full list of settings and their values, see
https://docs.djangoproject.com/en/4.2/ref/settings/
"""

from pathlib import Path

# 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/4.2/howto/deployment/checklist/

# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY = 'django-insecure-cd%2g!p_@ut(kc8)%bd9_*@)i@kff^orkvy=!c#i!l+ak98)%0'

# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'main_app',
]

MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'orm_skeleton.urls'

TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates']
,
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]

WSGI_APPLICATION = 'orm_skeleton.wsgi.application'


# Database
# https://docs.djangoproject.com/en/4.2/ref/settings/#databases

# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': BASE_DIR / 'db.sqlite3',
# }
# }

DATABASES = {
"default": {
"ENGINE": "django.db.backends.postgresql",
"NAME": "exam_prep_i",
"USER": "postgres-user",
"PASSWORD": "password",
"HOST": "localhost",
"PORT": "5432",
}
}

# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
{
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
},
{
'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
},
]


# Internationalization
# https://docs.djangoproject.com/en/4.2/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_TZ = True

LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'handlers': {
'console': {
'class': 'logging.StreamHandler',
},
},
'root': {
'handlers': ['console'],
'level': 'DEBUG', # Other levels CRITICAL, ERROR, WARNING, INFO, DEBUG
},
'loggers': {
'django.db.backends': { # responsible for the sql logs
'handlers': ['console'],
'level': 'DEBUG',
'propagate': False,
},
},
}


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/4.2/howto/static-files/

STATIC_URL = 'static/'

# Default primary key field type
# https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
22 changes: 22 additions & 0 deletions DataBases/PythonORM/exam_prep_I/orm_skeleton/urls.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
"""
URL configuration for orm_skeleton project.
The `urlpatterns` list routes URLs to views. For more information please see:
https://docs.djangoproject.com/en/4.2/topics/http/urls/
Examples:
Function views
1. Add an import: from my_app import views
2. Add a URL to urlpatterns: path('', views.home, name='home')
Class-based views
1. Add an import: from other_app.views import Home
2. Add a URL to urlpatterns: path('', Home.as_view(), name='home')
Including another URLconf
1. Import the include() function: from django.urls import include, path
2. Add a URL to urlpatterns: path('blog/', include('blog.urls'))
"""
from django.contrib import admin
from django.urls import path

urlpatterns = [
path('admin/', admin.site.urls),
]
16 changes: 16 additions & 0 deletions DataBases/PythonORM/exam_prep_I/orm_skeleton/wsgi.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
WSGI config for orm_skeleton project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/wsgi/
"""

import os

from django.core.wsgi import get_wsgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_wsgi_application()
Binary file added DataBases/PythonORM/exam_prep_I/requirements.txt
Binary file not shown.
67 changes: 67 additions & 0 deletions DataBases/PythonORM/exam_prep_II/caller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
import os
import django
from django.db.models import Q, Count, F, When, Case, Value

# Set up Django
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "orm_skeleton.settings")
django.setup()

# Import your models here

from main_app.models import Profile, Order, Product


# Create queries within functions

def get_profiles(search_string=None):
if search_string is None: return ""
profiles = Profile.objects.filter(Q(full_name__icontains=search_string) | Q(email__icontains=search_string) | Q(phone_number__icontains=search_string)).annotate(orders_count=Count('order')).order_by('full_name')
return '\n'.join(f'Profile: {p.full_name}, email: {p.email}, phone number: {p.phone_number}, orders: {p.orders_count}' for p in profiles) if len(profiles) else ""

def get_loyal_profiles():
profiles = Profile.objects.get_regular_customers()
return '\n'.join(f'Profile: {p.full_name}, orders: {p.order_count}' for p in profiles) if len(profiles) else ""

def get_last_sold_products():
order = Order.objects.prefetch_related('products').last()
return f"Last sold products: {', '.join(p.name for p in order.products.all().order_by('name'))}" if order else ""


def get_top_products():
recent_products = Product.objects.annotate(sales_count=Count('order')).filter(sales_count__gt=0).order_by('-sales_count','name')[:5]
result = "Top products:\n" +"\n".join(f"{p.name}, sold {p.sales_count} times" for p in recent_products)
return result if Order.objects.count() else ""


def apply_discounts():
orders_to_discount = Order.objects.annotate(product_count=Count('products')).filter(product_count__gt=2, is_completed=False).update(total_price=F('total_price') * 0.90)
return f"Discount applied to {orders_to_discount} orders."


def complete_order():
order = Order.objects.filter(is_completed=False).order_by('creation_date').first()
if not order:
return ""
order.products.update(
in_stock=F('in_stock') - 1,
is_available=Case(
When(in_stock__gt=1, then=Value(True)),
default=False
)
)

order.is_completed = True
order.save()
return "Order has been completed!"




if __name__ == "__main__":
# print(Profile.objects.get_regular_customers())
# print(get_profiles('the'))
# print(get_loyal_profiles())
# print(get_last_sold_products())
# print(get_top_products())
# print(apply_discounts())
print(complete_order())
Empty file.
25 changes: 25 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/admin.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
from django.contrib import admin

from main_app.models import Profile, Product, Order


# Register your models here.

@admin.register(Profile)
class ProfileAdmin(admin.ModelAdmin):
list_display = ['full_name', 'email', 'phone_number', 'is_active']
search_fields = ["full_name" , "email"]


@admin.register(Product)
class ProductAdmin(admin.ModelAdmin):
list_display = [ 'name', 'price', 'in_stock', 'is_available' ]
list_filter = [ 'is_available' ]
search_fields = [ 'name' ]


@admin.register(Order)
class OrderAdmin(admin.ModelAdmin):
list_display = ['profile', 'total_price', 'creation_date', 'is_completed']
list_filter = [ 'is_completed' ]
search_fields = [ 'profile__full_name' ]
6 changes: 6 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/apps.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
from django.apps import AppConfig


class MainAppConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
name = 'main_app'
8 changes: 8 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/managers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
from django.db import models
from django.db.models import Count


class ProfileManager(models.Manager):

def get_regular_customers(self):
return self.annotate(order_count=Count("order")).filter(order_count__gt=2).order_by('-order_count')
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
# Generated by Django 5.0.4 on 2024-07-29 11:56

import django.core.validators
import django.db.models.deletion
from django.db import migrations, models


class Migration(migrations.Migration):

initial = True

dependencies = [
]

operations = [
migrations.CreateModel(
name='Product',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('name', models.CharField(max_length=100)),
('description', models.TextField()),
('price', models.DecimalField(decimal_places=2, max_digits=10, validators=[django.core.validators.MinValueValidator(0.01)])),
('in_stock', models.PositiveIntegerField(validators=[django.core.validators.MinValueValidator(0)])),
('is_available', models.BooleanField(default=True)),
('creation_date', models.DateTimeField(auto_now_add=True)),
],
),
migrations.CreateModel(
name='Profile',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('full_name', models.CharField(max_length=100, validators=[django.core.validators.MinLengthValidator(2)])),
('email', models.EmailField(max_length=254)),
('phone_number', models.CharField(max_length=15)),
('address', models.TextField()),
('is_active', models.BooleanField(default=True)),
('creation_date', models.DateTimeField(auto_now_add=True)),
],
),
migrations.CreateModel(
name='Order',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('total_price', models.DecimalField(decimal_places=2, max_digits=10, validators=[django.core.validators.MinValueValidator(0.01)])),
('creation_date', models.DateTimeField(auto_now_add=True)),
('is_completed', models.BooleanField(default=False)),
('products', models.ManyToManyField(to='main_app.product')),
('profile', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='main_app.profile')),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# Generated by Django 5.0.4 on 2024-07-29 12:25

import django.db.models.manager
from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('main_app', '0001_initial'),
]

operations = [
migrations.AlterModelManagers(
name='profile',
managers=[
('objcets', django.db.models.manager.Manager()),
],
),
]
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# Generated by Django 5.0.4 on 2024-07-29 12:26

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('main_app', '0002_alter_profile_managers'),
]

operations = [
migrations.AlterModelManagers(
name='profile',
managers=[
],
),
]
Empty file.
45 changes: 45 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
from django.core.validators import MinLengthValidator, MinValueValidator
from django.db import models

from main_app.managers import ProfileManager


# Create your models here.

class Profile(models.Model):
full_name = models.CharField(max_length=100, validators=[MinLengthValidator(2)])
email = models.EmailField()
phone_number = models.CharField(max_length=15)
address = models.TextField()
is_active = models.BooleanField(default=True)
creation_date= models.DateTimeField(auto_now_add=True)

def __str__(self):
return self.full_name

objects = ProfileManager()



class Product(models.Model):
name = models.CharField(max_length=100)
description = models.TextField()
price = models.DecimalField(max_digits=10, decimal_places=2, validators=[MinValueValidator(0.01)])
in_stock = models.PositiveIntegerField(validators=[MinValueValidator(0)])
is_available = models.BooleanField(default=True)
creation_date = models.DateTimeField(auto_now_add=True)

def __str__(self):
return self.name



class Order(models.Model):
profile = models.ForeignKey(to='Profile', on_delete=models.CASCADE)
products = models.ManyToManyField(to='Product')
total_price = models.DecimalField(max_digits=10, decimal_places=2, validators=[MinValueValidator(0.01)])
creation_date = models.DateTimeField(auto_now_add=True)
is_completed = models.BooleanField(default=False)

def __str__(self):
return str(self.creation_date)
3 changes: 3 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/tests.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.test import TestCase

# Create your tests here.
3 changes: 3 additions & 0 deletions DataBases/PythonORM/exam_prep_II/main_app/views.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from django.shortcuts import render

# Create your views here.
22 changes: 22 additions & 0 deletions DataBases/PythonORM/exam_prep_II/manage.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env python
"""Django's command-line utility for administrative tasks."""
import os
import sys


def main():
"""Run administrative tasks."""
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')
try:
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc
execute_from_command_line(sys.argv)


if __name__ == '__main__':
main()
Empty file.
16 changes: 16 additions & 0 deletions DataBases/PythonORM/exam_prep_II/orm_skeleton/asgi.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
"""
ASGI config for orm_skeleton project.
It exposes the ASGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/4.2/howto/deployment/asgi/
"""

import os

from django.core.asgi import get_asgi_application

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'orm_skeleton.settings')

application = get_asgi_application()
Loading

0 comments on commit 93a83d1

Please sign in to comment.