Suppose I have a model with a field that restricts another model. For example, a Thing
whose name
has to be in the current set of AllowedThingNames
. The set of allowed_thing_names changes (infrequently) by an external source. I have code to get that external source and create AllowedThingNames
as needed.
Here is some code:
models.py:
class AllowedThingName(models.Model):
name = models.CharField(max_length=100, unique=True)
class Thing(models.Model):
name = models.CharField(max_length=100)
def __save__(self, *args, **kwargs):
if AllowedThingName.objects.filter(name=self.name).exists():
return super().save(*args, **kwargs)
return None
tasks.py:
@shared_task
def import_new_names():
response = request.get("some/external/url/where/allowed/names/are/listed")
new_names = clever_way_of_parsing_response(response.content)
for new_name in new_names:
AllowedThingName.objects.get_or_create(name=new_name)
I have created a fixture of AllowedThingNames
and I run the loaddata
command at startup.
I'm not sure what the best way is to keep the set of AllowedThingNames
up-to-date, though.
One solution is to periodically (via a task, or a cronjob, or whatever) call the import_new_names
function above and then call dumpdata
to overwrite the fixture. This will save it in the db and make sure that it gets re-loaded the next time the project restarts.
Does anybody in StackOverflow-Land have any better ideas?
Have you considered creating a ForeignKey relationship between Thing
and AllowedThingName
? Something along the lines of
class AllowedThingName(models.Model):
name = models.CharField(max_length=100, unique=True)
class Thing(models.Model):
name = models.ForeignKey(AllowedThingName, on_delete=models.CASCASE)