Skip to content

Commit

Permalink
[Tables] Enhance error info when client url ends with table name (Azu…
Browse files Browse the repository at this point in the history
  • Loading branch information
YalinLi0312 authored Sep 29, 2022
1 parent 6eff112 commit 7e1797d
Show file tree
Hide file tree
Showing 37 changed files with 1,880 additions and 107 deletions.
40 changes: 29 additions & 11 deletions sdk/tables/azure-data-tables/azure/data/tables/_error.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,19 +17,9 @@
)
from azure.core.pipeline.policies import ContentDecodePolicy

if sys.version_info < (3,):

def _str(value):
if isinstance(value, unicode): # pylint: disable=undefined-variable
return value.encode("utf-8")

return str(value)
else:
_str = str


def _to_str(value):
return _str(value) if value is not None else None
return str(value) if value is not None else None


_ERROR_TYPE_NOT_SUPPORTED = "Type not supported when sending data to the service: {0}."
Expand Down Expand Up @@ -220,6 +210,34 @@ def _process_table_error(storage_error, table_name=None):
_reraise_error(decoded_error)


def _reprocess_error(decoded_error, identifiers=None):
error_code = decoded_error.error_code
message = decoded_error.message
authentication_failed = "Server failed to authenticate the request"
invalid_input = "The number of keys specified in the URI does not match number of key properties for the resource"
invalid_query_parameter_value = "Value for one of the query parameters specified in the request URI is invalid"
invalid_url = "Request url is invalid"
properties_need_value = "The values are not specified for all properties in the entity"
table_does_not_exist = "The table specified does not exist"
if (error_code == "AuthenticationFailed" and authentication_failed in message or # pylint: disable=too-many-boolean-expressions
error_code == "InvalidInput" and invalid_input in message or
error_code == "InvalidInput" and invalid_url in message or
error_code == "InvalidQueryParameterValue" and invalid_query_parameter_value in message or
error_code == "PropertiesNeedValue" and properties_need_value in message or
error_code =="TableNotFound" and table_does_not_exist in message
):
args_list = list(decoded_error.args)
args_list[0] += "\nA possible cause of this error could be that the account URL used to"\
"create the Client includes an invalid path, for example the table name. Please check your account URL."
decoded_error.args = tuple(args_list)

if (identifiers is not None and error_code == "InvalidXmlDocument" and len(identifiers) > 5):
raise ValueError(
"Too many access policies provided. The server does not support setting more than 5 access policies"\
"on a single resource."
)


