How can I add more items to an EmbeddedDocument with MongoEngine? - python

I'm trying to check if there is already an item with the current date and if not I will add it. the code below is not prompting any errors but it's not saving anything to MongoDB
if len(site.DaylyLog) != 0:
print len(site.DaylyLog)
print site.DaylyLog[-1]
current_date_daylylog = site.DaylyLog[-1]['aggregate_date']
else:
current_date_daylylog = ''
if current_date_daylylog == datetime.date.today():
#update document
print current_date_daylylog
print "calculating averages"
site.DaylyLog[-1].average_response_time = (site.DaylyLog[-1].average_response_time+record_uptime.response_time)/2
site.DaylyLog[-1].average_uptime = (site.DaylyLog[-1].average_uptime+100)/2
site.save()
else:
print current_date_daylylog
print "adding new uptime"
print site.url
aggregate_uptime = AggregatedUptime()
aggregate_uptime.average_response_time = record_uptime.response_time
aggregate_uptime.average_uptime = 100
aggregate_uptime.total_downtime = 0
aggregate_uptime.aggregate_date = datetime.date.today()
print aggregate_uptime.aggregate_date
print aggregate_uptime.average_response_time
site.DaylyLog.append(aggregate_uptime)
site.save()
print site.DaylyLog[-1].aggregate_date

As I mentioned in the comment above. The code I've posted was ok, but it was refencing something that i've changed in the model. It was just a newbie problem. :-)
The old model was
class Checkr(Document):
name = StringField()
slug = SlugField()
url = URLField()
frequency = IntField()
owner = IntField()
start_date = DateTimeField()
end_date = DateTimeField()
current_response_time = FloatField()
current_response_code = IntField()
hourly_log = ListField(EmbeddedDocumentField(AggregatedUptime))
dayly_log = ListField(EmbeddedDocumentField(AggregatedUptime))
weekly_log = ListField(EmbeddedDocumentField(AggregatedUptime))
When it should be
class Checkr(Document):
name = StringField()
slug = SlugField()
url = URLField()
frequency = IntField()
owner = IntField()
start_date = DateTimeField()
end_date = DateTimeField()
current_response_time = FloatField()
current_response_code = IntField()
HourlyLog = ListField(EmbeddedDocumentField(AggregatedUptime))
DaylyLog = ListField(EmbeddedDocumentField(AggregatedUptime))
WeeklyLog = ListField(EmbeddedDocumentField(AggregatedUptime))

Related

'django model' object is not subscriptable

