Skip to content

Commit

Permalink
fix # 868 (#869)
Browse files Browse the repository at this point in the history
  • Loading branch information
thehesiod authored Jun 11, 2021
1 parent 2a7c7f5 commit 4c150b2
Show file tree
Hide file tree
Showing 12 changed files with 117 additions and 13 deletions.
3 changes: 2 additions & 1 deletion CHANGES.rst
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
Changes
-------
1.3.1 (2021-04-23)
1.3.1 (2021-06-11)
^^^^^^^^^^^^^^^^^^
* TCPConnector: change deprecated ssl_context to ssl
* fix non awaited generate presigned url calls # 868

1.3.0 (2021-04-09)
^^^^^^^^^^^^^^^^^^
Expand Down
4 changes: 2 additions & 2 deletions Pipfile
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ coverage = "==5.5"
flake8 = "==3.9.0"
flake8-formatter-abspath = "==1.0.1"
docker = '5.0.0'
moto = {extras = ["server","s3","sqs","lambda","dynamodb","cloudformation", "sns", "batch"],version = "==2.0.4"}
pytest = "==6.2.3"
moto = {extras = ["server","s3","sqs","lambda","dynamodb","cloudformation", "sns", "batch", "ec2", "rds"],version = "==2.0.8"}
pytest = "==6.2.4"
pytest-cov = "==2.11.1"
pytest-asyncio = "==0.14.0"
pytest-xdist = "==2.2.1"
Expand Down
2 changes: 1 addition & 1 deletion aiobotocore/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from .session import get_session, AioSession

__all__ = ['get_session', 'AioSession']
__version__ = '1.3.0'
__version__ = '1.3.1'
38 changes: 38 additions & 0 deletions aiobotocore/handlers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
from botocore.handlers import _get_presigned_url_source_and_destination_regions, \
_get_cross_region_presigned_url


async def inject_presigned_url_ec2(params, request_signer, model, **kwargs):
# The customer can still provide this, so we should pass if they do.
if 'PresignedUrl' in params['body']:
return
src, dest = _get_presigned_url_source_and_destination_regions(
request_signer, params['body'])
url = await _get_cross_region_presigned_url(
request_signer, params, model, src, dest)
params['body']['PresignedUrl'] = url
# EC2 Requires that the destination region be sent over the wire in
# addition to the source region.
params['body']['DestinationRegion'] = dest


async def inject_presigned_url_rds(params, request_signer, model, **kwargs):
# SourceRegion is not required for RDS operations, so it's possible that
# it isn't set. In that case it's probably a local copy so we don't need
# to do anything else.
if 'SourceRegion' not in params['body']:
return

src, dest = _get_presigned_url_source_and_destination_regions(
request_signer, params['body'])

# Since SourceRegion isn't actually modeled for RDS, it needs to be
# removed from the request params before we send the actual request.
del params['body']['SourceRegion']

if 'PreSignedUrl' in params['body']:
return

url = await _get_cross_region_presigned_url(
request_signer, params, model, src, dest)
params['body']['PreSignedUrl'] = url
27 changes: 22 additions & 5 deletions aiobotocore/session.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,26 @@
from .parsers import AioResponseParserFactory
from .signers import add_generate_presigned_url, add_generate_presigned_post, \
add_generate_db_auth_token
from .handlers import inject_presigned_url_ec2, inject_presigned_url_rds
from botocore.handlers import \
inject_presigned_url_rds as boto_inject_presigned_url_rds, \
inject_presigned_url_ec2 as boto_inject_presigned_url_ec2
from botocore.signers import \
add_generate_presigned_url as boto_add_generate_presigned_url, \
add_generate_presigned_post as boto_add_generate_presigned_post, \
add_generate_db_auth_token as boto_add_generate_db_auth_token
from .credentials import create_credential_resolver, AioCredentials


_HANDLER_MAPPING = {
boto_inject_presigned_url_ec2: inject_presigned_url_ec2,
boto_inject_presigned_url_rds: inject_presigned_url_rds,
boto_add_generate_presigned_url: add_generate_presigned_url,
boto_add_generate_presigned_post: add_generate_presigned_post,
boto_add_generate_db_auth_token: add_generate_db_auth_token,
}


