Django-tastypie: Erro: "classe Meta não tem atributo 'object_class'"

Criado em 21 jul. 2016  ·  6Comentários  ·  Fonte: django-tastypie/django-tastypie

Oi,

Quando atualizei minha torta saborosa de 13.3 para o cabeçote, tentar executar meu webapp gerou este erro:

Request Method: GET
Request URL: http://192.168.0.104:8888/accounts/login/?next=/dashboard/

Django Version: 1.8.8
Python Version: 2.7.12
Installed Applications:
('longerusernameandemail',
 'django.contrib.admin',
 'django.contrib.auth',
 'django.contrib.contenttypes',
 'django.contrib.sessions',
 'django.contrib.messages',
 'django.contrib.staticfiles',
 'tastypie',
 'myapp',
 'widget_tweaks',
 'corsheaders')
Installed Middleware:
('corsheaders.middleware.CorsMiddleware',
 'django.contrib.sessions.middleware.SessionMiddleware',
 'django.middleware.common.CommonMiddleware',
 'django.middleware.csrf.CsrfViewMiddleware',
 'django.contrib.auth.middleware.AuthenticationMiddleware',
 'django.contrib.messages.middleware.MessageMiddleware',
 'django.middleware.clickjacking.XFrameOptionsMiddleware')

Traceback:
File "/home/user/anaconda2/lib/python2.7/site-packages/django/core/handlers/base.py" in get_response
  119.                 resolver_match = resolver.resolve(request.path_info)
File "/home/user/anaconda2/lib/python2.7/site-packages/django/core/urlresolvers.py" in resolve
  365.             for pattern in self.url_patterns:
File "/home/user/anaconda2/lib/python2.7/site-packages/django/core/urlresolvers.py" in url_patterns
  401.         patterns = getattr(self.urlconf_module, "urlpatterns", self.urlconf_module)
File "/home/user/anaconda2/lib/python2.7/site-packages/django/core/urlresolvers.py" in urlconf_module
  395.             self._urlconf_module = import_module(self.urlconf_name)
File "/home/user/anaconda2/lib/python2.7/importlib/__init__.py" in import_module
  37.     __import__(name)
File "/home/user/webserver/myapp/urls.py" in <module>
  7. from myapp.api import UserResource
File "/home/user/webserver/myapp/api.py" in <module>
  303. class MyResource(ModelResource):
File "/home/user/anaconda2/lib/python2.7/site-packages/tastypie/resources.py" in __new__
  1797.             if meta and meta.object_class:

Exception Type: AttributeError at /accounts/login/
Exception Value: class Meta has no attribute 'object_class'

Se eu voltar para a versão 13.3 (commit a71dd6e85e18ec38e978e904c0c7a91dee11043d), então funcionará bem.

Alguma ideia do que pode estar errado?
Obrigado

bug unconfirmed

Comentários muito úteis

@SeanHayes : Acabei de ter esse mesmo problema, porque estava usando um recurso de base abstrata. Aqui está uma reprodução:

class BaseResource(ModelResource):
    class Meta:
        authentication = DefaultAuthentication()

class FooResource(BaseResource):
    class Meta(BaseResource.Meta):
        resource_name = 'foo'
        queryset = Foo.objects.all()

class BarResource(BaseResource):
    class Meta(BaseResource.Meta):
        resource_name = 'bar'
        queryset = Bar.objects.all()

Isso falha com o mesmo rastreamento de pilha colado por hashemian, na linha class BaseResource(ModelResource): , porque o BaseResource não tem um queryset.

Minha solução agora é adicionar object_class = None a BaseResource.Meta , então tudo funciona.

Acho que a correção real é alterar a linha de resources.py 1797 para if meta and getattr(meta, 'object_class'):

... ou se for um comportamento desejável para as subclasses de ModelResource lançar um erro quando o queryset não está definido, então esse erro pode ser mais explícito. Não acho que meu BaseResource deva falhar, desde então, não tenho certeza de como fazer o que estou tentando fazer aqui.

Obrigado!

Todos 6 comentários

Você poderia postar seus recursos?

em meu urls.py, eu importo tastypie.api.Api e, em seguida, importo meus recursos um por um. Parece que ele falha assim que tenta carregar o primeiro recurso. Por exemplo, este é um dos recursos, mas mesmo se eu comentar este, ele trava no próximo recurso.

class MyResource(ModelResource):
    class Meta:
        queryset = MyModel.objects.all()
        fields = ['my_field']
        allowed_methods = ['get']
        resource_name = 'my_resource'
        authentication = BasicAuthentication()
        include_resource_uri = False

Acabei de adicionar testes de regressão, mas eles não conseguiram reproduzir o erro: 3e1f5527b698c7121d4c5434d073b08d364d31f2

Mais alguma informação que você possa fornecer? Quão próximo está o seu exemplo de código do seu código real?

Obrigado Sean por investigar isso. O código de amostra é muito semelhante e basicamente apenas alterei os nomes. Vou verificar novamente do meu lado e tentar ver se há algum elemento que pode ser relevante e faltando.

Encerrando, fique à vontade para comentar se tiver mais informações.

@SeanHayes : Acabei de ter esse mesmo problema, porque estava usando um recurso de base abstrata. Aqui está uma reprodução:

class BaseResource(ModelResource):
    class Meta:
        authentication = DefaultAuthentication()

class FooResource(BaseResource):
    class Meta(BaseResource.Meta):
        resource_name = 'foo'
        queryset = Foo.objects.all()

class BarResource(BaseResource):
    class Meta(BaseResource.Meta):
        resource_name = 'bar'
        queryset = Bar.objects.all()

Isso falha com o mesmo rastreamento de pilha colado por hashemian, na linha class BaseResource(ModelResource): , porque o BaseResource não tem um queryset.

Minha solução agora é adicionar object_class = None a BaseResource.Meta , então tudo funciona.

Acho que a correção real é alterar a linha de resources.py 1797 para if meta and getattr(meta, 'object_class'):

... ou se for um comportamento desejável para as subclasses de ModelResource lançar um erro quando o queryset não está definido, então esse erro pode ser mais explícito. Não acho que meu BaseResource deva falhar, desde então, não tenho certeza de como fazer o que estou tentando fazer aqui.

Obrigado!

Esta página foi útil?
0 / 5 - 0 avaliações