avatarTeri Radichel

Free AI web copilot to create summaries, insights and extended knowledge, download it at here

9302

Abstract

e data in the bucket and write to the bucket</li></ul><p id="0021">On top of those policies, we can add notifications, Config rules (something I haven’t written about yet) and SCPs to limit actions on top of our IAM and S3 bucket policies.</p><p id="8166">I’ll continue to consider these threats as we work through this series and how to best create an policy architecture that lets people get things done while preventing egregious errors and reduces the chances of successful attacks.</p><p id="7dd0">~~</p><h2 id="41db">BucketName</h2><p id="58aa">Next we’ll need to set the <b>BucketName</b> property. We’ll pass in a parameter for that as well via a <b>ParamBucketName</b> parameter.</p><figure id="9a62"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*Ylw-PfE2iPg6POR4xO9AWA.png"><figcaption></figcaption></figure><h2 id="7e0c">LifecycleConfiguration</h2><p id="b39b">The CloudTrail bucket created by AWS Control Tower was 365 days with no archiving. We could set that same configuration here, but we can save money by archiving the data to a less expensive storage tier after a while if we don’t think we will need to access it. We can still access it in the future it will just take longer to retrieve.</p><div id="704b" class="link-block"> <a href="https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-properties-s3-bucket-lifecycleconfig.html"> <div> <div> <h2>AWS::S3::Bucket LifecycleConfiguration</h2> <div><h3>Specifies the lifecycle configuration for objects in an Amazon S3 bucket. For more information, see Object Lifecycle…</h3></div> <div><p>docs.aws.amazon.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/)"></div> </div> </div> </a> </div><figure id="8453"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*lmlTz0SxxHuktKY_rKZ69w.png"><figcaption></figcaption></figure><p id="ee7b">Alright click on Rule to find out how we need to configure a rule. We have a number of options.</p><figure id="f56a"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*iOBp-hVpVR46vybeVGpVBQ.png"><figcaption></figcaption></figure><h2 id="34de">ExpirationInDays</h2><p id="b786">First we can use <b>ExpirationInDays </b>to define how many days before the objects get deleted. We can pass in a parameter and I’ll set the default to 365 days.</p><figure id="973a"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*JrJxFVVfr2t3meNdBoW5Lw.png"><figcaption></figcaption></figure><h2 id="06f8">Transitions</h2><p id="5748">We can also use <b>Transitions </b>to transition files to a lower cost storage option.</p><p id="b91e">For Transitions, we can create a list of transitions which look like this.</p><figure id="3e0c"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*PbKiJm0iT9m115U3iOSc7g.png"><figcaption></figcaption></figure><p id="061d">We can choose from the following storage classes:</p><figure id="45b7"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*Edtlxtq1BQpkOheMoB7vYw.png"><figcaption></figcaption></figure><p id="8560">To determine which storage class to use, review the cost of each class and how quickly you can retrieve it. Consider how fast you would need to retrieve the data in the cast of a disaster (for backups) or a security incident (for archived CloudTrail and other logs).</p><div id="1855" class="link-block"> <a href="https://aws.amazon.com/s3/storage-classes/"> <div> <div> <h2>Object Storage Classes - Amazon S3</h2> <div><h3>Amazon S3 offers a range of storage classes that you can choose from based on the data access, resiliency, and cost…</h3></div> <div><p>aws.amazon.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/0*FuCF7zADK7nJqT5C)"></div> </div> </div> </a> </div><p id="2c7e">Here’s a chart showing a comparison of the different classes.</p><figure id="b80e"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*k59Fu7R83J6L9NVcW0NTjQ.png"><figcaption></figcaption></figure><p id="f793">I find a few things interesting above.</p><p id="3f6d">If you choose to use Intelligent tiering, then you don’t have to pay for retrieval. But with intelligent tiering the minimum time before you can move objects to the another tier is 90 days and then 180 days for deep archive. Perhaps you would save more money by immediately archiving objects for certain use cases instead of using intelligent tiering.</p><div id="42c9" class="link-block"> <a href="https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-properties-s3-bucket-intelligenttieringconfiguration.html"> <div> <div> <h2>AWS::S3::Bucket IntelligentTieringConfiguration</h2> <div><h3>undefined</h3></div> <div><p>undefined</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/)"></div> </div> </div> </a> </div><p id="3f84">Also, the minimum time you can leave objects in Deep Archive is 180 days. So your minimum cost will be the cost of that service times 180 days. Let’s look at the cost.</p><div id="9423" class="link-block"> <a href="https://aws.amazon.com/s3/pricing/"> <div> <div> <h2>Amazon S3 Simple Storage Service Pricing - Amazon Web Services</h2> <div><h3>Pay only for what you use. There is no minimum charge. There are six Amazon S3 cost components to consider when storing…</h3></div> <div><p>aws.amazon.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/0*25Qfh8heNFmXHhnN)"></div> </div> </div> </a> </div><p id="d0ff">Make sure you select the correct region.</p><figure id="9ab7"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*miXw1pGkhVdAvpEAPRlEJQ.png"><figcaption></figcaption></figure><p id="217f">As you can see above you can potentially save a lot of money using S3 Glacier Deep Archive when you look at the total size of your storage in GB.</p><p id="a11a">But check out the chart above again. The minimum capacity charge per object is 40KB. Keep that in mind if you are storing a lot of tiny objects. Like CloudTrail logs. Let’s take a look at my CloudTrail logs in my SSO account where I have a history of CloudTrail data.</p><p id="078f">As you can see almost every object is only about 740 bytes or about .74 KB. The minimum Capacity charge per object is 40 KB. In order to see if you will actually save money, if I understand correctly, you’ll need to calculate the total storage size after converting every object under 40 KB to a storage size of 40 KB. Then calculate your storage amount.</p><figure id="1ec0"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*IxHhrSSND8mV6mlFYgmnxA.png"><figcaption></figcaption></figure><p id="83ab">Maybe the <b>AWS Pricing Calculator </b>may help but you still have to feed it in all the correct inputs. How are you going to put in the number of files that are under 40KB.</p><div id="43a9" class="link-block"> <a href="https://calculator.aws/#/"> <div> <div> <h2>AWS Pricing Calculator</h2> <div><h3>AWS Pricing Calculator lets you explore AWS services, and create an estimate for the cost of your use cases on AWS.</h3></div> <div><p>calculator.aws</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/)"></div> </div> </div> </a> </div><p id="398d">The calculator is not going to be real precise. You can only enter an <b>average object size.</b></p><figure id="b19e"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*CrL7ERyfpie3hL0Uoc445w.png"><figcaption></figcaption></figure><p id="e7da">You could also just create a <b>spreadsheet</b>. Just make sure you are not missing anything in these complex formulas (been there done that) and beta test to make sure your assumptions are correct.</p><p id="9815">Math does not bring me joy. I’m going to leave off any sort of storage tiering to start and revisit this later as I have plans to change CloudTrail in the future anyway. Also, I can go back and see how intelligent tiering changed my costs, if it did, in my existing account. At the moment half a month has passed and my costs are already higher than last month for CloudTrail logs so I think it’s not a great option. But I’ll double check that later.</p><p id="af89">If and when I do use tiering, one way for me to save money would be to <b>zip up a bunch of those smaller files into minimum 40KB file

