From 1921372276aaff9adf43c2d86a0bd8181ece87b6 Mon Sep 17 00:00:00 2001 From: Turtuvshin Date: Tue, 12 Mar 2024 11:08:02 +0800 Subject: [PATCH 1/4] Refactor parent method name in CategoryFilter --- src/Http/Filter/CategoryFilter.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Http/Filter/CategoryFilter.php b/src/Http/Filter/CategoryFilter.php index 0a67996..3ad8eaf 100644 --- a/src/Http/Filter/CategoryFilter.php +++ b/src/Http/Filter/CategoryFilter.php @@ -18,7 +18,7 @@ public function parentsOnly() } } - public function parent(?string $id) + public function parentCategory(?string $id) { if (Str::isUuid($id)) { $this->builder->where('parent_uuid', $id); From 7a11d308011468cc9cbfecca2720032e38fce8e1 Mon Sep 17 00:00:00 2001 From: "Ronald A. Richardson" Date: Tue, 12 Mar 2024 14:56:12 +0800 Subject: [PATCH 2/4] bump version; hotfix `assignCompanyFromId()` --- composer.json | 2 +- src/Models/User.php | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/composer.json b/composer.json index 1b9bc07..eff05db 100644 --- a/composer.json +++ b/composer.json @@ -1,6 +1,6 @@ { "name": "fleetbase/core-api", - "version": "1.4.11", + "version": "1.4.12", "description": "Core Framework and Resources for Fleetbase API", "keywords": [ "fleetbase", diff --git a/src/Models/User.php b/src/Models/User.php index fe639c1..e4cf76e 100644 --- a/src/Models/User.php +++ b/src/Models/User.php @@ -303,7 +303,7 @@ public function isCompanyOwner(Company $company): bool */ public function assignCompanyFromId(?string $id): User { - if (!Str::isUuid($id) || !Utils::isPublicId($id)) { + if (!Str::isUuid($id) && !Utils::isPublicId($id)) { return $this; } From c089a3bb636997fac1987768fb68ea696de768df Mon Sep 17 00:00:00 2001 From: "Ronald A. Richardson" Date: Tue, 12 Mar 2024 17:39:41 +0800 Subject: [PATCH 3/4] added gcs configuration to filesystem settings, added gcs driver to be installed by default --- composer.json | 1 + .../Internal/v1/SettingController.php | 95 ++++++++++++++++--- src/Providers/CoreServiceProvider.php | 1 + 3 files changed, 84 insertions(+), 13 deletions(-) diff --git a/composer.json b/composer.json index eff05db..7af5d23 100644 --- a/composer.json +++ b/composer.json @@ -44,6 +44,7 @@ "pragmarx/countries": "^0.8.2", "sentry/sentry-laravel": "*", "spatie/laravel-activitylog": "^4.7", + "spatie/laravel-google-cloud-storage": "^2.2", "spatie/laravel-permission": "^6.3", "spatie/laravel-responsecache": "^7.4", "spatie/laravel-sluggable": "^3.5", diff --git a/src/Http/Controllers/Internal/v1/SettingController.php b/src/Http/Controllers/Internal/v1/SettingController.php index 3ac5374..a0fe626 100644 --- a/src/Http/Controllers/Internal/v1/SettingController.php +++ b/src/Http/Controllers/Internal/v1/SettingController.php @@ -46,12 +46,29 @@ public function getFilesystemConfig(AdminRequest $request) $s3Url = config('filesystems.disks.s3.url'); $s3Endpoint = config('filesystems.disks.s3.endpoint'); + // Get GCS bucket + $gcsBucket = config('filesystems.disks.gcs.bucket'); + + // Get GCS configurations + $isGoogleCloudStorageEnvConfigued = (!empty(env('GOOGLE_CLOUD_STORAGE_BUCKET')) && !empty(env('GOOGLE_CLOUD_PROJECT_ID'))) || !empty(env('GOOGLE_APPLICATION_CREDENTIALS')) || !empty(env('GOOGLE_CLOUD_KEY_FILE')); + + // Get the GCS configuration file if any + $gcsCredentialsFileId = config('filesystems.disks.gcs.key_file_id'); + $gcsCredentialsFile = null; + if (Str::isUuid($gcsCredentialsFileId)) { + $gcsCredentialsFile = File::where('uuid', $gcsCredentialsFileId)->first(); + } + return response()->json([ - 'driver' => $driver, - 'disks' => $disks, - 's3Bucket' => $s3Bucket, - 's3Url' => $s3Url, - 's3Endpoint' => $s3Endpoint, + 'driver' => $driver, + 'disks' => $disks, + 's3Bucket' => $s3Bucket, + 's3Url' => $s3Url, + 's3Endpoint' => $s3Endpoint, + 'gcsBucket' => $gcsBucket, + 'isGoogleCloudStorageEnvConfigued' => $isGoogleCloudStorageEnvConfigued, + 'gcsCredentialsFileId' => $gcsCredentialsFileId, + 'gcsCredentialsFile' => $gcsCredentialsFile, ]); } @@ -64,13 +81,59 @@ public function saveFilesystemConfig(AdminRequest $request) { $driver = $request->input('driver', 'local'); $s3 = $request->input('s3', config('filesystems.disks.s3')); + $gcs = static::_getGcsConfigWithIcomingRequest($request); Setting::configure('system.filesystem.driver', $driver); + Setting::configure('system.filesystem.gcs', $gcs); Setting::configure('system.filesystem.s3', array_merge(config('filesystems.disks.s3', []), $s3)); return response()->json(['status' => 'OK']); } + private static function _getGcsConfigWithIcomingRequest(Request $request): array + { + $gcsBucket = $request->input('gcsBucket'); + $gcsCredentialsFileId = $request->input('gcsCredentialsFileId'); + $gcsConfig = config('filesystems.disks.gcs'); + $gcsConfig['bucket'] = $gcsBucket; + $gcsConfig['key_file_path'] = env('GOOGLE_APPLICATION_CREDENTIALS', env('GOOGLE_CLOUD_KEY_FILE')); + if ($gcsCredentialsFileId) { + $gcsCredentialsContent = static::_setupGcsConfigUsingFileId($gcsCredentialsFileId); + if (is_array($gcsCredentialsContent)) { + $gcsConfig['key_file'] = $gcsCredentialsContent; + $gcsConfig['key_file_id'] = $gcsCredentialsFileId; + if (isset($gcsCredentialsContent['project_id'])) { + $gcsConfig['project_id'] = $gcsCredentialsContent['project_id']; + } + } + } else { + unset($gcsConfig['key_file_id']); + $gcsConfig['key_file'] = []; + } + + return $gcsConfig; + } + + private static function _setupGcsConfigUsingFileId(string $fileId): array + { + if (!Str::isUuid($fileId)) { + return []; + } + + // Get the "GOOGLE_APPLICATION_CREDENTIALS" file + $gcsCredentialsFile = File::where('uuid', $fileId)->first(); + if ($gcsCredentialsFile) { + $gcsCredentialsFileContents = Storage::disk($gcsCredentialsFile->disk)->get($gcsCredentialsFile->path); + if (is_string($gcsCredentialsFileContents)) { + $gcsCredentialsFileContents = json_decode($gcsCredentialsFileContents, true); + + return $gcsCredentialsFileContents; + } + } + + return []; + } + /** * Creates a file and uploads it to the users default disks. * @@ -80,24 +143,30 @@ public function saveFilesystemConfig(AdminRequest $request) */ public function testFilesystemConfig(AdminRequest $request) { - $disk = $request->input('disk', config('filesystems.default')); - $message = 'Filesystem configuration is successful, test file uploaded.'; - $status = 'success'; + $disk = $request->input('disk', config('filesystems.default')); + $message = 'Filesystem configuration is successful, test file uploaded.'; + $status = 'success'; + $uploaded = false; // set config values from input - config(['filesystem.default' => $disk]); - + config(['filesystems.default' => $disk]); try { - Storage::disk($disk)->put('testfile.txt', 'Hello World'); + $uploaded = Storage::disk($disk)->put('testfile.txt', 'Hello World'); } catch (\Aws\S3\Exception\S3Exception $e) { $message = $e->getMessage(); $status = 'error'; - } catch (\Exception $e) { + } catch (\Throwable $e) { $message = $e->getMessage(); $status = 'error'; } - return response()->json(['status' => $status, 'message' => $message]); + // sometimes there is no error but file is not uploaded + if (!$uploaded) { + $status = 'error'; + $message = 'Configuration is working, but test file upload failed for uknown reasons.'; + } + + return response()->json(['status' => $status, 'message' => $message, 'uploaded' => $uploaded]); } /** diff --git a/src/Providers/CoreServiceProvider.php b/src/Providers/CoreServiceProvider.php index 3934a51..843df56 100644 --- a/src/Providers/CoreServiceProvider.php +++ b/src/Providers/CoreServiceProvider.php @@ -172,6 +172,7 @@ public function mergeConfigFromSettings() $settings = [ ['settingsKey' => 'filesystem.driver', 'configKey' => 'filesystems.default'], ['settingsKey' => 'filesystem.s3', 'configKey' => 'filesystems.disks.s3'], + ['settingsKey' => 'filesystem.gcs', 'configKey' => 'filesystems.disks.gcs'], ['settingsKey' => 'mail.mailer', 'configKey' => 'mail.default'], ['settingsKey' => 'mail.from', 'configKey' => 'mail.from'], ['settingsKey' => 'mail.smtp', 'configKey' => 'mail.mailers.smtp'], From 0213b7d0c0a476d43550a2805661759130026fa0 Mon Sep 17 00:00:00 2001 From: "Ronald A. Richardson" Date: Tue, 12 Mar 2024 17:42:54 +0800 Subject: [PATCH 4/4] added docblock to filesystem setting methods --- .../Internal/v1/SettingController.php | 31 ++++++++++++++++--- 1 file changed, 26 insertions(+), 5 deletions(-) diff --git a/src/Http/Controllers/Internal/v1/SettingController.php b/src/Http/Controllers/Internal/v1/SettingController.php index a0fe626..13292f2 100644 --- a/src/Http/Controllers/Internal/v1/SettingController.php +++ b/src/Http/Controllers/Internal/v1/SettingController.php @@ -32,9 +32,12 @@ public function adminOverview(AdminRequest $request) } /** - * Loads and sends the filesystem configuration. + * Retrieves the current filesystem configuration including details about configured storage drivers. + * It specifically fetches configurations for AWS S3 and Google Cloud Storage (GCS). * - * @return \Illuminate\Http\JsonResponse + * @param AdminRequest $request the incoming request + * + * @return \Illuminate\Http\JsonResponse JSON response containing the filesystem configuration details */ public function getFilesystemConfig(AdminRequest $request) { @@ -73,9 +76,12 @@ public function getFilesystemConfig(AdminRequest $request) } /** - * Saves filesystem configuration. + * Saves the updated filesystem configuration based on the incoming request. + * It handles the settings for various filesystem drivers like local, AWS S3, and GCS. * - * @return \Illuminate\Http\JsonResponse + * @param AdminRequest $request the incoming request containing filesystem configuration data + * + * @return \Illuminate\Http\JsonResponse JSON response indicating the success status of the operation */ public function saveFilesystemConfig(AdminRequest $request) { @@ -90,13 +96,20 @@ public function saveFilesystemConfig(AdminRequest $request) return response()->json(['status' => 'OK']); } + /** + * Extracts the Google Cloud Storage (GCS) configuration from the incoming request. + * Updates the GCS configuration based on the provided bucket information and credentials file ID. + * + * @param Request $request the incoming request with GCS configuration details + * + * @return array the updated GCS configuration array + */ private static function _getGcsConfigWithIcomingRequest(Request $request): array { $gcsBucket = $request->input('gcsBucket'); $gcsCredentialsFileId = $request->input('gcsCredentialsFileId'); $gcsConfig = config('filesystems.disks.gcs'); $gcsConfig['bucket'] = $gcsBucket; - $gcsConfig['key_file_path'] = env('GOOGLE_APPLICATION_CREDENTIALS', env('GOOGLE_CLOUD_KEY_FILE')); if ($gcsCredentialsFileId) { $gcsCredentialsContent = static::_setupGcsConfigUsingFileId($gcsCredentialsFileId); if (is_array($gcsCredentialsContent)) { @@ -114,6 +127,14 @@ private static function _getGcsConfigWithIcomingRequest(Request $request): array return $gcsConfig; } + /** + * Sets up the Google Cloud Storage (GCS) configuration using a given file ID. + * Retrieves the credentials file for GCS and decodes its contents to use in the GCS configuration. + * + * @param string $fileId the UUID of the file containing GCS credentials + * + * @return array an array containing the parsed content of the GCS credentials file + */ private static function _setupGcsConfigUsingFileId(string $fileId): array { if (!Str::isUuid($fileId)) {