Reputation: 145
first of all, I'm aware that this question might've been answered already, but there are two reasons why I'm opening another question: One, obviously, is I'm struggling with the Django syntax. Secondly, and perhaps more importantly, I'm not quite sure whether my database setup makes even sense at this point. So, please bear with me.
I work in a hospital and one of my daily stuggles is that, oftentimes, one single drug can have a lot of different names. So, I thought that'd be a good task to practice some Django with.
Basically I want two databases: One that simply links the drugs "nick name" to it's actual name. And another one which links the actual name to some additional information, something along the lines of a wiki page.
What I've come up with so far:
(django)django@ip:~/medwiki$ cat medsearch/models.py
from django.db import models
# Create your models here.
class medsearch(models.Model):
proprietary_name = models.CharField(max_length = 100, unique = True)
non_proprietary_name = models.CharField(max_length = 100, unique = True)
def __str__(self):
return self.non_proprietary_name
class medwiki(models.Model):
proprietary_name = models.ForeignKey('medisearch', on_delete=models.CASCADE)
cetegory = models.CharField(max_length = 255)
#wiki = models.TextField() etc.
def __str__(self):
return self.proprietary_name
(django)django@ip-:~/medwiki$
So, I can add a new "medsearch object" just fine. However, when adding the "Category" at medwiki I get __str__ returned non-string (type medsearch)
. Presumably, because there's more than one key in medsearch? I thus suspect that "FroeignKey" is not suited for this application and I know that there are other ways to link databases in Django. However, I don't know which one to choose and how to implement it correctly.
Hopefully, some of you have some ideas?
EDIT: Here's what I've come up with so far:
class Proprietary_name(models.Model):
proprietary_name = models.CharField(max_length = 100, unique = True)
def __str__(self):
return self.proprietary_name
class Category(models.Model):
category = models.CharField(max_length = 100, unique = True)
def __str__(self):
return self.category
class Mediwiki(models.Model):
proprietary_name = models.ManyToManyField(Proprietary_name)
non_proprietary_name = models.CharField(max_length = 100, unique = True)
category = models.ManyToManyField(Category)
wiki_page = models.TextField()
def __str__(self):
return self.non_proprietary_name
Now I can attribute different categorys and different proprietary_names to one drug. Which works great so far.
So does looking up the non-proprietary_name when I know the proprietary "nick name".
>>> Mediwiki.objects.get(proprietary_name__proprietary_name="Aspirin")
<Mediwiki: acetylsalicylic acid>
>>>
However, I'd also like to display all the proprietary_names, when I know the non_proprietary_name. Do I have to further change the database design, or am I just missing some other thing here?
Upvotes: 0
Views: 662
Reputation: 5496
This would work:
return self.proprietary_name.proprietary_name
But that doesn't really make sense !
The main issue is that you've called the foreign key to medsearch
, proprietary_name
.
The second issue is just a convention one. In Python (and many programming languages), classes must start with an uppercase letter.
The following would be better:
class MedSearch(models.Model):
proprietary_name = models.CharField(max_length=100, unique=True)
non_proprietary_name = models.CharField(max_length=100, unique=True)
def __str__(self):
return self.non_proprietary_name
class MedWiki(models.Model):
med_search = models.ForeignKey('MedSearch', on_delete=models.CASCADE, related_name='wikis')
cetegory = models.CharField(max_length = 255)
#wiki = models.TextField() etc.
def __str__(self):
return self.med_serach.proprietary_name
Upvotes: 2
Reputation: 599490
As you note, the proprietary_name
field on medwiki is a ForeignKey. You can't return that value directly from the __str__
method because that needs to return a string. You need to convert that value into a string before returning it: either use the default string representation of the medsearch instance:
return str(self.proprietary_name)
or choose a specific string field to return:
return self.proprietary_name.proprietary_name
Upvotes: 1