Options

sizes</b>. If my files are 740 bytes and minimum object size is billed at 40KB and there are 40,000 bytes in 40KB then I can put 40,000 / 740 or roughly 55 files into a zip file to meet the minimum. But I randomly noticed I had some larger files as well. I could zip them into sizes <b>that align with GB increments since retrieval are charged per GB</b>. But I also need to be able to identify time ranges in each object to download a timeframe I require. So what if I zip them by month and year? Then I can tell what data I’m downloading instead of retrieving everything.</p><p id="1670">If this sound confusing it is. I already wrote about this in a security white paper for SANS institute on packet capture in AWS before AWS provided that capability because my advisor asked me how much it would cost to store logs on AWS. Not a simple answer to that question. We also had to perform similar analysis and file sizing when sending logs to S3 buckets when I worked for a firewall vendor.</p><p id="3f36">Maybe we’ll revisit this topic later.</p><h2 id="0c46">LoggingConfiguration</h2><p id="1765">For <b>LoggingConfiguration</b> we may or may not want to set a logging bucket. If we are creating the logging bucket we won’t turn this on. Then we’ll create the bucket where we want to store data. In that case, we probably want logs indicating when the objects in the buckets were accessed.</p><p id="f683">We’ll pass in the log bucket as an optional parameter named <b>ParamLogBucket</b>. If the bucket is passed in, logging will be configured otherwise it will not be. That means we need a condition. If the condition is set, we set values for the LoggingConfiguration.</p><div id="6a1c" class="link-block"> <a href="https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-properties-s3-bucket-loggingconfig.html"> <div> <div> <h2>AWS::S3::Bucket LoggingConfiguration</h2> <div><h3>undefined</h3></div> <div><p>undefined</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/)"></div> </div> </div> </a> </div><figure id="2e92"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*7VT-rUHx3JwB9FnGtpTcdQ.png"><figcaption></figcaption></figure><p id="3c18">Notice that we can also pass in a <b>LogFilePrefix</b>. That allows us to use one bucket but put logs for different buckets in that bucket with the logs for each bucket in a separate folder. (Yes, I know it’s technically not a “folder” but it looks and works like a folder — for those who like to be nit-picky.)</p><p id="e624">For example, let’s say we create bucket1 and bucket2.</p><p id="1d08">We could have the following folders in our “logs” bucket with the folders bucket1 and bucket2 storing the corresponding logs for each bucket.</p><div id="1397"><pre>/logs /bucket1 log1.txt log2.txt /bucket2 log1.txt log2.txt</pre></div><p id="c8fa">We’ll make the prefix an optional parameter as well — <b>ParamLogBucketPrefix</b>. If it’s set, we’ll configure the <b>LogFilePrefix</b> property.</p><p id="ddd4">Here’s what our conditions look like:</p><figure id="ed6a"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*soh1LK2au3ahG__2b_w1xQ.png"><figcaption></figcaption></figure><p id="ec09">Here’s the LoggingConfiguration property:</p><figure id="0a46"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*7aLypjPcbAEybt0hQOBYuw.png"><figcaption></figcaption></figure><h2 id="cbcf">PublicAccessBlockConfiguration</h2><p id="cd12">We want to block public access with the <b>PublicAccessBlockConfiguration</b>.</p><figure id="6484"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*bCGXxMvSkMV__uTTIeMazA.png"><figcaption></figcaption></figure><p id="401e">Since I always want this to be turned on, I’ll hardcode these values. Everyone should use this template, so they won’t be able to turn these off or enable an ACL.</p><figure id="8549"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*vtwhTZZhRzuRs-AFFcDBLQ.png"><figcaption></figcaption></figure><h2 id="adab">VersioningConfiguration</h2><p id="aea9">For <b>VersioningConfiguration</b>, we need to set the value to a VersioningConfiguration.</p><figure id="2406"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*8FVx0Jf1ovLdH8gmzzHdUQ.png"><figcaption></figcaption></figure><p id="8a89">I’m going to create a parameter that is set on by default.</p><figure id="4373"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*QBAH-L7y4plswg_6w1x9qg.png"><figcaption></figcaption></figure><p id="3865">Then set the value:</p><figure id="6d7d"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*IGNvi89Xzw_IRUOxfTIXeA.png"><figcaption></figcaption></figure><h2 id="483e">Outputs</h2><p id="89b4">Last we’ll want to create some outputs for values we may need later.</p><figure id="5bad"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*I5VLA6pCWTe1mP-rq-V6AQ.png"><figcaption></figcaption></figure><h2 id="a1c0">Full CloudFormation Template (Untested!)</h2><p id="c6c0">We now have the code for our S3 bucket written but we still need to create our deployment script and test it out. No guarantees the code works! I’ll test it out in an upcoming post and add the deployment scripts.</p><figure id="5687"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*-1NXEdPHvZqg5VJZa3dCyQ.png"><figcaption></figcaption></figure><p id="24a7">Find out how these templates can help you improve security in your cloud environment.</p><div id="9ff7" class="link-block"> <a href="https://readmedium.com/how-a-cloudformation-template-can-secure-your-s3-buckets-738cd293c23f"> <div> <div> <h2>How a CloudFormation Template Can Secure Your S3 Buckets</h2> <div><h3>ACM.193 Secure templates depend on a secure deployment pipeline</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/0*bGOT6OdAfl7V2Ial.png)"></div> </div> </div> </a> </div><p id="07df">I’ll publish the tested code in a subsequent post with the deployment scripts.</p><div id="3a4d" class="link-block"> <a href="https://readmedium.com/s3-bucket-for-s3-access-logs-f089a8419c20"> <div> <div> <h2>S3 Bucket for S3 Access Logs</h2> <div><h3>ACM.194 Deployment scripts for a generic S3 bucket template</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*-1NXEdPHvZqg5VJZa3dCyQ.png)"></div> </div> </div> </a> </div><div id="f90e" class="link-block"> <a href="https://readmedium.com/s3-bucket-for-cloudtrail-e603271a1bb5"> <div> <div> <h2>S3 Bucket for CloudTrail</h2> <div><h3>ACM.195 Creating a bucket with a server access logging bucket</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*RNyNEQTAMMs90aH_xTZnFw.png)"></div> </div> </div> </a> </div><p id="cb8d">Follow for updates.</p><p id="4a3a">Teri Radichel | <i>© <a href="https://2ndsightlab.com/?source=post_page---------------------------">2nd Sight Lab</a> 2023</i></p><div id="8b5f"><pre><span class="hljs-section">About Teri Radichel:

⭐️ Author: Cybersecurity Books
⭐️ Presentations: Presentations by Teri Radichel
⭐️ Recognition: SANS Award, AWS Security Hero, IANS Faculty
⭐️ Certifications: SANS ~ GSE 240
⭐️ Education: BA Business, Master of Software Engineering, Master of Infosec
⭐️ Company: Penetration Tests, Assessments, Phone Consulting ~ 2nd Sight Lab</pre></div><div id="caae"><pre><span class="hljs-section">Need Help With Cybersecurity, Cloud, or Application Security?
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~</span>
🔒 Request a penetration test or security assessment
🔒 Schedule a consulting call
🔒 Cybersecurity Speaker for Presentation</pre></div><div id="5a42"><pre>Follow <span class="hljs-keyword">for</span> more stories like <span class="hljs-keyword">this</span>:

❤️ Sign Up my Medium Email List ❤️ Twitter: <span class="hljs-meta">@teriradichel</span> ❤️ LinkedIn: https:<span class="hljs-comment">//www.linkedin.com/in/teriradichel</span> ❤️ Mastodon: <span class="hljs-meta">@teriradichel</span><span class="hljs-meta">@infosec</span>.exchange ❤️ Facebook: 2nd Sight Lab ❤️ YouTube: @2ndsightlab</pre></div><figure id="faf5"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/0*H9Ew1KCl-29nZiPR.jpeg"><figcaption></figcaption></figure></article></body>