class TableTransactionError(HttpResponseError):
"""There is a failure in the transaction operations.
Expand Down
25 changes: 14 additions & 11 deletions sdk/tables/azure-data-tables/azure/data/tables/_table_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,10 @@
from ._deserialize import _convert_to_entity, _trim_service_metadata
from ._entity import TableEntity
from ._error import (
_decode_error,
_process_table_error,
_reprocess_error,
_reraise_error,
_decode_error,
_validate_tablename_error
)
from ._generated.models import (
Expand Down Expand Up @@ -219,21 +220,15 @@ def set_table_access_policy(
permission=value.permission
)
identifiers.append(SignedIdentifier(id=key, access_policy=payload))
signed_identifiers = identifiers # type: ignore
try:
self._client.table.set_access_policy(
table=self.table_name, table_acl=signed_identifiers or None, **kwargs # type: ignore
table=self.table_name, table_acl=identifiers or None, **kwargs # type: ignore
)
except HttpResponseError as error:
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as table_error:
if (table_error.error_code == 'InvalidXmlDocument' # type: ignore
and len(signed_identifiers) > 5):
raise ValueError(
'Too many access policies provided. The server does not support setting '
'more than 5 access policies on a single resource.'
)
_reprocess_error(table_error, identifiers=identifiers)
raise

@distributed_trace
Expand All @@ -260,7 +255,11 @@ def create_table(
try:
result = self._client.table.create(table_properties, **kwargs)
except HttpResponseError as error:
_process_table_error(error, table_name=self.table_name)
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise
return TableItem(name=result.table_name) # type: ignore

@distributed_trace
Expand Down Expand Up @@ -289,7 +288,11 @@ def delete_table(
except HttpResponseError as error:
if error.status_code == 404:
return
_process_table_error(error, table_name=self.table_name)
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise

@overload
def delete_entity(self, partition_key, row_key, **kwargs):
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
)
from ._base_client import parse_connection_str, TablesBaseClient, TransportWrapper
from ._models import LocationMode
from ._error import _process_table_error
from ._error import _process_table_error, _reprocess_error
from ._table_client import TableClient
from ._serialize import _parameter_filter_substitution

Expand Down Expand Up @@ -134,7 +134,11 @@ def get_service_properties(self, **kwargs):
try:
service_props = self._client.service.get_properties(timeout=timeout, **kwargs) # type: ignore
except HttpResponseError as error:
_process_table_error(error)
try:
_process_table_error(error)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise
return service_properties_deserialize(service_props)

@distributed_trace
Expand Down Expand Up @@ -167,7 +171,11 @@ def set_service_properties(self, **kwargs):
try:
self._client.service.set_properties(props, **kwargs)
except HttpResponseError as error:
_process_table_error(error)
try:
_process_table_error(error)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise

@distributed_trace
def create_table(self, table_name, **kwargs):
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,9 @@
from .._serialize import serialize_iso, _parameter_filter_substitution, _prepare_key
from .._deserialize import deserialize_iso, _return_headers_and_deserialized
from .._error import (
_process_table_error,
_decode_error,
_process_table_error,
_reprocess_error,
_reraise_error,
_validate_tablename_error
)
Expand Down Expand Up @@ -224,12 +225,7 @@ async def set_table_access_policy(
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as table_error:
if (table_error.error_code == 'InvalidXmlDocument' # type: ignore
and len(identifiers) > 5):
raise ValueError(
'Too many access policies provided. The server does not support setting '
'more than 5 access policies on a single resource.'
)
_reprocess_error(table_error, identifiers=identifiers)
raise

@distributed_trace_async
Expand All @@ -253,7 +249,11 @@ async def create_table(self, **kwargs) -> TableItem:
try:
result = await self._client.table.create(table_properties, **kwargs)
except HttpResponseError as error:
_process_table_error(error, table_name=self.table_name)
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise
return TableItem(name=result.table_name) # type: ignore

@distributed_trace_async
Expand All @@ -279,7 +279,11 @@ async def delete_table(self, **kwargs) -> None:
except HttpResponseError as error:
if error.status_code == 404:
return
_process_table_error(error, table_name=self.table_name)
try:
_process_table_error(error, table_name=self.table_name)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise

@overload
async def delete_entity(self, partition_key: str, row_key: str, **kwargs: Any) -> None:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
from .._base_client import parse_connection_str
from .._generated.models import TableServiceProperties
from .._models import service_stats_deserialize, service_properties_deserialize
from .._error import _process_table_error
from .._error import _process_table_error, _reprocess_error
from .._models import TableItem, LocationMode
from .._serialize import _parameter_filter_substitution
from ._table_client_async import TableClient
Expand Down Expand Up @@ -135,7 +135,11 @@ async def get_service_properties(self, **kwargs) -> Dict[str, object]:
try:
service_props = await self._client.service.get_properties(timeout=timeout, **kwargs) # type: ignore
except HttpResponseError as error:
_process_table_error(error)
try:
_process_table_error(error)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise
return service_properties_deserialize(service_props)

@distributed_trace_async
Expand Down Expand Up @@ -174,7 +178,11 @@ async def set_service_properties(
try:
await self._client.service.set_properties(props, **kwargs) # type: ignore
except HttpResponseError as error:
_process_table_error(error)
try:
_process_table_error(error)
except HttpResponseError as decoded_error:
_reprocess_error(decoded_error)
raise

@distributed_trace_async
async def create_table(self, table_name: str, **kwargs) -> TableClient:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@

from devtools_testutils import is_live

from .testcase import TableTestCase, SLEEP_DELAY
from .testcase import TableTestCase


TEST_TABLE_PREFIX = "pytableasync"
Expand Down
2 changes: 0 additions & 2 deletions sdk/tables/azure-data-tables/tests/_shared/testcase.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,6 @@

from devtools_testutils import is_live

SLEEP_DELAY = 30

TEST_TABLE_PREFIX = "pytablesync"

SERVICE_UNAVAILABLE_RESP_BODY = '<?xml version="1.0" encoding="utf-8"?><StorageServiceStats><GeoReplication><Status' \
Expand Down
Loading

0 comments on commit 7e1797d

Please sign in to comment.