I'm trying to calculate the pending amount via models and export result in the csv. But the csv shows an empty column for amountpending
class FinancePendingResource(resources.ModelResource):
invoiceNumber = Field(attribute='invoiceNumber', column_name='Invoice Number')
student = Field(attribute='student', column_name='Student')
Schedule = Field(attribute='Schedule', column_name='Schedule')
TotalAmount = Field(attribute='TotalAmount', column_name='Total Value(PKR ₨)')
issueDate = Field(attribute='issueDate', column_name='Issue Date')
dueDate = Field(attribute='dueDate', column_name='Due Date')
amountPaid = Field(attribute='amountPaid', column_name='Amount Paid (PKR ₨)')
class Meta:
model = FinancePending
import_id_fields = ('invoiceNumber',)
fields = ('invoiceNumber', 'student', 'amountPaid', 'issueDate', 'dueDate', 'Schedule', 'TotalAmount',
'AmountPending',)
exclude = ('id',)
skip_unchanged = True
report_skipped = True
def before_export(self, queryset, *args, **kwargs):
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]
def Diff(li1, li2):
return (list(set(li1) - set(li2)))
amount_pending = Diff(TotalFee, AmountPaid)
finance_pending = FinancePending()
i = 1
while i <= len(amount_pending):
FinancePending.objects.filter(invoiceNumber=i).update(AmountPending=str(amount_pending[i]))
i = i + 1
queryset.refresh_from_db()
Assuming that you have the data to compute amountPending already in the dataset, perhaps you don't need to read from the DB: you could calculate the amount by processing the dataset in memory. This could be done in after_export(). Then you can added the computed column to the dataset.
Perhaps tablib's dynamic columns can assist in adding the amountPending column:
import decimal
import tablib
headers = ('invoiceNumber', 'amountPaid', 'totalAmount')
rows = [
('inv100', '100.00', "500.00"),
('inv101', '200.00', "250.00")
]
def amount_pending(row):
return decimal.Decimal(row[2]) - decimal.Decimal(row[1])
data = tablib.Dataset(*rows, headers=headers)
data.append_col(amount_pending, header="amountPending")
print(data)
This will produce the following:
invoiceNumber|amountPaid|totalAmount|amountPending
-------------|----------|-----------|-------------
inv100 |100.00 |500.00 |400.00
inv101 |200.00 |250.00 |50.00
Related
I've been working on it for a week, but I couldn't.
This is what he wants to do:
I want to average the "fiyat" column relative to the "ay_yil" column, i.e .:
{ '2020-09-15': 67333.3, '2020-02-15': 29750,0 }
models.py:
class Araba(models.Model):
marka = models.CharField(max_length=25, verbose_name='Marka')
model = models.CharField(max_length=25, verbose_name='Model')
motor = models.CharField(max_length=25, verbose_name='Motor')
yil = models.PositiveSmallIntegerField(verbose_name='Yil')
km = models.PositiveIntegerField(verbose_name='Km')
fiyat = models.PositiveIntegerField(verbose_name='Fiyat')
ay_yil= models.DateField(verbose_name='Ay Yıl')
def __str__(self):
return self.marka
views.py:
def veri(request,marka,model,motor):
veri= Araba.objects.filter(marka=marka,model=model,motor=motor)["ay_yil"]
veri2=veri.aggregate(ort=Avg('fiyat'))
print(veri2)
return render(request,"veri.html")
dataset:
from django.db.models import Avg
def veri(request, marka, model, motor):
veri= Araba.objects.filter(marka=marka,model=model,motor=motor).values('ay_yil')
veri2=veri.annotate(Avg('fiyat'))
print(veri2)
return render(request,"veri.html")
I created a script to avoid creating duplicate objects but it still created the same objects when I run the command 3 times it creates them 3 times over and over again. I would like you to help me and know what is wrong with my code.
from django.core.management.base import BaseCommand
from jobs.models import Job
import json
from datetime import datetime
import dateparser
class Command(BaseCommand):
help = 'Set up the database'
def handle(self, *args: str, **options: str):
with open('static/newdata.json', 'r') as handle:
big_json = json.loads(handle.read())
for item in big_json:
if len(item['description']) == 0:
print('Not created. Description empty')
continue
dt = dateparser.parse(item['publication_date'])
existing_job = Job.objects.filter(
job_title = item['job_title'],
company = item['company'],
company_url = item['company_url'],
description = item['description'],
publication_date = dt,
salary = item['salary'],
city = item['city'],
district = item['district'],
job_url = item['job_url'],
job_type = item['job_type'],
)
if existing_job.exists() is True:
print('This Job already exist')
else:
Job.objects.create(
job_title = item['job_title'],
company = item['company'],
company_url = item['company_url'],
description = item['description'],
publication_date = dt,
salary = item['salary'],
city = item['city'],
district = item['district'],
job_url = item['job_url'],
job_type = item['job_type'],
)
self.stdout.write(self.style.SUCCESS('added jobs!'))
Have you tried using built-in field validation unique=True?
https://docs.djangoproject.com/en/3.1/ref/models/fields/#unique
try
if existing_job.exists():
instead of
if existing_job.exists() is True:
because .exists() returns boolean itself
Have you tried using unique_together without the publication_date field? Docs
# models.py
class Job(models.Model):
# Your fields here...
class Meta:
unique_together = [[
'job_title',
'company',
'company_url',
'description',
'salary',
'city',
'district',
'job_url',
'job_type'
]]
dt = dateparser.parse(item['publication_date'])
new_date = date(dt.year, dt.month, dt.day)
here was the problem. I am scraping the publication date in this format ('1 Week Ago') and then I was changing to a date and time format. and when I run the script again the time of the conversion is a different time. so that's why the job is created again. because is not the same because the time creation
I have data that has been scraped from a website, parsed, and cleaned into the pieces I need. The data is stored in a two dimensional list as such [[address1, name1, ip1], [address2, name2, ip2]]. The scraping and storing of the aforementioned data is done through a django command, and I would like to update my model with the same command as it validates the data. I also have a model with the following fields and attributes:
class MonitoredData(models.Model):
external_id = models.UUIDField(
primary_key = True,
default = uuid.uuid4,
editable = False)
mac_address = models.CharField(max_length=12)
ipv4_address = models.CharField(max_length=200)
interface_name = models.CharField(max_length=200)
created_at = models.DateTimeField(auto_now_add=True)
update_at = models.DateTimeField(auto_now=True)
address1 needs to go in the mac_address field, name1 needs to go into the interface_name field, and ip1 needs to go into ipv4_address field. The other fields need to auto-fill according to their attributes.
The django command that grabs and parses the data is:
class Command(BaseCommand):
def handle(self, *args, **options):
url1 = 'https://next.json-generator.com/api/json/get/41wV8bj_O'
url2 = 'https://next.json-generator.com/api/json/get/Nk48cbjdO'
res1 = requests.get(url1)
data1 = str(res1.content)
res2 = requests.get(url2)
data2 = str(res2.content)
parsedData1 = parse1(data1)
goodMac1 = []
badMac1 = []
for k in parsedData1:
if len(k[0]) == 12:
if match(k[0]):
goodMac1.append(k)
else:
badMac1.append(k)
parsedData2 = parse2(data2)
goodMac2 = []
badMac2 = []
for j in parsedData2:
if len(j[0]) == 12:
if match(j[0]):
goodMac2.append(j)
else:
badMac2.append(j)
I'd like to store the data into the database instead of appending to the goodMac list in the nested if statement.
Any help with this would be greatly appreciated, I am using Python 3.7.5 and Django 3.0.5
I figured it out! I hope this will save someone all the time and trouble I went through solving this, the solution, as I suspected, was fairly trivial once I found it. You import your model, instantiate an object of it, then update the fields and use the save() function. Here is the fixed code.
import requests
from django.core.management.base import BaseCommand, CommandError
from Monitor.models import *
from Monitor.parse1 import parse1
from Monitor.parse2 import parse2
from Monitor.matcher import match
class Command(BaseCommand):
def handle(self, *args, **options):
url1 = 'https://next.json-generator.com/api/json/get/41wV8bj_O'
url2 = 'https://next.json-generator.com/api/json/get/Nk48cbjdO'
res1 = requests.get(url1)
data1 = str(res1.content)
res2 = requests.get(url2)
data2 = str(res2.content)
parsedData1 = parse1(data1)
goodMac1 = []
badMac1 = []
for k in parsedData1:
if len(k[0]) == 12:
if match(k[0]):
monInter = MonitoredData()
monInter.mac_address = k[0]
monInter.interface_name = k[1]
monInter.ipv4_address = k[2]
monInter.save()
goodMac1.append(k)
else:
badMac1.append(k)
parsedData2 = parse2(data2)
goodMac2 = []
badMac2 = []
for j in parsedData2:
if len(j[0]) == 12:
if match(j[0]):
goodMac2.append(j)
else:
badMac2.append(j)
Here are links to the documentation I ultimately ended up using:
https://docs.djangoproject.com/en/3.0/ref/models/instances/#django.db.models.Model.save
https://docs.djangoproject.com/en/3.0/topics/db/models/
I would like to use Python's Dictreader to import a csv file based on my Django model into the database.
My post model is:
class Post(models.Model):
STATUS_CHOICES = (
("draft", "Draft"),
("published", "Published")
);
slug = models.SlugField(max_length=250);
wine_id = models.IntegerField();
country = models.CharField(max_length=100);
description = models.TextField();
designation = models.TextField();
price = models.FloatField();
province = models.CharField(max_length=100);
region_1 = models.CharField(max_length=100);
region_2 = models.CharField(max_length=100);
variety = models.CharField(max_length=100);
winery = models.CharField(max_length=100);
objects = models.Manager();
class Meta:
ordering = ("id",);
def __str__(self):
return self.variety;
def get_absolute_url(self):
return reverse("post_detail", args=[self.id,
self.province,
self.slug]);
My script to read the csv data is:
class Command(BaseCommand):
# Shows this when the user types help:
help = "Loads data from wine_data.csv into our Post model.";
def handle(self, *args, **kwargs):
if Post.objects.exists():
print("Wine data already loaded... exiting...");
print(ALREADY_LOADED_ERROR_MESSAGE);
return;
print("Loading wine data for WCC.");
for row in DictReader(open("wine_data.csv")):
post = Post();
post.wine_id = row["wine_id"];
post.country = row["country"];
post.description = row["description"];
post.designation = row["designation"];
post.price = row["price"];
post.province = row["province"];
post.region_1 = row["region_1"];
post.region_2 = row["region_2"];
post.variety = row["variety"];
post.winery = row["winery"];
post.save();
However, when I use "python manage.py load_wine_data", the cmd says it is an unknown command. What am I doing wrong and how can I solve it?
I'm writing a football scoring app for a local league using the same schema as the NFL's gameday DB. I created a function that will eventually run on it's own updating each player's scores.
The problem comes when the function to create a new points record is run it duplicates the entry for each player, there's no error shown or anything, everything runs as expected except for the duplicate values.
here are my views.py:
def updatepoints(request):
actual = get_object_or_404(CurrentWeek, status='active')
week = actual.week
season = actual.season
ptsexist = Puntos.objects.filter(week=week, season=season)
if ptsexist:
pts = Player.objects.raw('''SELECT DISTINCT player.player_id,(SELECT (SELECT SUM(play_player.passing_yds))+(SELECT SUM(play_player.passing_tds))+(SELECT SUM(play_player.passing_twoptm))+(SELECT SUM(play_player.passing_int))+(SELECT SUM(play_player.rushing_yds))+(SELECT SUM(play_player.rushing_tds))+(SELECT SUM(play_player.rushing_twoptm))+(SELECT SUM(play_player.fumbles_lost))+(SELECT SUM(play_player.receiving_yds))+(SELECT SUM(play_player.receiving_tds))+(SELECT SUM(play_player.receiving_twoptm))+(SELECT SUM(play_player.receiving_rec))+(SELECT SUM(play_player.kicking_fgm))+(SELECT SUM(play_player.kicking_xpmade))+(SELECT SUM(play_player.fumbles_rec_tds))+(SELECT SUM(play_player.kicking_rec_tds))) AS total,id_puntos FROM player INNER JOIN play_player ON player.player_id = play_player.player_id INNER JOIN game ON play_player.gsis_id = game.gsis_id LEFT JOIN points ON player.player_id = points.player_id AND points.temporada = game.season_year AND "DraftFantasy_puntos".semana = game.week WHERE game.week = %s AND game.season_year = %s AND game.season_type != 'Warmup' AND game.season_type != 'Postseason' GROUP BY player.player_id,points.id_points''', [week, season])
for obj in pts:
obj.id = obj.player_id
obj.points = obj.total
obj.idpoints = obj.id_points
form = UpdatePointsForm(request.POST)
pointsf = form.save(commit=False)
pointsf.id_points = obj.idpoints
pointsf.player_id = obj.player_id
pointsf.temporada = season
pointsf.semana = week
pointsf.puntos_ppr = obj.total
pointsf.save()
return HttpResponseRedirect("/dashboard/")
else:
return HttpResponseRedirect("/savepoints/")
def savepoints(request):
actual = get_object_or_404(CurrentWeek, status='active')
week = actual.week
season = actual.season
ptsn = Player.objects.raw('''SELECT DISTINCT player.player_id,(SELECT (SELECT SUM(play_player.passing_yds))+(SELECT SUM(play_player.passing_tds))+(SELECT SUM(play_player.passing_twoptm))+(SELECT SUM(play_player.passing_int))+(SELECT SUM(play_player.rushing_yds))+(SELECT SUM(play_player.rushing_tds))+(SELECT SUM(play_player.rushing_twoptm))+(SELECT SUM(play_player.fumbles_lost))+(SELECT SUM(play_player.receiving_yds))+(SELECT SUM(play_player.receiving_tds))+(SELECT SUM(play_player.receiving_twoptm))+(SELECT SUM(play_player.receiving_rec))+(SELECT SUM(play_player.kicking_fgm))+(SELECT SUM(play_player.kicking_xpmade))+(SELECT SUM(play_player.fumbles_rec_tds))+(SELECT SUM(play_player.kicking_rec_tds))) AS total FROM player INNER JOIN play_player ON player.player_id = play_player.player_id INNER JOIN game ON play_player.gsis_id = game.gsis_id WHERE game.week = %s AND game.season_year = %s AND game.season_type != 'Warmup' AND game.season_type != 'Postseason' GROUP BY player.player_id''', [week, season])
for obj in ptsn:
obj.id = obj.player_id
obj.points = obj.total
formn = PointsForm(request.POST)
pointsfn = formn.save(commit=False)
pointsfn.player_id = obj.player_id
pointsfn.temporada = season
pointsfn.semana = week
pointsfn.points = obj.total
pointsfn.save()
return HttpResponseRedirect("/ligas/")
the forms.py:
class PointsForm(forms.ModelForm):
class Meta:
model = Points
exclude = ["player_id",
"season",
"week",
"puntos"]
class UpdatePointsForm(forms.ModelForm):
class Meta:
model = Points
exclude = ["id_points",
"player_id",
"season",
"week",
"points"]
and the models.py:
class Points(models.Model):
id_points = models.AutoField(primary_key=True, null=False, max_length=15)
player_id = models.CharField(max_length=100)
season = models.IntegerField(max_length=10)
week = models.IntegerField(max_length=10)
puntos = models.IntegerField(max_length=50)
class CurrentWeek(models.Model):
id_week = models.AutoField(primary_key=True, null=False, max_length=15)
week = models.IntegerField(max_length=10)
season = models.IntegerField(max_length=5)
status = models.CharField(max_length=50, default="done")
I'm really stumped so any help will be much appreciated.