-
Notifications
You must be signed in to change notification settings - Fork 432
feat(user-agent): add custom header User-Agent to AWS SDK requests #2267
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
leandrodamascena
merged 28 commits into
aws-powertools:develop
from
roger-zhangg:user-agent
Jun 1, 2023
Merged
Changes from 27 commits
Commits
Show all changes
28 commits
Select commit
Hold shift + click to select a range
6c36aa6
POC of user-agent
roger-zhangg 23f4155
Changes for Heitor's review
roger-zhangg 52ebc8b
Merge branch 'awslabs:develop' into user-agent
roger-zhangg a694ca2
Merge remote-tracking branch 'origin/user-agent' into user-agent
roger-zhangg dc8d1ad
Changes for Heitor's review
roger-zhangg 6404ee2
Changes for Heitor's review
roger-zhangg b2402e0
add patching function for resource
roger-zhangg deeeb08
Merge branch 'awslabs:develop' into user-agent
roger-zhangg b0c2e95
Merge remote-tracking branch 'origin/user-agent' into user-agent
roger-zhangg d1a0128
add importlib-metadata in poetry
roger-zhangg 5c7a5a2
user-agent: fixing small things
leandrodamascena 17d6df1
fix poetry
leandrodamascena 31a4c07
Merge remote-tracking branch 'upstream/develop' into user-agent
leandrodamascena 0dec5b2
fix mypy
leandrodamascena afe0ee9
fix mypy
leandrodamascena 00b75da
fix poetry
leandrodamascena 37bf656
fix mypy
leandrodamascena c53e384
feat(user-agent): using default botocore initializer + minor changes
leandrodamascena 60d188e
Merge branch 'awslabs:develop' into user-agent
roger-zhangg 12150e2
change back to use register in initializer
roger-zhangg 6b86d40
add docstring
roger-zhangg 85247b4
merge poetry
leandrodamascena ad61d62
sync upstream
roger-zhangg d88f04b
sync upstream
roger-zhangg 6c7767b
style/typo fixes for review
roger-zhangg 8cb4b96
merge develop
leandrodamascena 7148647
chore: docstring
leandrodamascena b79bd83
chore: docstring
leandrodamascena File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,165 @@ | ||
import logging | ||
import os | ||
|
||
from aws_lambda_powertools.shared.version import VERSION | ||
|
||
powertools_version = VERSION | ||
inject_header = True | ||
|
||
try: | ||
import botocore | ||
except ImportError: | ||
# if botocore failed to import, user might be using custom runtime and we can't inject header | ||
inject_header = False | ||
|
||
logger = logging.getLogger(__name__) | ||
|
||
EXEC_ENV = os.environ.get("AWS_EXECUTION_ENV", "NA") | ||
TARGET_SDK_EVENT = "request-created" | ||
FEATURE_PREFIX = "PT" | ||
DEFAULT_FEATURE = "no-op" | ||
HEADER_NO_OP = f"{FEATURE_PREFIX}/{DEFAULT_FEATURE}/{powertools_version} PTEnv/{EXEC_ENV}" | ||
|
||
|
||
def _initializer_botocore_session(session): | ||
""" | ||
This function is used to add an extra header for the User-Agent in the Botocore session, | ||
as described in the pull request: https://github.com/boto/botocore/pull/2682 | ||
|
||
Parameters | ||
---------- | ||
session : botocore.session.Session | ||
The Botocore session to which the user-agent function will be registered. | ||
|
||
Raises | ||
------ | ||
Exception | ||
If there is an issue while adding the extra header for the User-Agent. | ||
|
||
""" | ||
try: | ||
session.register(TARGET_SDK_EVENT, _create_feature_function(DEFAULT_FEATURE)) | ||
except Exception: | ||
logger.debug("Can't add extra header User-Agent") | ||
|
||
|
||
def _create_feature_function(feature): | ||
""" | ||
Create and return the `add_powertools_feature` function. | ||
|
||
The `add_powertools_feature` function is designed to be registered in boto3's event system. | ||
When registered, it appends the given feature string to the User-Agent header of AWS SDK requests. | ||
|
||
Parameters | ||
---------- | ||
feature : str | ||
The feature string to be appended to the User-Agent header. | ||
|
||
Returns | ||
------- | ||
add_powertools_feature : Callable | ||
The `add_powertools_feature` function that modifies the User-Agent header. | ||
|
||
|
||
""" | ||
|
||
def add_powertools_feature(request, **kwargs): | ||
try: | ||
headers = request.headers | ||
header_user_agent = ( | ||
f"{headers['User-Agent']} {FEATURE_PREFIX}/{feature}/{powertools_version} PTEnv/{EXEC_ENV}" | ||
) | ||
|
||
# This function is exclusive to client and resources objects created in Powertools | ||
# and must remove the no-op header, if present | ||
if HEADER_NO_OP in headers["User-Agent"] and feature != DEFAULT_FEATURE: | ||
# Remove HEADER_NO_OP + space | ||
header_user_agent = header_user_agent.replace(f"{HEADER_NO_OP} ", "") | ||
|
||
headers["User-Agent"] = f"{header_user_agent}" | ||
except Exception: | ||
logger.debug("Can't find User-Agent header") | ||
|
||
return add_powertools_feature | ||
|
||
|
||
# Add feature user-agent to given sdk boto3.session | ||
def register_feature_to_session(session, feature): | ||
""" | ||
Register the given feature string to the event system of the provided boto3 session | ||
and append the feature to the User-Agent header of the request | ||
|
||
Parameters | ||
---------- | ||
session : boto3.session.Session | ||
The boto3 session to which the feature will be registered. | ||
feature : str | ||
The feature string to be appended to the User-Agent header, e.g., "streaming" in Powertools. | ||
|
||
Raises | ||
------ | ||
AttributeError | ||
If the provided session does not have an event system. | ||
|
||
""" | ||
try: | ||
session.events.register(TARGET_SDK_EVENT, _create_feature_function(feature)) | ||
except AttributeError as e: | ||
logger.debug(f"session passed in doesn't have a event system:{e}") | ||
|
||
|
||
# Add feature user-agent to given sdk boto3.client | ||
def register_feature_to_client(client, feature): | ||
""" | ||
Register the given feature string to the event system of the provided boto3 client | ||
and append the feature to the User-Agent header of the request | ||
|
||
Parameters | ||
---------- | ||
session : boto3.session.Session.client | ||
The boto3 client to which the feature will be registered. | ||
feature : str | ||
The feature string to be appended to the User-Agent header, e.g., "streaming" in Powertools. | ||
|
||
Raises | ||
------ | ||
AttributeError | ||
If the provided client does not have an event system. | ||
|
||
""" | ||
try: | ||
client.meta.events.register(TARGET_SDK_EVENT, _create_feature_function(feature)) | ||
except AttributeError as e: | ||
logger.debug(f"session passed in doesn't have a event system:{e}") | ||
|
||
|
||
# Add feature user-agent to given sdk boto3.resource | ||
def register_feature_to_resource(resource, feature): | ||
""" | ||
Register the given feature string to the event system of the provided boto3 resource | ||
and append the feature to the User-Agent header of the request | ||
|
||
Parameters | ||
---------- | ||
session : boto3.session.Session.resource | ||
The boto3 client to which the feature will be registered. | ||
feature : str | ||
The feature string to be appended to the User-Agent header, e.g., "streaming" in Powertools. | ||
|
||
Raises | ||
------ | ||
AttributeError | ||
If the provided resource does not have an event system. | ||
|
||
""" | ||
try: | ||
resource.meta.client.meta.events.register(TARGET_SDK_EVENT, _create_feature_function(feature)) | ||
except AttributeError as e: | ||
logger.debug(f"resource passed in doesn't have a event system:{e}") | ||
|
||
|
||
def inject_user_agent(): | ||
if inject_header: | ||
# Customize botocore session to inject Powertools header | ||
# See: https://github.com/boto/botocore/pull/2682 | ||
botocore.register_initializer(_initializer_botocore_session) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
""" | ||
This file serves to create a constant that informs | ||
the current version of the Powertools package and exposes it in the main module | ||
|
||
Since Python 3.8 there the built-in importlib.metadata | ||
When support for Python3.7 is dropped, we can remove the optional importlib_metadata dependency | ||
See: https://docs.python.org/3/library/importlib.metadata.html | ||
""" | ||
import sys | ||
|
||
if sys.version_info >= (3, 8): | ||
from importlib.metadata import version | ||
else: | ||
from importlib_metadata import version | ||
|
||
VERSION = version("aws-lambda-powertools") |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.