PDF global templates export

This commit is contained in:
Roland Gruber 2020-05-30 12:35:22 +02:00
parent 2e5419b3ac
commit 7bd799bee3
5 changed files with 184 additions and 32 deletions

View File

@ -3082,6 +3082,15 @@ class htmlStatusMessage extends htmlElement {
return array(); return array();
} }
/**
* Returns the message type.
*
* @return String type
*/
public function getType() {
return $this->type;
}
} }
/** /**

View File

@ -34,6 +34,11 @@ use \LAM\ImageUtils\ImageManipulationFactory;
/** LAM configuration */ /** LAM configuration */
include_once(__DIR__ . "/config.inc"); include_once(__DIR__ . "/config.inc");
/**
* Use as server profile name to manage global templates.
*/
const GLOBAL_PROFILE = '__GLOBAL__';
/** LDAP object */ /** LDAP object */
include_once(__DIR__ . "/ldap.inc"); include_once(__DIR__ . "/ldap.inc");
@ -164,12 +169,15 @@ function copyStructureToTemplates($sourceType, $sourceName) {
* @param String $file full path of temporary file * @param String $file full path of temporary file
* @param String $name file name * @param String $name file name
* @param string $serverProfileName server profile name * @param string $serverProfileName server profile name
* @return StatusMessage status message to display * @return htmlStatusMessage status message to display
*/ */
function uploadPDFLogo($file, $name, $serverProfileName) { function uploadPDFLogo($file, $name, $serverProfileName) {
if (!preg_match('/[a-zA-Z0-9_-]+\\.(png)|(jpg)/i', $name)) { if (!preg_match('/[a-zA-Z0-9_-]+\\.(png)|(jpg)/i', $name)) {
return new htmlStatusMessage('ERROR', _('Unable to upload logo file.'), _('The file name must end with ".png" or ".jpg".')); return new htmlStatusMessage('ERROR', _('Unable to upload logo file.'), _('The file name must end with ".png" or ".jpg".'));
} }
if ($serverProfileName === GLOBAL_PROFILE) {
$serverProfileName = '../templates/pdf';
}
$dirPath = dirname(__FILE__) . '/../config/pdf/' . $serverProfileName . '/logos/'; $dirPath = dirname(__FILE__) . '/../config/pdf/' . $serverProfileName . '/logos/';
$success = copy($file, $dirPath . '/' . $name); $success = copy($file, $dirPath . '/' . $name);
if ($success) { if ($success) {
@ -242,21 +250,8 @@ function isValidPDFStructureName($name) {
* Installs template structures to the current server profile. * Installs template structures to the current server profile.
*/ */
function installPDFTemplates() { function installPDFTemplates() {
$templatePath = dirname(__FILE__) . '/../config/templates/pdf'; $templatePath = __DIR__ . '/../config/templates/pdf';
$templateDir = @dir($templatePath); $allTemplates = getPdfTemplateNames();
$allTemplates = array();
if ($templateDir) {
$entry = $templateDir->read();
while ($entry){
$parts = explode('.', $entry);
if ((strlen($entry) > 3) && (sizeof($parts) == 3)) {
$name = $parts[0];
$scope = $parts[1];
$allTemplates[$scope][] = $name;
}
$entry = $templateDir->read();
}
}
$basePath = dirname(__FILE__) . '/../config/pdf/' . $_SESSION['config']->getName(); $basePath = dirname(__FILE__) . '/../config/pdf/' . $_SESSION['config']->getName();
if (!file_exists($basePath)) { if (!file_exists($basePath)) {
mkdir($basePath, 0700, true); mkdir($basePath, 0700, true);
@ -278,20 +273,75 @@ function installPDFTemplates() {
if (!file_exists($basePath . '/logos')) { if (!file_exists($basePath . '/logos')) {
mkdir($basePath . '/logos'); mkdir($basePath . '/logos');
} }
$templatePath = dirname(__FILE__) . '/../config/templates/pdf/logos'; $logos = getPdfTemplateLogoNames();
foreach ($logos as $logo) {
$path = $basePath . '/logos/' . $logo;
$template = $templatePath . '/logos/' . $logo;
if (!is_file($path)) {
logNewMessage(LOG_DEBUG, 'Copy template ' . $template . ' to ' . $path);
@copy($template, $path);
}
}
}
/**
* Returns all PDF template names.
*
* @return array names (array('user' => array('default')))
*/
function getPdfTemplateNames() {
$templatePath = __DIR__ . '/../config/templates/pdf';
$templateDir = @dir($templatePath); $templateDir = @dir($templatePath);
$allTemplates = array();
if ($templateDir) { if ($templateDir) {
$entry = $templateDir->read(); $entry = $templateDir->read();
while ($entry){ while ($entry){
$path = $basePath . '/logos/' . $entry; $parts = explode('.', $entry);
if ((strpos($entry, '.') !== 0) && !is_file($path)) { if ((strlen($entry) > 3) && (sizeof($parts) == 3)) {
$template = $templatePath . '/' . $entry; $name = $parts[0];
logNewMessage(LOG_DEBUG, 'Copy template ' . $template . ' to ' . $path); $scope = $parts[1];
@copy($template, $path); $allTemplates[$scope][] = $name;
} }
$entry = $templateDir->read(); $entry = $templateDir->read();
} }
} }
return $allTemplates;
}
/**
* Returns all PDF template logo names.
*
* @return array names (array('user' => array('default.png')))
*/
function getPdfTemplateLogoNames() {
$templatePath = __DIR__ . '/../config/templates/pdf/logos';
$templateDir = @dir($templatePath);
$logos = array();
if ($templateDir) {
$entry = $templateDir->read();
while ($entry){
if ((strpos($entry, '.') !== 0) && is_file($templatePath . '/' . $entry)) {
$logos[] = $entry;
}
$entry = $templateDir->read();
}
}
return $logos;
}
/**
* Returns the binary data of the PDF template logo.
*
* @param string $name file name (without path)
* @return string binary
*/
function getPdfTemplateLogoBinary($name) {
$templatePath = __DIR__ . '/../config/templates/pdf/logos';
$fileName = $templatePath . '/' . $name;
$handle = fopen($fileName, 'r');
$logoBinary = fread($handle, 100000000);
fclose($handle);
return $logoBinary;
} }
/** /**
@ -309,7 +359,12 @@ class PDFStructureReader {
* @param $serverProfileName server profile name * @param $serverProfileName server profile name
*/ */
public function __construct($serverProfileName) { public function __construct($serverProfileName) {
$this->serverProfileName = $serverProfileName; if ($serverProfileName === GLOBAL_PROFILE) {
$this->serverProfileName = '../templates/pdf';
}
else {
$this->serverProfileName = $serverProfileName;
}
} }
/** /**
@ -345,6 +400,7 @@ class PDFStructureReader {
* @return PDFStructure structure * @return PDFStructure structure
*/ */
private function readPDFFile($file) { private function readPDFFile($file) {
logNewMessage(LOG_DEBUG, $file);
$xml = new \XMLReader(); $xml = new \XMLReader();
$xml->open($file); $xml->open($file);
$structure = new PDFStructure(); $structure = new PDFStructure();
@ -430,7 +486,12 @@ class PDFStructureWriter {
* @param string $serverProfileName server profile name * @param string $serverProfileName server profile name
*/ */
public function __construct($serverProfileName) { public function __construct($serverProfileName) {
$this->serverProfileName = $serverProfileName; if ($serverProfileName === GLOBAL_PROFILE) {
$this->serverProfileName = '../templates/pdf';
}
else {
$this->serverProfileName = $serverProfileName;
}
} }
/** /**
@ -460,10 +521,11 @@ class PDFStructureWriter {
throw new \LAMException(_('PDF structure name not valid'), throw new \LAMException(_('PDF structure name not valid'),
_('The name for that PDF-structure you submitted is not valid. A valid name must consist of the following characters: \'a-z\',\'A-Z\',\'0-9\',\'_\',\'-\'.')); _('The name for that PDF-structure you submitted is not valid. A valid name must consist of the following characters: \'a-z\',\'A-Z\',\'0-9\',\'_\',\'-\'.'));
} }
if(!is_writable(dirname(__FILE__) . '/../config/pdf/' . $this->serverProfileName)) { $baseDir = __DIR__ . '/../config/pdf/' . $this->serverProfileName;
throw new \LAMException(_('Could not save PDF structure, access denied.')); if(!is_writable($baseDir)) {
throw new \LAMException(_('Could not save PDF structure, access denied to ' . $baseDir . '.'));
} }
return dirname(__FILE__) . '/../config/pdf/' . $this->serverProfileName . '/' . $name . '.' . $typeId . '.xml'; return $baseDir . '/' . $name . '.' . $typeId . '.xml';
} }
/** /**

View File

@ -8,6 +8,9 @@ use LAMConfig;
use LAMException; use LAMException;
use function LAM\PDF\getAvailableLogos; use function LAM\PDF\getAvailableLogos;
use function LAM\PDF\getPDFStructures; use function LAM\PDF\getPDFStructures;
use function LAM\PDF\getPdfTemplateLogoBinary;
use function LAM\PDF\getPdfTemplateLogoNames;
use function LAM\PDF\getPdfTemplateNames;
use function LAM\PDF\uploadPDFLogo; use function LAM\PDF\uploadPDFLogo;
use function LAM\PROFILES\getAccountProfiles; use function LAM\PROFILES\getAccountProfiles;
use function LAM\PROFILES\getProfileTemplateNames; use function LAM\PROFILES\getProfileTemplateNames;
@ -68,8 +71,9 @@ class ConfigDataExporter {
} }
$jsonData['serverProfiles'] = $this->_getServerProfiles($serverProfiles); $jsonData['serverProfiles'] = $this->_getServerProfiles($serverProfiles);
$jsonData['accountProfiles'] = $this->_getAccountProfiles($serverProfiles); $jsonData['accountProfiles'] = $this->_getAccountProfiles($serverProfiles);
$jsonData['accountProfileTemplates'] = $this->_getAccountProfileTemplates($serverProfiles); $jsonData['accountProfileTemplates'] = $this->_getAccountProfileTemplates();
$jsonData['pdfProfiles'] = $this->_getPdfProfiles($serverProfiles); $jsonData['pdfProfiles'] = $this->_getPdfProfiles($serverProfiles);
$jsonData['pdfProfileTemplates'] = $this->_getPdfProfileTemplates();
/** /**
* TODO * TODO
* *
@ -147,11 +151,10 @@ class ConfigDataExporter {
/** /**
* Returns the content of the account profile templates. * Returns the content of the account profile templates.
* *
* @param array $serverProfiles list of server profiles (name => object)
* @return array $data * @return array $data
* @throws LAMException error reading template * @throws LAMException error reading template
*/ */
public function _getAccountProfileTemplates($serverProfiles) { public function _getAccountProfileTemplates() {
$data = array(); $data = array();
$accountProfileTemplateNames = getProfileTemplateNames(); $accountProfileTemplateNames = getProfileTemplateNames();
foreach ($accountProfileTemplateNames as $scope => $templateNames) { foreach ($accountProfileTemplateNames as $scope => $templateNames) {
@ -193,6 +196,29 @@ class ConfigDataExporter {
return $data; return $data;
} }
/**
* Returns the content of the account profile templates.
*
* @return array $data
* @throws LAMException error reading template
*/
public function _getPdfProfileTemplates() {
$data = array();
$pdfTemplateNames = getPdfTemplateNames();
$reader = new PDFStructureReader(\LAM\PDF\GLOBAL_PROFILE);
foreach ($pdfTemplateNames as $scope => $templateNames) {
foreach ($templateNames as $templateName) {
$pdfStructure = $reader->read($scope, $templateName);
$data['structures'][$scope][$templateName] = $pdfStructure->export();
}
}
$logoNames = getPdfTemplateLogoNames();
foreach ($logoNames as $logoName) {
$data['logos'][$logoName] = base64_encode(getPdfTemplateLogoBinary($logoName));
}
return $data;
}
} }
/** /**
@ -245,6 +271,9 @@ class ConfigDataImporter {
} }
$steps[] = $mainStep; $steps[] = $mainStep;
break; break;
case 'pdfProfileTemplates':
$steps[] = new ImporterStep(_('PDF structures') . ' - ' . _('Global templates'), 'pdfProfileTemplates', $value);
break;
default: default:
logNewMessage(LOG_WARNING, 'Unknown import type: ' . $key); logNewMessage(LOG_WARNING, 'Unknown import type: ' . $key);
} }
@ -286,6 +315,9 @@ class ConfigDataImporter {
case 'pdfProfiles': case 'pdfProfiles':
$this->importPdfProfiles($step); $this->importPdfProfiles($step);
break; break;
case 'pdfProfileTemplates':
$this->importPdfProfileTemplates($step);
break;
default: default:
logNewMessage(LOG_WARNING, 'Unknown import type: ' . $key); logNewMessage(LOG_WARNING, 'Unknown import type: ' . $key);
} }
@ -409,7 +441,7 @@ class ConfigDataImporter {
$writer->write($typeId, $pdfProfileName, $structure); $writer->write($typeId, $pdfProfileName, $structure);
} }
catch (LAMException $e) { catch (LAMException $e) {
logNewMessage('ERROR', $e->getMessage()); logNewMessage(LOG_ERR, $e->getTitle() . ' ' . $e->getMessage());
$failedProfiles[] = $serverProfileName . ':' . $typeId . ':' . $pdfProfileName; $failedProfiles[] = $serverProfileName . ':' . $typeId . ':' . $pdfProfileName;
} }
} }
@ -432,6 +464,54 @@ class ConfigDataImporter {
} }
} }
/**
* Imports the PDF profile templates.
*
* @param ImporterStep $step step
* @throws LAMException error during import
*/
private function importPdfProfileTemplates($step) {
$failedNames = array();
$data = $step->getValue();
if (isset($data['structures'])) {
$writer = new PDFStructureWriter(\LAM\PDF\GLOBAL_PROFILE);
foreach ($data['structures'] as $typeId => $pdfProfiles) {
foreach ($pdfProfiles as $pdfProfileName => $pdfProfileData) {
$structure = new PDFStructure();
$structure->import($pdfProfileData);
try {
$writer->write($typeId, $pdfProfileName, $structure);
}
catch (LAMException $e) {
$failedNames[] = $typeId . ':' . $pdfProfileName;
logNewMessage(LOG_ERR, $e->getTitle() . ' ' . $e->getMessage());
}
}
}
}
$failedLogos = array();
if (isset($data['logos'])) {
foreach ($data['logos'] as $logoFileName => $logoData) {
$tempFilePath = tempnam("/tmp", "lam");
$tempFile = fopen($tempFilePath, "w");
$logoBinary = base64_decode($logoData);
fwrite($tempFile, $logoBinary);
fclose($tempFile);
$message = uploadPDFLogo($tempFilePath, $logoFileName, \LAM\PDF\GLOBAL_PROFILE);
unlink($tempFilePath);
if ($message->getType() === 'ERROR') {
$failedLogos[] = $logoFileName;
}
}
}
if (!empty($failedNames)) {
throw new LAMException(_('Could not save PDF structure, access denied.'), implode(', ', $failedNames));
}
if (!empty($failedLogos)) {
throw new LAMException(_('Unable to upload logo file.'), implode(', ', $failedLogos));
}
}
} }
/** /**

View File

@ -114,7 +114,7 @@ function readAccountProfileFile($fileName) {
if ($file) { if ($file) {
while (!feof($file)) { while (!feof($file)) {
$line = fgets($file, 1024); $line = fgets($file, 1024);
if (($line == "\n")||($line[0] == "#")) { if (($line == '') || ($line == "\n") || ($line[0] == "#")) {
continue; // ignore comments continue; // ignore comments
} }
// search keywords // search keywords

View File

@ -262,6 +262,7 @@ printHeaderContents(_("Import and export configuration"), '../..');
$importer->runImport($importSteps); $importer->runImport($importSteps);
unlink($_SESSION['configImportFile']); unlink($_SESSION['configImportFile']);
$content->add(new htmlStatusMessage('INFO', _('Configuration import ended successful.')), 12); $content->add(new htmlStatusMessage('INFO', _('Configuration import ended successful.')), 12);
$content->add(new htmlButton('importNew', _('New import')), 12);
} }
catch (LAMException $e) { catch (LAMException $e) {
$content->add(new htmlStatusMessage('ERROR', htmlspecialchars($e->getTitle()), htmlspecialchars($e->getMessage())), 12); $content->add(new htmlStatusMessage('ERROR', htmlspecialchars($e->getTitle()), htmlspecialchars($e->getMessage())), 12);