jesse_orange_newable's avatar

Creating classes from existing package

I am using the Microsoft Azure Storage File PHP Client Library found here: https://github.com/Azure/azure-storage-php/tree/master/azure-storage-file in my project to send files to Azure.

In my app directory I created an Azure folder and then a class named Connector.php.

This class is basically just a wrapper so that I can use methods from the library above exactly as I want.

I was wondering if this is the best way, or whether I should be creating a Facade or attempting to extend Laravel's Storage?

Here is the class

<?php
namespace App\AzureFile;

use Exception;
use MicrosoftAzure\Storage\File\FileRestProxy;
use MicrosoftAzure\Storage\Common\Internal\StorageServiceSettings;
use MicrosoftAzure\Storage\File\FileSharedAccessSignatureHelper;
use MicrosoftAzure\Storage\Common\Internal\Resources;
use MicrosoftAzure\Storage\Common\Exceptions\ServiceException;

class Connector
{
    /**
     * The file client we will use to connect.
     */
    private $fileClient;

    /**
     * Create a new connection string.
     */
    public function __construct()
    {
        $endpointProtocol = config('services.azure-file.protocol');
        $accountName = config('services.azure-file.account_name');
        $accountKey = config('services.azure-file.account_key');

        $connectionString = 'DefaultEndpointsProtocol=' . $endpointProtocol . ';';
        $connectionString .= 'AccountName=' . $accountName . ';';
        $connectionString .= 'AccountKey=' . $accountKey . ';';

        $this->connectionString = $connectionString;
        $this->shareName = config('services.azure-file.share');
        $this->fileClient = FileRestProxy::createFileService($this->connectionString);
    }

    /**
     * Upload a file to the Azure File share specified.
     * Uses createFileFromContentAsync() to create a file given a name and contents of a file.
     *
     * @param string                          $path    the path of the file, but this can just be the file name.
     * @param StreamInterface|resource|string $content the content used to create the file.
     */
    public function uploadFile($path, $content)
    {
        try {
            $this->fileClient->createFileFromContentAsync($this->shareName, $path, $content);
        } catch (ServiceException $e) {
            Log::error('Attempt to communicate with Azure File storage failed', [
                'code' => $e->getCode(),
                'error' => $e->getMessage()
            ]);
        }
    }

    /**
     * Lists all directories and files within our specified Azure Share.
     */
    public function listDirectoriesAndFiles()
    {
        try {
            return $this->fileClient->listDirectoriesAndFiles($this->shareName);
        } catch (ServiceException $e) {
            Log::error('Attempt to communicate with Azure File storage failed', [
                'code' => $e->getCode(),
                'error' => $e->getMessage()
            ]);
        }
    }

    /**
     * Generates a download link to a given file using a sas token.
     * Ref:https://github.com/Azure/azure-storage-php/blob/master/samples/FileSamples.php
     */
    public function generateFileDownloadLinkWithSAS(string $fileName)
    {
        try {
            $settings = StorageServiceSettings::createFromConnectionString($this->connectionString);

            $accountName = $settings->getName();
            $accountKey = $settings->getKey();

            $helper = new FileSharedAccessSignatureHelper(
                $accountName,
                $accountKey
            );

            // Generate a file readonly SAS token
            // Refer to following link for full candidate values to construct a service level SAS
            // https://docs.microsoft.com/en-us/rest/api/storageservices/constructing-a-service-sas
            $sas = $helper->generateFileServiceSharedAccessSignatureToken(
                Resources::RESOURCE_TYPE_FILE,
                "$this->shareName/$fileName",
                'r',                        // Read
                '2030-01-01T08:30:00Z'      // A valid ISO 8601 format expiry time
            );

            $connectionStringWithSAS = Resources::FILE_ENDPOINT_NAME .
                '=' .
                'https://' .
                $accountName .
                '.' .
                Resources::FILE_BASE_DNS_NAME .
                ';' .
                Resources::SAS_TOKEN_NAME .
                '=' .
                $sas;

            $fileClientWithSAS = FileRestProxy::createFileService(
                $connectionStringWithSAS
            );

            // Get a downloadable file URL
            $fileUrlWithSAS = sprintf(
                '%s%s?%s',
                (string)$fileClientWithSAS->getPsrPrimaryUri(),
                "$this->shareName/$fileName",
                $sas
            );

            // Download the file from the URL directly
            $downloadFileName = 'outputBySAS.txt';

            file_put_contents($downloadFileName, fopen($fileUrlWithSAS, 'r'));

            // Clean up
            if (file_exists($downloadFileName)) {
                unlink($downloadFileName);
            }

            // Return the temporary readonly download URL link
            return $fileUrlWithSAS;
        } catch (Exception $e) {
            Log::error('Attempt to communicate with Azure File storage failed', [
                'code' => $e->getCode(),
                'error' => $e->getMessage()
            ]);
        }
    }
}
0 likes
0 replies

Please or to participate in this conversation.