[Django]-Non-database field in Django model

25๐Ÿ‘

โœ…

As long as you do not want the property to persist, I donโ€™t see why you canโ€™t create a property like you described. I actually do the same thing on certain models to determine which are editable.

class Email(EntryObj):
    ts = models.DateTimeField(auto_now_add=True)
    body = models.TextField(blank=True)
    user = models.ForeignKey(User, blank=True, null=True)
    editable = False
    ...


class Note(EntryObj):
    ts = models.DateTimeField(auto_now_add=True)
    note = models.TextField(blank=True)
    user = models.ForeignKey(User, blank=True, null=True)
    editable = True
๐Ÿ‘คJack M.

16๐Ÿ‘

Creating a property on the model will do this, but you wonโ€™t be able to query on it.

Example:

from django.db import models

class Person(models.Model):
    first_name = models.CharField(max_length=30)
    last_name = models.CharField(max_length=30)

    def _get_full_name(self):
        return "%s %s" % (self.first_name, self.last_name)

    def _set_full_name(self, combined_name):
        self.first_name, self.last_name = combined_name.split(' ', 1)

    full_name = property(_get_full_name)

    full_name_2 = property(_get_full_name, _set_full_name)

Usage:

from mysite.models import Person

a = Person(first_name='John', last_name='Lennon')
a.save()
a.full_name
'John Lennon'

# The "full_name" property hasn't provided a "set" method.
a.full_name = 'Paul McCartney'
Traceback (most recent call last):
    ...
AttributeError: can't set attribute

# But "full_name_2" has, and it can be used to initialise the class.
a2 = Person(full_name_2 = 'Paul McCartney')
a2.save()
a2.first_name
'Paul'

7๐Ÿ‘

To make it an instance variable (so each instance gets its own copy), youโ€™ll want to do this

class Book(models.Model):
    title = models.CharField(max_length=75)
    #etc

    def __init__(self, *args, **kwargs):
        super(Foo, self).__init__(*args, **kwargs)
        self.editable = False

Each Book will now have an editable that wont be persisted to the database

๐Ÿ‘คThe Mad Bug

1๐Ÿ‘

If you want i18n support:

# Created by BaiJiFeiLong@gmail.com at 2022/5/2
from typing import Optional

from django.db import models
from django.utils.translation import gettext_lazy as _


class Blog(models.Model):
    title = models.CharField(max_length=128, unique=True, verbose_name=_("Title"))
    content = models.TextField(verbose_name=_("Content"))
    _visitors: Optional[int] = None

    @property
    def visitors(self):
        return self._visitors

    @visitors.setter
    def visitors(self, value):
        self._visitors = value

    visitors.fget.short_description = _("Visitors")

๐Ÿ‘คBaiJiFeiLong

Leave a comment