|
2 | 2 | # (c) Copyright Instana Inc. 2020 |
3 | 3 |
|
4 | 4 | import os |
| 5 | +from io import BytesIO |
| 6 | + |
5 | 7 | import pytest |
| 8 | +import boto3 |
6 | 9 | from typing import Generator |
7 | 10 | from moto import mock_aws |
8 | | -import boto3 |
9 | 11 |
|
10 | 12 | from instana.singletons import tracer, agent |
11 | 13 | from tests.helpers import get_first_span_by_filter |
@@ -267,3 +269,52 @@ def test_s3_list_obj(self) -> None: |
267 | 269 |
|
268 | 270 | assert s3_span.data["s3"]["op"] == "ListObjects" |
269 | 271 | assert s3_span.data["s3"]["bucket"] == "aws_bucket_name" |
| 272 | + |
| 273 | + def test_s3_resource_bucket_upload_fileobj(self) -> None: |
| 274 | + """ |
| 275 | + Verify boto3.resource().Bucket().upload_fileobj() works correctly with BytesIO objects |
| 276 | + """ |
| 277 | + bucket_name = "resource-bucket-test" |
| 278 | + object_key = "somekey" |
| 279 | + test_data = b"somedata" |
| 280 | + |
| 281 | + # Create a bucket using the client first |
| 282 | + self.s3.create_bucket(Bucket=bucket_name) |
| 283 | + |
| 284 | + # Get an S3 resource and bucket object (like in the issue report) |
| 285 | + s3_resource = boto3.resource( |
| 286 | + "s3", |
| 287 | + region_name="us-east-1" |
| 288 | + ) |
| 289 | + bucket = s3_resource.Bucket(name=bucket_name) |
| 290 | + |
| 291 | + # Upload a BytesIO object wrapped in an Instana span |
| 292 | + with tracer.start_as_current_span("test"): |
| 293 | + bucket.upload_fileobj(BytesIO(test_data), object_key) |
| 294 | + |
| 295 | + # Verify the upload was successful by retrieving the object |
| 296 | + response = bucket.Object(object_key).get() |
| 297 | + file_content = response["Body"].read() |
| 298 | + |
| 299 | + # Assert the content matches what we uploaded |
| 300 | + assert file_content == test_data |
| 301 | + |
| 302 | + # Verify the spans were created correctly |
| 303 | + spans = self.recorder.queued_spans() |
| 304 | + assert len(spans) >= 2 # There might be more spans due to the resource operations |
| 305 | + |
| 306 | + filter = lambda span: span.n == "sdk" # noqa: E731 |
| 307 | + test_span = get_first_span_by_filter(spans, filter) |
| 308 | + assert test_span |
| 309 | + |
| 310 | + filter = lambda span: span.n == "s3" and span.data["s3"]["op"] == "UploadFileObj" # noqa: E731 |
| 311 | + s3_span = get_first_span_by_filter(spans, filter) |
| 312 | + assert s3_span |
| 313 | + |
| 314 | + assert s3_span.t == test_span.t |
| 315 | + assert s3_span.p == test_span.s |
| 316 | + |
| 317 | + assert not test_span.ec |
| 318 | + assert not s3_span.ec |
| 319 | + |
| 320 | + assert s3_span.data["s3"]["bucket"] == bucket_name |
0 commit comments