i have a litte probleme i have a legacy database that have a users table and in the table of users the last_login field is an integerfield when I have extend an absractbaseuser and put the last_login in IntegerField it give a me an error when trying to connect to django dashboard it say that the last_login field expected a number but got date time value any help please ?
CodePudding user response:
are you making last_login field in your user's table? Django's AbstractBaseUser has default last_login field which is a datetime field. if you are inheriting your model with django's AbstractBaseUser you don't have to create last_login field by yourself
here's what you can do. if you have and old database with user's data and you want to use that data in your current table. Create your own abstractbaseuser class and remove last_login from it
class MyNewAbstractBaseUser(models.Model):
password = models.CharField(_('password'), max_length=128)
is_active = True
REQUIRED_FIELDS = []
# Stores the raw password if set_password() is called so that it can
# be passed to password_changed() after the model is saved.
_password = None
class Meta:
abstract = True
def __str__(self):
return self.get_username()
def save(self, *args, **kwargs):
super().save(*args, **kwargs)
if self._password is not None:
password_validation.password_changed(self._password, self)
self._password = None
def get_username(self):
"""Return the username for this User."""
return getattr(self, self.USERNAME_FIELD)
def clean(self):
setattr(self, self.USERNAME_FIELD, self.normalize_username(self.get_username()))
def natural_key(self):
return (self.get_username(),)
@property
def is_anonymous(self):
"""
Always return False. This is a way of comparing User objects to
anonymous users.
"""
return False
@property
def is_authenticated(self):
"""
Always return True. This is a way to tell if the user has been
authenticated in templates.
"""
return True
def set_password(self, raw_password):
self.password = make_password(raw_password)
self._password = raw_password
def check_password(self, raw_password):
"""
Return a boolean of whether the raw_password was correct. Handles
hashing formats behind the scenes.
"""
def setter(raw_password):
self.set_password(raw_password)
# Password hash upgrades shouldn't be considered password changes.
self._password = None
self.save(update_fields=["password"])
return check_password(raw_password, self.password, setter)
def set_unusable_password(self):
# Set a value that will never be a valid hash
self.password = make_password(None)
def has_usable_password(self):
"""
Return False if set_unusable_password() has been called for this user.
"""
return is_password_usable(self.password)
def get_session_auth_hash(self):
"""
Return an HMAC of the password field.
"""
key_salt = "django.contrib.auth.models.AbstractBaseUser.get_session_auth_hash"
return salted_hmac(key_salt, self.password).hexdigest()
@classmethod
def get_email_field_name(cls):
try:
return cls.EMAIL_FIELD
except AttributeError:
return 'email'
@classmethod
def normalize_username(cls, username):
return unicodedata.normalize('NFKC', username) if isinstance(username, str) else username
use this class. removed last_login from it. Inherit your User model with this instead of Django's AbstractBaseUser. it has all the functionality of it minus last_login field and you're good to go. let me know if you need more explanation
CodePudding user response:
here is my code source :
from django.db import models
from django.contrib.auth.models import AbstractBaseUser,BaseUserManager
from .helper import get_current_unix_timestamp
from django.contrib.auth.signals import user_logged_in
class MyUserManager(BaseUserManager):
def create_user(self, username,password=None):
"""
Creates and saves a User with the given email, date of
birth and password.
"""
if not username:
raise ValueError('user must have a username')
user = self.model(
username=username,
)
user.set_password(password)
user.save(using=self._db)
return user
def create_superuser(self, username, password=None):
"""
Creates and saves a superuser with the given email, date of
birth and password.
"""
user = self.create_user(
username,
password=password,
)
user.is_admin = True
user.is_superuser = True
user.is_staff = True
user.save(using=self._db)
return user
class Account(AbstractBaseUser,PermissionsMixin):
id = models.AutoField(primary_key=True,verbose_name='ID',)
username = models.CharField(max_length=50, blank=True, null=True,unique=True)
password = models.CharField(max_length=255, blank=True, null=True)
email = models.CharField(max_length=255, blank=True, null=True)
ip = models.CharField(max_length=255,null=True,blank=True)
date_registered = models.IntegerField(default=get_current_unix_timestamp())
last_login = models.IntegerField(null=True,blank=True)
member_group_id = models.IntegerField(blank=True, null=True)
credits = models.FloatField(blank=True, null=True)
notes = models.TextField(blank=True, null=True)
status = models.IntegerField(blank=True, null=True)
reseller_dns = models.TextField(blank=True, null=True)
owner_id = models.IntegerField(blank=True, null=True)
override_packages = models.TextField(blank=True, null=True)
hue = models.CharField(max_length=50, blank=True, null=True)
theme = models.IntegerField(blank=True, null=True)
timezone = models.CharField(max_length=255, blank=True, null=True)
api_key = models.CharField(max_length=64, blank=True, null=True)
is_admin = models.BooleanField(default=False)
is_superuser = models.BooleanField(default=False)
is_staff = models.BooleanField(default=False)
is_active = models.BooleanField(default=True)
objects = MyUserManager()
USERNAME_FIELD = 'username'
class Meta:
managed = True
db_table = 'users'
ordering = ['username']
def __str__(self):
return self.username
def update_last_login(sender, user, **kwargs):
"""
A signal receiver which updates the last_login date for
the user logging in.
"""
user.last_login = get_current_unix_timestamp()
user.save(update_fields=['last_login'])
user_logged_in.send(update_last_login)
the get_current_unix_timestamp function source code :
import datetime
def get_current_unix_timestamp():
"""this function retrun a unix format datetime"""
return int(datetime.datetime.now().strftime('%s'))