# AWS S3 Test Guide

## ✅ **ĐÃ TẠO 3 APIs TEST S3**

| API | Endpoint | Mục đích |
|-----|----------|----------|
| 1️⃣ Upload Test | `POST /api/speakup/test-upload-s3` | Test upload file lên AWS S3 |
| 2️⃣ Download Test | `GET /api/speakup/test-download-s3` | Test download/get info file |
| 3️⃣ List Files Test | `GET /api/speakup/test-list-s3` | List files trong folder |

---

## ⚙️ **BƯỚC 1: CẤU HÌNH .ENV**

Cập nhật file `.env` với credentials AWS S3:

```bash
# AWS S3 Configuration
AWS_S3_ACCESS_KEY_ID=AKIAVFM5ZFITVSXY455D
AWS_S3_SECRET_ACCESS_KEY=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
AWS_S3_DEFAULT_REGION=ap-southeast-1
AWS_S3_BUCKET=aws-test-atung
AWS_S3_URL=https://aws-test-atung.s3.ap-southeast-1.amazonaws.com

# CloudFront URL (nếu có)
AWS_CLOUDFRONT_URL=https://d3rrb37z9aai1k.cloudfront.net/
```

**Clear cache:**
```bash
php artisan config:clear
```

---

## 🚀 **BƯỚC 2: TEST UPLOAD**

### **Test Upload API:**

```bash
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@/path/to/test-image.jpg' \
  -F 'folder=test_uploads'
```

**Hoặc với Postman:**
- Method: POST
- URL: `https://lmsnew.hocmai.net/api/speakup/test-upload-s3`
- Body: form-data
  - `file`: [Select file]
  - `folder`: `test_uploads` (optional)

---

### **Response Success:**

```json
{
    "status": true,
    "message": "File uploaded to AWS S3 successfully",
    "data": {
        "file_name": "test-image.jpg",
        "s3_key": "test_uploads/2025/11/14/test-image_1731552000_abc123.jpg",
        "s3_url": "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/test_uploads/2025/11/14/test-image_1731552000_abc123.jpg",
        "cloudfront_url": "https://d3rrb37z9aai1k.cloudfront.net/test_uploads/2025/11/14/test-image_1731552000_abc123.jpg",
        "file_size": 524288,
        "mime_type": "image/jpeg",
        "exists": true,
        "uploaded_at": "2025-11-14T10:00:00.000000Z"
    }
}
```

---

### **Response Error:**

```json
{
    "status": false,
    "message": "An error occurred: Error executing \"PutObject\" on \"https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/...\"; AWS HTTP error: Client error: `PUT ...` resulted in a `403 Forbidden`"
}
```

**Nếu gặp lỗi 403:**
- Check AWS credentials trong `.env`
- Check S3 bucket permissions
- Check IAM user có quyền `s3:PutObject`

---

## 🔍 **BƯỚC 3: TEST DOWNLOAD**

### **Test Download API:**

```bash
# Sử dụng s3_key từ upload response
curl 'https://lmsnew.hocmai.net/api/speakup/test-download-s3?s3_key=test_uploads/2025/11/14/test-image_1731552000_abc123.jpg'
```

---

### **Response Success:**

```json
{
    "status": true,
    "message": "File found on S3",
    "data": {
        "s3_key": "test_uploads/2025/11/14/test-image_1731552000_abc123.jpg",
        "file_size": 524288,
        "mime_type": "image/jpeg",
        "s3_url": "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/...",
        "cloudfront_url": "https://d3rrb37z9aai1k.cloudfront.net/...",
        "signed_url": "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/...?X-Amz-Signature=...",
        "signed_url_expires_at": "2025-11-14T11:00:00.000000Z"
    }
}
```

**Test URLs:**
- `s3_url`: Direct S3 URL (nếu bucket public)
- `cloudfront_url`: CloudFront URL (nhanh hơn, có CDN)
- `signed_url`: Signed URL (hoạt động dù bucket private, expires 1h)

---

## 📂 **BƯỚC 4: TEST LIST FILES**

### **Test List API:**

```bash
# List files trong folder 'test_uploads'
curl 'https://lmsnew.hocmai.net/api/speakup/test-list-s3?folder=test_uploads&limit=10'
```

---

### **Response:**

```json
{
    "status": true,
    "data": {
        "folder": "test_uploads",
        "total": 3,
        "files": [
            {
                "path": "test_uploads/2025/11/14/file1.jpg",
                "name": "file1.jpg",
                "size": 524288,
                "mime_type": "image/jpeg",
                "url": "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/test_uploads/2025/11/14/file1.jpg",
                "last_modified": 1731552000
            },
            {
                "path": "test_uploads/2025/11/14/file2.mp3",
                "name": "file2.mp3",
                "size": 5242880,
                "mime_type": "audio/mpeg",
                "url": "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/test_uploads/2025/11/14/file2.mp3",
                "last_modified": 1731552100
            }
        ]
    }
}
```

