Skip to content

Commit

Permalink
deprecate
Browse files Browse the repository at this point in the history
  • Loading branch information
richardm-stripe committed Dec 11, 2023
1 parent fd8949d commit 364f6db
Show file tree
Hide file tree
Showing 6 changed files with 84 additions and 20 deletions.
10 changes: 9 additions & 1 deletion stripe/_api_requestor.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
from stripe import oauth_error # noqa: SPY101
from stripe._encode import _api_encode
from stripe._multipart_data_generator import MultipartDataGenerator

from urllib.parse import urlencode, urlsplit, urlunsplit
from stripe._stripe_response import StripeResponse, StripeStreamResponse

Expand Down Expand Up @@ -78,7 +79,14 @@ def __init__(
self._default_proxy = proxy

@classmethod
@_util.deprecated(
"This method is internal to stripe-python and the public interface will be removed in a future stripe-python version"
)
def format_app_info(cls, info):
return cls._format_app_info(info)

@classmethod
def _format_app_info(cls, info):
str = info["name"]
if info["version"]:
str += "/%s" % (info["version"],)
Expand Down Expand Up @@ -230,7 +238,7 @@ def specific_oauth_error(self, rbody, rcode, resp, rheaders, error_code):
def request_headers(self, api_key, method):
user_agent = "Stripe/v1 PythonBindings/%s" % (_version.VERSION,)
if stripe.app_info:
user_agent += " " + self.format_app_info(stripe.app_info)
user_agent += " " + self._format_app_info(stripe.app_info)

ua = {
"bindings_version": _version.VERSION,
Expand Down
10 changes: 9 additions & 1 deletion stripe/_error.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@
import stripe # noqa: IMP101
from stripe._error_object import ErrorObject

from stripe import _util
import warnings


class StripeError(Exception):
_message: Optional[str]
Expand Down Expand Up @@ -43,7 +46,9 @@ def __init__(
self.headers = headers or {}
self.code = code
self.request_id = self.headers.get("request-id", None)
self.error = self.construct_error_object()
with warnings.catch_warnings():
warnings.simplefilter("ignore", DeprecationWarning)
self.error = self.construct_error_object()

def __str__(self):
msg = self._message or "<empty message>"
Expand All @@ -68,6 +73,9 @@ def __repr__(self):
self.request_id,
)

@_util.deprecated(
"For internal stripe-python use only. The public interface will be removed in a future version."
)
def construct_error_object(self) -> Optional[ErrorObject]:
if (
self.json_body is None
Expand Down
12 changes: 11 additions & 1 deletion stripe/_request_metrics.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
class RequestMetrics(object):
from stripe import _util


class _RequestMetrics(object):
def __init__(self, request_id, request_duration_ms):
self.request_id = request_id
self.request_duration_ms = request_duration_ms
Expand All @@ -8,3 +11,10 @@ def payload(self):
"request_id": self.request_id,
"request_duration_ms": self.request_duration_ms,
}


@_util.deprecated(
"This class is for internal stripe-python use only. The public interface will be removed in a future version."
)
class RequestMetrics(_RequestMetrics):
pass
48 changes: 40 additions & 8 deletions stripe/_stripe_object.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,9 @@
from stripe import _util

from stripe._stripe_response import StripeResponse, StripeStreamResponse
import warnings

_util.deprecated


@overload
Expand Down Expand Up @@ -70,13 +73,19 @@ def _serialize_list(


class StripeObject(Dict[str, Any]):
class ReprJSONEncoder(json.JSONEncoder):
class _ReprJSONEncoder(json.JSONEncoder):
def default(self, o: Any) -> Any:
if isinstance(o, datetime.datetime):
# pyright complains that _encode_datetime is "private", but it's
# private to outsiders, not to stripe_object
return _encode_datetime(o)
return super(StripeObject.ReprJSONEncoder, self).default(o)
return super(StripeObject._ReprJSONEncoder, self).default(o)

@_util.deprecated(
"For internal stripe-python use only. The public interface will be removed in a future version"
)
class ReprJSONEncoder(_ReprJSONEncoder):
pass

_retrieve_params: Dict[str, Any]
_previous: Optional[Dict[str, Any]]
Expand Down Expand Up @@ -307,6 +316,9 @@ def refresh_from(
self._previous = values

@classmethod
@_util.deprecated(
"This will be removed in a future version of stripe-python."
)
def api_base(cls) -> Optional[str]:
return None

Expand Down Expand Up @@ -351,10 +363,14 @@ def _request(
stripe_version = stripe_version or self.stripe_version
api_key = api_key or self.api_key
params = params or self._retrieve_params
api_base = None
with warnings.catch_warnings():
warnings.simplefilter("ignore")
api_base = self.api_base() # pyright: ignore[reportDeprecated]

requestor = stripe.APIRequestor(
key=api_key,
api_base=self.api_base(),
api_base=api_base,
api_version=stripe_version,
account=stripe_account,
)
Expand All @@ -378,9 +394,13 @@ def request_stream(
) -> StripeStreamResponse:
if params is None:
params = self._retrieve_params
api_base = None
with warnings.catch_warnings():
warnings.simplefilter("ignore")
api_base = self.api_base() # pyright: ignore[reportDeprecated]
requestor = stripe.APIRequestor(
key=self.api_key,
api_base=self.api_base(),
api_base=api_base,
api_version=self.stripe_version,
account=self.stripe_account,
)
Expand All @@ -407,23 +427,26 @@ def __repr__(self) -> str:

def __str__(self) -> str:
return json.dumps(
self.to_dict_recursive(),
self._to_dict_recursive(),
sort_keys=True,
indent=2,
cls=self.ReprJSONEncoder,
cls=self._ReprJSONEncoder,
)

@_util.deprecated(
"Deprecated. The public interface will be removed in a future version."
)
def to_dict(self) -> Dict[str, Any]:
return dict(self)

def to_dict_recursive(self) -> Dict[str, Any]:
def _to_dict_recursive(self) -> Dict[str, Any]:
def maybe_to_dict_recursive(
value: Optional[Union[StripeObject, Dict[str, Any]]]
) -> Optional[Dict[str, Any]]:
if value is None:
return None
elif isinstance(value, StripeObject):
return value.to_dict_recursive()
return value._to_dict_recursive()
else:
return value

Expand All @@ -434,7 +457,16 @@ def maybe_to_dict_recursive(
for key, value in dict(self).items()
}

@_util.deprecated(
"For internal stripe-python use only. The public interface will be removed in a future version."
)
def to_dict_recursive(self) -> Dict[str, Any]:
return self._to_dict_recursive()

@property
@_util.deprecated(
"For internal stripe-python use only. The public interface will be removed in a future version."
)
def stripe_id(self) -> Optional[str]:
return getattr(self, "id")

Expand Down
14 changes: 10 additions & 4 deletions stripe/_util.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,10 @@

# Used for global variables
import stripe # noqa: IMP101
from stripe._stripe_response import StripeResponse
from stripe._stripe_object import StripeObject

if TYPE_CHECKING:
from stripe._stripe_response import StripeResponse
from stripe._stripe_object import StripeObject

STRIPE_LOG = os.environ.get("STRIPE_LOG")

Expand Down Expand Up @@ -192,12 +194,12 @@ def get_object_classes():
return OBJECT_CLASSES


Resp = Union[StripeResponse, Dict[str, Any], List["Resp"]]
Resp = Union["StripeResponse", Dict[str, Any], List["Resp"]]


@overload
def convert_to_stripe_object(
resp: Union[StripeResponse, Dict[str, Any]],
resp: Union["StripeResponse", Dict[str, Any]],
api_key: Optional[str] = None,
stripe_version: Optional[str] = None,
stripe_account: Optional[str] = None,
Expand Down Expand Up @@ -232,6 +234,10 @@ def convert_to_stripe_object(
# the raw API response information
stripe_response = None

# Imports here at runtime to avoid circular dependencies
from stripe._stripe_response import StripeResponse
from stripe._stripe_object import StripeObject

if isinstance(resp, StripeResponse):
stripe_response = resp
resp = cast(Resp, stripe_response.data)
Expand Down
10 changes: 5 additions & 5 deletions tests/test_api_requestor.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
from stripe._stripe_response import StripeResponse, StripeStreamResponse
from stripe._encode import _api_encode

from urllib.parse import urlsplit
from urllib.parse import urlsplit, parse_qsl

import urllib3

Expand Down Expand Up @@ -135,7 +135,7 @@ def __init__(self, expected):
def __eq__(self, other):
query = urlsplit(other).query or other

parsed = stripe.util.parse_qsl(query)
parsed = parse_qsl(query)
return self.expected == sorted(parsed)

def __repr__(self):
Expand All @@ -158,7 +158,7 @@ def __eq__(self, other):
)
return False

q_matcher = QueryMatcher(stripe.util.parse_qsl(self.exp_parts.query))
q_matcher = QueryMatcher(parse_qsl(self.exp_parts.query))
return q_matcher == other

def __repr__(self):
Expand Down Expand Up @@ -447,7 +447,7 @@ def test_methods_with_params_and_response(
if method == "post":
check_call(
method,
post_data=QueryMatcher(stripe.util.parse_qsl(encoded)),
post_data=QueryMatcher(parse_qsl(encoded)),
)
else:
abs_url = "%s%s?%s" % (
Expand Down Expand Up @@ -487,7 +487,7 @@ def test_methods_with_params_and_streaming_response(
if method == "post":
check_call(
method,
post_data=QueryMatcher(stripe.util.parse_qsl(encoded)),
post_data=QueryMatcher(parse_qsl(encoded)),
is_streaming=True,
)
else:
Expand Down

0 comments on commit 364f6db

Please sign in to comment.