Skip to content

Commit

Permalink
Merge pull request #47 from oat-sa/develop
Browse files Browse the repository at this point in the history
Release v0.14.0
  • Loading branch information
augustas authored Nov 29, 2024
2 parents ae816de + de95fbc commit f6b7394
Show file tree
Hide file tree
Showing 6 changed files with 94 additions and 25 deletions.
2 changes: 1 addition & 1 deletion composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@
],
"require" : {
"php" : ">=7.2",
"league/flysystem-aws-s3-v3": "1.0.25",
"league/flysystem-aws-s3-v3": "^3.0.0",
"aws/aws-sdk-php": "^3.0.0"
},
"suggest": {
Expand Down
20 changes: 14 additions & 6 deletions src/AwsFlyWrapper.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,18 +19,18 @@

namespace oat\awsTools;

use League\Flysystem\AwsS3V3\AwsS3V3Adapter;
use League\Flysystem\FilesystemAdapter;
use League\Flysystem\Local\LocalFilesystemAdapter;
use oat\oatbox\service\ConfigurableService;
use League\Flysystem\AdapterInterface;
use oat\oatbox\filesystem\utils\FlyWrapperTrait;
use League\Flysystem\AwsS3v3\AwsS3Adapter;
use oat\flysystem\Adapter\LocalCacheAdapter;
use League\Flysystem\Adapter\Local;
use oat\oatbox\log\LoggerAwareTrait;
/**
*
* @author Joel Bout
*/
class AwsFlyWrapper extends ConfigurableService implements AdapterInterface
class AwsFlyWrapper extends ConfigurableService implements FilesystemAdapter
{
use FlyWrapperTrait;
use LoggerAwareTrait;
Expand Down Expand Up @@ -62,10 +62,18 @@ public function getClient()
public function getAdapter()
{
if (is_null($this->adapter)) {
$adapter = new AwsS3Adapter($this->getClient(),$this->getOption(self::OPTION_BUCKET),$this->getOption(self::OPTION_PREFIX));
$adapter = new AwsS3V3Adapter(
$this->getClient(),
$this->getOption(self::OPTION_BUCKET),
$this->getOption(self::OPTION_PREFIX),
new BucketOwnerVisibilityConverter(),
null,
[],
false // keeps the streams seekable
);
if ($this->hasOption(self::OPTION_CACHE)) {
if (class_exists(LocalCacheAdapter::class)) {
$cached = new Local($this->getOption(self::OPTION_CACHE));
$cached = new LocalFilesystemAdapter($this->getOption(self::OPTION_CACHE));
$adapter = new LocalCacheAdapter($adapter, $cached, true);

// FlySystem::listContents caching.
Expand Down
41 changes: 41 additions & 0 deletions src/BucketOwnerVisibilityConverter.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
<?php

namespace oat\awsTools;

use League\Flysystem\AwsS3V3\VisibilityConverter;
use League\Flysystem\Visibility;

class BucketOwnerVisibilityConverter implements VisibilityConverter
{
private const PUBLIC_GRANTEE_URI = 'http://acs.amazonaws.com/groups/global/AllUsers';
private const PUBLIC_GRANTS_PERMISSION = 'READ';
private const BUCKET_OWNER_ACL = 'bucket-owner-full-control';

public function __construct(private string $defaultForDirectories = Visibility::PUBLIC)
{
}

public function visibilityToAcl(string $visibility): string
{
return self::BUCKET_OWNER_ACL;
}

public function aclToVisibility(array $grants): string
{
foreach ($grants as $grant) {
$granteeUri = $grant['Grantee']['URI'] ?? null;
$permission = $grant['Permission'] ?? null;

if ($granteeUri === self::PUBLIC_GRANTEE_URI && $permission === self::PUBLIC_GRANTS_PERMISSION) {
return Visibility::PUBLIC;
}
}

return Visibility::PRIVATE;
}

public function defaultForDirectories(): string
{
return $this->defaultForDirectories;
}
}
10 changes: 6 additions & 4 deletions src/QtiItems/QtiItemAssetCloudFrontReplacer.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,11 @@
namespace oat\awsTools\QtiItems;

use Aws\S3\S3Client;
use League\Flysystem\AwsS3v3\AwsS3Adapter;
use League\Flysystem\AwsS3V3\AwsS3V3Adapter;
use League\Flysystem\Config;
use oat\awsTools\AwsClient;
use oat\awsTools\items\ItemCloudFrontReplacement;
use oat\awsTools\BucketOwnerVisibilityConverter;
use oat\oatbox\service\ConfigurableService;
use oat\taoItems\model\render\ItemAssetsReplacement;
use oat\taoQtiItem\model\compile\QtiAssetReplacer\QtiItemAssetReplacer;
Expand Down Expand Up @@ -153,12 +154,13 @@ private function getItemAssetsReplacement(): ItemAssetsReplacement
return $this->getServiceLocator()->get(ItemAssetsReplacement::SERVICE_ID);
}

protected function getAwsS3Adapter(S3Client $s3Client, string $bucket, string $prefix): AwsS3Adapter
protected function getAwsS3Adapter(S3Client $s3Client, string $bucket, string $prefix): AwsS3V3Adapter
{
return new AwsS3Adapter(
return new AwsS3V3Adapter(
$s3Client,
$bucket,
$prefix
$prefix,
new BucketOwnerVisibilityConverter()
);
}
}
32 changes: 23 additions & 9 deletions src/items/ItemCloudFrontReplacement.php
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,8 @@

namespace oat\awsTools\items;

use League\Flysystem\AwsS3v3\AwsS3Adapter;
use League\Flysystem\AwsS3V3\AwsS3V3Adapter;
use League\Flysystem\FilesystemException;
use oat\awsTools\AwsClient;
use oat\oatbox\service\ConfigurableService;
use oat\taoItems\model\render\ItemAssetsReplacement;
Expand Down Expand Up @@ -142,14 +143,10 @@ protected function retrieveKeyFile()
if (!file_exists($this->getOption(self::OPTION_LOCAL_KEYFILE))) {
if ($this->hasOption(self::OPTION_S3_KEYFILE) && $this->hasOption(self::OPTION_S3_BUCKET) && $this->hasOption(self::OPTION_S3_PREFIX)) {
$s3Client = $this->getClient()->getS3Client();
$s3Adapter = new AwsS3Adapter($s3Client, $this->getOption(self::OPTION_S3_BUCKET), $this->getOption(self::OPTION_S3_PREFIX));
$response = $s3Adapter->read($this->getOption(self::OPTION_S3_KEYFILE));
if ($response !== false) {
file_put_contents($this->getOption(self::OPTION_LOCAL_KEYFILE), $response['contents']);
chmod($this->getOption(self::OPTION_LOCAL_KEYFILE), 0600);
} else {
throw new \common_Exception('Unable to retrieve key file from s3 : ' . $this->getOption(self::OPTION_LOCAL_KEYFILE));
}
$s3Adapter = new AwsS3V3Adapter($s3Client, $this->getOption(self::OPTION_S3_BUCKET), $this->getOption(self::OPTION_S3_PREFIX));
$key = $this->readKeyFile($s3Adapter);
file_put_contents($this->getOption(self::OPTION_LOCAL_KEYFILE), $key);
chmod($this->getOption(self::OPTION_LOCAL_KEYFILE), 0600);
} else {
throw new \common_Exception('Unable to retrieve key file from s3. You should have a configuration for : ' . self::OPTION_S3_KEYFILE . ',' . self::OPTION_S3_BUCKET . 'and' . self::OPTION_S3_PREFIX);
}
Expand All @@ -173,4 +170,21 @@ protected function getClient()
}
return $this->getServiceLocator()->get($serviceId);
}

private function readKeyFile(AwsS3V3Adapter $s3Adapter): string
{
try {
$response = $s3Adapter->read($this->getOption(self::OPTION_S3_KEYFILE));
} catch (FilesystemException $e) {
} finally {
if (empty($response)) {
throw new \common_Exception(sprintf(
'Unable to retrieve key file from s3 : %s',
$this->getOption(self::OPTION_LOCAL_KEYFILE)
));
}
}

return $response;
}
}
14 changes: 9 additions & 5 deletions test/unit/QtiItemAssetCloudFrontReplacerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@

use Aws\S3\S3Client;
use GuzzleHttp\Psr7\Stream;
use League\Flysystem\AwsS3v3\AwsS3Adapter;
use League\Flysystem\AwsS3V3\AwsS3V3Adapter;
use oat\awsTools\AwsClient;
use oat\awsTools\items\ItemCloudFrontReplacement;
use oat\awsTools\QtiItems\QtiItemAssetCloudFrontReplacer;
Expand All @@ -37,6 +37,7 @@
use oat\taoItems\model\media\ItemMediaResolver;
use oat\taoItems\model\render\ItemAssetsReplacement;
use oat\taoQtiItem\model\compile\QtiAssetCompiler\QtiItemAssetCompiler;
use oat\taoQtiItem\model\compile\QtiAssetCompiler\XIncludeAdditionalAssetInjector;
use oat\taoQtiItem\model\compile\QtiAssetReplacer\QtiItemAssetReplacer;
use oat\taoQtiItem\model\compile\QtiAssetReplacer\QtiItemNonReplacer;
use oat\taoQtiItem\model\compile\QtiItemCompilerAssetBlacklist;
Expand Down Expand Up @@ -76,7 +77,7 @@ class QtiItemAssetCloudFrontReplacerTest extends TestCase
private $itemAssetsReplacement;

/**
* @var AwsS3Adapter
* @var AwsS3V3Adapter
*/
private $awsS3Adapter;

Expand All @@ -89,8 +90,8 @@ public function setUp(): void
$this->itemAssetsReplacement = $this->createMock(ItemCloudFrontReplacement::class);
$this->itemAssetsReplacement->method('getOption')->willReturn('bucket_test');

$this->awsS3Adapter = $this->createMock(AwsS3Adapter::class);
$this->awsS3Adapter->method('writeStream')->willReturn(true);
$this->awsS3Adapter = $this->createMock(AwsS3V3Adapter::class);
$this->awsS3Adapter->method('writeStream');

$replacer = new TestQtiItemAssetCloudFrontReplacer([
QtiItemAssetCloudFrontReplacer::OPTION_PREFIX => 'prefix',
Expand All @@ -108,6 +109,9 @@ public function setUp(): void
QtiItemCompilerAssetBlacklist::SERVICE_ID => $this->blackListService,
LoggerService::SERVICE_ID => new NullLogger(),
QtiItemAssetReplacer::SERVICE_ID => $replacer,
XIncludeAdditionalAssetInjector::class => $this->createMock(
XIncludeAdditionalAssetInjector::class
)
]));

$this->resolver = $this->createMock(ItemMediaResolver::class);
Expand Down Expand Up @@ -195,7 +199,7 @@ public function setAwsS3Adapter($mock)
$this->awsS3Adapter = $mock;
}

protected function getAwsS3Adapter(S3Client $s3Client, string $bucket, string $prefix): AwsS3Adapter
protected function getAwsS3Adapter(S3Client $s3Client, string $bucket, string $prefix): AwsS3V3Adapter
{
return $this->awsS3Adapter;
}
Expand Down

0 comments on commit f6b7394

Please sign in to comment.