Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Simple S3 Laravel Package

async-aws/simple-s3

AsyncAws Simple S3 is a lightweight wrapper around the AsyncAws S3 client that simplifies common S3 tasks and integrations. Install via Composer and use a higher-level API for working with buckets and objects without the boilerplate of raw S3 calls.

View on GitHub
Deep Wiki
Context7
## Getting Started

### Minimal Setup
1. **Installation**: Add the package via Composer:
   ```bash
   composer require async-aws/simple-s3
  1. Basic Instantiation: Initialize the client in a Laravel service or controller. Credentials are auto-loaded from environment variables (AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_DEFAULT_REGION), but you can override them:

    use AsyncAws\SimpleS3\SimpleS3Client;
    
    $client = new SimpleS3Client();
    
  2. First Use Case: Upload a file with minimal boilerplate:

    $client->upload('my-bucket', 'path/to/file.pdf', fopen('/local/path/file.pdf', 'r'));
    
    • Key Parameters:
      • bucket: Target S3 bucket name.
      • key: Destination path (e.g., uploads/2024/file.pdf).
      • source: File handle (resource, SplFileInfo, or Traversable).
  3. Configuration: For non-default regions or endpoints, pass options during instantiation:

    $client = new SimpleS3Client([
        'region' => 'eu-west-1',
        'endpoint' => 'https://s3.eu-west-1.amazonaws.com',
    ]);
    
    • Refer to the integration guide for advanced configs (e.g., custom credentials providers).

Implementation Patterns

Core Workflows

1. File Uploads/Downloads

  • Upload: Stream files directly to S3 without temporary storage:
    $client->upload('bucket', 'key', fopen('local/file', 'r'));
    
  • Download: Retrieve files as streams or save to disk:
    $stream = $client->download('bucket', 'key');
    file_put_contents('local/copy', $stream);
    
  • Check Existence: Verify object presence with has():
    if ($client->has('bucket', 'key')) { ... }
    

2. Presigned URLs for Secure Sharing

Generate time-limited URLs for client-side transfers (e.g., browser uploads):

$url = $client->getPresignedUrl(
    'bucket',
    'key',
    '+10 minutes', // Expiration (e.g., '+5 minutes', '2024-12-31T23:59:59Z')
    $versionId: 'abc123' // Optional for versioned buckets
);
  • Use Cases:
    • Direct uploads from user browsers (e.g., React/Vue apps).
    • Temporary access links for internal tools.

3. Bulk Operations with AsyncAws

Leverage AsyncAws\Core\Operation\ParallelExecutor for concurrent uploads/downloads:

use AsyncAws\Core\Operation\ParallelExecutor;

$executor = new ParallelExecutor();
$executor->run(
    array_map(fn ($file) => $client->upload(...), $files)
);
  • Best For: Media processing pipelines, batch imports/exports.

4. Laravel Service Binding

Register the client as a singleton in AppServiceProvider:

public function register()
{
    $this->app->singleton(SimpleS3Client::class, fn () => new SimpleS3Client());
}
  • Inject Anywhere: Use dependency injection in controllers, jobs, or commands:
    public function __construct(private SimpleS3Client $s3) {}
    

5. Fallback to Raw S3Client

Access the underlying S3Client for advanced operations (e.g., ACLs, CORS):

$s3Client = $client->getS3Client();
$result = $s3Client->putObject([
    'Bucket' => 'bucket',
    'Key' => 'key',
    'ACL' => 'public-read',
]);

Integration Tips

Laravel Filesystem Integration

  • Proxy Storage Disk: Extend Laravel’s Filesystem to delegate to SimpleS3Client:
    use Illuminate\Contracts\Filesystem\Filesystem;
    
    class S3Filesystem implements Filesystem {
        public function __construct(private SimpleS3Client $s3) {}
    
        public function write($path, $contents, $options = []) {
            $this->s3->upload('bucket', $path, fopen('php://temp', 'r+'));
        }
        // Implement other methods...
    }
    
  • Register in config/filesystems.php:
    'disks' => [
        's3' => [
            'driver' => 'custom-s3',
            's3' => env('AWS_BUCKET'),
        ],
    ],
    

Job Queues for Async Processing

  • Offload uploads/downloads to Laravel queues:
    use AsyncAws\SimpleS3\SimpleS3Client;
    use Illuminate\Bus\Queueable;
    use Illuminate\Contracts\Queue\ShouldQueue;
    
    class UploadFileJob implements ShouldQueue {
        use Queueable;
    
        public function __construct(
            private SimpleS3Client $s3,
            private string $bucket,
            private string $key,
            private string $localPath
        ) {}
    
        public function handle() {
            $this->s3->upload($this->bucket, $this->key, fopen($this->localPath, 'r'));
        }
    }
    

Error Handling

  • Catch AsyncAws\Core\Exception\RuntimeException for S3-specific errors:
    try {
        $client->upload('bucket', 'key', $stream);
    } catch (RuntimeException $e) {
        report($e); // Log via Laravel's error handler
        throw new \RuntimeException('Failed to upload file', 0, $e);
    }
    

Gotchas and Tips

Common Pitfalls

  1. PHP Version Mismatch

    • Issue: Version 3.x requires PHP 8.2+. Attempting to use it on older versions throws RuntimeException.
    • Fix: Downgrade to async-aws/simple-s3:2.x for PHP 8.1 or use a runtime check:
      if (version_compare(PHP_VERSION, '8.2.0') < 0) {
          throw new \RuntimeException('PHP 8.2+ required for this package version.');
      }
      
  2. Versioned Buckets and versionId

    • Issue: Omitting versionId in getPresignedUrl() or download() defaults to the latest version, which may not match expectations in versioned buckets.
    • Fix: Always specify versionId when working with versioned objects:
      $url = $client->getPresignedUrl('bucket', 'key', '+1 hour', $versionId: 'abc123');
      
  3. No Automatic Retries

    • Issue: Unlike AWS SDK v3, this package does not implement exponential backoff for throttling or transient errors.
    • Fix: Implement custom retry logic:
      $retries = 3;
      while ($retries--) {
          try {
              $client->upload(...);
              break;
          } catch (RuntimeException $e) {
              if ($retries === 0) throw $e;
              sleep(2 ** $retries); // Exponential backoff
          }
      }
      
  4. Missing ACL/Metadata Methods

    • Issue: The package does not expose S3 object ACLs, metadata, or tagging operations.
    • Fix: Use the raw S3Client:
      $s3Client = $client->getS3Client();
      $s3Client->putObject([
          'Bucket' => 'bucket',
          'Key' => 'key',
          'Metadata' => ['author' => 'John Doe'],
      ]);
      
  5. Stream Handling Quirks

    • Issue: Uploading from non-seekable streams (e.g., php://stdin) may fail if the package assumes seekability.
    • Fix: Ensure streams are seekable or use temporary files:
      $temp = tmpfile();
      stream_copy_to_stream($nonSeekableStream, $temp);
      rewind($temp);
      $client->upload('bucket', 'key', $temp);
      

Performance Tips

  1. Multipart Upload Threshold

    • The package automatically uses multipart uploads for files larger than PartSize (default: 8MB). Adjust via:
      $client = new SimpleS3Client(['multipart_upload_threshold' => 16 * 1024 * 1024]); // 16MB
      
  2. Parallel Uploads

    • For bulk uploads, use ParallelExecutor to maximize throughput:
      $executor = new ParallelExecutor();
      $executor->run(
          array_map(fn ($file) => $
      
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
boundwize/jsonrecast
nexmo/api-specification
capell-app/block-library
axium/identity
cetria/laravel-dummy-models
cetria/reflection-helper
agropredict/sso-auth-bundle
evolvestudio/spam-protection
datacore/hub-sdk
develia/commons
cuci/prototurk-sdk
cuci/prototurk-sdk-symfony
develia/geo-bundle
dreamzy/livewire-charts
touchestate-sdk/php-sdk
22h/doctrine-garbage-collection-bundle
agtp/agtp-php
agtp/mod-php
splash/sonata-admin
splash/metadata