Get Django to return only the first 50 characters of text stored as a models.TextField()

Question:

In Python Crash Course chapter 18 we make a Learning Log website.

I can’t make this return just the first 50 characters of a >50 character long entry when I go into the Learning Log website that we make (through localhost:8000). It doesn’t show the ellipsis either, it just shows the whole entry.

from django.db import models
from django.contrib.auth.models import User

class Topic(models.Model):
    """A topic the user is learning about"""
    text = models.CharField(max_length=200)
    date_added = models.DateTimeField(auto_now_add=True)
    owner = models.ForeignKey(User, on_delete=models.CASCADE)

    def __str__(self):
        """Return a string representation of the model."""
        return str(self.text)

class Entry(models.Model):
    """Something specific learned about a topic"""
    topic = models.ForeignKey(Topic, on_delete=models.PROTECT)
    text = models.TextField()
    date_added = models.DateTimeField(auto_now_add=True)

    class Meta:
        verbose_name_plural = 'entries'

    def __str__(self):
        """Return a string representation of the model."""
        if len(self.text) > 50:
            return f"{str(self.text)[:50]}..."
        else:
            return f"{str(self.text)}"

It is the same whether I include the if len(self.text) > 50 statement or not.
My code differs somewhat from the book in that:

  1. I use on_delete=models.PROTECT, as I understand that CASCADE
    can cause weird issues like accidentally getting something
    deleted that you didn’t intend to delete
  2. I use str(self.text) instead of just self.text in the __str__ definitions; if I don’t it raises a pylint error "Value ‘self.text’ is unsubscriptable". I can still make entries without the str() conversion – it still won’t show only the first 50 characters however.

Is it something about how models.TextField() function that causes this? Am I supposed to have to do the str() conversions to make the self.text variable "subscriptable"?

Asked By: fuffens1

||

Answers:

In Django 3.0 models.TextField returns a string(str) if you call it as self.text or Entry.text. So you don’t need to call str() function.

If you want to get first 50 characters:

def __str__(self):
    return self.text[:50]

In Python if you use [:50] for a subscriptable object, it will return first 50 parts (or all if it have less than 50 parts) of the object.

I wish my answer helps you.

Answered By: mhn2

According to what I see you can just say

def __str__(self):
    return self.text[:50]

but also

You can use truncate word filter when calling it in the HTML form

You did not show the views.py but say you have a view that returns to a page all the Entries in the Entry Class you and you happen to say
{% for Entry in Entries %}
you would just add

{{ Entry:text|truncatewords:50 }}

{% endfor %}

you can learn more at The Docs

Answered By: casualhuman

Also you can do this:

def __str__(self):
    if self.text[50:]:
        return f"{self.text[:50]}..."
    else:
        return f"{self.text[:50]}"
Answered By: Semen
def __str__(self):
        """Return a string representation of the model."""
        if len(self.text) > 50:
            return f"{str(self.text)[:50]}..."
        else:
            return f"{str(self.text)}"

This function gives you the first 50 characters, please remove and run your program.
Textfield support unlimited text in this field.

Answered By: prashant shastri
Categories: questions Tags: ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.