I get this error when I try to do a query set on the Django model
'AppUser' object is not subscriptable
despite it is working normally in a print statement but the error only appears when I put it in an IF statement
here is my code :
def to_representation(self, instance):
data = super().to_representation(instance)
print("reached here") #print normaly
print(AppUser.objects.filter(mobile=instance['mobile']).exists()) #print normally (False)
if AppUser.objects.filter(mobile=instance['mobile']).exists(): # Raises an Exception
if instance.playerprofile_set.all().count() > 0:
player_profile = instance.playerprofile_set.all()[0]
data['player_profile'] = PlayerProfileSerializer(
player_profile).data
for item in Team.objects.all():
if player_profile in item.players.all():
data['team'] = TeamSerializer(item).data
if item.cap.id == player_profile.id:
data['team'] = TeamSerializer(item).data
# data["team"] = instance.
return data
UPDATE
And here is my AppUser class:
class AppUser(models.Model):
first_name = models.CharField(max_length=33)
last_name = models.CharField(max_length=33)
mobile = models.CharField(max_length=33)
email = models.EmailField(null=True, blank=True, max_length=33)
birthdate = models.DateField(null=True, blank=True)
password = models.CharField(max_length=33)
confirm_password = models.CharField(max_length=33)
image = models.FileField(upload_to="uploads", null=True, blank=True)
main_user = models.ForeignKey(User, on_delete=models.CASCADE, null=True)
generated_code = models.PositiveIntegerField(null=True, blank=True)
user_langauge = models.CharField(max_length=33, default="en")
dark_mode = models.BooleanField(default=False)
def __str__(self):
return str(self.mobile) + " " + str(self.first_name) + " " + str(self.last_name)
so calling AppUser.objects.filter() should return a queryset or empty query set, and when adding exists() should return a True or
Instead of count, use exists():
if AppUser.objects.filter(mobile=instance['mobile']).exists():
if instance.playerprofile_set.exists():
player_profile = instance.playerprofile_set.first()
Because it is very efficient in contrast to count() and runs a very small query.
To your original problem, it is not possible to guess what is wrong from the sample code, specially when print works, if not.
Update
I think the error should be with this code:
instance['mobile']
Here instance should be an object, so instance.mobile or data['mobile'] should work.
try this:
def to_representation(self, instance):
data = super().to_representation(instance)
print("reached here") #print normaly
print(AppUser.objects.filter(mobile=instance['mobile']).count() > 0) #print normally (False)
if AppUser:
AppUser.objects.filter(mobile=instance['mobile']).count() > 0
if instance.playerprofile_set.all().count() > 0:
player_profile = instance.playerprofile_set.all()[0]
data['player_profile'] = PlayerProfileSerializer(
player_profile).data
for item in Team.objects.all():
if player_profile in item.players.all():
data['team'] = TeamSerializer(item).data
if item.cap.id == player_profile.id:
data['team'] = TeamSerializer(item).data
# data["team"] = instance.
return data

Select a valid choice Django Filtered Drop Down Menu

Devs,
In my project I have a form that has a field that has a student name selection, it is a drop down field by the students that are currently enrolled in that particular class. It gets this information from table Section Enrollment than checks the master Student table. The filtering works out correctly, however when I submit my form, it says the student name is not a valid choice. My guess is because its submitting that student name and not a ID, I'm not 100% sure. Here is my models and view. I don't know how to fix this. Appreciate that help.
QUERY IN QUESTION:
getstudents = SectionEnrollment.objects.filter(section_id=classid).select_related().values_list('studentpsid_id__student_name', flat = True)
MODELS:
# Creation of Classrooms and Assigned Teachers
class SectionEnrollment(models.Model):
sectionenrollmentpsid = models.CharField(primary_key = True,max_length = 50, default = "")
section = models.ForeignKey(Section,on_delete = models.PROTECT, default = "" ,)
studentpsid = models.ForeignKey(Student,on_delete = models.PROTECT, default = "" ,)
entry_date = models.DateField(blank=True)
exit_date = models.DateField(blank=True)
dropped = models.BooleanField(default = False, blank = True)
class Meta:
verbose_name = "Student Section Enrollment"
def __str__(self):
return self.sectionenrollmentpsid
# Where Basic Student Data Is Stored
class Student(models.Model):
studentpsid= models.CharField(primary_key = True , default = "", max_length = 50, unique = True)
student_name = models.CharField(max_length = 50)
first_name = models.CharField(max_length = 50, default = "")
last_name = models.CharField(max_length = 50,default = "")
gender = models.CharField(max_length = 1,default = "")
student_grade = models.CharField(max_length = 2, default = "")
home_room = models.CharField(max_length = 5, default = "")
student_enrollment = models.CharField(max_length = 2, default = "")
school_number = models.CharField(max_length = 15, default = "")
email = models.EmailField(default = "")
projected_graduation_year = models.CharField(max_length = 4, default = "")
counseling_goal = models.TextField(max_length = 255)
win_username = models.CharField(max_length = 50)
win_password = models.CharField(max_length = 50)
offsite_laptop = models.BooleanField(default = False, blank = True)
image = models.ImageField(default ="default.png", upload_to ='student_pics')
VIEW:
#login_required
def Rapid_Fire(request, classid):
if request.method == "GET":
date = datetime.date.today()
class_name = Section.objects.filter(sectionpsid=classid)
getstudents = SectionEnrollment.objects.filter(section_id=classid).select_related().values_list('studentpsid_id__student_name', flat = True)
student_selection = getstudents.all().order_by('studentpsid__student_name')
my_class_id = request.session['my_class_id']
sectionpsid = Section.objects.get(sectionpsid = my_class_id)
form = Rapid_Fire_Form()
form.fields["student_name"].queryset = getstudents
form.fields["sectionpsid"].queryset = class_name
context = ({'form': form, 'my_class_id': my_class_id, 'sectionpsid':sectionpsid,})
return render(request, 'points/rapid_fire.html', context )
elif request.method == "POST":
date = datetime.date.today()
class_name = Section.objects.filter(sectionpsid=classid)
getstudents = SectionEnrollment.objects.filter(section_id=classid).select_related().values_list('studentpsid_id__student_name', flat = True)
student_selection = getstudents.all().order_by('studentpsid__student_name')
my_class_id = request.session['my_class_id']
sectionpsid = Section.objects.get(sectionpsid = my_class_id)
form = Rapid_Fire_Form(request.POST)
form.fields["student_name"].queryset = getstudents
form.fields["sectionpsid"].queryset = class_name
if form.is_valid():
# Records logged in user to table
obj = form.save(commit= False)
userid = request.user
obj.created_by = userid
obj.save()
it seems the problem is here:
getstudents = SectionEnrollment.objects.filter(section_id=classid).select_related().values_list('studentpsid_id__student_name', flat = True)
student_selection = getstudents.all().order_by('studentpsid__student_name')
the values_list('studentpsid_id__student_name', flat = True) is collecting the students name not their id. so the form field will be field by incorrect data I think.
and if I'm right the solution may be:
students_id = SectionEnrollment.objects.filter(section_id=classid).select_related().values_list('studentpsid__id', flat = True)
student_selection = Student.objects.filter(id__in=students_id).order_by('student_name')
or:
student_selection = Student.objects.filter(sectionenrollment_set__section_id=classid).order_by('student_name')

