PMCORE-1619 Validations in the upload files related to cases notes before to move appDocument.

This commit is contained in:
Roly Rudy Gutierrez Pinto
2020-06-12 20:59:28 -04:00
parent fd7f944166
commit 9d9ce52fa8
9 changed files with 240 additions and 31 deletions

Binary file not shown.

View File

@@ -7,6 +7,7 @@ use G;
use ProcessMaker\Model\Application;
use ProcessMaker\Model\Delegation;
use ProcessMaker\Model\Documents;
use ProcessMaker\Model\User;
use RBAC;
use Tests\TestCase;
@@ -17,6 +18,21 @@ use Tests\TestCase;
*/
class CasesTest extends TestCase
{
/**
* Set up method.
*/
public function setUp()
{
parent::setUp();
Delegation::truncate();
Documents::truncate();
Application::truncate();
User::where('USR_ID', '=', 1)
->where('USR_ID', '=', 2)
->delete();
}
/**
* This checks the delete case
*
@@ -28,11 +44,11 @@ class CasesTest extends TestCase
{
// Set the RBAC
global $RBAC;
$_SESSION['USER_LOGGED'] = '00000000000000000000000000000002';
$RBAC = RBAC::getSingleton(PATH_DATA, session_id());
$_SESSION['USER_LOGGED'] = G::generateUniqueID();
$RBAC = RBAC::getSingleton();
$RBAC->initRBAC();
$application = factory(Application::class)->create();
$application = factory(Application::class)->create(['APP_INIT_USER' => G::generateUniqueID()]);
// Tried to delete case
$case = new Cases();
$case->deleteCase($application->APP_UID, $_SESSION['USER_LOGGED']);
@@ -50,7 +66,7 @@ class CasesTest extends TestCase
// Set the RBAC
global $RBAC;
$_SESSION['USER_LOGGED'] = '00000000000000000000000000000001';
$RBAC = RBAC::getSingleton(PATH_DATA, session_id());
$RBAC = RBAC::getSingleton();
$RBAC->initRBAC();
$application = factory(Application::class)->create(['APP_STATUS' => 'TO_DO']);
@@ -70,38 +86,17 @@ class CasesTest extends TestCase
{
// Set the RBAC
global $RBAC;
$_SESSION['USER_LOGGED'] = '00000000000000000000000000000001';
$RBAC = RBAC::getSingleton(PATH_DATA, session_id());
$_SESSION['USER_LOGGED'] = G::generateUniqueID();
$RBAC = RBAC::getSingleton();
$RBAC->initRBAC();
$application = factory(Application::class)->create(['APP_INIT_USER' => '00000000000000000000000000000002']);
$application = factory(Application::class)->create(['APP_INIT_USER' => G::generateUniqueID()]);
// Tried to delete case
$case = new Cases();
$case->deleteCase($application->APP_UID, $_SESSION['USER_LOGGED']);
}
/**
* Review the upload file related to the case notes, an return an exception when the array is empty
*
* @covers \ProcessMaker\BusinessModel\Cases::uploadFilesInCaseNotes()
*
* @test
* @expectedException Exception
*/
public function it_return_exception_in_upload_files_related_case_note()
{
$application = factory(Application::class)->create();
factory(Delegation::class)->states('foreign_keys')->create([
'APP_NUMBER' => $application->APP_NUMBER,
'APP_UID' => $application->APP_UID
]);
// Upload the file
$case = new Cases();
// Return an exception because the files does not exist
$case->uploadFilesInCaseNotes('00000000000000000000000000000001', $application->APP_UID, $filesReferences = []);
}
/**
* Review the upload file related to the case notes
*
* @covers \ProcessMaker\BusinessModel\Cases::uploadFilesInCaseNotes()

View File

@@ -112,6 +112,43 @@ class ValidationUploadedFilesTest extends TestCase
$this->assertEquals(0, $result->getStatus());
}
/**
* This test verify validation rules for files post in cases notes.
* @test
* @covers ::runRulesForPostFilesOfNote
*/
public function it_should_test_run_rules_for_post_files_of_note()
{
//assert for file has not exist
$file = [
'filename' => 'testDocument.pdf',
'path' => "testDocument.pdf"
];
$validation = new ValidationUploadedFiles();
$result = $validation->runRulesForPostFilesOfNote($file);
$this->assertTrue($result->fails());
//assert for file has not valid extension
$file = [
'filename' => 'projectData.json',
'path' => PATH_TRUNK . "tests/resources/projectData.json"
];
$validation = new ValidationUploadedFiles();
$result = $validation->runRulesForPostFilesOfNote($file);
$this->assertTrue($result->fails());
//assert the file exists and has valid extension
$file = [
'filename' => 'testDocument.pdf',
'path' => PATH_TRUNK . "tests/resources/testDocument.pdf"
];
$validation = new ValidationUploadedFiles();
$result = $validation->runRulesForPostFilesOfNote($file);
$this->assertFalse($result->fails());
$this->assertEmpty($result->getMessage());
$this->assertEquals(0, $result->getStatus());
}
/**
* It deletes the images created
*/
@@ -128,4 +165,4 @@ class ValidationUploadedFilesTest extends TestCase
unlink(PATH_DATA . '1.PnG');
}
}
}
}

