I have two model Business and Category. I want to save Multiple categories in Business.
class Business(models.Model):
user = models.ForeignKey('User', on_delete=models.CASCADE)
business_name = models.CharField(max_length=100)
category = models.IntegerField()
keyword = models.CharField(max_length=100)
and Category Model Is Here
class Category(models.Model):
name = models.CharField(max_length=100)
slug = models.CharField(max_length=100)
Category Model is already filled with values.
you have two option for that 1) many to one, 2) many to many
1) many to one is ForeignKey to add in category model and link each category with business, in this you can identify which category is child of buisness, you can find more details in django document
class Category(models.Model):
name = models.CharField(max_length=100)
slug = models.CharField(max_length=100)
business = models.ForeignKey(Business, on_delete=models.CASCADE)
2) many to many is select multiple category in business, and you can access all thing in business model and in you write query on business model and access to also category for that you need write category before buisness, you can find more detail in django document
class Business(models.Model):
user = models.ForeignKey('User', on_delete=models.CASCADE)
business_name = models.CharField(max_length=100)
category = models.IntegerField()
keyword = models.CharField(max_length=100)
category= models.ManyToManyField(Category)
Related
views
company = Company.objects.get(id = company_id) # getting input from django urls (<int:company_id>)
vehicles = CompanyContainVehicles.objects.filter(company_id=company.id) # Give all rows having same id (company.id)
all_vehicles = Vehicle.objects.filter(companies=company) # Gives all row with id provide by company
all_vehicles_parts = VehiclePart.objects.filter(__________) # Not Working
models
class Company(models.Model):
name = models.CharField(max_length=255)
slug = models.SlugField(blank=True, null=True, unique=True)
description = models.TextField()
class Vehicle(models.Model):
vehicle_number = models.IntegerField()
name = models.CharField(max_length=255)
slug = models.SlugField(blank=True, null=True, unique=True)
companies = models.ManyToManyField(
Company,
through='CompanyVehicle',
related_name='companies'
)
class CompanyVehicle(models.Model):
company = models.ForeignKey(Company, on_delete=models.CASCADE)
vehicle = models.ForeignKey(Vehicle, on_delete=models.CASCADE)
created_at = models.DateTimeField(auto_now_add=True)
class VehiclePart(models.Model):
id = models.AutoField(primary_key=True)
vehicle = models.ForeignKey(Vehicle, on_delete=models.CASCADE)
type = models.ForeignKey(PartType, on_delete=models.CASCADE)
created_at = models.DateTimeField(auto_now_add=True, blank=True)
How do I get VehiclePart's with their Vehicle? (I think I will give all the data in a variable and we should divide it and add it with their Vehicle). Also, what can we do to access data if VehiclePart contains a child class named VehiclePartDetail?
I think I will give all the data in a variable and we should divide it and add with their Vehicle.
You don't have to. Django can read ForeignKey relations in reverse. You can query with:
qs = Vehicle.objects.prefetch_related('vehiclepart_set')
then you can enumerate over the queryset, and for each Vehicle object, access this with .vehiclepart_set.all(). For example:
for item in qs:
print(vehicle_name)
for part in item.vehiclepart_set.all():
print(part.id)
I have two models (Product & Category) which every product has a linked category.
I have installed DjangoFilterBackend which the hope of filtering on the category field to return a list of products in that category.
However, whenever I send the query in Postman. I receive the error Select a valid choice. That choice is not one of the available choices..
I have tried filtering on another field in my product model (name for an example) and that works fine. So i'm not sure if i'm missing something for category to work.
Product/View.py:
class ProductView(ListAPIView):
serializer_class = ProductSerializer
queryset = Product.objects.all()
filter_backends = [DjangoFilterBackend]
filterset_fields = ('category', 'name')
Products/Models.py:
class Product(models.Model):
name = models.CharField(max_length=250, unique=True, blank=False)
photo = models.ImageField(upload_to=product_photo_path)
category = models.ForeignKey(Category, on_delete=models.CASCADE)
quantity = models.IntegerField()
description = models.TextField(blank=False)
price = models.DecimalField(max_digits=6, decimal_places=2)
in_stock = models.BooleanField(default=False)
trending = models.BooleanField(default=False)
def __str__(self):
return self.name
Products/serializers.py
class ProductSerializer(serializers.ModelSerializer):
category = serializers.CharField(source='category.name', read_only=True)
class Meta:
model = Product
fields = ('category', 'name', 'photo', 'quantity', 'description', 'price', 'in_stock', 'trending')
The query I am using is a GET request to:
http://127.0.0.1:8000/api/products?category=xxxx - I am sending no payload. The response I am receiving is a `400 Bad Request` and the exact error is:
{
"category": [
"Select a valid choice. That choice is not one of the available choices."
]
}
Ah-ha!
I changed the model to:
class Product(models.Model):
name = models.CharField(max_length=250, unique=True, blank=False)
photo = models.ImageField(upload_to=product_photo_path)
**category = models.ForeignKey(Category, to_field='name', on_delete=models.CASCADE)**
quantity = models.IntegerField()
description = models.TextField(blank=False)
price = models.DecimalField(max_digits=6, decimal_places=2)
in_stock = models.BooleanField(default=False)
trending = models.BooleanField(default=False)
And now it works!
Well, I am not sure, but try to filter on field category_id, this field is created automatically for FK fields
Just in case somebody will ever need the answer, to be able to use the name of a foreign field to filter instead of the primary key use a double underscore i.e category__name in this case. Note that name in this case is the field of the foreign model that you want to filter with and you can replace it with your field accordingly.
In my project there is an Attraction model and an AttractionTag model related through a ForeignKey relationship. Every Attraction has the same set of AttractionTag, they differ only by the value field.
Now, I want to order Attractions based on the value field of a specific AttractionTag. For example, there is an AttractionTag named 'modern' for every attraction. I want to order Attractions based on modern AttractionTag value field.
I've tried
attractions.order_by('-attractiontag__value')
but this command order Attractions on AttractionTag in general, not based on a particular AttractionTag.
Here are the models
class Attraction (models.Model) :
city = models.ForeignKey(City, on_delete=models.CASCADE)
name=models.CharField(max_length=50, unique=True)
image = models.ImageField(upload_to=attractionImagePath, null=True, blank=False)
imageTop = models.ImageField(upload_to=attractionTopImagePath, null=True, blank=True)
pub_date = models.DateTimeField(auto_now_add=True)
class AttractionTag (models.Model):
attraction=models.ForeignKey(Attraction, on_delete=models.CASCADE)
name = models.CharField(max_length=50)
value=models.IntegerField(default=0)
How can I solve?
Thank you
Ok, I found a solution.
tags = AttractionTag.objects.filter(attraction__city=city)
tags = tags.filter(name='modern').order_by('-value')
attraction = [tag.attraction for tag in tags]
Should work
In Django there are field types called ForeignKey and OneToMany/OneToOne, I was wondering would I use ForeignKey or the relationship type as the field type in this scenario? User to Profile has been identified as OneToOne but I'm unsure about the others.
class Profile(models.Model):
user = models.OneToOneField(User, on_delete = models.CASCADE)
fullname = models.CharField(max_length=100)
dob = models.DateField()
address = models.TextField()
city = models.CharField(max_length=100)
profilephoto = models.ImageField(default='default_profile.jpg', upload_to='reviewApp/static/profile_images')
class Product(models.Model):
name = models.CharField(max_length=100)
brand = models.CharField(max_length=100)
cost = models.DecimalField(max_digits=8, decimal_places=2, default=0.00)
category = models.CharField(max_length=100)
releasedate = models.DateField()
description = models.TextField()
productphoto = models.ImageField(default='default_product.jpg', upload_to='reviewApp/static/product_images')
class Review(models.Model):
product = models.ForeignKey(Product)
profile = models.ForeignKey(Profile)
author = models.ForeignKey(User, on_delete=models.CASCADE)
rating = model.PositiveSmallIntegerField(default=1, validators = [MinValueValidator(1), MaxValueValidator(5)])
reviewtext = models.TextField()
postdate = models.DateTimeField(auto_now_add=True)
lastmodified = models.DateTimeField(auto_now=True)
So from what I see here, it seems to be good if the following is what you want:
User can have only one profile and one Profile is related to only one user.
a Profile can make multiple Review but a Review belongs to only one profile.
A Product can have multiple Review but a Review is specific to one Product.
Be carefull to define the on_delete argument for your foreign keys depending of what you want to keep in your database after a delete.
More info from the doc : https://docs.djangoproject.com/fr/2.2/ref/models/fields/#arguments
The use case of my application is I will have various fields to fill and among them one is Industry field and another is Segment Field for brand. The industry field is like category that brand falls into. So, if i choose the industry as Health Care for XYZ brand then the segment field should show the items like 'Ayurveda', 'Dental Clinics' (all health care related items). Basically, its like sub-category.
Here is a sample model
class Industry(models.Model):
name = models.CharField(max_length=150, blank=True, null=True)
class Meta:
verbose_name = 'Industry'
verbose_name_plural = 'Industries'
def __str__(self):
return self.name
class Segment(models.Model):
industry = models.ForeignKey(Industry, related_name='segment', on_delete=models.CASCADE)
name = models.CharField(max_length=150, blank=True, null=True)
class Meta:
verbose_name = 'Segment'
verbose_name_plural = 'Segments'
def __str__(self):
return f'{self.industry.name} - {self.name}'
class BusinessModel(models):
industry = models.ForeignKey(Industry, blank=False, null=False, related_name='industry', on_delete=models.CASCADE)
# segements = models.ForeignKey()
total_investment = models.CharField() # will be choice field
This is a simple model and I have not created Segment model as I am not sure how to approach to this problem. I am just curios to know, if for such case, do i have to something special in models.py or in the view side. Such type of things get arise during development phase, thus, I want to be clear on problem solving pattern in django.
UPDATE
https://www.franchisebazar.com/franchisor-registration here if you choose industry inside Business model section, the segment will be updated accordingly.
You can have a 3 model design like
class Industry(models.Model):
name = models.CharField(max_length=150, blank=True, null=True)
class Segment(models.Model):
name = models.CharField(max_length=150, blank=True, null=True)
class Mapping(models.Model):
industry = models.ForeignKey(Industry)
segment = models.ForeignKey(Segment)
You need to define relations between your models. You can find documentation about ManyToMany relation here which is suitable in your case.
you can use ChainedForeginKey.. Check the below links
customizing admin of django to have dependent select fields
https://django-smart-selects.readthedocs.io/en/latest/installation.html