How to loop through object fields in django

I want to loop through the object fields to update their values but im not quite sure how to do this.
class FinancePending(models.Model):
invoiceNumber = models.IntegerField
amountPaid = models.CharField(max_length=20)
AmountPending = models.IntegerField( blank=True, null=True)
TotalAmount = models.CharField(max_length=50, default=0)
Now i want to calculate amountpending in a function. But its not working
amount_paid = FinancePending.objects.values_list('amountPaid', flat=True)
amount_paid = list(amount_paid)
total_amount = FinancePending.objects.values_list('TotalAmount', flat=True)
total_amount = list(total_amount)
# total - paid
TotalFee = [float(s.replace(',', '')) for s in total_amount]
AmountPaid = [float(s.replace(',', '')) for s in amount_paid]
finance_pending = FinancePending.objects.all()
i = 0
while i < len(TotalFee):
amount_pending = TotalFee[i] - AmountPaid[i]
FinancePending.objects.filter(invoiceNumber=i).values(AmountPending=amount_pending)
setattr(finance_pending, 'AmountPending', str(amount_pending))
i = 1 + i
Would suggest using Query Expression, more powerful and robust

Django Filter with AND

Am having a django query to filter trough a model and print out the condition that meets the search.
Here is the views
if user_search != '' and (start_date != '' and end_date != ''):
items = Order.objects.filter(
Q(client__email__iexact=user_search) , Q(created_on__range=(start_date, end_date))
)
print "items ", items
The django filter is to print email address the user searched for, that falls within the date range.
But the code am having also prints email that wasn't searched for but falls within the date range
Here is the model
class Order(models.Model):
client = models.ForeignKey(User, related_name = "order_user")
order_number = models.CharField(max_length = 12)null=True)
terms_and_conditions = models.BooleanField(default=False)
order_status = models.CharField(max_length = 20, choices = ORDER_STATUS, default = "new")
created_on = models.DateTimeField(auto_now_add = True)
edited_on = models.DateTimeField(auto_now_add = False)
def __unicode__(self):
return self.order_number
Use & for doing AND operations on Q objects.
if user_search != '' and (start_date != '' and end_date != ''):
items = Order.objects.filter(
Q(client__email__iexact=user_search) & Q(created_on__range=(start_date, end_date))
)
print "items ", items