Generic Template for an S3 Bucket

ACM.192 Creating a reusable CloudFormation template for S3 buckets

Part of my series on Automating Cybersecurity Metrics and stories on AWS S3 Buckets. The Code.

Free Content on Jobs in Cybersecurity | Sign up for the Email List

In the last post we looked at options for an S3 bucket.

In this post we’ll try to create a generic S3 bucket template ~ the kind of code I used to provide in my cloud security classes.

Likely this S3 CloudFormation template will evolve as we need to create new S3 buckets. We will need additional features and settings as we implement new resources, the same way our generic KMS key template evolved throughout the series.

In fact, I’m going to have to modify that KMS Key template again to support the CloudTrail changes we need to make.

Adding a directory to our GitHub repo for S3 bucket code

To start I’m going to create a new S3 directory and my standard directory structure, which should look familiar if you’ve been following along.

mkdir S3
cd S3
mkdir stacks
cd stacks
mkdir cfn

Create a CloudFormation template for an S3 bucket

Then I’ll create an Bucket.yaml file in my stacks/cfn folder.

vi Bucket.yaml

Now we start creating our bucket script. I know I’m going to have to pass in a name parameter. Referring to my last post and the first property I want to set is bucket encryption.

BucketEncryption

By default this will be set to AWS managed encryption. We want to set the KMS key here. To do that we need to configure the BucketEncryption property.

The BucketEncryption resource requires a ServerSideEncryptionRule resource.

The ServerSideEncryptionRule requires a ServerSideEncryptionByDefault resource.

And ironically the “SSE Encryption By Default” option that does not use a customer managed key allows us to assign a KMS key and algorithm. I imagine this is due to the fact that AWS S3 has been around a very long time — but no it was not the first AWS service. That was AWS SQS.

Why can’t we just assign a KMS Key ID to the bucket? I suspect this is due to the fact that AWS SSE and AWS S3 buckets existed prior to KMS and things have evolved in such a way they need to remain backwards compatible. It would be nice if AWS would add the option to assign the KMS Key ID directly to the bucket now that everything is encrypted by default. But for now, here’s our code.

We’ll provide a way to pass in a KMS key ID via a ParamKMSKeyId parameter.

~~

Threat Modeling Tangent: Rogue bucket encryption (misconfigurations and ransomware)