---

## 🎯 **FULL TEST WORKFLOW**

### **Test đầy đủ (5 phút):**

```bash
# 1. Upload file
RESPONSE=$(curl -s -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@test.jpg' \
  -F 'folder=my_test')

echo "Upload Response:"
echo $RESPONSE | jq

# 2. Get s3_key from response
S3_KEY=$(echo $RESPONSE | jq -r '.data.s3_key')
echo "S3 Key: $S3_KEY"

# 3. Download/get info
echo "Download Test:"
curl -s "https://lmsnew.hocmai.net/api/speakup/test-download-s3?s3_key=$S3_KEY" | jq

# 4. List files
echo "List Files:"
curl -s "https://lmsnew.hocmai.net/api/speakup/test-list-s3?folder=my_test" | jq

# 5. Test CloudFront URL trong browser
CLOUDFRONT_URL=$(echo $RESPONSE | jq -r '.data.cloudfront_url')
echo "Open in browser: $CLOUDFRONT_URL"
```

---

## ✅ **VERIFY S3 CONFIG**

### **Test connection:**

```bash
cd /var/www/html/lms_hocmai
php artisan tinker
```

```php
// Test S3 connection
>>> Storage::disk('s3-aws')->put('test.txt', 'Hello AWS S3');
=> true

// Check file exists
>>> Storage::disk('s3-aws')->exists('test.txt');
=> true

// Get URL
>>> Storage::disk('s3-aws')->url('test.txt');
=> "https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/test.txt"

// Delete test file
>>> Storage::disk('s3-aws')->delete('test.txt');
=> true
```

**Nếu có lỗi:**
- Check `.env` đã update chưa
- Run `php artisan config:clear`
- Check AWS credentials có đúng không

---

## 🔧 **TROUBLESHOOTING**

### **Lỗi 1: "Error executing PutObject... 403 Forbidden"**

**Nguyên nhân:** Credentials sai hoặc không có quyền

**Giải pháp:**
1. Check `.env`:
   ```bash
   grep AWS_S3 .env
   ```
2. Verify trên AWS Console:
   - IAM User có quyền `s3:PutObject`, `s3:GetObject`
   - Bucket policy cho phép user này
3. Clear cache:
   ```bash
   php artisan config:clear
   ```

---

### **Lỗi 2: "SignatureDoesNotMatch"**

**Nguyên nhân:** Secret key sai

**Giải pháp:**
- Copy lại secret key từ AWS Console
- Đảm bảo không có khoảng trắng thừa
- Update `.env`
- Clear cache

---

### **Lỗi 3: "The bucket you are attempting to access must be addressed using the specified endpoint"**

**Nguyên nhân:** Region sai hoặc endpoint sai

**Giải pháp:**
```bash
# Trong .env, KHÔNG set AWS_S3_ENDPOINT cho AWS S3 thật
AWS_S3_DEFAULT_REGION=ap-southeast-1
AWS_S3_BUCKET=aws-test-atung
# AWS_S3_ENDPOINT=  # ← BỎ dòng này cho AWS S3!
```

**Lưu ý:** 
- `AWS_ENDPOINT` → Cho MinIO (có endpoint custom)
- `AWS_S3_*` → Cho AWS S3 thật (KHÔNG cần endpoint)

---

## 📋 **CONFIG CHECKLIST**

### **File `.env`:**

```bash
# ✅ MinIO (s3 disk) - Keep as is
AWS_ACCESS_KEY_ID=lmsnew.hocmai.com
AWS_SECRET_ACCESS_KEY=F83K9k5cPMPUbs6wDFgeJvIMWvj6LHhv
AWS_BUCKET=icanwork
AWS_ENDPOINT=https://s3.icankid.io/
AWS_USE_PATH_STYLE_ENDPOINT=true

# ✅ AWS S3 (s3-aws disk) - NEW
AWS_S3_ACCESS_KEY_ID=AKIAVFM5ZFITVSXY455D
AWS_S3_SECRET_ACCESS_KEY=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
AWS_S3_DEFAULT_REGION=ap-southeast-1
AWS_S3_BUCKET=aws-test-atung
# KHÔNG set AWS_S3_ENDPOINT cho AWS S3!

# ✅ CloudFront (optional)
AWS_CLOUDFRONT_URL=https://d3rrb37z9aai1k.cloudfront.net/
```

---