class ClientCreatorContext:
def __init__(self, coro):
self._coro = coro
Expand All @@ -34,11 +51,11 @@ def __init__(self, session_vars=None, event_hooks=None,

super().__init__(session_vars, event_hooks, include_builtin_handlers, profile)

# Register our own handlers. These normally happen via
# `botocore.handlers.BUILTIN_HANDLERS`
self.register('creating-client-class', add_generate_presigned_url)
self.register('creating-client-class.s3', add_generate_presigned_post)
self.register('creating-client-class.rds', add_generate_db_auth_token),
def register(self, event_name, handler, unique_id=None,
unique_id_uses_count=False):
handler = _HANDLER_MAPPING.get(handler, handler)

return super().register(event_name, handler, unique_id, unique_id_uses_count)

def _register_response_parser_factory(self):
self._components.register_component('response_parser_factory',
Expand Down
2 changes: 1 addition & 1 deletion tests/botocore/test_credentials.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from unittest import TestCase
from functools import partial

import mock
from unittest import mock
from typing import Optional

import pytest
Expand Down
2 changes: 1 addition & 1 deletion tests/botocore/test_signers.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import datetime
from datetime import timezone
import pytest
import mock
from unittest import mock

import aiobotocore
import aiobotocore.credentials
Expand Down
2 changes: 1 addition & 1 deletion tests/botocore/test_utils.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import asyncio
import pytest
import json
import mock
from unittest import mock
import itertools
import unittest
from typing import Union, List, Tuple
Expand Down
8 changes: 8 additions & 0 deletions tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -224,6 +224,14 @@ async def rds_client(session, region, config, rds_server, mocking_test):
yield client


@pytest.fixture
async def ec2_client(session, region, config, ec2_server, mocking_test):
kw = moto_config(ec2_server) if mocking_test else {}
async with session.create_client('ec2', region_name=region,
config=config, **kw) as client:
yield client


async def recursive_delete(s3_client, bucket_name):
# Recursively deletes a bucket and all of its contents.
paginator = s3_client.get_paginator('list_object_versions')
Expand Down
8 changes: 7 additions & 1 deletion tests/mock_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -144,5 +144,11 @@ async def iam_server():

@pytest.fixture
async def rds_server():
async with MotoService('iam') as svc:
async with MotoService('rds') as svc:
yield svc.endpoint_url


@pytest.fixture
async def ec2_server():
async with MotoService('ec2') as svc:
yield svc.endpoint_url
27 changes: 27 additions & 0 deletions tests/test_ec2.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import pytest


@pytest.mark.moto
@pytest.mark.asyncio
async def test_ec2_snapshot(ec2_client):
# TODO: this needs to somehow validate the presigned url sent because moto is not
volume_response = await ec2_client.create_volume(
AvailabilityZone="us-east-1", Size=10)
tag_spec = [
{"ResourceType": "snapshot", "Tags": [{"Key": "key", "Value": "value"}]}
]

create_snapshot_response = await ec2_client.create_snapshot(
VolumeId=volume_response["VolumeId"], TagSpecifications=tag_spec
)

copy_snapshot_response = await ec2_client.copy_snapshot(
SourceSnapshotId=create_snapshot_response["SnapshotId"],
SourceRegion="us-east-1",
DestinationRegion="us-east-1",
Encrypted=True,
TagSpecifications=tag_spec,
KmsKeyId="key-1234",
)

assert copy_snapshot_response['SnapshotId']
7 changes: 7 additions & 0 deletions tests/test_patches.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@
CanonicalNameCredentialSourcer, BotoProvider, OriginalEC2Provider, \
create_credential_resolver, get_credentials, create_mfa_serial_refresher, \
AssumeRoleWithWebIdentityCredentialFetcher, SSOCredentialFetcher, SSOProvider
from botocore.handlers import inject_presigned_url_ec2, inject_presigned_url_rds


# This file ensures that our private patches will work going forward. If a
# method gets updated this will assert and someone will need to validate:
Expand Down Expand Up @@ -240,6 +242,7 @@
Session.get_service_data: {'e28f2de9ebaf13214f1606d33349dfa8e2555923'},
Session.get_service_model: {'1c8f93e6fb9913e859e43aea9bc2546edbea8365'},
Session.get_available_regions: {'bc455d24d98fbc112ff22325ebfd12a6773cb7d4'},
Session.register: {'39791fd2cffcea480f81e77c7daf3974581d9291'},

# signers.py
RequestSigner.handler: {'371909df136a0964ef7469a63d25149176c2b442'},
Expand Down Expand Up @@ -288,6 +291,10 @@
NormalizedOperationMethod.__call__: {'79723632d023739aa19c8a899bc2b814b8ab12ff'},
Waiter.wait: {'e9c7f98b12ac8d9ba44637e89499617590bc4f6f'},
create_waiter_with_client: {'c3d12c9a4293105cc8c2ecfc7e69a2152ad564de'},

# handlers.py
inject_presigned_url_rds: {'5a34e1666d84f6229c54a59bffb69d46e8117b3a'},
inject_presigned_url_ec2: {'37fad2d9c53ca4f1783e32799fa8f70930f44c23'},
}


Expand Down

0 comments on commit 4c150b2

Please sign in to comment.