async def query(self, query_body: Union[QueryBody, str], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) if isinstance(query_body, str): query_body = QueryBody.parse(query_body) if len(query_body.query.ordering_clause) > 1: raise Exception("Ordering emulated only for 1 ordering clause") eq_clauses = [clause for clause in query_body.query.where_clause if clause.relation == "eq"] + \ [WhereClause(column="owner", relation="eq", term=owner)] data = self.data["documents"] r = [ d for d in data if all([d[clause.column] == clause.term for clause in eq_clauses]) ] for ordering in self.table_body.table_options.clustering_order: order = ordering.order col = ordering.name sorted_result = sorted(r, key=lambda doc: doc[col]) r = sorted_result if order == "DESC": r.reverse() return {"documents": r[0:query_body.max_results]}
async def update_document(self, doc, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) doc["owner"] = owner data = json.load( self.data_path.open('r')) if self.data_path.exists() else { "documents": [] } index = [ i for i, d in enumerate(data["documents"]) if self.primary_key_id(d) == self.primary_key_id(doc) ] if len(index) == 1: data["documents"][index[0]] = doc else: data["documents"].append(doc) self.data_path.open('w').write(json.dumps(data, indent=4)) return {}
async def delete_group(self, prefix: Union[Path, str], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) path = self.get_full_path(owner, prefix) if path.exists(): shutil.rmtree(path)
async def post_text(self, path: Union[str, Path], text, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) full_path = self.get_full_path(owner, path) create_dir_if_needed(full_path) full_path.open('w').write(text) return {}
async def post_json(self, path: Union[str, Path], json: JSON, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) full_path = self.get_full_path(owner, path) create_dir_if_needed(full_path) full_path.open('w').write(_json.dumps(json, indent=4)) return {}
async def post_file(self, form: FileData, headers: Mapping[str, str] = None, **_kwargs): owner = form.owner if not headers: headers = {} if not owner: owner = get_default_owner(headers) full_path = self.get_full_path(owner, form.objectName) create_dir_if_needed(full_path) full_path.open('wb').write(form.objectData) return {}
async def get_bytes(self, path: Union[str, Path], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) full_path = self.get_full_path(owner, path) if not full_path.is_file(): raise HTTPException(status_code=404, detail="File not found") return full_path.open('rb').read()
async def list_files(self, prefix: Union[str, Path], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) owner = owner[1:] results = [[(Path(root) / f).relative_to(self.bucket_path / owner) for f in files] for root, _, files in os.walk(self.bucket_path / owner / prefix)] return [{"name": str(r)} for r in flatten(results)]
async def delete(self, path: Union[str, Path], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) full_path = self.get_full_path(owner, path) if full_path.is_dir(): shutil.rmtree(full_path) return os.remove(full_path) return {}
async def post_object(self, path: Union[Path, str], content: bytes, content_type: str, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) if isinstance(content, str): content = str.encode(content) data = content full_path = self.get_full_path(owner, path) create_dir_if_needed(full_path) full_path.open('wb').write(data)
async def query(self, query_body: Union[QueryBody, str], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) if isinstance(query_body, str): query_body = QueryBody.parse(query_body) if len(query_body.query.ordering_clause) > 1: raise Exception("Ordering emulated only for 1 ordering clause") data = json.loads(self.data_path.read_text())["documents"] where_clauses = [ WhereClause(column="owner", relation="eq", term=owner) ] + query_body.query.where_clause def is_matching(doc): for clause in where_clauses: matching = clause.is_matching(doc) if not matching: return False return True r = [doc for doc in data if is_matching(doc)] query_ordering = { clause.name: clause.order for clause in query_body.query.ordering_clause } for ordering in self.table_body.table_options.clustering_order: order = ordering.order col = ordering.name sorted_result = sorted(r, key=lambda doc: doc[col]) r = sorted_result if order == "DESC" or (col in query_ordering and query_ordering[col] == "DESC"): r.reverse() return {"documents": r[0:query_body.max_results]}
async def delete_document(self, doc, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) self.data["documents"] = [ d for d in self.data["documents"] if not (self.primary_key_id(d) == self.primary_key_id(doc) and d["owner"] == owner) ] return {}
async def delete_document(self, doc: Dict[str, any], owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) data = json.load(self.data_path.open()) data["documents"] = [ d for d in data["documents"] if not (self.primary_key_id(d) == self.primary_key_id(doc) and d["owner"] == owner) ] self.data_path.write_text(json.dumps(data, indent=4)) return {}
async def update_document(self, doc, owner: Union[str, None], headers: Mapping[str, str] = None, **_kwargs): if not headers: headers = {} if not owner: owner = get_default_owner(headers) doc["owner"] = owner index = [ i for i, d in enumerate(self.data["documents"]) if self.primary_key_id(d) == self.primary_key_id(doc) ] if len(index) == 1: self.data["documents"][index[0]] = doc else: self.data["documents"].append(doc) return {}