2012-02-26 3 views
0

Я создал подкласс объекта Django File, чтобы позаботиться о удаленном файле. Я также хотел сделать ленивую версию, создав RemoteFileLazy, подклассифицирующий класс Lazyobject, но он не работает так, как я ожидал. Я получаю сообщение об ошибке.RuntimeError: максимальная глубина рекурсии: почему?

import urllib2 
from django.core.files.base import File 
from django.utils.functional import LazyObject 

class RemoteFile(File): 

    def __init__(self, url): 
     super(RemoteFile, self).__init__(urllib2.urlopen(urllib2.Request(url))) 

    def __str__(self): 
     return 'Remote content' 

    def __nonzero__(self): 
     return True 

    def open(self, mode=None): 
     self.seek(0) 

    def close(self): 
     pass 

    def chunks(self, chunk_size=None): 
    # CHUNKS taking care of no known size! 
     if not chunk_size: 
      chunk_size = self.DEFAULT_CHUNK_SIZE 

     if hasattr(self, 'seek'): 
      self.seek(0) 
     # Assume the pointer is at zero... 
     counter = self.size 

     while True: 
      data = self.read(chunk_size) 
      if not data: 
       break 
      yield data 

class RemoteFileLazy(LazyObject): 

    def __init__(self, url): 
     # # as said in the django code: For some reason, we have to inline LazyObject.__init__ here to avoid 
     # recursion 
     self._wrapped = None 
     self.url = url 

    def _setup(self): 
     self._wrapped = RemoteFile(self.url) 

Когда я запускаю этот код:

rfl = filehelper.RemoteFileLazy(url="http://www.google.fr") 

Я получил эту ошибку:

RuntimeError: maximum recursion depth exceeded 

Любая идея? Я не называл LazyObject. init как было указано в коде django, хотя ... Я думаю, что «self.url = url» в init метод запускает эту ошибку правильно? Значит, я не могу использовать ленивый объект с атрибутами?

Спасибо.

Traceback:

c:\Users\Michael\Dropbox\development\tools\Portable Python 2.7.2.1-django1.3.1\App\lib\site-packages\django\utils\functional.pyc in __getattr__(self, name) 
    274  def __getattr__(self, name): 
    275   if self._wrapped is None: 
--> 276    self._setup() 
    277   return getattr(self._wrapped, name) 
    278 

C:\Users\Michael\Dropbox\development\projects\django-socialdealing\socialdealing\apps\etl\utils\filehelper.py in _setup(self) 
    58 
    59  def _setup(self): 
---> 60   self._wrapped = RemoteFile(self.url) 
    61 
    62 

c:\Users\Michael\Dropbox\development\tools\Portable Python 2.7.2.1-django1.3.1\App\lib\site-packages\django\utils\functional.pyc in __getattr__(self, name) 
    274  def __getattr__(self, name): 
    275   if self._wrapped is None: 
--> 276    self._setup() 
    277   return getattr(self._wrapped, name) 
    278 
+1

Не могли бы вы вставить часть трассировки, чтобы мы могли видеть, какая функция была бесконечно рекурсивно? –

+0

Конечно, добавляю. – Michael

ответ

1

Вы не можете назначить атрибуты на LazyObject обертке обычного способа, он предназначен, чтобы рассматриваться как ему это обернутый объект, поэтому пытается передать доступ через к завернутому объект, который еще не был создан в точке, которую вы назначили url.

Чтобы это исправить, заменить

self.url = url # this tries to retrieve the wrapped object to set its 'url' attribute 

с

self.__dict__['url'] = url # this actually stores an attribute on the LazyObject container. 

Как и в сторону, когда «заимствование» Джанго внутренностей, как это вы хотите проверить действительно трудно каждый раз при обновлении Джанго ,

Смежные вопросы