# Secure Temporary File Sharing in AWS S3 with pre-signed URLs: A Hands-On Guide

**Why Presigned URLs Matter in the Real World**  
Imagine you're building a healthcare app where doctors need to securely access patient lab reports stored in a *private S3 bucket*. You don’t want to make the bucket public, but you need to grant time-limited access to specific files. Presigned URLs solve this by generating temporary, expiring links that authorize access to private S3 objects. Other use cases:

* Sharing confidential documents with clients.
    
* Distributing time-sensitive media (e.g., concert recordings).
    
* Allowing users to download purchased software securely.
    

---

### How to Grant Users Access to S3 Objects

By default, all objects stored in Amazon S3 are private, meaning only the owner of the bucket has access to them. However, if you need to grant users access to specific buckets or objects without making them publicly available, you can do so by assigning the appropriate permissions through an IAM policy. Alternatively, you can use **presigned URLs** to provide temporary access without requiring users to have AWS credentials or IAM permissions.

### So Why to use Presigned URLs?

A presigned URL is a time-limited URL that grants temporary access to a specific S3 object. These URLs allow users to either **read** or **write** (update) an object, depending on the permissions you configure. The URL includes specific parameters set by your application, ensuring controlled and secure access. These parameters include:

* **Bucket:** The name of the bucket where the object is stored (or will be stored).
    
* **Key:** The name or path of the object.
    
* **Expires:** The duration for which the URL remains valid.
    

Once the expiration time passes, the URL becomes invalid, and the user can no longer access the object. Importantly, presigned URLs are securely signed by the S3 bucket owner, ensuring that only authorized users can interact with the object during the specified time frame.

**Project Lab: Create and Test Presigned URLs**  
*Objective*: Build a system to share private S3 objects securely and temporarily using pre-signed URLs.

**Prerequisites**:

### **Prerequisites for Using** `aws s3 cp`

1. **AWS CLI Installed**:  
    The AWS Command Line Interface (CLI) must be installed on your machine.
    

* Installation instructions: [AWS CLI Installat](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html)[ion Guide.](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html)
    
* Verify installation:
    
    ```bash
    # Run to verify AWS CLI is installed 
    aws --version
    
    # Configure AWS CLI with AWS Credential and Default Region. 
    aws configure  
    ```
    
* You’ll be prompted for:
    
    * **AWS Access Key ID**: Your IAM user’s access key.
        
    * **AWS Secret Access Key**: Your IAM user’s secret key.
        
    * ***Default* Region Name**: The AWS region (e.g., `us-east-1`).
        
    * **Default Output Format**: Optional (e.g. jason)
        
* [Verify configuration:](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html)
    
    ```bash
    cat ~/.aws/credentials  
    cat ~/.aws/config  
    ```
    

---

### **Step 1: Create an S3 Bu**[**cket and Upload a Test Fil**](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html)**e**

1. **Create a private S3 bucket**:
    
    ```bash
    aws s3api create-bucket --bucket your-unique-bucket-name --region us-east-1
    ```
    
2. **Upload a sample file** (e.g., `medical-report.pdf`):
    
    ```bash
    echo "Confidential Patient Data" > medical-report.pdf  
    aws s3 cp medical-report.pdf s3://your-unique-bucket-name/
    ```
    

### **Step 2: Generate a Presigned URL via AWS CLI**

Generate a URL that expires in **5 minutes** (300 seconds):

```bash
aws s3 presign s3://your-unique-bucket-name/medical-report.pdf --expires-in 300  
```

```bash
https://your-unique-bucket-name.s3.amazonaws.com/medical-report.pdf?AWSAccessKeyId=...&Signature=...&Expires=...  
```

### **Step 3: Generate a Presigned URL with Python (Boto3)**

1. **Install Boto3**:
    
    ```bash
    pip install boto3  
    ```
    
