AWS code-library documentation change
Summary
Added a comprehensive code example demonstrating S3 directory bucket setup, performance comparisons, and structural differences. Renamed section headers from 'ActionsScenarios' to 'BasicsActionsScenarios' and expanded documentation.
Security assessment
The changes focus on demonstrating S3 directory bucket functionality, performance benchmarking, and structural differences. While IAM user/policy setup is shown, this is standard AWS configuration guidance rather than addressing a specific security vulnerability or documenting new security features.
Diff
diff --git a/code-library/latest/ug/java_2_s3-directory-buckets_code_examples.md b/code-library/latest/ug/java_2_s3-directory-buckets_code_examples.md index 84fe75182..635a3c0d8 100644 --- a/code-library/latest/ug/java_2_s3-directory-buckets_code_examples.md +++ b/code-library/latest/ug/java_2_s3-directory-buckets_code_examples.md @@ -5 +5 @@ -ActionsScenarios +BasicsActionsScenarios @@ -12,0 +13,2 @@ The following code examples show you how to perform actions and implement common +_Basics_ are code examples that show you how to perform the essential operations within a service. + @@ -214,0 +217,2 @@ There's more on GitHub. Find the complete example and learn how to set up and ru + * Basics + @@ -219,0 +225,1130 @@ There's more on GitHub. Find the complete example and learn how to set up and ru + +## Basics + +The following code example shows how to: + + * Set up a VPC and VPC Endpoint. + + * Set up the Policies, Roles, and User to work with S3 directory buckets and the S3 Express One Zone storage class. + + * Create two S3 Clients. + + * Create two buckets. + + * Create an object and copy it over. + + * Demonstrate performance difference. + + * Populate the buckets to show the lexicographical difference. + + * Prompt the user to see if they want to clean up the resources. + + + + +**SDK for Java 2.x** + + +###### Note + +There's more on GitHub. Find the complete example and learn how to set up and run in the [AWS Code Examples Repository](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/javav2/example_code/s3#code-examples). + +Run an interactive scenario demonstrating Amazon S3 features. + + + public class S3DirectoriesScenario { + + public static final String DASHES = new String(new char[80]).replace("\0", "-"); + + private static final Logger logger = LoggerFactory.getLogger(S3DirectoriesScenario.class); + static Scanner scanner = new Scanner(System.in); + + private static S3AsyncClient mS3RegularClient; + private static S3AsyncClient mS3ExpressClient; + + private static String mdirectoryBucketName; + private static String mregularBucketName; + + private static String stackName = "cfn-stack-s3-express-basics--" + UUID.randomUUID(); + + private static String regularUser = ""; + private static String vpcId = ""; + private static String expressUser = ""; + + private static String vpcEndpointId = ""; + + private static final S3DirectoriesActions s3DirectoriesActions = new S3DirectoriesActions(); + + public static void main(String[] args) { + try { + s3ExpressScenario(); + } catch (RuntimeException e) { + logger.info(e.getMessage()); + } + } + + // Runs the scenario. + private static void s3ExpressScenario() { + logger.info(DASHES); + logger.info("Welcome to the Amazon S3 Express Basics demo using AWS SDK for Java V2."); + logger.info(""" + Let's get started! First, please note that S3 Express One Zone works best when working within the AWS infrastructure, + specifically when working in the same Availability Zone (AZ). To see the best results in this example and when you implement + directory buckets into your infrastructure, it is best to put your compute resources in the same AZ as your directory + bucket. + """); + waitForInputToContinue(scanner); + logger.info(DASHES); + + // Create an optional VPC and create 2 IAM users. + UserNames userNames = createVpcUsers(); + String expressUserName = userNames.getExpressUserName(); + String regularUserName = userNames.getRegularUserName(); + + // Set up two S3 clients, one regular and one express, + // and two buckets, one regular and one directory. + setupClientsAndBuckets(expressUserName, regularUserName); + + // Create an S3 session for the express S3 client and add objects to the buckets. + logger.info("Now let's add some objects to our buckets and demonstrate how to work with S3 Sessions."); + waitForInputToContinue(scanner); + String bucketObject = createSessionAddObjects(); + + // Demonstrate performance differences between regular and directory buckets. + demonstratePerformance(bucketObject); + + // Populate the buckets to show the lexicographical difference between + // regular and express buckets. + showLexicographicalDifferences(bucketObject); + + logger.info(DASHES); + logger.info("That's it for our tour of the basic operations for S3 Express One Zone."); + logger.info("Would you like to cleanUp the AWS resources? (y/n): "); + String response = scanner.next().trim().toLowerCase(); + if (response.equals("y")) { + cleanUp(stackName); + } + } + + /* + Delete resources created by this scenario. + */ + public static void cleanUp(String stackName) { + try { + if (mdirectoryBucketName != null) { + s3DirectoriesActions.deleteBucketAndObjectsAsync(mS3ExpressClient, mdirectoryBucketName).join(); + } + logger.info("Deleted directory bucket " + mdirectoryBucketName); + mdirectoryBucketName = null; + if (mregularBucketName != null) { + s3DirectoriesActions.deleteBucketAndObjectsAsync(mS3RegularClient, mregularBucketName).join(); + } + } catch (CompletionException ce) { + Throwable cause = ce.getCause(); + if (cause instanceof S3Exception) { + logger.error("S3Exception occurred: {}", cause.getMessage(), ce); + } else { + logger.error("An unexpected error occurred: {}", cause.getMessage(), ce); + } + } + + logger.info("Deleted regular bucket " + mregularBucketName); + mregularBucketName = null; + CloudFormationHelper.destroyCloudFormationStack(stackName); + } + + private static void showLexicographicalDifferences(String bucketObject) { + logger.info(DASHES); + logger.info(""" + 7. Populate the buckets to show the lexicographical (alphabetical) difference + when object names are listed. Now let's explore how directory buckets store + objects in a different manner to regular buckets. The key is in the name + "Directory". Where regular buckets store their key/value pairs in a + flat manner, directory buckets use actual directories/folders. + This allows for more rapid indexing, traversing, and therefore + retrieval times! + + The more segmented your bucket is, with lots of + directories, sub-directories, and objects, the more efficient it becomes. + This structural difference also causes `ListObject` operations to behave + differently, which can cause unexpected results. Let's add a few more + objects in sub-directories to see how the output of + ListObjects changes. + """); + + waitForInputToContinue(scanner); + + // Populate a few more files in each bucket so that we can use + // ListObjects and show the difference. + String otherObject = "other/" + bucketObject; + String altObject = "alt/" + bucketObject; + String otherAltObject = "other/alt/" + bucketObject; + + try { + s3DirectoriesActions.putObjectAsync(mS3RegularClient, mregularBucketName, otherObject, "").join(); + s3DirectoriesActions.putObjectAsync(mS3ExpressClient, mdirectoryBucketName, otherObject, "").join(); + s3DirectoriesActions.putObjectAsync(mS3RegularClient, mregularBucketName, altObject, "").join(); + s3DirectoriesActions.putObjectAsync(mS3ExpressClient, mdirectoryBucketName, altObject, "").join(); + s3DirectoriesActions.putObjectAsync(mS3RegularClient, mregularBucketName, otherAltObject, "").join(); + s3DirectoriesActions.putObjectAsync(mS3ExpressClient, mdirectoryBucketName, otherAltObject, "").join(); + + } catch (CompletionException ce) { + Throwable cause = ce.getCause(); + if (cause instanceof NoSuchBucketException) { + logger.error("S3Exception occurred: {}", cause.getMessage(), ce); + } else { + logger.error("An unexpected error occurred: {}", cause.getMessage(), ce); + } + return; + } + + try { + // List objects in both S3 buckets. + List<String> dirBucketObjects = s3DirectoriesActions.listObjectsAsync(mS3ExpressClient, mdirectoryBucketName).join(); + List<String> regBucketObjects = s3DirectoriesActions.listObjectsAsync(mS3RegularClient, mregularBucketName).join(); + + logger.info("Directory bucket content");