How to Export Foreign Key Field to Excel In Django Views.py? - excel

Getting this Error:- 'Restaurant' object has no attribute 'menu_here__starters'
I'm using Django-Excel Lib
In My Models.py
Class Restaurant(models.Model):
name = models.CharField(max_length=20)
area = models.CharField(max_length = 30)
menu_here = models.ForeignKey(Menu)
Class Menu(models.Model):
starters = models.CharField(max_length = 50)
desserts = models.CharField(max_length = 50)
In my Views.py
def download_excel_4(request):
query_set = Restaurant.objects.all() # Foreign column is Menu
column_names = ['menu_here__starters','menu_here__desserts' ]
return excel.make_response_from_query_sets(
query_set,
column_names,
'xls',
file_name="Restaurant With Complete Menu Database"
)

The make_response_from_query_sets takes the objects returned by query_set and displays it along with column names which should correspond with the field names of the objects.
The column_names acts like a filter displaying only the field names you want but it cannot further query after the objects are got. Therefore valid names are ['name', 'area', 'menu_here'].
An alternative would be to get objects as a dict with the related fields while querying using the .values() method and then using excel.make_response_from_records.
query_record = Restaurant.objects.all().values('name', 'area', 'menu_here__starters', 'menu_here__desserts')
return excel.make_response_from_records(
query_record,
'xls',
file_name="Restaurant With Complete Menu Database"
)

Related

How to handle foreign-keys during the iteration through attributes of Django model (Python)?

Dear Django/Python experts. I have a Django model (python class) which contain standard fields and also fields represented by foreign keys. It is easy to iterate throught attributes of a model however I have no idea how to handle foreign keys?
Here is a model nr.1 Employee containing foreign key which refers to another model EmployeeLocation:
class Employee(models.Model):
firstname = models.CharField(max_length=128)
lastname = models.CharField(max_length=128)
location = models.ForeignKey(EmployeeLocation, on_delete=models.CASCADE)
and here is a model nr.2 EmployeeLocation:
class EmployeeLocation(models.Model):
id = models.BinaryField(primary_key=True, max_length=16, null=False)
city = models.CharField(max_length=32)
and now I iterate via attributes of Employee in the following way:
# Collecting names of class fields.
field_names = [f.name for f in Employee._meta.get_fields()]
for current_attribute in field_names:
field_value = str(getattr(my_employee, current_attribute))
This solution works fine for standard attributes but does not return values when reaches the location which is a foreign key.
To tackle this issue I did the following stunts :) :
I have made a dictionary containing names of foreign keys and as values I have placed Django queryset, that gets a value - but this is not an elegant hack :) In this way then iteration ecounters attribute which is foreign-key, it takes value from dictionary (which is generated by queryset):
FKs = {'location': EmployeeLocation.objects.filter(id=my_employee.location_id)[0].city,
...
...}
# Collecting names of class fields.
field_names = [f.name for f in Employee._meta.get_fields()]
for current_attribute in field_names:
if current_attribute in FKs.keys():
field_value = FKs[current_attribute]
else:
field_value = str(getattr(my_employee, current_attribute))
Please tell me in simple way how shall I realize it properly. Thank you so much in advance :)

update a field in all records of a table through a single form Django 4

I have the following model 'ARTICULO', which I have created and templates to edit it individually
# MODEL
class Articulo(models.Model):
id = models.AutoField(primary_key=True, verbose_name='codigo')
nombre = models.CharField(max_length=100, verbose_name='nombre elemento')
cantidad = models.PositiveSmallIntegerField(verbose_name='cantidad total')
cantidad_disponible = models.PositiveSmallIntegerField(verbose_name='cantidad disponible', default=5)
UNIDAD = 'und'
KILO = 'kg'
LITRO = 'L'
UNIDADES_BASE = [
(UNIDAD, 'unidades'),
(KILO, 'Kilogramos'),
(LITRO, 'litros'),
]
unidades = models.CharField(max_length=3, choices=UNIDADES_BASE, default=UNIDAD, verbose_name='unidad base')
area = models.CharField(max_length=100, verbose_name='tipo inventario', default='primaria')
persona_asignada = models.CharField(max_length=100, default='almacen', verbose_name='persona asignada')
def __str__(self):
trama = "articulo: " + self.nombre
return trama
#form to edit individually
class ArticuloEditarForm(forms.ModelForm):
class Meta:
model = Articulo
fields = ['nombre', 'cantidad', 'unidades']
# view for generate form of individual article
def editar(request, id):
articulo = Articulo.objects.get(id=id)
formulario = ArticuloEditarForm(request.POST or None, instance=articulo)
if formulario.is_valid() and request.POST:
formulario.save()
return redirect('inventario_inicio')
return render(request, 'inventario/editar.html', {'formulario': formulario})
but additionally I would like to create a page where I can perform an update of all the records of the table as a whole (as in the following image)
When clicking on the button, all records with the checkbox activated are updated in the database according to the value indicated in their text box.
From what I have investigated so far, I think I understand that I should use the form.Form class and not form.ModelForm in combination with formsets, but in the attempts I have made, I tried trying to define a form in this way, but it does not work for me.
class AsignarReservasArticulos(forms.Form):
articulos = Articulo.objects.all()
for x in articulos:
print(x)
participa = forms.BooleanField(label='')
My deduction tells me that I must generate the form that I show in my image in an integral way from my FORM or I must make a part in the form and another in the view.

How to overwrite Django Admin result_list?

