2009-06-12 95 views
0

我正在尝试创建自定义时间戳字段。Django:时间戳字符串自定义字段

class TimestampKey(models.CharField): 
    __metaclass__ = models.SubfieldBase 

    def __init__(self, *args, **kwargs): 
     import time 

     kwargs['unique'] = True 
     kwargs['max_length'] = 20 
     kwargs['auto_created'] = True 
     kwargs['editable']=False 
     super(TimestampKey, self).__init__(*args, **kwargs) 

    def to_python(self, value) : 
     return value 

    def get_db_prep_value(self, value) : 
     try: 
      import time 
      t = time.localtime() 
      value = reduce(lambda a,b:str(a)+str(b),t) 
     except ValueError: 
      value = {} 

     return value 


class Table1(models.Model): 
     f = TimestampKey(primary_key=True) 
     n = .... 

它将适当的时间戳值存储在数据库中。但它不填充对象中的字段'f'。

如:

t1 = Table1(n="some value") 
t1.f -> blank 

t1.save() 

t1.f -> blank. 

这就是问题所在。我是否错过了一些东西,以便它不填充该字段? 请在此阐明一些。

谢谢。

回答

1

get_db_prep_value方法只为数据库准备一个值,但不会以任何方式将准备好的值发送回Python对象。为此,我认为你需要pre_save方法。

幸运的是,DateField和DateTimeField上已有一个“auto_now”选项,它使用pre_save来做你想做的事。尝试:

class Table1(models.Model): 
    f = models.DateTimeField(auto_now=True) 

(如果你必须编写自己的pre_save,看看如何auto_now修改实际模型实例在/django/db/models/fields/__init__.py上线486-492:

def pre_save(self, model_instance, add): 
    if self.auto_now or (self.auto_now_add and add): 
     value = datetime.datetime.now() 
     setattr(model_instance, self.attname, value) 
     return value 
    else: 
     return super(DateField, self).pre_save(model_instance, add) 

+0

谢谢krubo。这实际上帮助了我。 – MSW 2009-06-13 01:46:21

3

是否明智使用时间戳作为主键?如果你的数据库使用ISO 8601或任何时间格式,其中第二个是最小的时间间隔......好吧,无论如何,我的观点是你没有保证,特别是如果这将是一个面向网络的应用程序,两个条目将在最短的时间间隔内解决。也就是说,如果最小的时间间隔是一秒钟,就像在ISO 8601中一样,如果你在同一秒内得到两个保存请求,你将会得到一个错误条件。为什么不坚持自动递增整数键,只是将时间戳设置为自己的字段?

+0

是的,如果我将它用作日期(),那么你是对的。但是我打算将整个时间戳用作VARCHAR。如果你看看代码,你可能会看到我正在将元组缩减为一个字符串。所以,不应该是一个问题。 – MSW 2009-06-13 01:47:36