How can I override __str__ in models.py?

Apologies if this is a silly question, I am pretty new to python and django.

I am following along with a django tutorial, and we are creating a fake movie site that lists movies by genre, title, etc.

I am currently trying to override the __str__ function in the models.py file, so rather than displaying Genre (1), it displays the actual genre (ex. "Action").

Here's how my models.py looks currently:

from tkinter import CASCADE
from django.db import models
from django.utils import timezone

# Create your models here.
class Genre(models.Model):
    name = models.CharField(max_length=255)

    def __str__ (self):
        return self.name

class Movie(models.Model):
    title = models.CharField(max_length=255)
    release_year = models.IntegerField()
    number_in_stock = models.IntegerField()
    daily_rate = models.FloatField()
    genre = models.ForeignKey(Genre, on_delete=models.CASCADE)
    date_created = models.DateTimeField(default=timezone.now)

However, vscode is underlining the

def __str__ (self):

When I hover over it, it tells me:

str does not return str pylint(E0307: invalid -str- returned

I tried looking at other solutions, but I could not find one that seemed to match my scenario, so I do apologize if this has been solved elsewhere, and I am too incompetent to understand the problem.

Thanks for your patience!

This question has a couple of good illustrations of why it's important to understand your code before you rely too heavily on IDEs and tools like pylint. I've two suggestions:

  1. The pylint error is just a warning to indicate that your code might have a problem - it is not an absolute fact. The E0307 error says:

    Used when a __str__ method returns something which is not a string.

    It would be more accurate if it had said "when the pylint checker cannot be sure that you're returning a string". In this case, it's because it doesn't recognise that a Django CharField will in fact return a valid string instance. Your existing __str__ method would work perfectly fine if you ran the code - regardless of what pylint thinks.

    You can work around this by forcing the return value to look like a string, e.g., with:

    return str(self.name)
    

    or

    return f"{self.name}"
    

    But it would be equally valid to disable the check for this line in pylint, with the understanding of why it reported the error. Just applying a fix found on Stack Overflow without understanding the issue is going to make it hard to debug your code in future.

  2. There is a second, completely unrelated issue in your code which will cause you problems later, and that is this line:

    from tkinter import CASCADE
    

    I am pretty confident that this has been inserted by your IDE, without your explicitly adding it, because you tried to use CASCADE in your ForeignKey. This is the IDE trying to be helpful - unfortunately it has imported something completely useless, that can cause you problems when you try to deploy your code.

Both of these highlight an important principle: don't rely on IDEs or linters. They are not a substitute for understanding your own code.

Back to Top