View File

@@ -25307,6 +25307,12 @@ msgstr "Error: The application {0} is not canceled."
msgid "The default configuration was not defined"
msgstr "The default configuration was not defined"
# TRANSLATION
# LABEL/ID_THE_FILE_COULDNT_BE_UPLOADED
#: LABEL/ID_THE_FILE_COULDNT_BE_UPLOADED
msgid "The file couldnt be uploaded please review the allowed files or contact your System Administrator."
msgstr "The file couldnt be uploaded please review the allowed files or contact your System Administrator."
# TRANSLATION
# LABEL/ID_THE_FILE_SIZE_IS_BIGGER_THAN_THE_MAXIMUM_ALLOWED
#: LABEL/ID_THE_FILE_SIZE_IS_BIGGER_THAN_THE_MAXIMUM_ALLOWED
@@ -27707,6 +27713,12 @@ msgstr "Yesterday"
msgid "[LABEL/ID_YES_VALUE] Yes"
msgstr "Yes"
# TRANSLATION
# LABEL/ID_YOUR_FILE_HAS_EXCEEDED
#: LABEL/ID_YOUR_FILE_HAS_EXCEEDED
msgid "Your file has exceeded the file maximum size that is {0}."
msgstr "Your file has exceeded the file maximum size that is {0}."
# TRANSLATION
# LABEL/ID_YOUR_IMAGE_HAS_BEEN_SUCCESSFULLY
#: LABEL/ID_YOUR_IMAGE_HAS_BEEN_SUCCESSFULLY
@@ -27761,6 +27773,12 @@ msgstr "You do not select any user to import"
msgid "you have an error"
msgstr "you have an error"
# TRANSLATION
# LABEL/ID_YOU_UPLOADED_AN_UNSUPPORTED_FILE_EXTENSION
#: LABEL/ID_YOU_UPLOADED_AN_UNSUPPORTED_FILE_EXTENSION
msgid "You uploaded an unsupported file extension, please review the permitted files uploaded in the wiki of ProcessMaker for the cases notes."
msgstr "You uploaded an unsupported file extension, please review the permitted files uploaded in the wiki of ProcessMaker for the cases notes."
# TRANSLATION
# LABEL/ID_ZIP_CODE
#: LABEL/ID_ZIP_CODE

View File

