2015-08-26 21:08:42 +00:00
|
|
|
import cStringIO as StringIO
|
|
|
|
import hashlib
|
2014-04-03 21:31:46 +00:00
|
|
|
|
2015-08-26 21:08:42 +00:00
|
|
|
from collections import defaultdict
|
|
|
|
from uuid import uuid4
|
2014-04-03 21:31:46 +00:00
|
|
|
|
2015-08-26 21:08:42 +00:00
|
|
|
from storage.basestorage import BaseStorageV2
|
|
|
|
|
2018-10-31 18:13:25 +00:00
|
|
|
_GLOBAL_FAKE_STORAGE_MAP = defaultdict(StringIO.StringIO)
|
2015-08-26 21:08:42 +00:00
|
|
|
|
|
|
|
class FakeStorage(BaseStorageV2):
|
2016-11-10 18:54:04 +00:00
|
|
|
def __init__(self, context):
|
2016-01-15 16:15:40 +00:00
|
|
|
super(FakeStorage, self).__init__()
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map = (defaultdict(StringIO.StringIO)
|
|
|
|
if context == 'local' else _GLOBAL_FAKE_STORAGE_MAP)
|
2016-01-15 16:15:40 +00:00
|
|
|
|
2014-04-03 21:31:46 +00:00
|
|
|
def _init_path(self, path=None, create=False):
|
|
|
|
return path
|
|
|
|
|
2017-09-25 21:14:28 +00:00
|
|
|
def get_direct_download_url(self, path, request_ip=None, expires_in=60, requires_cors=False, head=False):
|
2016-01-19 20:52:34 +00:00
|
|
|
try:
|
|
|
|
if self.get_content('supports_direct_download') == 'true':
|
2016-08-24 16:55:33 +00:00
|
|
|
return 'http://somefakeurl?goes=here'
|
2016-01-19 20:52:34 +00:00
|
|
|
except:
|
|
|
|
pass
|
|
|
|
|
|
|
|
return None
|
|
|
|
|
2014-04-03 21:31:46 +00:00
|
|
|
def get_content(self, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
if not path in self._fake_storage_map:
|
|
|
|
raise IOError('Fake file %s not found. Exist: %s' % (path, self._fake_storage_map.keys()))
|
2015-05-29 22:08:17 +00:00
|
|
|
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map.get(path).seek(0)
|
|
|
|
return self._fake_storage_map.get(path).read()
|
2014-04-03 21:31:46 +00:00
|
|
|
|
|
|
|
def put_content(self, path, content):
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map.pop(path, None)
|
|
|
|
self._fake_storage_map[path].write(content)
|
2014-04-03 21:31:46 +00:00
|
|
|
|
|
|
|
def stream_read(self, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
io_obj = self._fake_storage_map[path]
|
2015-08-26 21:08:42 +00:00
|
|
|
io_obj.seek(0)
|
|
|
|
while True:
|
|
|
|
buf = io_obj.read(self.buffer_size)
|
|
|
|
if not buf:
|
|
|
|
break
|
|
|
|
yield buf
|
2014-04-03 21:31:46 +00:00
|
|
|
|
2015-06-28 10:29:22 +00:00
|
|
|
def stream_read_file(self, path):
|
2015-11-20 19:47:56 +00:00
|
|
|
return StringIO.StringIO(self.get_content(path))
|
2015-06-28 10:29:22 +00:00
|
|
|
|
2014-09-11 19:33:10 +00:00
|
|
|
def stream_write(self, path, fp, content_type=None, content_encoding=None):
|
2018-10-31 18:13:25 +00:00
|
|
|
out_fp = self._fake_storage_map[path]
|
2015-08-26 21:08:42 +00:00
|
|
|
out_fp.seek(0)
|
|
|
|
self.stream_write_to_fp(fp, out_fp)
|
2014-04-03 21:31:46 +00:00
|
|
|
|
|
|
|
def remove(self, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map.pop(path, None)
|
2014-04-03 21:31:46 +00:00
|
|
|
|
|
|
|
def exists(self, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
if self._fake_storage_map.get('all_files_exist', None):
|
2016-05-05 17:55:24 +00:00
|
|
|
return True
|
2018-10-31 18:13:25 +00:00
|
|
|
return path in self._fake_storage_map
|
2014-09-09 19:54:03 +00:00
|
|
|
|
|
|
|
def get_checksum(self, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
return hashlib.sha256(self._fake_storage_map[path].read()).hexdigest()[:7]
|
2015-08-26 21:08:42 +00:00
|
|
|
|
|
|
|
def initiate_chunked_upload(self):
|
|
|
|
new_uuid = str(uuid4())
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map[new_uuid].seek(0)
|
2015-08-26 21:08:42 +00:00
|
|
|
return new_uuid, {}
|
|
|
|
|
2015-11-30 20:45:45 +00:00
|
|
|
def stream_upload_chunk(self, uuid, offset, length, in_fp, _, content_type=None):
|
2018-10-31 18:13:25 +00:00
|
|
|
upload_storage = self._fake_storage_map[uuid]
|
2015-08-26 21:08:42 +00:00
|
|
|
upload_storage.seek(offset)
|
2018-10-31 18:13:25 +00:00
|
|
|
|
2015-12-10 04:16:33 +00:00
|
|
|
try:
|
|
|
|
return self.stream_write_to_fp(in_fp, upload_storage, length), {}, None
|
|
|
|
except IOError as ex:
|
|
|
|
return 0, {}, ex
|
2015-08-26 21:08:42 +00:00
|
|
|
|
|
|
|
def complete_chunked_upload(self, uuid, final_path, _):
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map[final_path] = self._fake_storage_map[uuid]
|
|
|
|
self._fake_storage_map.pop(uuid, None)
|
2015-08-26 21:08:42 +00:00
|
|
|
|
|
|
|
def cancel_chunked_upload(self, uuid, _):
|
2018-10-31 18:13:25 +00:00
|
|
|
self._fake_storage_map.pop(uuid, None)
|
2016-07-11 18:33:29 +00:00
|
|
|
|
|
|
|
def copy_to(self, destination, path):
|
2018-10-31 18:13:25 +00:00
|
|
|
if self.exists('break_copying'):
|
|
|
|
raise IOError('Broken!')
|
|
|
|
|
|
|
|
if self.exists('fake_copying'):
|
|
|
|
return
|
|
|
|
|
|
|
|
if self.exists('except_copying'):
|
|
|
|
raise Exception("I'm an exception!")
|
|
|
|
|
2016-07-11 18:33:29 +00:00
|
|
|
content = self.get_content(path)
|
|
|
|
destination.put_content(path, content)
|