2015-03-11 4 views
0

Я прочитал документацию, но я не совсем уверен, как реализовать serializer.serialize для объектов JSON на моем view.py. Если кто-нибудь может помочь мне понять это немного лучше. У меня есть следующий код в моем view.py:Django "не JSON serializable" - ajax, views.py - Как реализовать?

@user_passes_test(lambda u: u.is_superuser) 
def ProjDetails(request): 
    proj_id = request.GET['proj_id'] 
    proj = Proj.objects.filter(id=proj_id) 
    role_list = ProjRole.objects.filter(proj=proj) 
    proj = { 
     "proj": proj, 
     "roles": [] 
    } 
    for r in role_list: 
     proj['roles'].append(r.id) 

    return HttpResponse(json.dumps(proj), content_type='application/json; charset=UTF-8') 

Я пытаюсь вызвать это с .ajax (я до сих пор работает на AJAX, так что это, вероятно, не правильно):

$('#proj_list #sel_proj').click(function(){ 
    $('div.sel').removeClass("sel"); 
    $(this).addClass("sel"); 

    var project_id = $(this).data('id'); 

    $.ajax({ 
     url:'../../proj_details', 
     data: {proj_id: proj_id}, 
     // dataType: 'html', 
     success: function(data){ 
      $('#proj_display').html(data) 
     }, 
     error: function() { 
      alert("Failed to find the project!") 
     } 
}); 

Как только я получаю вызов JSON для работы, я больше сосредоточусь на ajax.

Самая большая проблема, я получаю сообщение об ошибке 500 HTTP с:

TypeError at ../proj_details 
[<Project: Example>] is not JSON serializable 

Я использую Django 1.7, но я даже добавил SESSION_SERIALIZER = 'django.contrib.sessions.serializers.PickleSerializer' к моему settings.py без удачи. Поэтому я импортировал сериализаторы из django.core и пытался использовать serializer.serialize, но я не понимаю, как реализовать его, я думаю, потому что мои ошибки продолжают ухудшаться. Я видел другие сообщения с одинаковой ошибкой, но до сих пор не понимаю моих конкретных требований.

+++++++++++++++ EDIT +++++++++++++++++++

Таким образом, единственный способ, которым я был возможность получить эту работу без множественных ошибок, круговыми ошибок, несколько ошибок аргументов, и т.д., является следующее:

def ProjDetails(request): 
    def date_handler(obj): 
     return obj.strftime("%B %d, %Y") if hasattr(obj, 'strftime') else obj 

     proj_id = request.GET['proj_id'] 
     proj = Proj.objects.get(id=proj_id) 
     corp = Corp.objects.get(id=proj.corp.id) 
     role_list = ProjRole.objects.filter(proj=proj).all() 
     proj = { 
     "proj": { 
      'title': proj.title, 
      'id': proj.id, 
      'date': proj.date, 
      'description': proj.description 
     } 
     "roles": [], 
     "company": { 
      'name': corp.name, 
      'pic': unicode(corp.pic), 
     } 
    } 
    for r in role_list: 
     proj['roles'].append(r.name) 

return HttpResponse(json.dumps(proj, default=date_handler), content_type='application/json; charset=UTF-8') 

Единственное, что мне не нравится это, я на самом деле нужно вручную тянуть какие атрибуты I хотите от модели в словаре, а не все атрибуты, извлекаемые из модели, а затем я могу выбрать, какие из них я хочу использовать в своих шаблонах. Я бы предпочел не тянуть все, как мой пример выше. 'roles' = [] дает мне некоторые икоты, потому что я не могу заставить его работать, когда есть несколько ролей для объекта proj.

Мне нравится метод Юджина, потому что он был бы чище, но я не могу заставить его работать с моделью корпуса. В таблицах proj есть corp_id, но я продолжаю получать corp_id, это не атрибут, когда я пытаюсь использовать его с помощью .value(). Get() для объекта proj. Я не понимаю, как реализовать ответ grzgrzgrz3. Я обычно больше работаю с JS, HTML и CSS, и я новичок в Django/python для веб-разработки.

Так что любые предложения, чтобы сделать это более эффективным было бы здорово. Спасибо !!

ответ

0

Мой ответ, как описано выше выше. Это то, что сработало для меня.

def ProjDetails(request): 
    def date_handler(obj): 
     return obj.strftime("%B %d, %Y") if hasattr(obj, 'strftime') else obj 

     proj_id = request.GET['proj_id'] 
     proj = Proj.objects.get(id=proj_id) 
     corp = Corp.objects.get(id=proj.corp.id) 
     role_list = ProjRole.objects.filter(proj=proj).all() 
     proj = { 
     "proj": { 
      'title': proj.title, 
      'id': proj.id, 
      'date': proj.date, 
      'description': proj.description 
     } 
     "roles": [], 
     "company": { 
      'name': corp.name, 
      'pic': unicode(corp.pic), 
     } 
    } 
    for r in role_list: 
     proj['roles'].append(r.name) 

return HttpResponse(json.dumps(proj, default=date_handler), content_type='application/json; charset=UTF-8') 
1

Экземпляр модели Django не может быть сериализован, вы должны использовать метод values ​​() для извлечения dict вместо экземпляра класса. Кроме того, вы можете использовать метод только(), чтобы получить поле идентификатора только для ролей:

proj = Proj.objects.filter(id=proj_id).values().get() 
role_list = ProjRole.objects.only("id").filter(proj__id=proj_id) 
proj = { 
    "proj": proj, 
    "roles": role_list 
} 
+0

Затем я получаю ValueError: 'invalid literal для int() с базой 10:' Может быть, это имеет какое-то отношение к фактическим данным в базе данных? Я также видел что-то об использовании списка(). Может ли это быть необходимым? – charlwillia6

+0

Извините, я отредактировал ответ –

+0

Спасибо за ответ. Теперь я получаю атрибут AttributeError, который говорит, что объект «Proj» не имеет атрибутов «значения» – charlwillia6

1

Написать обычай HttpResponse и обрабатывать там все не сериализуемые объекты Python/Django.

class HttpJsonResponse(HttpResponse): 
    content_type="application/json" 


    def __init__(self,data): 

     def json_serial(obj): 
      """JSON serializer for objects not serializable by default json code""" 

      if isinstance(obj, datetime.date): 
       serial = obj.isoformat() 
       return serial 

     json_data = json.dumps(data, indent=4, default=json_serial) 
     super(HttpJsonResponse, self).__init__(json_data, self.content_type) 

В примере функции преобразование json_serialdatetime.date объекта в строке объект, который является сериализуемым.

* UPDATE

Вы можете смешать оба ответа.

def ProjDetails(request): 
    proj_id = request.GET['proj_id'] 
    proj = Proj.objects.filter(id=proj_id).values().get() 
    corp = Corp.objects.filter(id=proj.corp.id).values().get() 
    role_list = ProjRole.objects.filter(proj=proj).values().all() 
    proj = { 
     "proj": proj, 
     "roles": role_list, 
     "company": corp 
    } 

    return HttpJsonResponse(proj) 

Убедитесь, что вы импортируете модуль datetime.

import datetime 

вместо DateTime класс

import datetime.datetime 
+0

Есть ли пример реализации этого в представлении? Я до сих пор не могу получить сообщение об ошибке «не является JSON-сериализуемым», или я получаю сообщение об ошибке, в которой требуется 2 аргумента. – charlwillia6

+0

Я получаю это при использовании вашего примера: 'isinstance() arg 2 должен быть классом, типом или кортежем классов и типов. – charlwillia6

+0

Вы добавили свой пользовательский оператор if в функцию' json_serial'? Если да, покажите это. – grzgrzgrz3