Skip to content
Snippets Groups Projects
DocumentController.php 9.93 KiB
Newer Older
  • Learn to ignore specific revisions
  • Damien's avatar
    Damien committed
    <?php
    
    /**
    * Copyright Maarch since 2008 under licence GPLv3.
    * See LICENCE.txt file at the root folder for more details.
    * This file is part of Maarch software.
    *
    */
    
    /**
    * @brief Resource Controller
    * @author dev@maarch.org
    */
    
    namespace Document\controllers;
    
    
    use SrcCore\models\CoreConfigModel;
    
    Damien's avatar
    Damien committed
    use Attachment\models\AttachmentModel;
    
    use Convert\models\AdrModel;
    
    Damien's avatar
    Damien committed
    use Docserver\controllers\DocserverController;
    
    use Docserver\models\DocserverModel;
    
    Damien's avatar
    Damien committed
    use Document\models\DocumentModel;
    use Slim\Http\Request;
    use Slim\Http\Response;
    
    use SrcCore\models\ValidatorModel;
    use Status\models\StatusModel;
    
    Damien's avatar
    Damien committed
    use User\models\UserModel;
    
    use History\controllers\HistoryController;
    use setasign\Fpdi\TcpdfFpdi;
    
    Florian Azizian's avatar
    Florian Azizian committed
    use Action\models\ActionModel;
    
    Damien's avatar
    Damien committed
    
    class DocumentController
    {
        public function get(Request $request, Response $response)
        {
            $data = $request->getQueryParams();
    
    Alex ORLUC's avatar
    Alex ORLUC committed
            $data['limit'] = (int)$data['limit'];
            $data['offset'] = (int)$data['offset'];
    
    Damien's avatar
    Damien committed
    
    
    Damien's avatar
    Damien committed
            if (empty($data['offset'])) {
    
    Damien's avatar
    Damien committed
                $data['offset'] = 0;
            }
    
    Damien's avatar
    Damien committed
            if (empty($data['limit'])) {
    
    Damien's avatar
    Damien committed
                $data['limit'] = 0;
            }
    
    
    Damien's avatar
    Damien committed
            $user = UserModel::getByEmail(['email' => $GLOBALS['email'], 'select' => ['id']]);
    
    Damien's avatar
    Damien committed
    
    
    Damien's avatar
    Damien committed
            $fullCount = 0;
    
    Alex ORLUC's avatar
    Alex ORLUC committed
            $documents = DocumentModel::getByUserId(['select' => ['id', 'reference', 'subject', 'status', 'count(1) OVER()'], 'userId' => $user['id'], 'limit' => $data['limit'], 'offset' => $data['offset']]);
    
            foreach ($documents as $key => $document) {
                $status = StatusModel::getById(['select' => ['label'], 'id' => $document['status']]);
                $documents[$key]['statusDisplay'] = $status['label'];
    
    Damien's avatar
    Damien committed
                $fullCount = $document['count'];
                unset($documents[$key]['count']);
    
    Damien's avatar
    Damien committed
    
    
    Damien's avatar
    Damien committed
            return $response->withJson(['documents' => $documents, 'fullCount' => $fullCount]);
    
    Damien's avatar
    Damien committed
        }
    
    
        public function getById(Request $request, Response $response, array $args)
        {
    
    Damien's avatar
    Damien committed
            if (!DocumentController::hasRightById(['id' => $args['id'], 'email' => $GLOBALS['email']])) {
    
                return $response->withStatus(403)->withJson(['errors' => 'Document out of perimeter']);
            }
    
            $document = DocumentModel::getById(['select' => ['*'], 'id' => $args['id']]);
            if (empty($document)) {
                return $response->withStatus(400)->withJson(['errors' => 'Document does not exist']);
            }
    
            $status = StatusModel::getById(['select' => ['label'], 'id' => $document['status']]);
            $document['statusDisplay'] = $status['label'];
    
    
            $actions = ActionModel::get(['select' => ['id', 'label', 'color', 'logo', 'event'], 'where' => ['previous_status_id = ?'], 'data' => [$document['status']]]);
    
    Florian Azizian's avatar
    Florian Azizian committed
            $document['actionsAllowed'] = $actions;
    
            $document['processingUserDisplay'] = UserModel::getLabelledUserById(['id' => $document['processing_user']]);
    
    
    Damien's avatar
    Damien committed
            $adr = AdrModel::getDocumentsAdr([
    
    Damien's avatar
    Damien committed
                'select'    => ['path', 'filename', 'fingerprint'],
    
                'where'     => ['main_document_id = ?', 'type = ?'],
                'data'      => [$args['id'], 'DOC']
            ]);
    
            $docserver = DocserverModel::getByType(['type' => 'DOC', 'select' => ['path']]);
            if (empty($docserver['path']) || !file_exists($docserver['path'])) {
                return $response->withStatus(400)->withJson(['errors' => 'Docserver does not exist']);
            }
    
    
    Damien's avatar
    Damien committed
            $pathToDocument = $docserver['path'] . $adr[0]['path'] . $adr[0]['filename'];
    
            if (!file_exists($pathToDocument)) {
                return $response->withStatus(404)->withJson(['errors' => 'Document not found on docserver']);
            }
    
    
    Damien's avatar
    Damien committed
            //TODO Commenté pour tests
    //        $fingerprint = DocserverController::getFingerPrint(['path' => $pathToDocument]);
    //        if ($adr[0]['fingerprint'] != $fingerprint) {
    //            return $response->withStatus(404)->withJson(['errors' => 'Fingerprints do not match']);
    //        }
    
            $document['encodedDocument'] = base64_encode(file_get_contents($pathToDocument));
    
    Damien's avatar
    Damien committed
            $document['attachments'] = AttachmentModel::getByDocumentId(['select' => ['id'], 'documentId' => $args['id']]);
    
    
            return $response->withJson(['document' => $document]);
        }
    
    
    Florian Azizian's avatar
    Florian Azizian committed
        public function makeAction(Request $request, Response $response, array $args)
    
        {
            $data = $request->getParams();
    
    
            ValidatorModel::notEmpty($data, ['action_id']);
    
    Florian Azizian's avatar
    Florian Azizian committed
            ValidatorModel::intVal($data, ['action_id']);
    
            /*if (!empty($data['signatures'])) {
    
                foreach ($data['signatures'] as $signature) {
                    foreach (['fullPath', 'width', 'positionX', 'positionY', 'page'] as $value) {
                        if (empty($signature[$value])) {
                            return $response->withStatus(400)->withJson(['errors' => $value . ' is empty']);
                        }
    
    Damien's avatar
    Damien committed
            if (!DocumentController::hasRightById(['id' => $args['id'], 'email' => $GLOBALS['email']])) {
    
                return $response->withStatus(403)->withJson(['errors' => 'Document out of perimeter']);
            }
    
    
    Florian Azizian's avatar
    Florian Azizian committed
            $action = ActionModel::getById(['select' => ['next_status_id', 'label'], 'id' => $data['action_id']]);
    
    Florian Azizian's avatar
    Florian Azizian committed
            if (empty($action)) {
                return $response->withStatus(403)->withJson(['errors' => 'Action does not exist']);
            }
    
    
            $adr = AdrModel::getDocumentsAdr([
                'select'  => ['path', 'filename'],
                'where'   => ['main_document_id = ?', 'type = ?'],
                'data'    => [$args['id'], 'DOC']
            ]);
            if (empty($adr)) {
                return $response->withStatus(400)->withJson(['errors' => 'Document does not exist in database']);
            }
    
            $docserver = DocserverModel::getByType(['type' => 'DOC', 'select' => ['path']]);
            if (empty($docserver['path']) || !file_exists($docserver['path'])) {
                return $response->withStatus(400)->withJson(['errors' => 'Docserver does not exist']);
            }
    
            $pathToDocument = $docserver['path'] . $adr[0]['path'] . $adr[0]['filename'];
            if (!file_exists($pathToDocument)) {
                return $response->withStatus(404)->withJson(['errors' => 'Document not found on docserver']);
            }
    
            $tmpPath     = CoreConfigModel::getTmpPath();
    
    Damien's avatar
    Damien committed
            $tmpFilename = $tmpPath . $GLOBALS['email'] . '_' . rand() . '_' . $adr[0]['filename'];
    
            copy($pathToDocument, $tmpFilename);
    
    
            $pdf     = new TcpdfFpdi('P');
    
            $nbPages = $pdf->setSourceFile($tmpFilename);
            $pdf->setPrintHeader(false);
    
    
            for ($i = 1; $i <= $nbPages; $i++) {
                $page = $pdf->importPage($i);
                $size = $pdf->getTemplateSize($page);
                $pdf->AddPage($size['orientation'], $size);
                $pdf->useImportedPage($page);
    
                $pdf->SetAutoPageBreak(false, 0);
                $pdf->SetMargins(0, 0, 0);
    
                if (!empty($data['signatures'])) {
                    foreach ($data['signatures'] as $signature) {
                        if ($signature['page'] == $i) {
                            if (preg_match('/^data:image\/(\w+);base64,/', $signature['fullPath'], $extension)) {
                                $data      = substr($signature['fullPath'], strpos($signature['fullPath'], ',') + 1);
                                $extension = strtolower($extension[1]);
            
                                if ($extension != 'png') {
                                    return $response->withStatus(400)->withJson(['errors' => 'Invalid image type']);
                                }
                            } else {
                                $data = $signature['fullPath'];
    
                            $image = base64_decode($data);
            
                            if ($image === false) {
                                return $response->withStatus(400)->withJson(['errors' => 'base64_decode failed']);
                            }
                            
    
    Damien's avatar
    Damien committed
                            $imageTmpPath = $tmpPath . $GLOBALS['email'] . '_' . rand() . '_writing.png';
    
                            file_put_contents($imageTmpPath, $image);
    
    
                            // $pdf->Image($imageTmpPath, $signature['positionX'], $signature['positionY']);
                            
                            $pdf->SetY(0);
                            $html = '<img src="'.$signature['fullPath'].'"/>';
                            $pdf->writeHTML($html, true, false, true, false, '');
    
                        }
                    }
                }
            }
            $fileContent = $pdf->Output('', 'S');
    
            $storeInfos = DocserverController::storeResourceOnDocServer([
                'encodedFile'     => base64_encode($fileContent),
                'format'          => 'pdf',
    
                'docserverType'   => 'HANDWRITTEN'
    
            ]);
    
            AdrModel::createDocumentAdr([
                'documentId'     => $args['id'],
    
    Florian Azizian's avatar
    Florian Azizian committed
                'type'           => 'HANDWRITTEN',
    
                'path'           => $storeInfos['path'],
                'filename'       => $storeInfos['filename'],
                'fingerprint'    => $storeInfos['fingerprint']
            ]);
    
    
    Florian Azizian's avatar
    Florian Azizian committed
            DocumentModel::update([
    
    Florian Azizian's avatar
    Florian Azizian committed
                'set' => ['status' => $action['next_status_id']],
    
    Florian Azizian's avatar
    Florian Azizian committed
                'where' => ['id = ?'],
                'data' => [$args['id']]
            ]);
    
    
            HistoryController::add([
                'tableName' => 'main_documents',
                'recordId'  => $args['id'],
                'eventType' => 'UP',
    
    Florian Azizian's avatar
    Florian Azizian committed
                'info'      => _ACTION_DONE . ' : ' . $action['label'],
    
                'moduleId'  => 'document',
                'eventId'   => 'documentup',
            ]);
    
            return $response->withJson(['success' => 'success']);
        }
    
    
        public static function hasRightById(array $args)
        {
    
    Damien's avatar
    Damien committed
            ValidatorModel::notEmpty($args, ['id', 'email']);
    
            ValidatorModel::intVal($args, ['id']);
    
    Damien's avatar
    Damien committed
            ValidatorModel::stringType($args, ['email']);
    
    Damien's avatar
    Damien committed
            $user = UserModel::getByEmail(['email' => $GLOBALS['email'], 'select' => ['id']]);
    
    
            $document = DocumentModel::get(['select' => [1], 'where' => ['processing_user = ?', 'id = ?'], 'data' => [$user['id'], $args['id']]]);
            if (empty($document)) {
                return false;
            }
    
            return true;
        }
    
    Damien's avatar
    Damien committed
    }