What is the proper way of saving data to an embedded document using Mongoengine and Pyramid?

I am sure I am missing something, because I cant get Mongoengine/Pyramid to save the embedded document.
I have the following:
class Job_history(DynamicEmbeddedDocument):
job_title = StringField()
from_ = DateTimeField()
to_ = DateTimeField()
class Candidates(Document):
first_name = StringField(required=True)
second_name = StringField()
surname = StringField(required=True)
id_number = StringField(primary_key=True, required=True)
id_type = StringField()
id_nationality = StringField()
home_number = StringField()
mobile_number = StringField(required=True)
email = EmailField(required=True)
notice_period = StringField()
date_of_entry = ComplexDateTimeField()
city_town = StringField()
province = StringField()
postal_code = StringField()
country = StringField()
job_history = ListField(EmbeddedDocumentField(Job_history))
meta = {"indexes": ["id_number", "mobile_number", 'province', 'email', 'postal_code']}
When I try to save data to Candidates I get the following error:
ValidationError: ValidationError (Candidates:9109205021082) (Invalid embedded document instance provided to an EmbeddedDocumentField: ['job_history'])
^ ^ ^
this is the id_number field
I get the data I try to save from an HTML form, I handle this data like this:
#view_config(name='edit', renderer="json", request_method='POST')
def modify(self):
params = self.request.params
print params
self.context.first_name = params.get('first_name')
self.context.second_name = params.get('second_name')
self.context.surname = params.get('surname')
self.context.id_number = params.get('id_number')
self.context.id_type = params.get('id_type')
self.context.id_nationality = params.get('id_nationality')
self.context.home_number = params.get('home_number')
self.context.mobile_number = params.get('mobile_number')
self.context.email = params.get('email')
self.context.city_town = params.get('city_town')
self.context.province = params.get('province')
self.context.postal_code = params.get('postal_code')
self.context.country = params.get('country')
self.context.from_ = params.get("from[]") #embedded document field
self.context.to_ = params.get("to[]") #embedded document field
self.context.industries = params.get("industries[]") #embedded document field
can_id = Candidates.objects(id_number=self.context.id_number)
from_list = []
to_list= []
job_title_list = []
industries_list = []
for k, v in params.iteritems():
if k == "industries[]":
industries_list.append(v)
for k, v in params.iteritems():
if k == "to[]":
to_list.append(v)
for k, v in params.iteritems():
if k == "from[]":
from_list.append(v)
for k, v in params.iteritems():
if k == "job_title[]":
job_title_list.append(v)
self.context.job_history = [[j,f,t] for j,f,t in zip(job_title_list, from_list, to_list)] # add the embedded document fields into to a list
try:
self.context.save() # try to save to `Candidates`
print self.context
self.request.session.flash({"text": "Success!", "type": "success", "heading": "Success"})
except:
self.request.session.flash({"text": "Database error", "type": 'danger', "heading": ""})
candidate_url = self.request.route_url('candidates', id_number=self.context.id_number, traverse="edit")
return
The code shown here is shortened.
What am I missing? or what am I doing wrong?
Just going by the api docs on mongoengine. Your schema defines an array of Job_history documents. So rather than creating a list of 3 item tuples from your form input in your list comprehension, just create an instance of Job_history for what the zip function yields.
self.context.job_history = [Job_history(job_title=j, from_=f, to_=t) for j,f,t in zip(job_title_list, from_list, to_list)]

Categories