My mind wanders here for a minute. One consideration here is making sure people pass in a valid key ID. In the case of a misconfiguration, what if someone updates a stack to the wrong key ID? What happens when the new key starts encrypting all your CloudTrail logs and you can’t access them? Here’s where you want to lock down who can change your CloudTrail stacks and resources to limit who can update them. You might think about an SCP on your CloudTrail to lock it to a particular Key ID — but what happens when you go to rotate that key? Probably better to limit who can update the key associated with your CloudTrail logs.

In the nefarious scenario, could an attacker encrypt all your data with a key ID from some other rogue AWS account? Well, one of the benefits of KMS when it comes to ransomware is that if an attacker used a key from AWS, AWS should be able to help you get that data back, or at least help you revert the configuration to the correct key.

In order to encrypt the data in your S3 bucket with some other mechanism, the attacker would first need to be able to get permission to decrypt the data in your S3 bucket via the key policy associated with the customer managed key we have assigned and proper IAM permissions. Perhaps you have administrators who can decrypt and view your CloudTrail logs.

However, the attacker would also need to be able to write back to the S3 bucket. In this case we are going to limit writing to the bucket to CloudTrail (covered in the next post when we create a bucket policy). So in order for ransomware to encrypt your CloudTrail logs they would need

  • Permission to change the S3 bucket policy
  • Obtain or create credentials with an IAM Policy allowed to decrypt the data in the bucket and write to the bucket

On top of those policies, we can add notifications, Config rules (something I haven’t written about yet) and SCPs to limit actions on top of our IAM and S3 bucket policies.

I’ll continue to consider these threats as we work through this series and how to best create an policy architecture that lets people get things done while preventing egregious errors and reduces the chances of successful attacks.

~~

BucketName

Next we’ll need to set the BucketName property. We’ll pass in a parameter for that as well via a ParamBucketName parameter.

LifecycleConfiguration

The CloudTrail bucket created by AWS Control Tower was 365 days with no archiving. We could set that same configuration here, but we can save money by archiving the data to a less expensive storage tier after a while if we don’t think we will need to access it. We can still access it in the future it will just take longer to retrieve.

Alright click on Rule to find out how we need to configure a rule. We have a number of options.

ExpirationInDays

First we can use ExpirationInDays to define how many days before the objects get deleted. We can pass in a parameter and I’ll set the default to 365 days.

Transitions

We can also use Transitions to transition files to a lower cost storage option.

For Transitions, we can create a list of transitions which look like this.

We can choose from the following storage classes:

To determine which storage class to use, review the cost of each class and how quickly you can retrieve it. Consider how fast you would need to retrieve the data in the cast of a disaster (for backups) or a security incident (for archived CloudTrail and other logs).

Here’s a chart showing a comparison of the different classes.

I find a few things interesting above.

If you choose to use Intelligent tiering, then you don’t have to pay for retrieval. But with intelligent tiering the minimum time before you can move objects to the another tier is 90 days and then 180 days for deep archive. Perhaps you would save more money by immediately archiving objects for certain use cases instead of using intelligent tiering.

Also, the minimum time you can leave objects in Deep Archive is 180 days. So your minimum cost will be the cost of that service times 180 days. Let’s look at the cost.

Make sure you select the correct region.

As you can see above you can potentially save a lot of money using S3 Glacier Deep Archive when you look at the total size of your storage in GB.

But check out the chart above again. The minimum capacity charge per object is 40KB. Keep that in mind if you are storing a lot of tiny objects. Like CloudTrail logs. Let’s take a look at my CloudTrail logs in my SSO account where I have a history of CloudTrail data.

As you can see almost every object is only about 740 bytes or about .74 KB. The minimum Capacity charge per object is 40 KB. In order to see if you will actually save money, if I understand correctly, you’ll need to calculate the total storage size after converting every object under 40 KB to a storage size of 40 KB. Then calculate your storage amount.

Maybe the AWS Pricing Calculator may help but you still have to feed it in all the correct inputs. How are you going to put in the number of files that are under 40KB.

The calculator is not going to be real precise. You can only enter an average object size.

You could also just create a spreadsheet. Just make sure you are not missing anything in these complex formulas (been there done that) and beta test to make sure your assumptions are correct.

Math does not bring me joy. I’m going to leave off any sort of storage tiering to start and revisit this later as I have plans to change CloudTrail in the future anyway. Also, I can go back and see how intelligent tiering changed my costs, if it did, in my existing account. At the moment half a month has passed and my costs are already higher than last month for CloudTrail logs so I think it’s not a great option. But I’ll double check that later.

