2011-12-23 20 views
5

estoy usando un campo Django personalizada para representar JSON datos codificados:Uso forms.TextArea para el campo JSON personalizada en el sitio de administración de Django

class JSONField(models.TextField): 
    __metaclass__ = models.SubfieldBase 

    def to_python(self, value): 
     if value == "": 
      return None 

     try: 
      if isinstance(value, basestring): 
       return json_decode(value) 
     except ValueError: 
      pass 

     return value 

    def get_prep_value(self, value): 
     if value == "": 
      return None 
     if isinstance(value, dict) or isinstance(value, dict): 
      value = json_encode(value) 
      return super(JSONField, self).get_prep_value(value) 

    def value_to_string(self, obj): 
     value = self._get_val_from_obj(obj) 
     return self.get_db_prep_value(value,connection=None) 

El campo en sí funciona bien. Sin embargo, no es posible editar a través del sitio de administración ya que la cadena de la base de datos está decodificada con JSON y convertida a diccionario, de modo que cuando se representa el sitio de administración, no se muestra la cadena JSON real de la base de datos (por ejemplo, {foo; "bar"}), pero su representación del diccionario (por ejemplo, {u'foo ': u'bar'}).

Obviamente, esto genera problemas al guardar el objeto de la base de datos, porque la representación de cadena del diccionario no es una cadena JSON válida.

Lo que me gustaría tener es el sitio de administración mostrando el valor real de la base de datos (es decir, la cadena tal como se guarda en la base de datos), en lugar de la cadena del objeto Python devuelto por to_python.

Mi intento sería escribir un widget personalizado para esto que simplemente vuelva a llamar a json_encode en el diccionario, pero ¿hay una manera mejor?

Respuesta

4

value_from_object ayudará a resolver el problema. Su implementación depende de qué serializador se haya utilizado, pero para SimpleJson debería verse como:

from django.utils import simplejson as json 
from django.core.serializers.json import DjangoJSONEncoder 

class JSONField(models.TextField): 
.... 

    def value_from_object(self, obj): 
     return json.dumps(super(JSONField, self).value_from_object(obj)) 
+0

Esto ayudó. ¡Muchas gracias! – ChrisM

Cuestiones relacionadas