diff --git a/services/authorization/oas_commit b/services/authorization/oas_commit index 064e1081f..e3713dde3 100644 --- a/services/authorization/oas_commit +++ b/services/authorization/oas_commit @@ -1 +1 @@ -cfcfc32bc1ae335acecd7bf7ffb60354fdc565ab +0e64886dd0847341800d7191ed193b75413be998 diff --git a/services/authorization/src/stackit/authorization/api_client.py b/services/authorization/src/stackit/authorization/api_client.py index 2f7d319dc..31a16c954 100644 --- a/services/authorization/src/stackit/authorization/api_client.py +++ b/services/authorization/src/stackit/authorization/api_client.py @@ -12,11 +12,13 @@ """ # noqa: E501 import datetime +import decimal import json import mimetypes import os import re import tempfile +import uuid from enum import Enum from typing import Dict, List, Optional, Tuple, Union from urllib.parse import quote @@ -63,8 +65,10 @@ class ApiClient: "bool": bool, "date": datetime.date, "datetime": datetime.datetime, + "decimal": decimal.Decimal, "object": object, } + _pool = None def __init__(self, configuration, header_name=None, header_value=None, cookie=None) -> None: self.config: Configuration = configuration @@ -267,7 +271,7 @@ def response_deserialize( return_data = self.__deserialize_file(response_data) elif response_type is not None: match = None - content_type = response_data.getheader("content-type") + content_type = response_data.headers.get("content-type") if content_type is not None: match = re.search(r"charset=([a-zA-Z\-\d]+)[\s;]?", content_type) encoding = match.group(1) if match else "utf-8" @@ -284,7 +288,7 @@ def response_deserialize( return ApiResponse( status_code=response_data.status, data=return_data, - headers=response_data.getheaders(), + headers=response_data.headers, raw_data=response_data.data, ) @@ -296,6 +300,7 @@ def sanitize_for_serialization(self, obj): If obj is str, int, long, float, bool, return directly. If obj is datetime.datetime, datetime.date convert to string in iso8601 format. + If obj is decimal.Decimal return string representation. If obj is list, sanitize each element in the list. If obj is dict, return the dict. If obj is OpenAPI model, return the properties dict. @@ -311,12 +316,16 @@ def sanitize_for_serialization(self, obj): return obj.get_secret_value() elif isinstance(obj, self.PRIMITIVE_TYPES): return obj + elif isinstance(obj, uuid.UUID): + return str(obj) elif isinstance(obj, list): return [self.sanitize_for_serialization(sub_obj) for sub_obj in obj] elif isinstance(obj, tuple): return tuple(self.sanitize_for_serialization(sub_obj) for sub_obj in obj) elif isinstance(obj, (datetime.datetime, datetime.date)): return obj.isoformat() + elif isinstance(obj, decimal.Decimal): + return str(obj) elif isinstance(obj, dict): obj_dict = obj @@ -326,7 +335,7 @@ def sanitize_for_serialization(self, obj): # and attributes which value is not None. # Convert attribute name to json key in # model definition for request. - if hasattr(obj, "to_dict") and callable(obj.to_dict): + if hasattr(obj, "to_dict") and callable(getattr(obj, "to_dict")): obj_dict = obj.to_dict() else: obj_dict = obj.__dict__ @@ -354,7 +363,7 @@ def deserialize(self, response_text: str, response_type: str, content_type: Opti data = json.loads(response_text) except ValueError: data = response_text - elif re.match(r"^application/(json|[\w!#$&.+-^_]+\+json)\s*(;|$)", content_type, re.IGNORECASE): + elif re.match(r"^application/(json|[\w!#$&.+\-^_]+\+json)\s*(;|$)", content_type, re.IGNORECASE): if response_text == "": data = "" else: @@ -400,12 +409,14 @@ def __deserialize(self, data, klass): if klass in self.PRIMITIVE_TYPES: return self.__deserialize_primitive(data, klass) - elif klass == object: + elif klass is object: return self.__deserialize_object(data) - elif klass == datetime.date: + elif klass is datetime.date: return self.__deserialize_date(data) - elif klass == datetime.datetime: + elif klass is datetime.datetime: return self.__deserialize_datetime(data) + elif klass is decimal.Decimal: + return decimal.Decimal(data) elif issubclass(klass, Enum): return self.__deserialize_enum(data, klass) else: @@ -553,12 +564,14 @@ def __deserialize_file(self, response): os.close(fd) os.remove(path) - content_disposition = response.getheader("Content-Disposition") + content_disposition = response.headers.get("Content-Disposition") if content_disposition: m = re.search(r'filename=[\'"]?([^\'"\s]+)[\'"]?', content_disposition) if m is None: raise ValueError("Unexpected 'content-disposition' header value") - filename = m.group(1) + filename = os.path.basename(m.group(1)) # Strip any directory traversal + if filename in ("", ".", ".."): # fall back to tmp filename + filename = os.path.basename(path) path = os.path.join(os.path.dirname(path), filename) with open(path, "wb") as f: diff --git a/services/authorization/src/stackit/authorization/exceptions.py b/services/authorization/src/stackit/authorization/exceptions.py index 379d04b59..1f9ada4ac 100644 --- a/services/authorization/src/stackit/authorization/exceptions.py +++ b/services/authorization/src/stackit/authorization/exceptions.py @@ -129,7 +129,7 @@ def __init__( self.body = http_resp.data.decode("utf-8") except Exception: # noqa: S110 pass - self.headers = http_resp.getheaders() + self.headers = http_resp.headers @classmethod def from_response( diff --git a/services/authorization/src/stackit/authorization/models/__init__.py b/services/authorization/src/stackit/authorization/models/__init__.py index bcb6b9af3..f15652803 100644 --- a/services/authorization/src/stackit/authorization/models/__init__.py +++ b/services/authorization/src/stackit/authorization/models/__init__.py @@ -12,7 +12,6 @@ Do not edit the class manually. """ # noqa: E501 - # import models into model package from stackit.authorization.models.add_custom_role_response import AddCustomRoleResponse from stackit.authorization.models.add_members_payload import AddMembersPayload diff --git a/services/authorization/src/stackit/authorization/models/add_members_payload.py b/services/authorization/src/stackit/authorization/models/add_members_payload.py index 9dcba75f0..a01cd4e13 100644 --- a/services/authorization/src/stackit/authorization/models/add_members_payload.py +++ b/services/authorization/src/stackit/authorization/models/add_members_payload.py @@ -80,9 +80,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in members (list) _items = [] if self.members: - for _item in self.members: - if _item: - _items.append(_item.to_dict()) + for _item_members in self.members: + if _item_members: + _items.append(_item_members.to_dict()) _dict["members"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/add_role_payload.py b/services/authorization/src/stackit/authorization/models/add_role_payload.py index e339f5041..ca9c58241 100644 --- a/services/authorization/src/stackit/authorization/models/add_role_payload.py +++ b/services/authorization/src/stackit/authorization/models/add_role_payload.py @@ -81,9 +81,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in permissions (list) _items = [] if self.permissions: - for _item in self.permissions: - if _item: - _items.append(_item.to_dict()) + for _item_permissions in self.permissions: + if _item_permissions: + _items.append(_item_permissions.to_dict()) _dict["permissions"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/list_members_response.py b/services/authorization/src/stackit/authorization/models/list_members_response.py index 6d39bd693..ebdb4d4e5 100644 --- a/services/authorization/src/stackit/authorization/models/list_members_response.py +++ b/services/authorization/src/stackit/authorization/models/list_members_response.py @@ -88,9 +88,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in members (list) _items = [] if self.members: - for _item in self.members: - if _item: - _items.append(_item.to_dict()) + for _item_members in self.members: + if _item_members: + _items.append(_item_members.to_dict()) _dict["members"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/list_permissions_response.py b/services/authorization/src/stackit/authorization/models/list_permissions_response.py index 120b03d0a..222e76078 100644 --- a/services/authorization/src/stackit/authorization/models/list_permissions_response.py +++ b/services/authorization/src/stackit/authorization/models/list_permissions_response.py @@ -71,9 +71,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in permissions (list) _items = [] if self.permissions: - for _item in self.permissions: - if _item: - _items.append(_item.to_dict()) + for _item_permissions in self.permissions: + if _item_permissions: + _items.append(_item_permissions.to_dict()) _dict["permissions"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/list_user_memberships_response.py b/services/authorization/src/stackit/authorization/models/list_user_memberships_response.py index d728907a3..e6ecebf55 100644 --- a/services/authorization/src/stackit/authorization/models/list_user_memberships_response.py +++ b/services/authorization/src/stackit/authorization/models/list_user_memberships_response.py @@ -71,9 +71,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in items (list) _items = [] if self.items: - for _item in self.items: - if _item: - _items.append(_item.to_dict()) + for _item_items in self.items: + if _item_items: + _items.append(_item_items.to_dict()) _dict["items"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/list_user_permissions_response.py b/services/authorization/src/stackit/authorization/models/list_user_permissions_response.py index 52b146931..5e4010c9b 100644 --- a/services/authorization/src/stackit/authorization/models/list_user_permissions_response.py +++ b/services/authorization/src/stackit/authorization/models/list_user_permissions_response.py @@ -71,9 +71,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in items (list) _items = [] if self.items: - for _item in self.items: - if _item: - _items.append(_item.to_dict()) + for _item_items in self.items: + if _item_items: + _items.append(_item_items.to_dict()) _dict["items"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/members_response.py b/services/authorization/src/stackit/authorization/models/members_response.py index da3fed2ce..46154d22c 100644 --- a/services/authorization/src/stackit/authorization/models/members_response.py +++ b/services/authorization/src/stackit/authorization/models/members_response.py @@ -90,9 +90,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in members (list) _items = [] if self.members: - for _item in self.members: - if _item: - _items.append(_item.to_dict()) + for _item_members in self.members: + if _item_members: + _items.append(_item_members.to_dict()) _dict["members"] = _items # override the default output from pydantic by calling `to_dict()` of written_at if self.written_at: diff --git a/services/authorization/src/stackit/authorization/models/remove_members_payload.py b/services/authorization/src/stackit/authorization/models/remove_members_payload.py index 49fbc3fa2..5658461f1 100644 --- a/services/authorization/src/stackit/authorization/models/remove_members_payload.py +++ b/services/authorization/src/stackit/authorization/models/remove_members_payload.py @@ -81,9 +81,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in members (list) _items = [] if self.members: - for _item in self.members: - if _item: - _items.append(_item.to_dict()) + for _item_members in self.members: + if _item_members: + _items.append(_item_members.to_dict()) _dict["members"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/role.py b/services/authorization/src/stackit/authorization/models/role.py index 5014984d0..facd5125f 100644 --- a/services/authorization/src/stackit/authorization/models/role.py +++ b/services/authorization/src/stackit/authorization/models/role.py @@ -93,9 +93,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in permissions (list) _items = [] if self.permissions: - for _item in self.permissions: - if _item: - _items.append(_item.to_dict()) + for _item_permissions in self.permissions: + if _item_permissions: + _items.append(_item_permissions.to_dict()) _dict["permissions"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/roles_response.py b/services/authorization/src/stackit/authorization/models/roles_response.py index 0d1659d9e..336e59aa1 100644 --- a/services/authorization/src/stackit/authorization/models/roles_response.py +++ b/services/authorization/src/stackit/authorization/models/roles_response.py @@ -88,9 +88,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in roles (list) _items = [] if self.roles: - for _item in self.roles: - if _item: - _items.append(_item.to_dict()) + for _item_roles in self.roles: + if _item_roles: + _items.append(_item_roles.to_dict()) _dict["roles"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/update_role_payload.py b/services/authorization/src/stackit/authorization/models/update_role_payload.py index 59c70f283..772370476 100644 --- a/services/authorization/src/stackit/authorization/models/update_role_payload.py +++ b/services/authorization/src/stackit/authorization/models/update_role_payload.py @@ -82,9 +82,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in permissions (list) _items = [] if self.permissions: - for _item in self.permissions: - if _item: - _items.append(_item.to_dict()) + for _item_permissions in self.permissions: + if _item_permissions: + _items.append(_item_permissions.to_dict()) _dict["permissions"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/models/user_permission.py b/services/authorization/src/stackit/authorization/models/user_permission.py index cc3a55615..6d132bdb3 100644 --- a/services/authorization/src/stackit/authorization/models/user_permission.py +++ b/services/authorization/src/stackit/authorization/models/user_permission.py @@ -88,9 +88,9 @@ def to_dict(self) -> Dict[str, Any]: # override the default output from pydantic by calling `to_dict()` of each item in permissions (list) _items = [] if self.permissions: - for _item in self.permissions: - if _item: - _items.append(_item.to_dict()) + for _item_permissions in self.permissions: + if _item_permissions: + _items.append(_item_permissions.to_dict()) _dict["permissions"] = _items return _dict diff --git a/services/authorization/src/stackit/authorization/rest.py b/services/authorization/src/stackit/authorization/rest.py index b39602e94..4c73496bf 100644 --- a/services/authorization/src/stackit/authorization/rest.py +++ b/services/authorization/src/stackit/authorization/rest.py @@ -38,12 +38,17 @@ def read(self): self.data = self.response.content return self.data + @property + def headers(self): + """Returns a dictionary of response headers.""" + return self.response.headers + def getheaders(self): - """Returns a dictionary of the response headers.""" + """Returns a dictionary of the response headers; use ``headers`` instead.""" return self.response.headers def getheader(self, name, default=None): - """Returns a given response header.""" + """Returns a given response header; use ``headers.get()`` instead.""" return self.response.headers.get(name, default) @@ -93,6 +98,7 @@ def request(self, method, url, headers=None, body=None, post_params=None, _reque url, data=request_body, headers=headers, + timeout=_request_timeout, ) elif content_type == "application/x-www-form-urlencoded": r = self.session.request( @@ -100,6 +106,7 @@ def request(self, method, url, headers=None, body=None, post_params=None, _reque url, params=post_params, headers=headers, + timeout=_request_timeout, ) elif content_type == "multipart/form-data": # must del headers['Content-Type'], or the correct @@ -113,6 +120,7 @@ def request(self, method, url, headers=None, body=None, post_params=None, _reque url, files=post_params, headers=headers, + timeout=_request_timeout, ) # Pass a `string` parameter directly in the body to support # other content types than JSON when `body` argument is @@ -123,10 +131,17 @@ def request(self, method, url, headers=None, body=None, post_params=None, _reque url, data=body, headers=headers, + timeout=_request_timeout, ) elif headers["Content-Type"].startswith("text/") and isinstance(body, bool): request_body = "true" if body else "false" - r = self.session.request(method, url, data=request_body, headers=headers) + r = self.session.request( + method, + url, + data=request_body, + headers=headers, + timeout=_request_timeout, + ) else: # Cannot generate the request from given parameters msg = """Cannot prepare a request message for provided @@ -140,6 +155,7 @@ def request(self, method, url, headers=None, body=None, post_params=None, _reque url, params={}, headers=headers, + timeout=_request_timeout, ) except requests.exceptions.SSLError as e: msg = "\n".join([type(e).__name__, str(e)])