Last active
January 15, 2026 12:54
-
-
Save alecs/2f45b8812b6859b2a7d93959aadcd1b6 to your computer and use it in GitHub Desktop.
symfony v2 s3
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| // s3_operations.php | |
| // Bootstrap the Symfony environment | |
| require_once __DIR__ . '/app/bootstrap.php.cache'; | |
| require_once __DIR__ . '/app/AppKernel.php'; | |
| use Symfony\Component\Console\Input\ArgvInput; | |
| use Symfony\Component\Debug\Debug; | |
| use Aws\S3\S3Client; | |
| // Get the environment and debug mode from console arguments or use defaults | |
| $input = new ArgvInput(); | |
| $env = $input->getParameterOption(['--env', '-e'], getenv('SYMFONY_ENV') ?: 'dev'); | |
| $debug = getenv('SYMFONY_DEBUG') !== '0' && !$input->hasParameterOption(['--no-debug', '']) && $env !== 'prod'; | |
| if ($debug) { | |
| Debug::enable(); | |
| } | |
| // Create the kernel and boot it | |
| $kernel = new AppKernel($env, $debug); | |
| $kernel->loadClassCache(); | |
| $kernel->boot(); | |
| // Get the service container | |
| $container = $kernel->getContainer(); | |
| // Get AWS credentials from Symfony parameters | |
| $awsKey = $container->getParameter('aws_key'); | |
| $awsSecretKey = $container->getParameter('aws_secret_key'); | |
| $awsRegion = $container->getParameter('aws_region') ?: 'us-east-1'; | |
| // Ensure we have credentials | |
| if (empty($awsKey) || empty($awsSecretKey)) { | |
| echo "ERROR: AWS credentials are not properly configured.\n"; | |
| exit(1); | |
| } | |
| // Create S3 client | |
| $s3Client = new S3Client([ | |
| 'version' => 'latest', | |
| 'region' => $awsRegion, | |
| 'credentials' => [ | |
| 'key' => $awsKey, | |
| 'secret' => $awsSecretKey, | |
| ], | |
| ]); | |
| // Parse command line arguments | |
| $argc = $_SERVER['argc']; | |
| $argv = $_SERVER['argv']; | |
| if ($argc < 2) { | |
| showUsage(); | |
| exit(1); | |
| } | |
| $operation = $argv[1]; | |
| // Handle different operations | |
| switch ($operation) { | |
| case 'cp': | |
| if ($argc < 4) { | |
| echo "ERROR: 'cp' requires source and destination parameters.\n"; | |
| showUsage(); | |
| exit(1); | |
| } | |
| $source = $argv[2]; | |
| $destination = $argv[3]; | |
| // Determine if uploading or downloading | |
| if (strpos($source, 's3://') === 0) { | |
| // Download from S3 | |
| $parts = parse_url($source); | |
| $bucket = $parts['host']; | |
| $key = ltrim($parts['path'], '/'); | |
| try { | |
| echo "Downloading s3://$bucket/$key to $destination\n"; | |
| $s3Client->getObject([ | |
| 'Bucket' => $bucket, | |
| 'Key' => $key, | |
| 'SaveAs' => $destination | |
| ]); | |
| echo "Download completed successfully.\n"; | |
| } catch (Exception $e) { | |
| echo "ERROR: " . $e->getMessage() . "\n"; | |
| exit(1); | |
| } | |
| } elseif (strpos($destination, 's3://') === 0) { | |
| // Upload to S3 | |
| $parts = parse_url($destination); | |
| $bucket = $parts['host']; | |
| $key = ltrim($parts['path'], '/'); | |
| try { | |
| echo "Uploading $source to s3://$bucket/$key\n"; | |
| $s3Client->putObject([ | |
| 'Bucket' => $bucket, | |
| 'Key' => $key, | |
| 'SourceFile' => $source | |
| ]); | |
| echo "Upload completed successfully.\n"; | |
| } catch (Exception $e) { | |
| echo "ERROR: " . $e->getMessage() . "\n"; | |
| exit(1); | |
| } | |
| } else { | |
| echo "ERROR: Either source or destination must be an S3 URL (s3://bucket/path).\n"; | |
| exit(1); | |
| } | |
| break; | |
| case 'ls': | |
| if ($argc < 3) { | |
| echo "ERROR: 'ls' requires an S3 path.\n"; | |
| showUsage(); | |
| exit(1); | |
| } | |
| $s3Path = $argv[2]; | |
| if (strpos($s3Path, 's3://') !== 0) { | |
| echo "ERROR: Path must be an S3 URL (s3://bucket/path).\n"; | |
| exit(1); | |
| } | |
| $parts = parse_url($s3Path); | |
| $bucket = $parts['host']; | |
| $prefix = ''; | |
| if (isset($parts['path']) && !empty($parts['path'])) { | |
| $prefix = ltrim($parts['path'], '/'); | |
| } | |
| try { | |
| // Add trailing slash to prefix if it's not empty and doesn't have one | |
| if (!empty($prefix) && substr($prefix, -1) !== '/') { | |
| $prefix .= '/'; | |
| } | |
| $params = [ | |
| 'Bucket' => $bucket, | |
| ]; | |
| // Only add prefix if it's not empty to avoid listing everything in the bucket | |
| if (!empty($prefix)) { | |
| $params['Prefix'] = $prefix; | |
| } | |
| // For directory-like behavior, use delimiter | |
| $params['Delimiter'] = '/'; | |
| $result = $s3Client->listObjectsV2($params); | |
| // Display common prefixes (directories) | |
| if (isset($result['CommonPrefixes']) && !empty($result['CommonPrefixes'])) { | |
| echo "Directories:\n"; | |
| foreach ($result['CommonPrefixes'] as $commonPrefix) { | |
| echo " " . $commonPrefix['Prefix'] . "\n"; | |
| } | |
| } | |
| // Display objects (files) | |
| if (isset($result['Contents']) && !empty($result['Contents'])) { | |
| echo "Files:\n"; | |
| foreach ($result['Contents'] as $object) { | |
| // Skip the directory placeholder object (if prefix ends with /) | |
| if ($object['Key'] === $prefix) { | |
| continue; | |
| } | |
| $size = formatBytes($object['Size']); | |
| $lastModified = $object['LastModified']->format('Y-m-d H:i:s'); | |
| $displayName = str_replace($prefix, '', $object['Key']); | |
| // Skip empty display names (can happen with directories) | |
| if (empty($displayName)) { | |
| continue; | |
| } | |
| echo " {$displayName} ({$size}) - {$lastModified}\n"; | |
| } | |
| } | |
| if ((!isset($result['CommonPrefixes']) || empty($result['CommonPrefixes'])) && | |
| (!isset($result['Contents']) || empty($result['Contents']))) { | |
| echo "No objects found.\n"; | |
| } | |
| } catch (Exception $e) { | |
| echo "ERROR: " . $e->getMessage() . "\n"; | |
| exit(1); | |
| } | |
| break; | |
| default: | |
| echo "Operation '$operation' not supported. Currently only 'cp' and 'ls' are supported.\n"; | |
| showUsage(); | |
| exit(1); | |
| } | |
| // Shutdown the kernel | |
| $kernel->shutdown(); | |
| /** | |
| * Display usage information | |
| */ | |
| function showUsage() { | |
| echo "Usage:\n"; | |
| echo " For upload: php s3_operations.php cp /local/path s3://bucket/path\n"; | |
| echo " For download: php s3_operations.php cp s3://bucket/path /local/path\n"; | |
| echo " For listing: php s3_operations.php ls s3://bucket/path\n"; | |
| } | |
| /** | |
| * Format bytes to human-readable format | |
| * | |
| * @param int $bytes Size in bytes | |
| * @param int $precision Precision for rounding | |
| * @return string Formatted size | |
| */ | |
| function formatBytes($bytes, $precision = 2) { | |
| $units = ['B', 'KB', 'MB', 'GB', 'TB', 'PB']; | |
| $bytes = max($bytes, 0); | |
| $pow = floor(($bytes ? log($bytes) : 0) / log(1024)); | |
| $pow = min($pow, count($units) - 1); | |
| $bytes /= pow(1024, $pow); | |
| return round($bytes, $precision) . ' ' . $units[$pow]; | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment