From aaf0ff76453cf33b8540dd32d64d0741d0c10328 Mon Sep 17 00:00:00 2001 From: weichien00 Date: Sat, 3 Jul 2021 00:58:24 +0800 Subject: [PATCH] new: Add classes required to upload identity document during account registration. #5 --- .../DataTransferObjects/DocumentObject.php | 80 +++++++++++ .../DataTransferObjects/FileObject.php | 86 ++++++++++++ .../UploadIdentityDocumentProcessor.php | 46 +++++++ .../Services/ConvertsBase64ToFile.php | 125 ++++++++++++++++++ .../Documents/Services/CreatesDocument.php | 26 ++++ .../Documents/Services/CreatesFiles.php | 32 +++++ .../ValueObjects/Constants/DocumentType.php | 24 ++++ .../ValueObjects/Constants/FileType.php | 24 ++++ app/Models/Document.php | 59 +++++++++ app/Models/File.php | 31 +++++ 10 files changed, 533 insertions(+) create mode 100644 app/Classes/Modules/Documents/DataTransferObjects/DocumentObject.php create mode 100644 app/Classes/Modules/Documents/DataTransferObjects/FileObject.php create mode 100644 app/Classes/Modules/Documents/Processors/UploadIdentityDocumentProcessor.php create mode 100644 app/Classes/Modules/Documents/Services/ConvertsBase64ToFile.php create mode 100644 app/Classes/Modules/Documents/Services/CreatesDocument.php create mode 100644 app/Classes/Modules/Documents/Services/CreatesFiles.php create mode 100644 app/Classes/ValueObjects/Constants/DocumentType.php create mode 100644 app/Classes/ValueObjects/Constants/FileType.php create mode 100644 app/Models/Document.php create mode 100644 app/Models/File.php diff --git a/app/Classes/Modules/Documents/DataTransferObjects/DocumentObject.php b/app/Classes/Modules/Documents/DataTransferObjects/DocumentObject.php new file mode 100644 index 00000000..8f73dc1b --- /dev/null +++ b/app/Classes/Modules/Documents/DataTransferObjects/DocumentObject.php @@ -0,0 +1,80 @@ +document_type = $document_type; + $this->files = $files; + $this->reference = $reference; + $this->status = $status; + $this->path = $path; + } + + + /** + * @return string + */ + public function getDocumentType(): string + { + return $this->document_type; + } + + /** + * @return string + */ + public function getReference(): string + { + return $this->reference; + } + + /** + * @return int + */ + public function getStatus(): int + { + return $this->status; + } + + + /** + * @return array + * @throws \App\Classes\Exceptions\MalformedRequestException + */ + public function getFiles(): array + { + return (new ConvertsBase64ToFile($this->path))->convert($this->files); + } + + + +} \ No newline at end of file diff --git a/app/Classes/Modules/Documents/DataTransferObjects/FileObject.php b/app/Classes/Modules/Documents/DataTransferObjects/FileObject.php new file mode 100644 index 00000000..ed289eac --- /dev/null +++ b/app/Classes/Modules/Documents/DataTransferObjects/FileObject.php @@ -0,0 +1,86 @@ +data = $data; + } + + /** + * @return \Intervention\Image\Image|string + * @throws MalformedRequestException + */ + public function getData() + { + return $this->getExtension() === 'pdf' ? $this->data : (new imageManager())->make($this->data); + } + + /** + * @return string + */ + public function getFileName(): string + { + return (string) Str::uuid(); + } + + /** + * @return string + */ + public function getMimeType(): string + { + return finfo_file(finfo_open(), $this->data, FILEINFO_MIME_TYPE); + } + + /** + * @return string + * @throws MalformedRequestException + */ + public function getExtension(): string + { + if(array_key_exists($this->getMimeType(), FileType::EXTENSION)){ + return FileType::EXTENSION[$this->getMimeType()]; + } + + throw new MalformedRequestException('Failed to save file due to Unknown file extension'); + } + + /** + * @return string + * @throws MalformedRequestException + */ + public function getDecodedData(): string + { + return $this->getExtension() === 'pdf' ? + base64_decode((explode('base64,', $this->getData()))[1]): + $this->getData()->encode('data-url')->encoded; + } + + /** + * @param string $data + */ + public function setData(string $data): void + { + $this->data = $data; + } + + + + + +} \ No newline at end of file diff --git a/app/Classes/Modules/Documents/Processors/UploadIdentityDocumentProcessor.php b/app/Classes/Modules/Documents/Processors/UploadIdentityDocumentProcessor.php new file mode 100644 index 00000000..9fb09c4a --- /dev/null +++ b/app/Classes/Modules/Documents/Processors/UploadIdentityDocumentProcessor.php @@ -0,0 +1,46 @@ +createsDocument = $createsDocument; + $this->createsFile = $createsFile; + } + + /** + * @param DocumentObject $object + * @return Array + * @throws \App\Classes\Exceptions\AccessForbiddenException + * @throws \App\Classes\Exceptions\MalformedRequestException + * @throws \App\Classes\Exceptions\RequestValidationException + */ + public function execute(Request $request, Company $company): Array { + + $object = new DocumentObject($company->type === CompanyType::COMPANY_BUSINESS ? + DocumentType::SSM_REGISTRATION : DocumentType::IDENTITY_CARD, $request->input('files'), + $request->input('identification_no'), ApprovalStatus::PENDING_VERIFICATION, 'identifications'); + + /** @var Document $document */ + $document = $this->createsDocument->execute($company, $object); + return $this->createsFile->execute($document, $object); + } + +} \ No newline at end of file diff --git a/app/Classes/Modules/Documents/Services/ConvertsBase64ToFile.php b/app/Classes/Modules/Documents/Services/ConvertsBase64ToFile.php new file mode 100644 index 00000000..a7a5c8b6 --- /dev/null +++ b/app/Classes/Modules/Documents/Services/ConvertsBase64ToFile.php @@ -0,0 +1,125 @@ +path = $path; + $this->filesInfo = []; + } + + + /** + * @param array $files + * @return array + * @throws MalformedRequestException + */ + public function convert($files = []){ + foreach ($files as $file) { + + $object = new FileObject($file); + $object->getExtension() === 'pdf' ? $this->generatePDF($object) : $this->generateImage($object); + + } + + return $this->filesInfo; + + } + + /** + * @param FileObject $file + * @throws MalformedRequestException + */ + private function generatePDF(FileObject $file){ + + $filePath = $this->generateFile($file); + $this->updateFiles($file, [ 'original' => [ 'file' => $filePath ] ]); + } + + /** + * @param FileObject $file + * @throws MalformedRequestException + */ + private function generateImage(FileObject $file){ + + $fileInfo = []; + + foreach (['original' => null, 'large' => 800, 'medium' => 480, 'small' => 320] as $size => $value) { + $suffix = $size !== 'original' ? '_'.$size : ''; + + if($size !== 'original') { + $thumbnail = $file->getData()->widen($value, function ($constraint) { + + $constraint->upsize(); + + })->heighten($value, function ($constraint) { + + $constraint->upsize(); + + }); + + $file->setData($thumbnail->encode('data-url')->encoded); + } + + + $filePath = $this->generateFile($file, $suffix); + + $fileInfo[] = [ $size => [ 'file' => $filePath, 'width' => $file->getData()->width(), 'height' => $file->getData()->height() ]]; + + + } + + $this->updateFiles($file, $fileInfo); + + } + + /** + * @param FileObject $file + * @param string $suffix + * @return string + * @throws MalformedRequestException + */ + private function generateFile(FileObject $file, string $suffix = '') { + + $filePath = $this->path.'/'.$file->getFileName().$suffix.'.'.$file->getExtension(); + + Storage::disk('documents')->put($filePath, $file->getDecodedData()); + + return $filePath; + + } + + /** + * @param FileObject $file + * @param array $fileInfo + * @throws MalformedRequestException + */ + private function updateFiles(FileObject $file, array $fileInfo){ + $this->filesInfo[] = json_encode([ + 'path' => $this->path, + 'filename' => $file->getFileName().'.'.$file->getExtension(), + 'mime_type' => $file->getMimeType(), + 'extension' => $file->getExtension(), + 'file_info' => $fileInfo + ]); + } + +} \ No newline at end of file diff --git a/app/Classes/Modules/Documents/Services/CreatesDocument.php b/app/Classes/Modules/Documents/Services/CreatesDocument.php new file mode 100644 index 00000000..16e7d094 --- /dev/null +++ b/app/Classes/Modules/Documents/Services/CreatesDocument.php @@ -0,0 +1,26 @@ +document_type = $object->getDocumentType(); + $model->reference = $object->getReference(); + + return $this->handler($documentable->documents(), $model); + } +} \ No newline at end of file diff --git a/app/Classes/Modules/Documents/Services/CreatesFiles.php b/app/Classes/Modules/Documents/Services/CreatesFiles.php new file mode 100644 index 00000000..30c85a13 --- /dev/null +++ b/app/Classes/Modules/Documents/Services/CreatesFiles.php @@ -0,0 +1,32 @@ +getFiles() as $file) { + + $model = new File(['file' => $file]); + $models[] = $this->handler($document->files(), $model); + + } + + return $models; + + } +} \ No newline at end of file diff --git a/app/Classes/ValueObjects/Constants/DocumentType.php b/app/Classes/ValueObjects/Constants/DocumentType.php new file mode 100644 index 00000000..2b053163 --- /dev/null +++ b/app/Classes/ValueObjects/Constants/DocumentType.php @@ -0,0 +1,24 @@ + 'gif', + 'image/png' => 'png', + 'image/jpeg' => 'jpeg', + 'application/pdf' => 'pdf', + ]; + +} \ No newline at end of file diff --git a/app/Models/Document.php b/app/Models/Document.php new file mode 100644 index 00000000..eb3f8c77 --- /dev/null +++ b/app/Models/Document.php @@ -0,0 +1,59 @@ +morphTo(); + } + + /** + * @return hasMany + */ + public function files(): hasMany + { + return $this->hasMany(File::class, 'document_id'); + } + + /** + * @return HasOne + */ + public function approver(): hasOne + { + return $this->hasOne(User::class, 'id', 'approver'); + } + +} diff --git a/app/Models/File.php b/app/Models/File.php new file mode 100644 index 00000000..6707fd9f --- /dev/null +++ b/app/Models/File.php @@ -0,0 +1,31 @@ +