From 8d484f62eafed10af6beedc3504222b386e72a2b Mon Sep 17 00:00:00 2001 From: Mike Koch Date: Mon, 20 Mar 2017 22:16:35 -0400 Subject: [PATCH] Mostly done with attachment uploading --- api/ApplicationContext.php | 10 +++++ .../Attachments/AttachmentHandler.php | 25 ++++++++++-- .../Attachments/CreateAttachmentModel.php | 3 -- .../StaffAttachmentsController.php | 10 ----- .../StaffTicketAttachmentsController.php | 39 +++++++++++++++++++ api/Controllers/Tickets/TicketController.php | 2 +- .../Attachments/AttachmentHandlerTest.php | 34 +++++++++++++++- 7 files changed, 103 insertions(+), 20 deletions(-) delete mode 100644 api/Controllers/Attachments/StaffAttachmentsController.php create mode 100644 api/Controllers/Attachments/StaffTicketAttachmentsController.php diff --git a/api/ApplicationContext.php b/api/ApplicationContext.php index 5e873c38..5ec0939f 100644 --- a/api/ApplicationContext.php +++ b/api/ApplicationContext.php @@ -1,6 +1,7 @@ get[EmailSenderHelper::class], $this->get[UserGateway::class], $this->get[ModsForHeskSettingsGateway::class]); + + // Attachments + $this->get[FileWriter::class] = new FileWriter(); + $this->get[AttachmentGateway::class] = new AttachmentGateway(); + $this->get[AttachmentHandler::class] = new AttachmentHandler($this->get[TicketGateway::class], + $this->get[AttachmentGateway::class], + $this->get[FileWriter::class]); } } \ No newline at end of file diff --git a/api/BusinessLogic/Attachments/AttachmentHandler.php b/api/BusinessLogic/Attachments/AttachmentHandler.php index 4ef3d72b..d56ce05e 100644 --- a/api/BusinessLogic/Attachments/AttachmentHandler.php +++ b/api/BusinessLogic/Attachments/AttachmentHandler.php @@ -32,16 +32,17 @@ class AttachmentHandler { * @return TicketAttachment the newly created attachment */ function createAttachmentForTicket($createAttachmentModel, $heskSettings) { - $this->validate($createAttachmentModel); + $this->validate($createAttachmentModel, $heskSettings); $decodedAttachment = base64_decode($createAttachmentModel->attachmentContents); $ticket = $this->ticketGateway->getTicketById($createAttachmentModel->ticketId, $heskSettings); $cleanedFileName = $this->cleanFileName($createAttachmentModel->displayName); + $fileParts = pathinfo($cleanedFileName); $ticketAttachment = new TicketAttachment(); $ticketAttachment->savedName = $this->generateSavedName($ticket->trackingId, - $cleanedFileName, $createAttachmentModel->fileExtension); + $cleanedFileName, $fileParts['extension']); $ticketAttachment->displayName = $cleanedFileName; $ticketAttachment->ticketTrackingId = $ticket->trackingId; $ticketAttachment->type = $createAttachmentModel->type; @@ -58,9 +59,10 @@ class AttachmentHandler { /** * @param $createAttachmentModel CreateAttachmentForTicketModel + * @param $heskSettings array * @throws ValidationException */ - private function validate($createAttachmentModel) { + private function validate($createAttachmentModel, $heskSettings) { $errorKeys = array(); if ($createAttachmentModel->attachmentContents === null || trim($createAttachmentModel->attachmentContents) === '') { @@ -85,7 +87,21 @@ class AttachmentHandler { $errorKeys[] = 'INVALID_ATTACHMENT_TYPE'; } - //-- TODO Extension, size + $fileParts = pathinfo($createAttachmentModel->displayName); + if (!isset($fileParts['extension']) || !in_array(".{$fileParts['extension']}", $heskSettings['attachments']['allowed_types'])) { + $errorKeys[] = 'EXTENSION_NOT_PERMITTED'; + } + + $fileContents = base64_decode($createAttachmentModel->attachmentContents); + if (function_exists('mb_strlen')) { + $fileSize = mb_strlen($fileContents, '8bit'); + } else { + $fileSize = strlen($fileContents); + } + + if ($fileSize > $heskSettings['attachments']['max_size']) { + $errorKeys[] = 'FILE_SIZE_TOO_LARGE'; + } if (count($errorKeys) > 0) { $validationModel = new ValidationModel(); @@ -96,6 +112,7 @@ class AttachmentHandler { } private function generateSavedName($trackingId, $displayName, $fileExtension) { + $fileExtension = ".{$fileExtension}"; $useChars = 'AEUYBDGHJLMNPQRSTVWXZ123456789'; $tmp = uniqid(); for ($j = 1; $j < 10; $j++) { diff --git a/api/BusinessLogic/Attachments/CreateAttachmentModel.php b/api/BusinessLogic/Attachments/CreateAttachmentModel.php index cf137828..9a5f5428 100644 --- a/api/BusinessLogic/Attachments/CreateAttachmentModel.php +++ b/api/BusinessLogic/Attachments/CreateAttachmentModel.php @@ -10,9 +10,6 @@ class CreateAttachmentModel { /* @var $displayName string */ public $displayName; - /* @var $fileExtension string */ - public $fileExtension; - /* @var $id int */ public $fileSize; diff --git a/api/Controllers/Attachments/StaffAttachmentsController.php b/api/Controllers/Attachments/StaffAttachmentsController.php deleted file mode 100644 index 6bfbbd81..00000000 --- a/api/Controllers/Attachments/StaffAttachmentsController.php +++ /dev/null @@ -1,10 +0,0 @@ -get[AttachmentHandler::class]; + + $createAttachmentForTicketModel = $this->createModel(JsonRetriever::getJsonData()); + + $createdAttachment = $attachmentHandler->createAttachmentForTicket($createAttachmentForTicketModel, $hesk_settings); + + return output($createdAttachment, 201); + } + + private function createModel($json) { + $model = new CreateAttachmentForTicketModel(); + $model->attachmentContents = Helpers::safeArrayGet($json, 'data'); + $model->displayName = Helpers::safeArrayGet($json, 'displayName'); + $model->ticketId = Helpers::safeArrayGet($json, 'ticketId'); + $model->type = Helpers::safeArrayGet($json, 'type'); + + return $model; + } +} \ No newline at end of file diff --git a/api/Controllers/Tickets/TicketController.php b/api/Controllers/Tickets/TicketController.php index 017e6819..a26b18e2 100644 --- a/api/Controllers/Tickets/TicketController.php +++ b/api/Controllers/Tickets/TicketController.php @@ -33,7 +33,7 @@ class TicketController { //else if assigned to owner, email new owner //else email all staff - return output($ticket); + return output($ticket, 201); } /** diff --git a/api/Tests/BusinessLogic/Attachments/AttachmentHandlerTest.php b/api/Tests/BusinessLogic/Attachments/AttachmentHandlerTest.php index e58a77f9..0a6feddc 100644 --- a/api/Tests/BusinessLogic/Attachments/AttachmentHandlerTest.php +++ b/api/Tests/BusinessLogic/Attachments/AttachmentHandlerTest.php @@ -36,13 +36,17 @@ class AttachmentHandlerTest extends TestCase { $this->attachmentGateway = $this->createMock(AttachmentGateway::class); $this->fileWriter = $this->createMock(FileWriter::class); $this->heskSettings = array( - 'attach_dir' => 'attachments' + 'attach_dir' => 'attachments', + 'attachments' => array( + 'allowed_types' => array('.txt'), + 'max_size' => 999 + ) ); $this->attachmentHandler = new AttachmentHandler($this->ticketGateway, $this->attachmentGateway, $this->fileWriter); $this->createAttachmentForTicketModel = new CreateAttachmentForTicketModel(); $this->createAttachmentForTicketModel->attachmentContents = base64_encode('string'); - $this->createAttachmentForTicketModel->displayName = 'DisplayName'; + $this->createAttachmentForTicketModel->displayName = 'DisplayName.txt'; $this->createAttachmentForTicketModel->ticketId = 1; $this->createAttachmentForTicketModel->type = AttachmentType::MESSAGE; } @@ -143,6 +147,32 @@ class AttachmentHandlerTest extends TestCase { $this->attachmentHandler->createAttachmentForTicket($this->createAttachmentForTicketModel, $this->heskSettings); } + function testThatValidateThrowsAnExceptionWhenTheFileExtensionIsNotPermitted() { + //-- Arrange + $this->heskSettings['attachments']['allowed_types'] = array('.gif'); + $this->createAttachmentForTicketModel->ticketId = 0; + + //-- Assert + $this->expectException(ValidationException::class); + $this->expectExceptionMessageRegExp('/EXTENSION_NOT_PERMITTED/'); + + //-- Act + $this->attachmentHandler->createAttachmentForTicket($this->createAttachmentForTicketModel, $this->heskSettings); + } + + function testThatValidateThrowsAnExceptionWhenTheFileSizeIsLargerThanMaxPermitted() { + //-- Arrange + $this->createAttachmentForTicketModel->attachmentContents = base64_encode("msg"); + $this->heskSettings['attachments']['max_size'] = 1; + + //-- Assert + $this->expectException(ValidationException::class); + $this->expectExceptionMessageRegExp('/FILE_SIZE_TOO_LARGE/'); + + //-- Act + $this->attachmentHandler->createAttachmentForTicket($this->createAttachmentForTicketModel, $this->heskSettings); + } + function testItSavesATicketWithTheProperProperties() { //-- Arrange $this->createAttachmentForTicketModel->ticketId = 1;