django: getting foreign key information - django

I created a model with couple of classes and with foreign key and I was able to save it on the database.
I have the following models:
class Player_Bios(models.Model):
my_id = models.SlugField(unique=True)
player_id = models.IntegerField(max_length=50, unique=True)
name = models.CharField(max_length=50)
last = models.CharField(max_length=50)
middle = models.CharField(max_length=50, blank=True)
class BatStat (models.Model):
player_id = models.ForeignKey('Player_Bios')
team_id = models.ForeignKey('Team')
bat_stat_id = models.CharField(max_length=50, unique=True)
sport_code = models.CharField(max_length=50, blank=True)
ab = models.IntegerField(max_length=50, null=True)
class Team (models.Model):
team_id = models.IntegerField(max_length=50, unique=True)
team_short = models.CharField(max_length=50, blank=True)
team_full = models.CharField(max_length=50, blank=True)
When I save it to the database I can see that the team_id on the Team table is the same as the team_id on the BatStat table, but the player_id on the BatStat is different that the player_id on the Player_Bios table. This is how I save the data to the database:
p_id = Player_Bios.objects.get(player_id=st['player_id'])
t_id = Team.objects.get(team_id=st['team_id']) #I get the team_id from the Team Class
bat_id = str(st['season'])+ str(st['team_seq'])
bat_id = str(p_id.player_id) + bat_id
c = BatStat(player_id = p_id,team_id=t_id, bat_stat_id=bat_id, sport_code =st["sport_code"],ab=st['ab'])
c.save()
st['player_id'] is a dictionary. I did a print and it show the right player_id number

In BatStat you are storing the key to Player_Bios, which is not player_id
class Player_Bios(models.Model):
...
player_id = models.IntegerField(max_length=50, unique=True)
class BatStat (models.Model):
...
player_id = models.ForeignKey('Player_Bios')
I'm not sure why your team_id is the same, however, it seems like you already have the ids. You could avoid looking up the Player_Bios and Team by setting the id directly.
Django: Set foreign key using integer?
class Player_Bios(models.Model):
...
player_id = models.IntegerField(primary_key=True, max_length=50)
class Team (models.Model):
...
team_id = models.IntegerField(primary_key=True, max_length=50)
class BatStat (models.Model):
...
player = models.ForeignKey('Player_Bios') # notice i renamed this to not have '_id'
team = models.ForeignKey('Team') # notice i renamed this to not have '_id'
c = BatStat(bat_stat_id=bat_id,
sport_code =st["sport_code"],
ab=st['ab'])
c.player_id = st['player_id'], # notice that this has '_id'
c.team_id = st['team_id'], # notice this has '_id'
c.save()

Related

Filter related field Django orm shows multiple invalid results

Query
TechnicianAssignment.objects.filter(Q(slot__slot_date=curr_datetime.date())&Q(assigned_technician__attendance_Technician__attendance_status__in=['Rejected', 'Absent', 'Someone else reported', 'Present']))
Models in short:
**Table 1**:
class TechnicianTeam(models.Model):
id = models.AutoField(primary_key=True)
supervisor = models.ForeignKey('self', null=True, blank=True, related_name="TechnicianSupervisor", on_delete=models.DO_NOTHING)
customer_profile = models.ForeignKey('login.CustomerProfile',
related_name="technician_TeamUser", on_delete=models.DO_NOTHING)
class Meta:
db_table = "technician_team"
**Table2:**
class TechnicianAssignment(models.Model):
id = models.AutoField(primary_key=True)
slot = models.ForeignKey('technician_management.TechnicianSlot',
related_name="assignment_Slot", on_delete=models.DO_NOTHING)
assigned_technician = models.ForeignKey('technician_management.TechnicianTeam',
related_name="assignment_Technician", on_delete=models.DO_NOTHING)
class Meta:
db_table = "technician_assignment"
**Table3**
ATTENDANCE_CHOICES = [
('Rejected','Rejected'),
('Someone else reported','Someone else reported'),
('Absent','Absent'),
('Present','Present')
]
class TechnicianAttendance(models.Model):
id = models.AutoField(primary_key=True)
technician = models.ForeignKey('technician_management.TechnicianTeam',
related_name="attendance_Technician", on_delete=models.DO_NOTHING)
slot = models.ForeignKey('technician_management.TechnicianSlot',
related_name="attendance_Slot", on_delete=models.DO_NOTHING)
attendance_status = models.CharField(max_length=30, choices=ATTENDANCE_CHOICES, null=True)
class Meta:
db_table = "technician_attendance"
Question what is wrong with my query:
I need to filter out from TechnicianAssignment where in entries were "slot__slot_date" is current date and "__attendance_Technician__attendance_status__in" = ['Rejected', 'Absent', 'Someone else reported', 'Present']
there is only 1 entry in db with attendance status 'Present' but i am getting many output because of "__attendance_Technician__attendance_status__in" this filter.

