Title: Obscure error message `ValueError: Request obj does not match any template` when required field is not provided · Issue #327 · googleapis/python-api-core · GitHub
Open Graph Title: Obscure error message `ValueError: Request obj does not match any template` when required field is not provided · Issue #327 · googleapis/python-api-core
X Title: Obscure error message `ValueError: Request obj does not match any template` when required field is not provided · Issue #327 · googleapis/python-api-core
Description: In PR googleapis/python-compute#147, I had to apply this change to the samples tests because a required field usage_export_location_resource was not provided. I've opened this issue because the error message ValueError: Request obj does ...
Open Graph Description: In PR googleapis/python-compute#147, I had to apply this change to the samples tests because a required field usage_export_location_resource was not provided. I've opened this issue because the err...
X Description: In PR googleapis/python-compute#147, I had to apply this change to the samples tests because a required field usage_export_location_resource was not provided. I've opened this issue because the...
Opengraph URL: https://github.com/googleapis/python-api-core/issues/327
X: @github
Domain: github.com
{"@context":"https://schema.org","@type":"DiscussionForumPosting","headline":"Obscure error message `ValueError: Request obj does not match any template` when required field is not provided","articleBody":"In PR https://github.com/googleapis/python-compute/pull/147, I had to apply [this change](https://github.com/googleapis/python-compute/pull/147/commits/e955cc63b4bf30ea84114ebb23a160a0f2b8da83) to the samples tests because a required field `usage_export_location_resource ` was not provided. I've opened this issue because the error message `ValueError: Request obj does not match any template` could be improved. We should provide more information to help users debug the issue as I found it difficult to find the root cause.\r\n\r\nSee build log [here](https://source.cloud.google.com/results/invocations/b22865c2-86f5-4ac8-bc14-feac78dcb9fd/log) and stack trace below.\r\n```\r\n=================================== FAILURES ===================================\r\n_____________________ test_set_usage_export_bucket_default _____________________\r\n\r\ncapsys = \u003c_pytest.capture.CaptureFixture object at 0x7fee8a8dd690\u003e\r\ntemp_bucket = \u003cBucket: teste4bc9ab375\u003e\r\n\r\n def test_set_usage_export_bucket_default(capsys: typing.Any,\r\n temp_bucket: storage.Bucket) -\u003e None:\r\n set_usage_export_bucket(project_id=PROJECT, bucket_name=temp_bucket.name)\r\n time.sleep(5) # To make sure the settings are properly updated\r\n uel = get_usage_export_bucket(project_id=PROJECT)\r\n assert(uel.bucket_name == temp_bucket.name)\r\n assert(uel.report_name_prefix == 'usage_gce')\r\n out, _ = capsys.readouterr()\r\n assert('default prefix of `usage_gce`.' in out)\r\n\r\n\u003e disable_usage_export(project_id=PROJECT)\r\n\r\ntest_sample_default_values.py:48:\r\n_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _\r\nsample_default_values.py:118: in disable_usage_export\r\n project=project_id, usage_export_location_resource=None)\r\n../../google/cloud/compute_v1/services/projects/client.py:1399: in set_usage_export_bucket\r\n response = rpc(request, retry=retry, timeout=timeout, metadata=metadata,)\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/gapic_v1/method.py:154: in __call__\r\n return wrapped_func(*args, **kwargs)\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/grpc_helpers.py:66: in error_remapped_callable\r\n return callable_(*args, **kwargs)\r\n../../google/cloud/compute_v1/services/projects/transports/rest.py:1352: in _set_usage_export_bucket\r\n transcoded_request = path_template.transcode(http_options, **request_kwargs)\r\n_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _\r\n\r\nhttp_options = [{'body': 'usage_export_location_resource', 'method': 'post', 'uri': '/compute/v1/projects/{project}/setUsageExportBucket'}]\r\nrequest_kwargs = {'project': 'python-docs-samples-tests-py37'}\r\nhttp_option = {'body': 'usage_export_location_resource', 'method': 'post', 'uri': '/compute/v1/projects/{project}/setUsageExportBucket'}\r\nrequest = {'uri': '/compute/v1/projects/python-docs-samples-tests-py37/setUsageExportBucket'}\r\nuri_template = '/compute/v1/projects/{project}/setUsageExportBucket'\r\npath_fields = ['project']\r\npath_args = {'project': 'python-docs-samples-tests-py37'}, leftovers = {}\r\npath_field = 'project'\r\n\r\n def transcode(http_options, **request_kwargs):\r\n \"\"\"Transcodes a grpc request pattern into a proper HTTP request following the rules outlined here,\r\n https://github.com/googleapis/googleapis/blob/master/google/api/http.proto#L44-L312\r\n\r\n Args:\r\n http_options (list(dict)): A list of dicts which consist of these keys,\r\n 'method' (str): The http method\r\n 'uri' (str): The path template\r\n 'body' (str): The body field name (optional)\r\n (This is a simplified representation of the proto option `google.api.http`)\r\n\r\n request_kwargs (dict) : A dict representing the request object\r\n\r\n Returns:\r\n dict: The transcoded request with these keys,\r\n 'method' (str) : The http method\r\n 'uri' (str) : The expanded uri\r\n 'body' (dict) : A dict representing the body (optional)\r\n 'query_params' (dict) : A dict mapping query parameter variables and values\r\n\r\n Raises:\r\n ValueError: If the request does not match the given template.\r\n \"\"\"\r\n for http_option in http_options:\r\n request = {}\r\n\r\n # Assign path\r\n uri_template = http_option[\"uri\"]\r\n path_fields = [\r\n match.group(\"name\") for match in _VARIABLE_RE.finditer(uri_template)\r\n ]\r\n path_args = {field: get_field(request_kwargs, field) for field in path_fields}\r\n request[\"uri\"] = expand(uri_template, **path_args)\r\n\r\n # Remove fields used in uri path from request\r\n leftovers = copy.deepcopy(request_kwargs)\r\n for path_field in path_fields:\r\n delete_field(leftovers, path_field)\r\n\r\n if not validate(uri_template, request[\"uri\"]) or not all(path_args.values()):\r\n continue\r\n\r\n # Assign body and query params\r\n body = http_option.get(\"body\")\r\n\r\n if body:\r\n if body == \"*\":\r\n request[\"body\"] = leftovers\r\n request[\"query_params\"] = {}\r\n else:\r\n try:\r\n request[\"body\"] = leftovers.pop(body)\r\n except KeyError:\r\n continue\r\n request[\"query_params\"] = leftovers\r\n else:\r\n request[\"query_params\"] = leftovers\r\n request[\"method\"] = http_option[\"method\"]\r\n return request\r\n\r\n\u003e raise ValueError(\"Request obj does not match any template\")\r\nE ValueError: Request obj does not match any template\r\n\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/path_template.py:300: ValueError\r\n_____________________ test_set_usage_export_bucket_custom ______________________\r\n\r\ncapsys = \u003c_pytest.capture.CaptureFixture object at 0x7fee8a74ba90\u003e\r\ntemp_bucket = \u003cBucket: teste4bc9ab375\u003e\r\n\r\n def test_set_usage_export_bucket_custom(capsys: typing.Any,\r\n temp_bucket: storage.Bucket) -\u003e None:\r\n set_usage_export_bucket(project_id=PROJECT, bucket_name=temp_bucket.name,\r\n report_name_prefix=TEST_PREFIX)\r\n time.sleep(5) # To make sure the settings are properly updated\r\n uel = get_usage_export_bucket(project_id=PROJECT)\r\n assert(uel.bucket_name == temp_bucket.name)\r\n assert(uel.report_name_prefix == TEST_PREFIX)\r\n out, _ = capsys.readouterr()\r\n assert('usage_gce' not in out)\r\n\r\n\u003e disable_usage_export(project_id=PROJECT)\r\n\r\ntest_sample_default_values.py:66:\r\n_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _\r\nsample_default_values.py:118: in disable_usage_export\r\n project=project_id, usage_export_location_resource=None)\r\n../../google/cloud/compute_v1/services/projects/client.py:1399: in set_usage_export_bucket\r\n response = rpc(request, retry=retry, timeout=timeout, metadata=metadata,)\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/gapic_v1/method.py:154: in __call__\r\n return wrapped_func(*args, **kwargs)\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/grpc_helpers.py:66: in error_remapped_callable\r\n return callable_(*args, **kwargs)\r\n../../google/cloud/compute_v1/services/projects/transports/rest.py:1352: in _set_usage_export_bucket\r\n transcoded_request = path_template.transcode(http_options, **request_kwargs)\r\n_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _\r\n\r\nhttp_options = [{'body': 'usage_export_location_resource', 'method': 'post', 'uri': '/compute/v1/projects/{project}/setUsageExportBucket'}]\r\nrequest_kwargs = {'project': 'python-docs-samples-tests-py37'}\r\nhttp_option = {'body': 'usage_export_location_resource', 'method': 'post', 'uri': '/compute/v1/projects/{project}/setUsageExportBucket'}\r\nrequest = {'uri': '/compute/v1/projects/python-docs-samples-tests-py37/setUsageExportBucket'}\r\nuri_template = '/compute/v1/projects/{project}/setUsageExportBucket'\r\npath_fields = ['project']\r\npath_args = {'project': 'python-docs-samples-tests-py37'}, leftovers = {}\r\npath_field = 'project'\r\n\r\n def transcode(http_options, **request_kwargs):\r\n \"\"\"Transcodes a grpc request pattern into a proper HTTP request following the rules outlined here,\r\n https://github.com/googleapis/googleapis/blob/master/google/api/http.proto#L44-L312\r\n\r\n Args:\r\n http_options (list(dict)): A list of dicts which consist of these keys,\r\n 'method' (str): The http method\r\n 'uri' (str): The path template\r\n 'body' (str): The body field name (optional)\r\n (This is a simplified representation of the proto option `google.api.http`)\r\n\r\n request_kwargs (dict) : A dict representing the request object\r\n\r\n Returns:\r\n dict: The transcoded request with these keys,\r\n 'method' (str) : The http method\r\n 'uri' (str) : The expanded uri\r\n 'body' (dict) : A dict representing the body (optional)\r\n 'query_params' (dict) : A dict mapping query parameter variables and values\r\n\r\n Raises:\r\n ValueError: If the request does not match the given template.\r\n \"\"\"\r\n for http_option in http_options:\r\n request = {}\r\n\r\n # Assign path\r\n uri_template = http_option[\"uri\"]\r\n path_fields = [\r\n match.group(\"name\") for match in _VARIABLE_RE.finditer(uri_template)\r\n ]\r\n path_args = {field: get_field(request_kwargs, field) for field in path_fields}\r\n request[\"uri\"] = expand(uri_template, **path_args)\r\n\r\n # Remove fields used in uri path from request\r\n leftovers = copy.deepcopy(request_kwargs)\r\n for path_field in path_fields:\r\n delete_field(leftovers, path_field)\r\n\r\n if not validate(uri_template, request[\"uri\"]) or not all(path_args.values()):\r\n continue\r\n\r\n # Assign body and query params\r\n body = http_option.get(\"body\")\r\n\r\n if body:\r\n if body == \"*\":\r\n request[\"body\"] = leftovers\r\n request[\"query_params\"] = {}\r\n else:\r\n try:\r\n request[\"body\"] = leftovers.pop(body)\r\n except KeyError:\r\n continue\r\n request[\"query_params\"] = leftovers\r\n else:\r\n request[\"query_params\"] = leftovers\r\n request[\"method\"] = http_option[\"method\"]\r\n return request\r\n\r\n\u003e raise ValueError(\"Request obj does not match any template\")\r\nE ValueError: Request obj does not match any template\r\n\r\n.nox/py-3-7/lib/python3.7/site-packages/google/api_core/path_template.py:300: ValueError\r\n```\r\n\r\n","author":{"url":"https://github.com/parthea","@type":"Person","name":"parthea"},"datePublished":"2021-11-12T17:30:40.000Z","interactionStatistic":{"@type":"InteractionCounter","interactionType":"https://schema.org/CommentAction","userInteractionCount":2},"url":"https://github.com/327/python-api-core/issues/327"}
| route-pattern | /_view_fragments/issues/show/:user_id/:repository/:id/issue_layout(.:format) |
| route-controller | voltron_issues_fragments |
| route-action | issue_layout |
| fetch-nonce | v2:254f6c05-bb91-364a-0413-3713a3aa2a59 |
| current-catalog-service-hash | 81bb79d38c15960b92d99bca9288a9108c7a47b18f2423d0f6438c5b7bcd2114 |
| request-id | 86E2:A5482:9F3074:E84BCA:6A4E1CFE |
| html-safe-nonce | 17cfea59eb34ab48914a19330270f6cc0555ffa9c6125c8716308a175e2bd209 |
| visitor-payload | eyJyZWZlcnJlciI6IiIsInJlcXVlc3RfaWQiOiI4NkUyOkE1NDgyOjlGMzA3NDpFODRCQ0E6NkE0RTFDRkUiLCJ2aXNpdG9yX2lkIjoiNjA1ODQ2OTIwMDA5NDk2MDg5NCIsInJlZ2lvbl9lZGdlIjoiaWFkIiwicmVnaW9uX3JlbmRlciI6ImlhZCJ9 |
| visitor-hmac | c7985e53d5c329e6688e0ae23f34454b3167ac10ecadfdd8b337f3bedd4d34df |
| hovercard-subject-tag | issue:1093613216 |
| github-keyboard-shortcuts | repository,issues,copilot |
| google-site-verification | Apib7-x98H0j5cPqHWwSMm6dNU4GmODRoqxLiDzdx9I |
| octolytics-url | https://collector.github.com/github/collect |
| analytics-location | / |
| fb:app_id | 1401488693436528 |
| apple-itunes-app | app-id=1477376905, app-argument=https://github.com/_view_fragments/issues/show/googleapis/python-api-core/327/issue_layout |
| twitter:image | https://opengraph.githubassets.com/d5206bbc08fc05d01bee16689867c37291024c99ca49a188a7ba83d5e2649c1f/googleapis/python-api-core/issues/327 |
| twitter:card | summary_large_image |
| og:image | https://opengraph.githubassets.com/d5206bbc08fc05d01bee16689867c37291024c99ca49a188a7ba83d5e2649c1f/googleapis/python-api-core/issues/327 |
| og:image:alt | In PR googleapis/python-compute#147, I had to apply this change to the samples tests because a required field usage_export_location_resource was not provided. I've opened this issue because the err... |
| og:image:width | 1200 |
| og:image:height | 600 |
| og:site_name | GitHub |
| og:type | object |
| og:author:username | parthea |
| hostname | github.com |
| expected-hostname | github.com |
| None | 030096ee0db095447bfe77409d33bfac127ca7128299c58deef27c52eaa1b1f0 |
| turbo-cache-control | no-preview |
| go-import | github.com/googleapis/python-api-core git https://github.com/googleapis/python-api-core.git |
| octolytics-dimension-user_id | 16785467 |
| octolytics-dimension-user_login | googleapis |
| octolytics-dimension-repository_id | 226992456 |
| octolytics-dimension-repository_nwo | googleapis/python-api-core |
| octolytics-dimension-repository_public | true |
| octolytics-dimension-repository_is_fork | false |
| octolytics-dimension-repository_network_root_id | 226992456 |
| octolytics-dimension-repository_network_root_nwo | googleapis/python-api-core |
| turbo-body-classes | logged-out env-production page-responsive |
| disable-turbo | false |
| browser-stats-url | https://api.github.com/_private/browser/stats |
| browser-errors-url | https://api.github.com/_private/browser/errors |
| release | 5fe497b4815fcce3df76c0e246faa739a82c3124 |
| ui-target | full |
| theme-color | #1e2327 |
| color-scheme | light dark |
Links:
Viewport: width=device-width