## 🎉 **QUICK TEST (Copy/Paste)**

```bash
# Test upload ngay
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@test.jpg'

# Nếu thành công, bạn sẽ thấy:
# {
#   "status": true,
#   "message": "File uploaded to AWS S3 successfully",
#   "data": {
#     "s3_url": "https://...",
#     "cloudfront_url": "https://d3rrb37z9aai1k.cloudfront.net/..."
#   }
# }
```

**Mở CloudFront URL trong browser để xem file!** 🖼️

---

## 📊 **TEST VỚI NHIỀU FILE TYPES**

```bash
# Test image
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@image.jpg' \
  -F 'folder=images'

# Test audio
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@audio.mp3' \
  -F 'folder=audio'

# Test video
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@video.mp4' \
  -F 'folder=videos'

# Test PDF
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@document.pdf' \
  -F 'folder=documents'
```

---

## 🔗 **URLs EXPLAINED**

### **1. S3 URL:**
```
https://aws-test-atung.s3.ap-southeast-1.amazonaws.com/test_uploads/file.jpg
```
- Direct S3 URL
- Hoạt động nếu bucket/file public
- Không có CDN

### **2. CloudFront URL:**
```
https://d3rrb37z9aai1k.cloudfront.net/test_uploads/file.jpg
```
- Qua CloudFront CDN
- Nhanh hơn (cached ở edge locations)
- **RECOMMENDED để dùng!**

### **3. Signed URL:**
```
https://aws-test-atung.s3.../file.jpg?X-Amz-Signature=...
```
- Có chữ ký điện tử
- Expires sau 1 giờ
- Hoạt động dù bucket private

---

## ✅ **EXPECTED RESULTS**

### **Sau khi upload thành công:**

1. **File trên S3:**
   ```
   Bucket: aws-test-atung
   Path: test_uploads/2025/11/14/file_1731552000_abc123.jpg
   Size: 524KB
   ```

2. **Truy cập qua CloudFront:**
   ```
   https://d3rrb37z9aai1k.cloudfront.net/test_uploads/2025/11/14/file_1731552000_abc123.jpg
   ```
   
3. **Trong database:** (Nếu integrate với upload controller khác)

---

## 🎯 **NEXT STEPS**

### **Sau khi test thành công:**

1. **Integrate vào upload workflow:**
   ```php
   // Sử dụng trong controller khác
   $s3Key = 'uploads/' . $filename;
   Storage::disk('s3-aws')->put($s3Key, $fileContent);
   $url = Storage::disk('s3-aws')->url($s3Key);
   ```

2. **Dùng CloudFront URL:**
   ```php
   $cloudfront = rtrim(env('AWS_CLOUDFRONT_URL'), '/');
   $cloudFrontUrl = $cloudfront . '/' . ltrim($s3Key, '/');
   ```

3. **Generate signed URLs:**
   ```php
   $signedUrl = Storage::disk('s3-aws')->temporaryUrl(
       $s3Key,
       now()->addHours(1)
   );
   ```

---

## 🆘 **COMMON ERRORS**

### **Error: "InvalidAccessKeyId"**
→ Check `AWS_S3_ACCESS_KEY_ID` trong `.env`

### **Error: "SignatureDoesNotMatch"**
→ Check `AWS_S3_SECRET_ACCESS_KEY` trong `.env`

### **Error: "NoSuchBucket"**
→ Check `AWS_S3_BUCKET` có đúng không

### **Error: "Region mismatch"**
→ Check `AWS_S3_DEFAULT_REGION=ap-southeast-1`

### **Error: "Access Denied"**
→ Check IAM permissions:
- `s3:PutObject`
- `s3:GetObject`
- `s3:ListBucket`

---

## 📚 **AWS IAM PERMISSIONS**

### **Minimum permissions cần thiết:**

```json
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "s3:PutObject",
                "s3:GetObject",
                "s3:DeleteObject",
                "s3:ListBucket"
            ],
            "Resource": [
                "arn:aws:s3:::aws-test-atung",
                "arn:aws:s3:::aws-test-atung/*"
            ]
        }
    ]
}
```

---

## 🎉 **SUMMARY**

**APIs đã tạo:**
- ✅ Test Upload
- ✅ Test Download
- ✅ Test List Files

**Config cần thiết:**
- ✅ AWS credentials trong `.env`
- ✅ CloudFront URL (optional)

**Bắt đầu test:**
```bash
# Update .env
# Clear cache
php artisan config:clear

# Test upload
curl -X POST 'https://lmsnew.hocmai.net/api/speakup/test-upload-s3' \
  -F 'file=@test.jpg'
```

**🚀 Test ngay để verify S3 hoạt động!**

