2011-03-09 10 views
20

Tengo un modelo de base de datos que se está actualizando en función de los cambios en los datos remotos (a través de un raspador de HTML).Detectar si un modelo ha cambiado antes de llamar a guardar en Django

quiero mantener un campo llamado changed - una marca de tiempo que indica cuando la última vez que los valores de ese modelo cambiado de lo que eran antes (tenga en cuenta que esto es diferente de auto_now ya que estos campos se actualizan cada vez que el método de un modelo save se llama)

Aquí es mi pregunta:

En el método de un modelo save, hay una manera fácil de detectar si los valores actuales de una instancia de modelo son diferentes de los valores en la base de datos? O bien, ¿hay algún método alternativo para mantener fácilmente una marca de tiempo changed?

+0

alguien ha tenido experiencia con 'django-de las extensiones del? Tienen una clase 'TimeStampedModel' que podría hacer lo que estoy buscando, pero la documentación no es muy útil (http://packages.python.org/django-extensions/model_extensions.html) – advait

Respuesta

1

Me parece que lo que quiere es Signals: http://docs.djangoproject.com/en/1.2/topics/signals/

se puede utilizar una señal de post_save para actualizar un campo relacionado en otro modelo para almacenar el valor anterior. Luego, en la próxima ronda, tendrías algo para comparar.

3

Puede intentar calcular una suma de comprobación de los valores de registro cuando los guarda. Luego, cuando lo leas más tarde, vuelve a calcular la suma de comprobación y verifica si ha cambiado. Tal vez la función crc32 en el módulo estándar Python zlib. (No estoy seguro de qué tipo de rendimiento que esto tendría. Así que es posible que desee investigar eso.)

+0

Interesante. ¿Hay una manera fácil de ver la totalidad de los datos de un objeto para que se pueda verificar fácilmente? Y es posible que dos instancias idénticas (que tienen los mismos valores de campo) de un objeto tengan diferentes "datos" (la entrada leída por nuestra función de suma de comprobación). – advait

+0

1. El método que usaría es simplemente obtener todos los datos de campo, convertir cada uno a una cadena, concatenarlo todo, y suma de comprobación eso. 2. En teoría, es posible tener dos instancias con diferentes datos con la misma suma de comprobación, pero es muy poco probable. Si realmente está preocupado por eso, puede usar una función hash criptográfica en la que eso sea casi imposible; pero sería más costoso de calcular. – dappawit

+0

@dappawit, también debería considerar ordenar una concatenación que podría causar problemas con su lógica. hash ("a = 1b = 2c = 3")! = hash ("a = 1c = 3b = 2"). De todos modos, otro buen enfoque. – Chris

34

Si guarda su instancia a través de un formulario, puede marcar form.has_changed().

+13

Y si quiere saber qué campos cambiaron: 'form.changed_data' –

+0

Gracias, necesitaban ambos :) – Lee

Cuestiones relacionadas