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],