I was thinking about making a Hostel Allocation Web application. It has models, Student, Room, Hostel. What I want is to create a function that allocates students after each year. For that, I thought in the student view each student after completing his four years of stay can click on vacate hostel after completing his degree, and for others, I want to create something that allocates them,
Now there are certain constraints, there are Undergraduate students with degree period 4 years and each year has access to different types of rooms, First-year triple sharing, second and third-year double sharing and fourth-year single rooms. Also, a Hostel has Ph.D. students as well but their stay period is not defined.
So, what I was thinking is that First years should be allotted by uploading a CSV file and I have made that part, So the next part is to allot subsequent years based on their preferences, So how could I make something like this in Django that allows them to make it based on their preference, I was thinking each student would be given a unique token, and while filling for rooms one student can do for a room, and that token needs to be entered. Is this the right way or should I do something else. I am a newbie please suggest me a good way to do this.
models.py
class Student(models.Model):
name = models.CharField(max_length = 40,help_text = "Name of the student")
entry_number = models.CharField(max_length = 11,help_text = "Entry Number of a student")
hostel_name = models.ForeignKey('Hostel', on_delete = models.SET_NULL,null = True)
room = models.ForeignKey('Room',on_delete = models.SET_NULL,null = True)
CHOICES = (
('m','Male'),
('f','Female'),
('e','Engaged'),
)
gender = models.CharField(max_length=1,choices=CHOICES)
def __str__(self):
return '%s, %s' % (self.name,self.entry_number)
def get_absolute_url(self):
return reverse('student-detail',args=[str(self.id)])
class Meta:
verbose_name="Student Record"
class Hostel(models.Model):
name= models.CharField(max_length= 15)
locality= models.URLField(max_length= 200, blank= True, default='',help_text='Google maps URL of the hostel')
total_rooms= models.PositiveSmallIntegerField(null=True, blank =True)
CHOICES = (
('m', 'Male'),
('f', 'Female'),
('e', 'Engaged'),
)
gender = models.CharField(max_length=1, choices=CHOICES, verbose_name=_('Type of Hostel'), help_text='Either Boys/Girls or Married students Hostel')
def __str__(self):
return self.name
def get_absolute_url(self):
return reverse('hostel-detail',args=[str(self.id)])
class Meta:
verbose_name="Hostel Record"
class Room(models.Model):
hostel= models.ForeignKey(Hostel, on_delete=models.CASCADE)
name= models.CharField(max_length = 5)
floor= models.CharField(max_length = 1, blank=True)
wing= models.CharField(max_length = 1, blank=True)
comment= models.CharField(max_length = 100,blank=True, default = "comment here")
room_capacity = models.PositiveSmallIntegerField(validators=[MaxValueValidator(3),])
room_accomodation= models.PositiveSmallIntegerField()
def __str__(self):
return self.name
def get_absolute_url(self):
return reverse('room-detail',args=[str(self.id)])
class Meta:
verbose_name="Room Record"
Related
I'm creating a site to register students. So basically it is divided into 3 parts
1. A student register model which take the name, fathername, etc of student.
2. A student fee model which use foreignkey to get register student.
3. ModelForm for showing student fee model to enter data.
Now the problem if I want to fill a student fee of class 1 it shows all the student of other classes, but I want the student filter according to their classes and their name show and in front of them editable fee and pending fee form.
By some reach I got to know about ModelForm instance I wrote code for automatically add register students to student fee.
def student_fee(request):
# add a selection field to a variable for filtering student_class below this.
students = StudentRegister.objects.filter(student_class="1")
....
for x in students:
if not StudentFee.objects.filter(student=x):
StudentFee.objects.create(student=x, fee=0, pending_fee=0)
But for instance I have to know primary key of every student I can loop through them but it only get the last element.
models.py
class StudentRegister(models.Model):
student_image = models.ImageField(upload_to="register_student", blank=True)
student_class = models.CharField(max_length=2, choices=STUDENT_CLASS, default="1")
mobile_number = models.CharField(max_length=50)
student_name = models.CharField(max_length=50)
father_name = models.CharField(max_length=50)
mother_name = models.CharField(max_length=50)
address = models.CharField(max_length=200)
student_fee = models.CharField(max_length=10, default="0")
Date_Of_Birth = models.DateField(auto_now=False)
admission_fee = models.CharField(max_length=10)
Admission_date = models.DateField(auto_now=False)
adhaar_no = models.CharField(max_length=100)
def __str__(self):
return "%s class: %s" % (self.student_name, self.student_class)
class StudentFee(models.Model):
student = models.ForeignKey(StudentRegister, on_delete=models.CASCADE)
fee = models.CharField(max_length=20)
pending_fee = models.CharField(max_length=20)
def __str__(self):
return "%s " % (self.student)
forms.py
class StudentFeeForm(forms.ModelForm):
class Meta:
model = StudentFee
fields = '__all__'
views.py(its messy sorry)
def student_fee(request):
# add a selection field to a variable for filtering student_class below this.
students = StudentRegister.objects.filter(student_class="1")
real = StudentFee.objects.all()
# student_form = StudentFeeForm(request.POST or None)
student_form = StudentFeeForm(request.POST)#, instance=students)
# print(dir(students))
q = (students.get(pk=1))
global list_student_pk
list_student_pk = []
for x in students:
list_student_pk.append(x.pk)
student_get_instance = StudentFeeForm(instance=q)
# print(student_get_instance)
# This thing done don't touch----------------------------------
for x in students:
if not StudentFee.objects.filter(student=x):
StudentFee.objects.create(student=x, fee=0, pending_fee=0)
if request.method == "POST":
if student_form.is_valid():
pass # this thing will done after the form problem solved.
# till here ==========================================================
return render(request, "student_fee_home.html", {"students": students, "real":real, "student_form":student_form, "list_student_pk":list_student_pk, "student_get_instance":student_get_instance})
I want that modelforms filter according to class.
Then the student fee model which already having register student(student name, fee, pending fee) can edit. So that it shows the student name and right in front of him a editable fee form and a pending fee form.
It is working right now like this showing all student of all classes, but I want that students name will show instead of selection field. In my knowledge only option to display names of student display names direct from models then use a form to take input of fee and pending fee then create it in models.
djang0-filter will help you for filtering
pip install django-filter
Model.py
class Dispatcher(models.Model):
_safedelete_policy = SOFT_DELETE
Individual = 'Individual'
Company = 'Company'
TYPES = [
(Individual, 'Individual'),
(Company, 'Company')
]
type = models.CharField(max_length=255,
choices=TYPES,
default=Individual)
Views.py
class DispatcherViewSet(viewsets.ModelViewSet):
queryset = Dispatcher.objects.all()
serializer_class = DispatcherSerializer
filter_backends = (DjangoFilterBackend,)
filterset_fields = ['type']
I'm working on this big project with Django and I have to update the database. I have to add another table which will replace another later.
So I want to add in a model the possibility to have a field where I can have either the old model OR the new one.
Here is the code of the old model:
class Harvests(models.Model):
ident_culture = models.IntegerField(primary_key=True)
intitule_culture = models.CharField(max_length=50, blank=True)
nom_fertiweb = models.CharField(max_length=50, blank=True, null = True)
affichage_quintaux_tonne = models.CharField(max_length=1,
choices=RENDEMENT_CHOICES, default = 'T')
type_culture = models.ForeignKey("TypeCulture", null=True)
slug = models.SlugField(null=True, blank=True)
image = models.ImageField(upload_to = 'images_doc_culture/',
null=True, blank = True)
affichage = models.BooleanField(default = True)
class Meta:
verbose_name = "Liste - Culture"
verbose_name_plural = "Liste - Cultures"
ordering = ['intitule_culture']
def __str__(self):
return self.intitule_culture
def label(self):
return self.intitule_culture or ''
#classmethod
def get_choices(cls):
choices = [('', corp.EMPTY_CHOICE_LBL)]
c_category_lbl, c_category = '', []
for item in cls.objects.all():
choices.append((item.pk, item.intitule_culture))
return choices
And there is the code od the new one I created:
class Crops(models.Model):
intitule_culture = models.CharField(max_length=75, blank=True)
affichage_quintaux_tonne = models.CharField(max_length=2,
choices=RENDEMENT_CHOICES, default = 'T')
type_culture = models.ForeignKey("TypeCulture", null=True)
ident_culture = models.IntegerField(primary_key=True)
affichage = models.BooleanField(default = True)
id_marle = models.IntegerField(null=True)
class Meta:
verbose_name = "Liste - Culture 2019"
verbose_name_plural = "Liste - Cultures 2019"
ordering = ['intitule_culture']
def __str__(self):
return self.intitule_culture
def label(self):
return self.intitule_culture or ''
#classmethod
def get_choices(cls):
choices = [('', corp.EMPTY_CHOICE_LBL)]
c_category_lbl, c_category = '', []
for item in cls.objects.all():
choices.append((item.pk, item.intitule_culture))
return choices
I want to accept both models in the field culture in this model:
class CompanyHarvest(models.Model):
company = models.ForeignKey('corp.Company', verbose_name='Exploitation',
related_name ='cultures')
culture = models.ForeignKey(Harvests, verbose_name ='Culture')
precision = models.CharField(max_length=255, blank=True)
saison_culture = models.CharField(max_length=1, choices=SAISON_CHOICES,
default = 'P')
class Meta:
verbose_name = "Expl. - Culture"
verbose_name_plural = "Expl. - Cultures"
unique_together = ('company', 'culture', 'precision', 'saison_culture')
def __str__(self):
return str(self.culture) + ' ' + self.precision + \
' ' + str(self.get_saison_culture_display() )
#property
def slug(self):
return "_".join([slugify(str(self.culture or '')),
slugify(str(self.precision or ''))]
)
I'm new to Django, can anyone help me with this please ? (^-^)
This is not possible - at least not this way. And this is not a Django limitation but a SQL one, a foreign key cannot reference either one table or another.
A possible and simple obvious solution here would be to have two foreign keys in CompanyHarvest - one for each of the old and new model -, each with blank=True et default=None, but it can quickly make a mess of all the client code (all code using CompanyHarvest).
Much better solutions would be to either only keep the existing model (adding any new field/feature to it and eventually hiding obsolete ones) or migrate all old model records to the new model (this can be combined with the naive "two foreign keys" solution so you can keep the old table and records as archives if necessary).
Also - totally unrelated but -, this:
#classmethod
def get_choices(cls):
choices = [('', corp.EMPTY_CHOICE_LBL)]
c_category_lbl, c_category = '', []
for item in cls.objects.all():
choices.append((item.pk, item.intitule_culture))
return choices
1/ should be defined on the manager (cf https://docs.djangoproject.com/en/2.1/topics/db/managers/#adding-extra-manager-methods)
2/ should be written using .values() queryset (which will save on both the db query and building full-blown instances for no good reason):
for item in cls.objects.values("pk", "intitule_culture"):
choices.append(item)
3/ and could very possibly (i'd have to see how it's used) replaced by a ModelChoiceField in the calling code.
Oh and yes: if you allow blanks for text fields, you very probably want to force the empty string as default so you don't two possible (and incompatible) cases (sql NULL and the empty string) when no value is given.
So the title states my objective. Here's the code I wrote to achieve it:
#for each cycle in instructional cycles:
for cycle in Instructional_Cycle.objects.all():
#for each standard in the currently selected cycle:
for standard in cycle.standards.all():
#generate random percentage of correct grade-level students to pass that standard, say between 20 and 90%
percent_pass = randint(20,90)
#calculate number of total students for that grade-level that percentage represents (percentage times total number of students in that grade)
total_students_passing = (percent_pass/100) * Student.objects.filter(grade_level = standard.grade_level).count()
already_selected = []
#while length of list of already selected students < total needed
while len(already_selected) < total_students_passing:
#select a random student out of that grade
count = Student.objects.filter(grade_level=standard.grade_level).count()
random_student = Student.objects.all()[randint(0, count - 1)] #single random object
#if that student isn't in list of already selected students
if not random_student.id in already_selected:
#create a passing progress report with the end date of that instructional cycle
Progress_Report.objects.create(date=cycle.date_finished, student=random_student, standard_mastered=standard, mastery_status=True)
#add that student to list of already selected students
already_selected.append(random_student.id)
This ends with the following error:
django.db.utils.IntegrityError: UNIQUE constraint failed:
student_progress_progress_report.standard_mastered_id
The progress_report table that I'm trying to fill is empty. I can add records to it using the admin interface. So I'm not sure where to look to fix my issue, because I'm not really sure what the problem is. Thanks for looking and any tips that you can provide. -- GH
Here are the models:
from django.db import models
from django.urls import reverse
gradeLevels = ((6,6), (7,7),(8,8),(9,9), (10,10), (11,11), (12,12))
subjects = (('Literacy','Literacy'), ('Math','Math'),
('Science','Science'), ('Social Studies','Social Studies'))
class Student(models.Model):
student_id = models.CharField(max_length=8, unique=True)
last_name = models.CharField(max_length=100)
first_name = models.CharField(max_length=100)
grade_level = models.IntegerField(choices=gradeLevels)
active_status = models.BooleanField(default=True)
class Meta:
ordering = ['grade_level', 'last_name']
def __str__(self):
#Return a string representation of the model.
return self.student_id + ' ' + self.last_name + ', ' + self.first_name
def student_name(self):
return self.last_name + ', ' + self.first_name
def get_absolute_url(self):
return reverse('student_progress:student_detail', args=[str(self.id)])
class Standard(models.Model):
subject = models.CharField(max_length=14, choices=subjects)
grade_level = models.IntegerField(choices=gradeLevels)
descriptor = models.CharField(max_length=15)
description = models.TextField()
essential_status = models.BooleanField(default=False)
class Meta:
ordering = ["subject", "grade_level", "descriptor"]
def __str__(self):
return self.descriptor + ': ' + self.description[:100]
def get_absolute_url(self):
return reverse('student_progress:standard_detail', args=[str(self.id)])
class Milestone (models.Model):
step_number = models.IntegerField()
statement = models.CharField(max_length=250, default="I can ...")
standard = models.ForeignKey(Standard, on_delete=models.CASCADE,
related_name='milestones', null=True, blank=True)
def __str__(self):
return str(self.step_number) + ': ' + self.statement[:50]
class Progress_Report(models.Model):
date = models.DateField(null=True)
student = models.OneToOneField(Student, on_delete=models.CASCADE)
standard_mastered = models.OneToOneField(Standard,
on_delete=models.CASCADE)
mastery_status = models.BooleanField(default=True)
class Meta:
ordering = ["date", "student"]
def __str__(self):
return self.date
class Instructional_Cycle(models.Model):
date_started = models.DateField(blank=False)
date_finished = models.DateField(blank=False)
standards = models.ManyToManyField(Standard, related_name="standards")
class Meta:
ordering = ['date_started']
def __str__(self):
return str(self.date_started) + ' to ' + str(self.date_finished)
def get_absolute_url(self):
return reverse('student_progress:cycle_detail', args=[str(self.id)])
you've told the database you want to maintain a unique constraint! the data you're trying to insert would violate that constraint and therefore the transaction is failing.
Django provides various helpers for this. For example Progress_Report.objects.update_or_create(…) might help. For more info, see:
https://docs.djangoproject.com/en/2.1/ref/models/querysets/#update-or-create
The exact invocation would depend on the constraints you're wanting to enforce.
I stumbled on the answer accidentally: I changed the field types of Progress_Report.student and Progress_Report.standard_mastered from OnetoOneField to ForeignKey. Now the python code runs perfectly and populates the database exactly as intended without error.
I have no idea why this solved the problem. I wish I understood better what the problem is, but I'm thankful it's fixed.
I'm making a program that helps log missions in a game. In each of these missions I would like to be able to select a number of astronauts that will go along with it out of the astronauts table. This is fine when I only need one, but how could I approach multiple foreign keys in a field?
I currently use a 'binary' string that specifies which astronauts are to be associated with the mission (1 refers to Jeb, but not Bill, Bob, or Val and 0001 means only Val), with the first digit specifying the astronaut with id 1 and so forth. This works, but it feels quite clunky.
Here's the model.py for the two tables in question.
class astronauts(models.Model):
name = models.CharField(max_length=200)
adddate = models.IntegerField(default=0)
experience = models.IntegerField(default=0)
career = models.CharField(max_length=9, blank=True, null=True)
alive = models.BooleanField(default=True)
def __str__(self):
return self.name
class Meta:
verbose_name_plural = "Kerbals"
class missions(models.Model):
# mission details
programid = models.ForeignKey(programs, on_delete=models.SET("Unknown"))
missionid = models.IntegerField(default=0)
status = models.ForeignKey(
missionstatuses, on_delete=models.SET("Unknown"))
plan = models.CharField(max_length=1000)
# launch
launchdate = models.IntegerField(default=0)
crewmembers = models.IntegerField(default=0)
# recovery
summary = models.CharField(max_length=1000, blank=True)
recdate = models.IntegerField(default=0)
def __str__(self):
return str(self.programid) + '-' + str(self.missionid)
class Meta:
verbose_name_plural = "Missions"
I saw a post about an 'intermediate linking table' to store the crew list but that also isn't ideal.
Thanks!
This is the use case for Django's ManyToManyField. Change the appropriate field on the missions:
class missions(models.Model):
crewmembers = models.ManyToManyField('astronauts')
You can access this from the Astronaut model side like so:
jeb = astronaut.objects.get(name='Jebediah Kerman')
crewed_missions = jeb.missions_set.all()
Or from the mission side like so:
mission = missions.objects.order_by('?')[0]
crew = mission.crewmembers.all()
This creates another table in the database, in case that is somehow a problem for you.
My models are :
model 1:
class source_of_enquiry(models.Model):
source_of_enquiry = models.CharField(max_length=200, null=True, blank=True)
def __unicode__(self):
return '%s' % self.source_of_enquiry
model 2:
class customers(models.Model):
cutomer_name = models.CharField(max_lentgth=200)
customer_src_n_type = models.Foreign_key(source_of_enquiry)
customer_contact = models.CharField(max_lentgth=200)
def __unicode__(self):
return '%s' % self.customer_name
model 3:
class sales_cycle(models.Model):
item_name = models.CharField(max_length=200)
customer_name = models.Foreignkey(customers)
def __unicode__(self):
return '%s' % self.item_name
how should i know how many sales had peen completed based on source of enquiry??
tried many from `select_related' and 'prefetch_selected' , but all were kaput.
First of all - python naming convention state that classes should not have underscores and prefer upper-case letters instead. So your models should be SourceEnquiry, Customer (not plural) and SaleCycle.
That being said, let's say I have a SourceEnquiry item (I'm going to pick one arbitrarily), and you want all related SaleCycle items, you do it like so:
>>> sinq = SourceEnquiry.objects.get(pk=1)
>>> SaleCycle.objects.all().filter(customer_name__customer_src_n_type=sinq)
p.s.
also, going back to the naming convention thing, it's redundant to use customer as part of a field name inside the class Customer. You alread know it's a customer object, so it's better to name it like so:
class Customer(models.Model):
name = models.CharField(max_lentgth=200)
src_n_type = models.Foreign_key(source_of_enquiry)
contact = models.CharField(max_lentgth=200)
You other fields can also be cleaner:
class SourceEnquiry(models.Model):
value = models.CharField(max_length=200, null=True, blank=True)
class SaleCycle(models.Model):
item = models.CharField(max_length=200)
customer = models.Foreignkey(Customer)