If and when I do use tiering, one way for me to save money would be to zip up a bunch of those smaller files into minimum 40KB file sizes. If my files are 740 bytes and minimum object size is billed at 40KB and there are 40,000 bytes in 40KB then I can put 40,000 / 740 or roughly 55 files into a zip file to meet the minimum. But I randomly noticed I had some larger files as well. I could zip them into sizes that align with GB increments since retrieval are charged per GB. But I also need to be able to identify time ranges in each object to download a timeframe I require. So what if I zip them by month and year? Then I can tell what data I’m downloading instead of retrieving everything.

If this sound confusing it is. I already wrote about this in a security white paper for SANS institute on packet capture in AWS before AWS provided that capability because my advisor asked me how much it would cost to store logs on AWS. Not a simple answer to that question. We also had to perform similar analysis and file sizing when sending logs to S3 buckets when I worked for a firewall vendor.

Maybe we’ll revisit this topic later.

LoggingConfiguration

For LoggingConfiguration we may or may not want to set a logging bucket. If we are creating the logging bucket we won’t turn this on. Then we’ll create the bucket where we want to store data. In that case, we probably want logs indicating when the objects in the buckets were accessed.

We’ll pass in the log bucket as an optional parameter named ParamLogBucket. If the bucket is passed in, logging will be configured otherwise it will not be. That means we need a condition. If the condition is set, we set values for the LoggingConfiguration.

Notice that we can also pass in a LogFilePrefix. That allows us to use one bucket but put logs for different buckets in that bucket with the logs for each bucket in a separate folder. (Yes, I know it’s technically not a “folder” but it looks and works like a folder — for those who like to be nit-picky.)

For example, let’s say we create bucket1 and bucket2.

We could have the following folders in our “logs” bucket with the folders bucket1 and bucket2 storing the corresponding logs for each bucket.

/logs
    /bucket1
       log1.txt
       log2.txt
    /bucket2
       log1.txt
       log2.txt

We’ll make the prefix an optional parameter as well — ParamLogBucketPrefix. If it’s set, we’ll configure the LogFilePrefix property.

Here’s what our conditions look like:

Here’s the LoggingConfiguration property:

PublicAccessBlockConfiguration

We want to block public access with the PublicAccessBlockConfiguration.

Since I always want this to be turned on, I’ll hardcode these values. Everyone should use this template, so they won’t be able to turn these off or enable an ACL.

VersioningConfiguration

For VersioningConfiguration, we need to set the value to a VersioningConfiguration.

I’m going to create a parameter that is set on by default.

Then set the value:

Outputs

Last we’ll want to create some outputs for values we may need later.

Full CloudFormation Template (Untested!)

We now have the code for our S3 bucket written but we still need to create our deployment script and test it out. No guarantees the code works! I’ll test it out in an upcoming post and add the deployment scripts.

Find out how these templates can help you improve security in your cloud environment.

I’ll publish the tested code in a subsequent post with the deployment scripts.

Follow for updates.

Teri Radichel | © 2nd Sight Lab 2023

About Teri Radichel:
~~~~~~~~~~~~~~~~~~~~
⭐️ Author: Cybersecurity Books
⭐️ Presentations: Presentations by Teri Radichel
⭐️ Recognition: SANS Award, AWS Security Hero, IANS Faculty
⭐️ Certifications: SANS ~ GSE 240
⭐️ Education: BA Business, Master of Software Engineering, Master of Infosec
⭐️ Company: Penetration Tests, Assessments, Phone Consulting ~ 2nd Sight Lab
Need Help With Cybersecurity, Cloud, or Application Security?
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
🔒 Request a penetration test or security assessment
🔒 Schedule a consulting call
🔒 Cybersecurity Speaker for Presentation
Follow for more stories like this:
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
❤️ Sign Up my Medium Email List
❤️ Twitter: @teriradichel
❤️ LinkedIn: https://www.linkedin.com/in/teriradichel
❤️ Mastodon: @teriradichel@infosec.exchange
❤️ Facebook: 2nd Sight Lab
❤️ YouTube: @2ndsightlab
S3
AWS
Cloud Security
Cybersecurity
Cloudformation
Recommended from ReadMedium
avatarMunidimple Muchalli
AWS GuardDuty

AWS Guard Duty

4 min read