Django newbie here..
I am working on a project that I need to do search in Django Admin Panel.
I have a model named SearchModel and it has colums named "id", "word" and an object called Desert and this object has '1' as id
I have another model named Result000 ('000' refers to the first three letters of md5 of "Desert" word). It has columns named "id", "word_id", "score", "title" and has an object named "Sahara Desert" whose word_id is the same as the id of the Desert object in the first table.
No ForeignKey or any other relation types between those table's items
here's the question:
When I search for Desert in SearchModel's search field. I want to list all objects in table Result000 which have word_id same as id of Desert object in SearchModel
here's my current code:
# root/admin.py
class BookAdmin(admin.ModelAdmin):
def __init__(self, model, admin_site):
self.list_display = [field.name for field in model._meta.fields]
self.search_fields = [field.name for field in model._meta.fields]
self.temp_model = "SearchModel"
self.temp_term = ""
self.word_id = None
self.search_term = self.temp_term
super().__init__(model, admin_site)
def get_search_results(self, request, queryset, search_term):
queryset, may_have_duplicate = super().get_search_results(
request, queryset, search_term
)
if len(search_term) > 0: self.search_term = search_term
else: self.search_term = self.temp_term
hashable, ret = self.md5_er(LowerTurkish(self.search_term).lower())
if hashable: table_name = f"Result{ret}"
else: table_name = request.path_info.split("/")[-2]
try:
# modelname = apps.get_model("root", table_name)
modelname = self.model_finder(table_name)
print("try içinde modelname: ", modelname)
messages.info(
request,
f"`{table_name}` modeli içindeki arama sonuçları")
word_id = self.model_finder(self.temp_model).objects.values_list("id")
std_content = modelname.objects.filter(word_id=word_id)
queryset = std_content
except:
std_content = self.model_finder(self.temp_model).objects.all()
# "nonetype not iterable" hatasının çözümü
return queryset, may_have_duplicate
def model_finder(self, table_name):
return apps.get_model("root", table_name)
def md5_er(self, data):
"""
:#params: data: md5 hashi alınacak olan veri, type: string
"""
hash_object = hashlib.md5(data.encode())
md5_hash = hash_object.hexdigest()
if md5_hash != "d41d8cd98f00b204e9800998ecf8427e":
"d41d8cd98f00b204e9800998ecf8427e refers md5 of empty string"
ret = md5_hash[:3]
return True, ret
else:
return False, False
I can get what I want if the SearchModel and Desert table have the same column names, but it doesn't work when the column names are changed. I've read almost all of Django's documentation, looked up examples from the internet, and looked at almost all entries on stackoverflow but as I said I'm Django newbie 🥲. Thanks in advance

Django models filter query not recognising field

I am working on a Django project, filter query function is not working as expected
I imported the model, did migration
I don't understand where the code is wrong, it is not able to recognize the field (rating)
Model I created
class Problem(models.Model):
contestID = models.IntegerField()
index = models.CharField(max_length=5)
name = models.CharField(max_length=50)
rating = models.IntegerField(default=0)
link = models.URLField(max_length=200)
tags = models.ManyToManyField(Tag,blank=True,related_name="Problme")
My code in views: ( object.all() is working properly but the filter is not working)
def fetchProblems(min = 0, max = 5000, filter = False):
if not filter:
problemSet = Problem.objects.all().values()
else:
problems = Problem.objects.filter(rating < max,rating > min)
return problemSet
My error : ( rating not defined) (basically I tried all fields it shows all not defined)
NameError: name 'rating' is not defined
Thank you for help
The correct syntax is
.filter(rating__gt=min)
You can find out more about the various lookup types (separated by double underscores) over at https://docs.djangoproject.com/en/3.2/topics/db/queries/#field-lookups

Odoo: on create save current ID in a many2one field of another model

what I'm trying to do is I'm creating a custom.modify.price model for products, where I'm able to choose a certain criteria to result in a selection of products, then I fill in a percentage that affects the prices of all the previous selection. I want it to create a new record, for each product in the selection, in a another model custom.sale.price and each record should be holding the ID of the custom.modify.price record that created it in a many2one field. The thing is I can create a new record of this custom.sale.price by overriding the custom.modify.price create method and feeding it the values to do so, but I am not able to feed it the current ID of "not yet created" custom.modify.price record
class CustomModifyPrice(models.Model):
date = fields.Datetime(string='Date', required=True, default=fields.Datetime.now())
brand_id = fields.Many2many(comodel_name="custom.brand", string="Brand", required=False, )
origin_id = fields.Many2many(comodel_name="custom.country", string="Origin", required=False, )
percentage = fields.Float(string="Percentage")
product_ids = fields.Many2many(comodel_name="custom.product", string="Products", readonly=True, )
#api.model
def create(self, vals):
values = {'product_id': product.id, 'date': vals['date'], 'sell_price': mod_sell_price, 'modification_id': self.id}###self.id returns nothing here
price = self.env['custom.sale.price'].create(values)
result = super(CustomModifyPrice, self).create(vals)
return result
class CustomSalePrice(models.Model):
product_id = fields.Many2one(comodel_name="custom.product", string="Product", required=False, )
date = fields.Datetime(string="Date", default=fields.Datetime.now())
sell_price = fields.Float(string="Selling Price")
sale_id = fields.Many2one(comodel_name="custom.sale", string="Sales Order", required=False, )
You need to to create custom.modify.price and update values with the result id then create custom.sale.price
#api.model
def create(self, vals):
result = super(CustomModifyPrice, self).create(vals)
values = {'modification_id': result.id, ...}
self.env['custom.sale.price'].create(values)
return result

Resources