import tempfile class Storage(object): """Storage is organized as follow: $ROOT/images//json $ROOT/images//layer $ROOT/repositories/// """ # Useful if we want to change those locations later without rewriting # the code which uses Storage repositories = 'repositories' images = 'images' # Set the IO buffer to 64kB buffer_size = 64 * 1024 @staticmethod def temp_store_handler(): tmpf = tempfile.TemporaryFile() def fn(buf): try: tmpf.write(buf) except IOError: pass return tmpf, fn #FIXME(samalba): Move all path resolver in each module (out of the base) def images_list_path(self, namespace, repository): return '{0}/{1}/{2}/_images_list'.format(self.repositories, namespace, repository) def image_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/'.format(self.images, namespace, repository, image_id) def image_json_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/json'.format(self.images, namespace, repository, image_id) def image_mark_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/_inprogress'.format(self.images, namespace, repository, image_id) def image_checksum_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/_checksum'.format(self.images, namespace, repository, image_id) def image_layer_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/layer'.format(self.images, namespace, repository, image_id) def image_ancestry_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/ancestry'.format(self.images, namespace, repository, image_id) def repository_namespace_path(self, namespace, repository): return '{0}/{1}/{2}/'.format(self.images, namespace, repository) def image_file_trie_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/files.trie'.format(self.images, namespace, repository, image_id) def image_file_diffs_path(self, namespace, repository, image_id): return '{0}/{1}/{2}/{3}/diffs.json'.format(self.images, namespace, repository, image_id) def get_direct_download_url(self, path, expires_in=60): return None def get_content(self, path): raise NotImplementedError def put_content(self, path, content): raise NotImplementedError def stream_read(self, path): raise NotImplementedError def stream_read_file(self, path): raise NotImplementedError def stream_write(self, path, fp): raise NotImplementedError def list_directory(self, path=None): raise NotImplementedError def exists(self, path): raise NotImplementedError def remove(self, path): raise NotImplementedError def get_size(self, path): raise NotImplementedError