2. **Python script** (`generate_presigned_`[`url.py`](http://url.py)):
    
    ```python
    import boto3  
    from datetime import timedelta  
    
    s3_client = boto3.client('s3')  
    
    url = s3_client.generate_presigned_url(  
        ClientMethod='get_object',  
        Params={  
            'Bucket': 'your-unique-bucket-name',  
            'Key': 'medical-report.pdf'  
        },  
        ExpiresIn=300  # 5 minutes  
    )  
    
    print("Presigned URL:", url)  
    ```
    
3. **Run the script**:
    
    ```python
    python generate_presigned_url.py  
    ```
    
    When you run the script, it will generate a presigned URL that looks something like this:
    
    plaintext
    
    Copy
    
    ```bash
    Presigned URL: https://your-unique-bucket-name.s3.amazonaws.com/medical-report.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=AKIAIOSFODNN7EXAMPLE%2F20231015%2Fus-east-1%2Fs3%2Faws4_request&X-Amz-Date=20231015T123456Z&X-Amz-Expires=300&X-Amz-SignedHeaders=host&X-Amz-Signature=1a2b3c4d5e6f7g8h9i0j1k2l3m4n5o6p7q8r9s0t1u2v3w4x5y6z7a8b9c0d
    ```
    
    What Does This Mean?
    
    * **URL Structure:** The URL points to the `medical-report.pdf` file stored in the `your-unique-bucket-name` S3 bucket.
        
    * **Temporary Access:** The URL is valid for **5 minutes** (as specified by `ExpiresIn=300`).
        
    * **Security:** The URL includes a signature (`X-Amz-Signature`) and other parameters that ensure only authorized users can access the file during the specified time frame.
        
    
    ### How to Use the URL
    
    1. Copy the pre-signed URL and share it with the intended user.
        
    2. The user can open the URL in a web browser or use it in a tool like `curl` or `wget` to download the file.
        
    3. After 5 minutes, the URL will expire, and access to the file will be revoked.
        

### **Step 4: Test URL Expiration**

1. Generate a URL with a **10-second expiration**:
    
    ```python
    aws s3 presign s3://your-unique-bucket-name/medical-report.pdf --expires-in 10  
    ```
    
2. Wait 15 seconds and try accessing the URL. You’ll see an **HTTP 403 Forbidden** error.
    

### **Step 5: Security Best Practices**

1. **Short Expiration Times**: Use 5-15 minutes for most cases.
    
2. **HTTPS Only**: Always generate presigned URLs with HTTPS.
    
3. **Restrict IAM Policies**: Limit the IAM user/role to only `s3:GetObject` permissions.
    
    ```python
    {  
        "Version": "2012-10-17",  
        "Statement": [{  
            "Effect": "Allow",  
            "Action": "s3:GetObject",  
            "Resource": "arn:aws:s3:::your-unique-bucket-name/*"  
        }]  
    }  
    ```
    

---

**Conclusion**  
Presigned URLs are a powerful way to securely share private S3 objects without exposing your bucket to the public. By following this guide, you’ve learned to generate URLs via CLI and SDK, test their expiration, and apply security best practices. Use this for secure document sharing, time-bound downloads, or even temporary access in serverless apps!

For more information and reference on this, please follow

* [AWS S3 Presigned URL Documentation](https://docs.aws.amazon.com/AmazonS3/latest/userguide/ShareObjectPreSignedURL.html)
    
* [**Download and upload objects with presigned URLs**](https://docs.aws.amazon.com/AmazonS3/latest/userguide/using-presigned-url.html)
    
* [Generate a presigned URL in modular AWS SDK for JavaScript](https://aws.amazon.com/blogs/developer/generate-presigned-url-modular-aws-sdk-javascript/)
    

I hope this Blog helps you understand Amazon S3 Presigned URLs' capabilities and gives you insights into the amazing new ways to share Temporary Files with Amazon S3 Objects.

For more information on this, please follow [**Working with Mountpoint for Amazon S3**](https://docs.aws.amazon.com/AmazonS3/latest/userguide/mountpoint.html)

Thank you for the read. Hope you like it.  
I appreciate your time.

Follow for more Azure and AWS Content. Happy Learning!

Regards,  
[**Jineshkumar Patel**](https://www.linkedin.com/in/jineshkumarpatel/)