django, travsersing multiple tables (models) in a filter

I have a functioning search function shown below, it works without issue. We are redesigning the system, the area_easting value now sits in its own table (model). To get to the area_easting he route is as follows: Trench.trench_id --> Context.context_id --> Sample.sample_id (I know this is non-standard notation).
So how would I traverse these joins? Something like:
qs = qs.filter(sample_id__context_id__trench_id__area_easting__icontains=easting_query)
Which returns Unsupported lookup 'context_id' for AutoField or join on the field not permitted.
from excavation.models import Trench, Context, Sample
from ceramic.models import Ceramic
...
def CeramicFliterView(request):
qs = Sample.objects.all()
easting_query = request.GET.get('area_easting')
if easting_query != '' and easting_query is not None:
qs = qs.filter(area_easting__icontains=easting_query)
...
Models.py
class Trench(models.Model):
trench_id = models.AutoField(primary_key=True)
name = models.CharField(max_length=500, default='', blank=True, null=True)
area_easting = models.IntegerField()
area_northing = models.IntegerField()
...
class Context(models.Model):
context_id = models.AutoField(primary_key=True)
trench_id = models.ForeignKey(Trench, db_column='trench_id', on_delete = models.PROTECT)
...
class Sample(models.Model):
sample_id = models.AutoField(primary_key=True)
context_id = models.ForeignKey(Context, db_column='context_id', on_delete = models.PROTECT)
...
class Ceramic(models.Model):
ceramic_id = models.AutoField(primary_key=True)
sample_id = models.ForeignKey(Sample, db_column='sample_id', on_delete = models.PROTECT)

How to Query for Many to Many Fields in Django

I have these classes -
class DocumentType(models.Model):
type_id = models.AutoField(primary_key=True)
name = models.CharField('type name', max_length=200)
class MetaData(models.Model):
metadata_id = models.AutoField(primary_key = True)
name = models.CharField('metadata name', max_length=200, unique=True)
description = models.TextField('description')
class DocumentTypeMetaData(models.Model):
documentType_id = models.ManyToManyField(DocumentType,)
metadata_id = models.ManyToManyField(MetaData,)
required = models.BooleanField(default=False)
For example, a DocumentType value of 'Photo' would have Required Metadata of 'Decade' and 'Orientation'.
In the DocumentTypeMetaData class I would like to have a def __str__(self) function that returns something like the following in the admin page -
Photo: (Decade, Photo Type) required
The format is not critical, I just want to know which metadata is required. Currently, all that is displayed is
DocumentTypeMetaData object
on the admin page.
I am struggling with how to write the queries for this function.
Thanks!
Mark
These relationships are not right. The many-to-many relationship is between DocumentType and MetaData; DocumentTypeMetaData is the through table. So:
class DocumentType(models.Model):
type_id = models.AutoField(primary_key=True)
name = models.CharField('type name', max_length=200)
metadata = models.ManyToManyField('MetaData', through='DocumentTypeMetaData')
class MetaData(models.Model):
metadata_id = models.AutoField(primary_key = True)
name = models.CharField('metadata name', max_length=200, unique=True)
description = models.TextField('description')
class DocumentTypeMetaData(models.Model):
document_type = models.ForeignKey(DocumentType)
metadata = models.ForeignKey(MetaData)
required = models.BooleanField(default=False)
def __str__(self):
return '{} {} {}'.format(self.document_type, self.metadata, self.required)

