diff --git a/migration/20.03/2003.sql b/migration/20.03/2003.sql index b0b80f58006dea446a9f5750f08e0ae18c99d019..a3f4332b2fc1d8946236deda4386b19a03348948 100644 --- a/migration/20.03/2003.sql +++ b/migration/20.03/2003.sql @@ -469,12 +469,17 @@ ALTER TABLE res_attachments ADD COLUMN recipient_type character varying(256); ALTER TABLE res_attachments DROP COLUMN IF EXISTS recipient_id; ALTER TABLE res_attachments ADD COLUMN recipient_id integer; -ALTER TABLE adr_letterbox DROP COLUMN IF EXISTS relation; -ALTER TABLE adr_letterbox ADD COLUMN relation integer; -UPDATE adr_letterbox SET relation = 1; -ALTER TABLE adr_letterbox ALTER COLUMN relation SET NOT NULL; +ALTER TABLE adr_letterbox DROP COLUMN IF EXISTS version; +ALTER TABLE adr_letterbox ADD COLUMN version integer; +UPDATE adr_letterbox SET version = 1; +ALTER TABLE adr_letterbox ALTER COLUMN version SET NOT NULL; ALTER TABLE adr_letterbox DROP CONSTRAINT adr_letterbox_unique_key; -ALTER TABLE adr_letterbox ADD CONSTRAINT adr_letterbox_unique_key UNIQUE (res_id, type, relation); +ALTER TABLE adr_letterbox ADD CONSTRAINT adr_letterbox_unique_key UNIQUE (res_id, type, version); + +ALTER TABLE res_letterbox DROP COLUMN IF EXISTS version; +ALTER TABLE res_letterbox ADD COLUMN version integer; +UPDATE res_letterbox SET version = 1; +ALTER TABLE res_letterbox ALTER COLUMN version SET NOT NULL; ALTER TABLE res_letterbox DROP COLUMN IF EXISTS integrations; ALTER TABLE res_letterbox ADD COLUMN integrations jsonb DEFAULT '{}' NOT NULL; diff --git a/sql/structure.sql b/sql/structure.sql index d95f2d321a8470d378bf7f01b31dd1af5c15139e..d95fb6e75381b28ed9973d665b56f6643ab3d673 100755 --- a/sql/structure.sql +++ b/sql/structure.sql @@ -966,7 +966,8 @@ CREATE TABLE res_letterbox alarm2_date timestamp without time zone, flag_alarm1 char(1) default 'N'::character varying, flag_alarm2 char(1) default 'N'::character varying, - model_id integer NOT NULL, + model_id INTEGER NOT NULL, + version INTEGER NOT NULL, integrations jsonb DEFAULT '{}' NOT NULL, custom_fields jsonb, linked_resources jsonb NOT NULL DEFAULT '[]', @@ -979,13 +980,13 @@ CREATE TABLE adr_letterbox id serial NOT NULL, res_id bigint NOT NULL, type character varying(32) NOT NULL, - relation INTEGER NOT NULL, + version INTEGER NOT NULL, docserver_id character varying(32) NOT NULL, path character varying(255) NOT NULL, filename character varying(255) NOT NULL, fingerprint character varying(255) DEFAULT NULL, CONSTRAINT adr_letterbox_pkey PRIMARY KEY (id), - CONSTRAINT adr_letterbox_unique_key UNIQUE (res_id, type, relation) + CONSTRAINT adr_letterbox_unique_key UNIQUE (res_id, type, version) ) WITH (OIDS=FALSE); diff --git a/src/app/attachment/controllers/AttachmentController.php b/src/app/attachment/controllers/AttachmentController.php index 5c0b571625768e038cc74e2e7a1af7027f5f52fd..40df0df48fcff4eec2678092ab6d5a2a4c06e383 100755 --- a/src/app/attachment/controllers/AttachmentController.php +++ b/src/app/attachment/controllers/AttachmentController.php @@ -388,7 +388,7 @@ class AttachmentController ]); if (empty($tnlAdr)) { - ConvertThumbnailController::convert(['collId' => 'attachments_coll', 'resId' => $args['id']]); + ConvertThumbnailController::convert(['type' => 'attachment', 'resId' => $args['id']]); $tnlAdr = AdrModel::getTypedAttachAdrByResId([ 'select' => ['docserver_id', 'path', 'filename'], diff --git a/src/app/convert/controllers/ConvertPdfController.php b/src/app/convert/controllers/ConvertPdfController.php index 2f2b73442b90b64791ed21fc0ca3bb51d4e4871b..0fb34de283894010ed596487c1a2cfcb64676d07 100755 --- a/src/app/convert/controllers/ConvertPdfController.php +++ b/src/app/convert/controllers/ConvertPdfController.php @@ -56,7 +56,7 @@ class ConvertPdfController { ValidatorModel::notEmpty($aArgs, ['collId', 'resId']); ValidatorModel::stringType($aArgs, ['collId']); - ValidatorModel::intVal($aArgs, ['resId', 'relation']); + ValidatorModel::intVal($aArgs, ['resId', 'version']); if ($aArgs['collId'] == 'letterbox_coll') { $resource = ResModel::getById(['resId' => $aArgs['resId'], 'select' => ['docserver_id', 'path', 'filename', 'format']]); @@ -123,7 +123,7 @@ class ConvertPdfController 'docserverId' => $storeResult['docserver_id'], 'path' => $storeResult['destination_dir'], 'filename' => $storeResult['file_destination_name'], - 'relation' => $aArgs['relation'] ?? 1, + 'version' => $aArgs['version'] ?? 1, 'fingerprint' => $storeResult['fingerPrint'] ]); } else { @@ -173,22 +173,36 @@ class ConvertPdfController return $aReturn; } - public static function getConvertedPdfById(array $aArgs) + public static function getConvertedPdfById(array $args) { - ValidatorModel::notEmpty($aArgs, ['resId', 'collId']); - ValidatorModel::intVal($aArgs, ['resId']); - - $convertedDocument = AdrModel::getConvertedDocumentById([ - 'select' => ['docserver_id','path', 'filename', 'fingerprint'], - 'resId' => $aArgs['resId'], - 'collId' => $aArgs['collId'], - 'type' => 'PDF' - ]); - + ValidatorModel::notEmpty($args, ['resId', 'collId']); + ValidatorModel::intVal($args, ['resId']); + + if ($args['collId'] == 'letterbox_coll') { + $resource = ResModel::getById(['resId' => $args['resId'], 'select' => ['version']]); + + $convertedDocument = AdrModel::getDocuments([ + 'select' => ['docserver_id', 'path', 'filename', 'fingerprint'], + 'where' => ['res_id = ?', 'type in (?)', 'version = ?'], + 'data' => [$args['resId'], ['PDF', 'SIGN'], $resource['version']], + 'orderBy' => ["type='SIGN' DESC"], + 'limit' => 1 + ]); + $convertedDocument = $convertedDocument[0] ?? null; + } else { + $convertedDocument = AdrModel::getConvertedDocumentById([ + 'select' => ['docserver_id','path', 'filename', 'fingerprint'], + 'resId' => $args['resId'], + 'collId' => 'attachment', + 'type' => 'PDF' + ]); + } + if (empty($convertedDocument)) { $convertedDocument = ConvertPdfController::convert([ - 'resId' => $aArgs['resId'], - 'collId' => $aArgs['collId'] + 'resId' => $args['resId'], + 'collId' => $args['collId'], + 'version' => $resource['version'] ?? 1 ]); } diff --git a/src/app/convert/controllers/ConvertThumbnailController.php b/src/app/convert/controllers/ConvertThumbnailController.php index e304a3b0ca50e5f0624a20e2ee0017b95e0ecdab..4353b5494c39d1ab69f644e950a1697967b1825a 100755 --- a/src/app/convert/controllers/ConvertThumbnailController.php +++ b/src/app/convert/controllers/ConvertThumbnailController.php @@ -27,59 +27,49 @@ class ConvertThumbnailController { public static function convert(array $aArgs) { - ValidatorModel::notEmpty($aArgs, ['collId', 'resId']); - ValidatorModel::stringType($aArgs, ['collId']); - ValidatorModel::intVal($aArgs, ['resId', 'outgoingId']); - ValidatorModel::boolType($aArgs, ['isOutgoingVersion']); - - if ($aArgs['collId'] == 'letterbox_coll') { - if (empty($aArgs['outgoingId'])) { - $resource = ResModel::getById(['resId' => $aArgs['resId'], 'select' => ['docserver_id', 'path', 'filename']]); - $convertedDocument = AdrModel::getConvertedDocumentById([ - 'select' => ['docserver_id','path', 'filename'], - 'resId' => $aArgs['resId'], - 'collId' => $aArgs['collId'], - 'type' => 'PDF' - ]); - } else { - $resource = AttachmentModel::getById(['id' => $aArgs['outgoingId'], 'select' => ['docserver_id', 'path', 'filename']]); - $convertedDocument = AdrModel::getConvertedDocumentById([ - 'select' => ['docserver_id','path', 'filename'], - 'resId' => $aArgs['outgoingId'], - 'collId' => 'attachments_coll', - 'type' => 'PDF' - ]); + ValidatorModel::notEmpty($aArgs, ['resId', 'type']); + ValidatorModel::stringType($aArgs, ['type']); + ValidatorModel::intVal($aArgs, ['resId']); + + if ($aArgs['type'] == 'resource') { + $resource = ResModel::getById(['resId' => $aArgs['resId'], 'select' => ['filename', 'version']]); + if (empty($resource)) { + return ['errors' => '[ConvertThumbnail] Resource does not exist']; } + if (empty($resource['filename'])) { + return true; + } + + $convertedDocument = AdrModel::getDocuments([ + 'select' => ['docserver_id', 'path', 'filename'], + 'where' => ['res_id = ?', 'type in (?)', 'version = ?'], + 'data' => [$aArgs['resId'], ['PDF', 'SIGN'], $resource['version']], + 'orderBy' => ["type='SIGN' DESC"], + 'limit' => 1 + ]); + $convertedDocument = $convertedDocument[0] ?? null; } else { - $resource = AttachmentModel::getById(['id' => $aArgs['resId'], 'select' => ['docserver_id', 'path', 'filename']]); + $resource = AttachmentModel::getById(['id' => $aArgs['resId'], 'select' => [1]]); + if (empty($resource)) { + return ['errors' => '[ConvertThumbnail] Resource does not exist']; + } + $convertedDocument = AdrModel::getConvertedDocumentById([ 'select' => ['docserver_id','path', 'filename'], 'resId' => $aArgs['resId'], - 'collId' => $aArgs['collId'], + 'collId' => 'attachment', 'type' => 'PDF' ]); } - if (empty($resource)) { - return ['errors' => '[ConvertThumbnail] Resource does not exist']; - } - if (empty($convertedDocument)) { - $docserver = DocserverModel::getByDocserverId(['docserverId' => $resource['docserver_id'], 'select' => ['path_template']]); - if (empty($docserver['path_template']) || !file_exists($docserver['path_template'])) { - return ['errors' => '[ConvertThumbnail] Docserver does not exist']; - } + return true; + } - $pathToDocument = $docserver['path_template'] . str_replace('#', DIRECTORY_SEPARATOR, $resource['path']) . $resource['filename']; - if (!file_exists($pathToDocument)) { - return ['errors' => '[ConvertThumbnail] Document does not exist on docserver']; - } - } else { - $docserver = DocserverModel::getByDocserverId(['docserverId' => $convertedDocument['docserver_id'], 'select' => ['path_template']]); - $pathToDocument = $docserver['path_template'] . str_replace('#', DIRECTORY_SEPARATOR, $convertedDocument['path']) . $convertedDocument['filename']; - if (!file_exists($pathToDocument)) { - return ['errors' => '[ConvertThumbnail] Document does not exist on docserver']; - } + $docserver = DocserverModel::getByDocserverId(['docserverId' => $convertedDocument['docserver_id'], 'select' => ['path_template']]); + $pathToDocument = $docserver['path_template'] . str_replace('#', DIRECTORY_SEPARATOR, $convertedDocument['path']) . $convertedDocument['filename']; + if (!file_exists($pathToDocument)) { + return ['errors' => '[ConvertThumbnail] Document does not exist on docserver']; } $ext = pathinfo($pathToDocument, PATHINFO_EXTENSION); @@ -111,7 +101,7 @@ class ConvertThumbnailController $resource = file_get_contents("{$tmpPath}{$fileNameOnTmp}.png"); $storeResult = DocserverController::storeResourceOnDocServer([ - 'collId' => $aArgs['collId'], + 'collId' => $aArgs['type'] == 'resource' ? 'letterbox_coll' : 'attachments_coll', 'docserverTypeId' => 'TNL', 'encodedResource' => base64_encode($resource), 'format' => 'png' @@ -121,14 +111,14 @@ class ConvertThumbnailController return ['errors' => "[ConvertThumbnail] {$storeResult['errors']}"]; } - if ($aArgs['collId'] == 'letterbox_coll') { + if ($aArgs['type'] == 'resource') { AdrModel::createDocumentAdr([ 'resId' => $aArgs['resId'], 'type' => 'TNL', 'docserverId' => $storeResult['docserver_id'], 'path' => $storeResult['destination_dir'], 'filename' => $storeResult['file_destination_name'], - 'relation' => 1 + 'version' => $resource['version'] ]); } else { AdrModel::createAttachAdr([ diff --git a/src/app/convert/controllers/FullTextController.php b/src/app/convert/controllers/FullTextController.php index 0433824b7dd8069df7354f83873093192022bfdf..9c5616d9ec147a44bc705f4eb1506d3cf4d3d9c7 100644 --- a/src/app/convert/controllers/FullTextController.php +++ b/src/app/convert/controllers/FullTextController.php @@ -30,12 +30,24 @@ class FullTextController ValidatorModel::intVal($args, ['resId']); ValidatorModel::stringType($args, ['collId']); - $document = AdrModel::getConvertedDocumentById([ - 'select' => ['docserver_id', 'path', 'filename', 'fingerprint'], - 'resId' => $args['resId'], - 'collId' => $args['collId'], - 'type' => 'PDF' - ]); + if ($args['collId'] == 'letterbox_coll') { + $document = AdrModel::getDocuments([ + 'select' => ['docserver_id', 'path', 'filename', 'fingerprint'], + 'where' => ['res_id = ?', 'type = ?'], + 'data' => [$args['resId'], 'PDF'], + 'orderBy' => ['version DESC'], + 'limit' => 1 + ]); + $document = $document[0] ?? null; + } else { + $document = AdrModel::getConvertedDocumentById([ + 'select' => ['docserver_id','path', 'filename', 'fingerprint'], + 'resId' => $args['resId'], + 'collId' => 'attachment', + 'type' => 'PDF' + ]); + } + if (empty($document)) { return ['errors' => 'Converted document does not exist']; } diff --git a/src/app/resource/controllers/ResController.php b/src/app/resource/controllers/ResController.php index 28886df5bd1d7d6c0f22c2e001f03490abe4e4ae..bfce862341aada8af858b3ed7a603a6f1d7c253e 100755 --- a/src/app/resource/controllers/ResController.php +++ b/src/app/resource/controllers/ResController.php @@ -90,7 +90,7 @@ class ResController ConvertPdfController::convert([ 'resId' => $resId, 'collId' => 'letterbox_coll', - 'relation' => 1 + 'version' => 1 ]); $customId = CoreConfigModel::getCustomId(); @@ -262,10 +262,7 @@ class ResController return $response->withStatus(400)->withJson(['errors' => $control['errors']]); } - $resource = ResModel::getById(['resId' => $args['resId'], 'select' => ['alt_identifier', 'filename', 'docserver_id', 'path', 'fingerprint']]); - $oldRelation = AdrModel::getDocuments(['select' => ['MAX(relation)'], 'where' => ['res_id = ?'], 'data' => [$args['resId']]]); - $relation = empty($oldRelation[0]['max']) ? 1 : ($oldRelation[0]['max'] + 1); - + $resource = ResModel::getById(['resId' => $args['resId'], 'select' => ['alt_identifier', 'filename', 'docserver_id', 'path', 'fingerprint', 'version']]); if (!empty($resource['filename']) && !empty($body['encodedFile'])) { AdrModel::createDocumentAdr([ 'resId' => $args['resId'], @@ -273,7 +270,7 @@ class ResController 'docserverId' => $resource['docserver_id'], 'path' => $resource['path'], 'filename' => $resource['filename'], - 'relation' => $relation - 1, + 'version' => $resource['version'], 'fingerprint' => $resource['fingerprint'] ]); } @@ -290,7 +287,7 @@ class ResController ConvertPdfController::convert([ 'resId' => $args['resId'], 'collId' => 'letterbox_coll', - 'relation' => $relation + 'version' => $resource['version'] + 1 ]); $customId = CoreConfigModel::getCustomId(); @@ -585,20 +582,19 @@ class ResController $pathToThumbnail = 'apps/maarch_entreprise/img/noThumbnail.png'; - $document = ResModel::getById(['select' => ['filename'], 'resId' => $args['resId']]); + $document = ResModel::getById(['select' => ['filename', 'version'], 'resId' => $args['resId']]); if (empty($document)) { return $response->withStatus(400)->withJson(['errors' => 'Document does not exist']); } if (!empty($document['filename']) && ResController::hasRightByResId(['resId' => [$args['resId']], 'userId' => $GLOBALS['id']])) { - $relation = AdrModel::getDocuments(['select' => ['MAX(relation)'], 'where' => ['res_id = ?'], 'data' => [$args['resId']]]); - $relation = $relation[0]['max']; - - $tnlAdr = AdrModel::getDocuments(['select' => ['docserver_id', 'path', 'filename'], 'where' => ['res_id = ?', 'type = ?', 'relation = ?'], 'data' => [$args['resId'], 'TNL', $relation]]); - + $tnlAdr = AdrModel::getDocuments(['select' => ['docserver_id', 'path', 'filename'], 'where' => ['res_id = ?', 'type = ?', 'version = ?'], 'data' => [$args['resId'], 'TNL', $document['version']]]); if (empty($tnlAdr[0])) { - ConvertThumbnailController::convert(['collId' => 'letterbox_coll', 'resId' => $args['resId']]); - $tnlAdr = AdrModel::getDocuments(['select' => ['docserver_id', 'path', 'filename'], 'where' => ['res_id = ?', 'type = ?', 'relation = ?'], 'data' => [$args['resId'], 'TNL', $relation]]); + $control = ConvertThumbnailController::convert(['type' => 'resource', 'resId' => $args['resId']]); + if (!empty($control['errors'])) { + return $response->withStatus(400)->withJson(['errors' => $control['errors']]); + } + $tnlAdr = AdrModel::getDocuments(['select' => ['docserver_id', 'path', 'filename'], 'where' => ['res_id = ?', 'type = ?', 'version = ?'], 'data' => [$args['resId'], 'TNL', $document['version']]]); } if (!empty($tnlAdr[0])) { diff --git a/src/app/resource/controllers/StoreController.php b/src/app/resource/controllers/StoreController.php index 669fbc7546866a9038ecc5720f8a91de3ef02074..fe34e32989adc5fadcb67356505d17fe29a2489a 100755 --- a/src/app/resource/controllers/StoreController.php +++ b/src/app/resource/controllers/StoreController.php @@ -200,6 +200,7 @@ class StoreController 'departure_date' => $args['departureDate'] ?? null, 'process_limit_date' => $args['processLimitDate'] ?? null, 'priority' => $args['priority'] ?? null, + 'version' => 1, 'barcode' => $args['barcode'] ?? null, 'origin' => $args['origin'] ?? null, 'custom_fields' => !empty($args['customFields']) ? json_encode($args['customFields']) : null, @@ -253,7 +254,10 @@ class StoreController if (!empty($args['processLimitDate']) && !empty($args['priority'])) { $preparedData['priority'] = IndexingController::calculatePriorityWithProcessLimitDate(['processLimitDate' => $args['processLimitDate']]); } - + if (!empty($args['encodedFile'])) { + $resource = ResModel::getById(['resId' => $args['id'], 'select' => ['version']]); + $preparedData['version'] = $resource['version'] + 1; + } if (!empty($args['externalId']) && is_array($args['externalId'])) { $resource = ResModel::getById(['resId' => $args['id'], 'select' => ['external_id']]); $externalId = array_merge(json_decode($resource['external_id'], true), $args['externalId']); diff --git a/src/app/search/controllers/SearchController.php b/src/app/search/controllers/SearchController.php index 9a073793c85ad89f35f9479e5a66671cbd79878b..b35e1275b3177da647074e480bb0823d0e35a549 100644 --- a/src/app/search/controllers/SearchController.php +++ b/src/app/search/controllers/SearchController.php @@ -148,7 +148,7 @@ class SearchController 'select' => ['res_id as "resId"'], 'where' => $searchWhere, 'data' => $searchData, - 'orderBy' => ['creation_date DESC'] + 'orderBy' => ['creation_date DESC'] ]); if (empty($allResources[$offset])) { return $response->withJson(['resources' => [], 'count' => 0]); @@ -168,7 +168,7 @@ class SearchController $resources = ResModel::get([ 'select' => [ 'res_id as "resId"', 'category_id as "category"', 'alt_identifier as "chrono"', 'subject', 'barcode', 'filename', 'creation_date as "creationDate"', - 'type_id as "type"', 'priority', 'status', 'dest_user as "destUser"', 'count(1) OVER()' + 'type_id as "type"', 'priority', 'status', 'dest_user as "destUser"' ], 'where' => ['res_id in (?)'], 'data' => [$resIds],