@@ -10,6 +10,7 @@
*/
use ProcessMaker\BusinessModel\Cases as BmCases;
use ProcessMaker\Exception\CaseNoteUploadFile;
use ProcessMaker\Model\AppNotes as Notes;
use ProcessMaker\Model\Documents;
use ProcessMaker\Util\DateTime;
@@ -165,6 +166,11 @@ class AppProxy extends HttpProxyController
try {
$sendMail = intval($httpData->swSendMail);
$response = $cases->addNote($appUid, $usrUid, $noteContent, $sendMail);
} catch (CaseNoteUploadFile $e) {
$response = new stdclass();
$response->success = 'success';
$response->message = $e->getMessage();
die(G::json_encode($response));
} catch (Exception $error) {
$response = new stdclass();
$response->success = 'success';

View File

@@ -61109,6 +61109,7 @@ INSERT INTO TRANSLATION (TRN_CATEGORY,TRN_ID,TRN_LANG,TRN_VALUE,TRN_UPDATE_DATE
( 'LABEL','ID_THERE_PROBLEM_SENDING_EMAIL','en','There was a problem sending the email to','2016-04-08') ,
( 'LABEL','ID_THE_APPLICATION_IS_NOT_CANCELED','en','Error: The application {0} is not canceled.','2016-06-15') ,
( 'LABEL','ID_THE_DEFAULT_CONFIGURATION','en','The default configuration was not defined','2016-11-16') ,
( 'LABEL','ID_THE_FILE_COULDNT_BE_UPLOADED','en','The file couldnt be uploaded please review the allowed files or contact your System Administrator.','2020-06-12') ,
( 'LABEL','ID_THE_FILE_SIZE_IS_BIGGER_THAN_THE_MAXIMUM_ALLOWED','en','The file size is bigger than the maximum allowed, the maximum size allowed is {0} Mbytes.','2019-02-26') ,
( 'LABEL','ID_THE_MAXIMUM_VALUE_OF_THIS_FIELD_IS','en','The maximum value of this field is {0}.','2019-02-26') ,
( 'LABEL','ID_THE_MIMETYPE_EXTENSION_ERROR','en','The mime type does not correspond to the permitted extension, please verify your file.','2018-10-02') ,
@@ -61519,6 +61520,7 @@ INSERT INTO TRANSLATION (TRN_CATEGORY,TRN_ID,TRN_LANG,TRN_VALUE,TRN_UPDATE_DATE
( 'LABEL','ID_YES','en','Yes','2014-01-15') ,
( 'LABEL','ID_YESTERDAY','en','Yesterday','2014-01-15') ,
( 'LABEL','ID_YES_VALUE','en','Yes','2014-01-15') ,
( 'LABEL','ID_YOUR_FILE_HAS_EXCEEDED','en','Your file has exceeded the file maximum size that is 10MB.','2020-06-12') ,
( 'LABEL','ID_YOUR_IMAGE_HAS_BEEN_SUCCESSFULLY','en','Your image has been successfully uploaded','2014-01-15') ,
( 'LABEL','ID_YOUR_LICENSE','en','Your license','2014-09-18') ,
( 'LABEL','ID_YOUR_PASSWORD_IS','en','Your password is','2014-01-15') ,
@@ -61528,6 +61530,7 @@ INSERT INTO TRANSLATION (TRN_CATEGORY,TRN_ID,TRN_LANG,TRN_VALUE,TRN_UPDATE_DATE
( 'LABEL','ID_YOU_DO_NOT_HAVE_PERMISSION','en','Error: You do not have permission.','2016-06-15') ,
( 'LABEL','ID_YOU_DO_NOT_SELECT_ANY_USER_TO_IMPORT','en','You do not select any user to import','2015-09-15') ,
( 'LABEL','ID_YOU_HAVE_ERROR','en','you have an error','2014-01-15') ,
( 'LABEL','ID_YOU_UPLOADED_AN_UNSUPPORTED_FILE_EXTENSION','en','You uploaded an unsupported file extension, please review the permitted files uploaded in the wiki of ProcessMaker for the cases notes.','2020-06-12') ,
( 'LABEL','ID_ZIP_CODE','en','Zip Code','2014-01-15') ,
( 'LABEL','IMAGE_DETAIL','en','Image detail','2014-01-15') ,
( 'LABEL','IMPORT_LANGUAGE_ERR_NO_WRITABLE','en','The XML forms directory is not writable','2014-01-15') ,

View File

@@ -41,6 +41,7 @@ use ProcessMaker\BusinessModel\Task as BmTask;
use ProcessMaker\BusinessModel\User as BmUser;
use ProcessMaker\Core\System;
use ProcessMaker\Exception\UploadException;
use ProcessMaker\Exception\CaseNoteUploadFile;
use ProcessMaker\Model\Application as ModelApplication;
use ProcessMaker\Model\AppNotes as Notes;
use ProcessMaker\Model\Delegation;
@@ -49,6 +50,7 @@ use ProcessMaker\Plugins\PluginRegistry;
use ProcessMaker\Services\OAuth2\Server;
use ProcessMaker\Util\DateTime as UtilDateTime;
use ProcessMaker\Validation\ExceptionRestApi;
use ProcessMaker\Validation\ValidationUploadedFiles;
use ProcessMaker\Validation\Validator as FileValidator;
use ProcessPeer;
use ProcessUser;
@@ -3960,6 +3962,21 @@ class Cases
}
}
//rules validation
foreach ($files as $key => $value) {
$entry = [
"filename" => $value['name'],
"path" => $value['tmp_name']
];
$validator = ValidationUploadedFiles::getValidationUploadedFiles()
->runRulesForPostFilesOfNote($entry);
if ($validator->fails()) {
Notes::where('NOTE_ID', '=', $noteId)->delete();
$messageError = G::LoadTranslation('ID_THE_FILE_COULDNT_BE_UPLOADED');
throw new CaseNoteUploadFile($messageError . ' ' . $validator->getMessage());
}
}
// Get the delIndex related to the case
$cases = new ClassesCases();
$delIndex = $cases->getCurrentDelegation($appUid);
@@ -4007,8 +4024,6 @@ class Cases
throw new UploadException($fileName['error']);
}
}
} else {
throw new Exception(G::LoadTranslation('ID_ERROR_UPLOAD_FILE_CONTACT_ADMINISTRATOR'));
}
return $response;