Django Nonetype object has no attribute 'id'

I want create product element and redirect to him page
def newprodcreate(request, c_id):
if models.company.objects.get(email = request.user.username).id == int(c_id):
name = request.POST['newprodname']
comp = models.company.objects.get(id = int(c_id))
prod = models.product()
prod.name = name
prod.comp_id = int(c_id)
prod.address = comp.address
prod.lat = comp.lat
prod.lng = comp.lng
prod.phone = comp.phone
prod.cur_id = 2
prod.save()
return HttpResponseRedirect("/p/" + str(prod.id))
the element created in database, but prod.id is Null
model:
class product(models.Model):
class Meta:
db_table = "product"
id = models.IntegerField(primary_key=True)
crdate = models.DateTimeField(default = datetime.now())
comp_id = models.IntegerField()
categ = models.CharField(max_length=200, default="")
img = models.FileField(upload_to=MEDIA_ROOT +"/product/", max_length=200)
name = models.CharField(max_length=200)...
Dear michael in django ORM for creating autho field or serial field which used for id primary key or etc we use Autofield instead of integer field .
id = models.AutoField(primary_key=True)
your model in corrected state:
class product(models.Model):
class Meta:
db_table = "product"
id = models.AutoField(primary_key=True)
crdate = models.DateTimeField(default =
datetime.now())
comp_id = models.IntegerField()
categ = models.CharField(max_length=200, default="")
img = models.FileField(upload_to=MEDIA_ROOT. +"/product/", max_length=200)
name = models.CharField(max_length=200)...
For django models There will be a default field with name "id" which is auto increment field. you have override that id with IntegerField that is id = models.IntegerField(primary_key=True)
So you have to provide id explicitly every time when you create product object
Better solution is to change id IntegerField to AutoField
id = models.AutoField(primary_key=True)
Then your id will be created automatically no need to pass id every time you create new object.

Filtering on foreign key table's attribute

These are my relevant models..
class Books(models.Model):
name = models.CharField(max_length=120)
author = models.CharField(max_length=120)
edition = models.CharField(max_length=120)
class Meta:
unique_together = ('name', 'edition',)
def __str__(self):
return self.name
class Items(models.Model):
book = models.ForeignKey(Books)
seller = models.ForeignKey(User,related_name = 'item_seller')
buyer = models.ForeignKey(User, related_name = 'item_buyer', null=True,blank= True)
requestee = models.ManyToManyField(User,related_name = 'item_requestee',blank= True)
cost_price = models.DecimalField(max_digits=8, decimal_places=2)
sale_price = models.DecimalField(max_digits=8, decimal_places=2)
sold = models.BooleanField(default=False)
date_added = models.DateTimeField(auto_now=False, auto_now_add=True)
def __str__(self):
return self.book.name
And this is the part in view fuction where I am trying to filter on foreign key table's attribute
book_item = Items.objects.filter(book__name==q)
Where q is a string a get from user.
But I am getting error - book__name not defined. What am I doing wrong ?
You are using a boolean operator foo==bar where you should be using an assignment operator foo=bar.
Don't do:
book_item = Items.objects.filter(book__name==q)
Instead do:
book_item = Items.objects.filter(book__name=q)
When calling filter you want it to look through all the Items that have been created and return the Items that have a Book that has a name = (equal) to q (or what ever search variable you're looking for).