View File

@@ -0,0 +1,21 @@
<?php
namespace ProcessMaker\Exception;
use Exception;
use Throwable;
class CaseNoteUploadFile extends Exception
{
/**
* Constructor method.
* @param string $message
* @param int $code
* @param Throwable $previous
*/
public function __construct(string $message = "", int $code = 0, Throwable $previous = null)
{
parent::__construct($message, $code, $previous);
}
}

View File

@@ -27,6 +27,16 @@ class ValidationUploadedFiles
*/
private $fails = [];
/**
* Return this constant when rule is invalid.
*/
private const INVALID = true;
/**
* Return this constant when rule is valid.
*/
private const VALID = false;
/**
* Check if the loaded files comply with the validation rules, add here if you
* want more validation rules.
@@ -280,6 +290,110 @@ class ValidationUploadedFiles
return $validator->validate();
}
/**
* Check if the loaded files comply with the validation rules, add here if you
* want more validation rules.
* Accept per argument an array or object that contains a "filename" and "path" values.
* The rules are verified in the order in which they have been added.
*
* @param array|object $file
* @return Validator
*/
public function runRulesForPostFilesOfNote($file)
{
$validator = new Validator();
//rule: file exists
$rule = $validator->addRule();
$rule->validate($file, function($file) use($rule) {
$path = isset($file->path) ? $file->path : "";
$filesystem = new Filesystem();
if (!$filesystem->exists($path)) {
$rule->message(G::LoadTranslation('ID_NOT_EXISTS_FILE'));
return self::INVALID;
}
return self::VALID;
})
->status(400)
->log(function($rule) {
/**
* Levels supported by MonologProvider is:
* 100 "DEBUG"
* 200 "INFO"
* 250 "NOTICE"
* 300 "WARNING"
* 400 "ERROR"
* 500 "CRITICAL"
* 550 "ALERT"
* 600 "EMERGENCY"
*/
Bootstrap::registerMonologPhpUploadExecution('phpUpload', $rule->getStatus(), $rule->getMessage(), $rule->getData()->filename);
});
//rule: extensions
$rule = $validator->addRule();
$rule->validate($file, function($file) use($rule) {
$filesystem = new Filesystem();
$extension = strtolower($filesystem->extension($file->filename));
$extensions = [
'pdf', 'gif', 'jpg', 'png', 'doc', 'docx', 'xls', 'xlsx', 'txt', 'mp4', 'mpv', 'mpeg', 'mpg', 'mov'
];
if (!in_array($extension, $extensions)) {
$rule->message(G::LoadTranslation('ID_YOU_UPLOADED_AN_UNSUPPORTED_FILE_EXTENSION'));
return self::INVALID;
}
return self::VALID;
})
->status(400)
->log(function($rule) {
/**
* Levels supported by MonologProvider is:
* 100 "DEBUG"
* 200 "INFO"
* 250 "NOTICE"
* 300 "WARNING"
* 400 "ERROR"
* 500 "CRITICAL"
* 550 "ALERT"
* 600 "EMERGENCY"
*/
Bootstrap::registerMonologPhpUploadExecution('phpUpload', $rule->getStatus(), $rule->getMessage(), $rule->getData()->filename);
});
//rule: file size
$rule = $validator->addRule();
$rule->validate($file, function($file) use($rule) {
$path = isset($file->path) ? $file->path : "";
$filesystem = new Filesystem();
$limitSize = '10M';
$size = $filesystem->size($path);
$phpShorthandByte = new PhpShorthandByte();
$postMaxSizeBytes = $phpShorthandByte->valueToBytes($limitSize);
if ($size > $postMaxSizeBytes) {
$rule->message(G::LoadTranslation('ID_YOUR_FILE_HAS_EXCEEDED', [$limitSize]));
return self::INVALID;
}
return self::VALID;
})
->status(400)
->log(function($rule) {
/**
* Levels supported by MonologProvider is:
* 100 "DEBUG"
* 200 "INFO"
* 250 "NOTICE"
* 300 "WARNING"
* 400 "ERROR"
* 500 "CRITICAL"
* 550 "ALERT"
* 600 "EMERGENCY"
*/
Bootstrap::registerMonologPhpUploadExecution('phpUpload', $rule->getStatus(), $rule->getMessage(), $rule->getData()->filename);
});
return $validator->validate();
}
/**
* Get the first error and call the argument function.
*