[10.0.001.dev] Intégration gestion données manque l'import

This commit is contained in:
Fred Tempez 2019-12-10 10:53:31 +01:00
parent 72a37677c1
commit 31b1561750
9 changed files with 1443 additions and 656 deletions

View File

@ -34,7 +34,7 @@ class common {
const TEMP_DIR = 'site/tmp/';
// Numéro de version
const ZWII_VERSION = '10.0.000.dev';
const ZWII_VERSION = '10.0.001.dev';
public static $actions = [];
public static $coreModuleIds = [
@ -47,6 +47,14 @@ class common {
'theme',
'user'
];
public static $dataStage = [
'config',
'core',
'module',
'page',
'user',
'theme'
];
private $data = [];
private $hierarchy = [
'all' => [],
@ -59,6 +67,8 @@ class common {
];
public static $inputBefore = [];
public static $inputNotices = [];
public static $importNotices = [];
public static $coreNotices = [];
public $output = [
'access' => true,
'content' => '',
@ -133,22 +143,22 @@ class common {
$this->input['_COOKIE'] = $_COOKIE;
}
// Import des données d'une version 8
// Import version 9
if (file_exists(self::DATA_DIR . 'core.json') === true &&
$this->getData(['core','dataVersion']) < 10000 &&
$this->getData(['core','dataVersion']) !== 0) { // Retour d'importation ne pas déclencher l'import
$this->importData();
// Génère le fichier de données lorque les deux fichiers sont absents ou seulement le thème est - installation fraîche par défaut
if(file_exists(self::DATA_DIR.'core.json') === false OR
file_exists(self::DATA_DIR.'theme.json') === false) {
include_once('core/module/install/ressource/defaultdata.php');
$this->setData([install::$defaultData]);
$this->saveData();
chmod(self::DATA_DIR.'core.json', 0755);
chmod(self::DATA_DIR.'theme.json', 0755);
common::$importNotices [] = "Importation réalisée avec succès" ;
//echo '<script>window.location.replace("' . helper::baseUrl() . $this->getData(['config','homePageId']) . '")</script>';
}
// Installation fraîche, initialisation des modules manquants
// La langue d'installation par défaut est fr
foreach (self::$dataStage as $stageId) {
$folder = $this->dirData ($stageId, 'fr');
if (file_exists($folder . $stageId .'.json') === false) {
$this->initData($stageId,'fr');
common::$coreNotices [] = $stageId ;
}
// Import des données d'un fichier data.json déjà présent
if($this->data === []) {
$this->readData();
}
// Utilisateur connecté
@ -223,62 +233,6 @@ class common {
$this->update();
}
/**
* Lecture des fichiers de données
*
*/
public function readData() {
// Trois tentatives
for($i = 0; $i < 3; $i++) {
$this->setData([json_decode(file_get_contents(self::DATA_DIR.'core.json'), true) + json_decode(file_get_contents(self::DATA_DIR.'theme.json'), true)]);
if($this->data) {
break;
}
elseif($i === 2) {
exit('Unable to read data file.');
}
// Pause de 10 millisecondes
usleep(10000);
}
}
/**
* Import des données de la version 8
* Converti un fichier de données data.json puis le renomme
*/
public function importData() {
if(file_exists(self::DATA_DIR.'data.json')) {
// Trois tentatives
for($i = 0; $i < 3; $i++) {
$tempData = [json_decode(file_get_contents(self::DATA_DIR.'data.json'), true)];
if($tempData) {
for($i = 0; $i < 3; $i++) {
if(file_put_contents(self::DATA_DIR.'core.json', json_encode(array_slice($tempData[0],0,5)), LOCK_EX) !== false) {
break;
}
// Pause de 10 millisecondes
usleep(10000);
}
for($i = 0; $i < 3; $i++) {
if(file_put_contents(self::DATA_DIR.'theme.json', json_encode(array_slice($tempData[0],5)), LOCK_EX) !== false) {
break;
}
// Pause de 10 millisecondes
usleep(10000);
}
rename (self::DATA_DIR.'data.json',self::DATA_DIR.'imported_data.json');
break;
}
elseif($i === 2) {
exit('Unable to read data file.');
}
// Pause de 10 millisecondes
usleep(10000);
}
}
}
/**
* Ajoute les valeurs en sortie
* @param array $output Valeurs en sortie
@ -318,27 +272,44 @@ class common {
* @param array $keys Clé(s) des données
*/
public function deleteData($keys) {
//Retourne une chaine contenant le dossier à créer
$folder = $this->dirData ($keys[0],'fr');
// Constructeur JsonDB
require_once "core/vendor/jsondb/Dot.php";
require_once "core/vendor/jsondb/JsonDb.php";
$db = new \Prowebcraft\JsonDb([
'name' => $keys[0] . '.json',
'dir' => $folder,
'template' => self::TEMP_DIR . 'data.template.json'
]);
switch(count($keys)) {
case 1:
unset($this->data[$keys[0]]);
$db->delete($keys[0]);
$db->save();
break;
case 2:
unset($this->data[$keys[0]][$keys[1]]);
$db->delete($keys[0].'.'.$keys[1]);
$db->save();
break;
case 3:
unset($this->data[$keys[0]][$keys[1]][$keys[2]]);
$db->delete($keys[0].'.'.$keys[1].'.'.$keys[2]);
$db->save();
break;
case 4:
unset($this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]]);
$db->delete($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3]);
$db->save();
break;
case 5:
unset($this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]][$keys[4]]);
$db->delete($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4]);
$db->save();
break;
case 6:
unset($this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]][$keys[4]][$keys[5]]);
$db->delete($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4].'.'.$keys[5]);
$db->save();
break;
case 7:
unset($this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]][$keys[4]][$keys[5]][$keys[6]]);
$db->delete($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4].'.'.$keys[5].'.'.$keys[6]);
$db->save();
break;
}
}
@ -373,24 +344,43 @@ class common {
* @return mixed
*/
public function getData($keys = null) {
// Retourne l'ensemble des données
if($keys === null) {
return $this->data;
if (count($keys) >= 1) {
//Retourne une chaine contenant le dossier à créer
$folder = $this->dirData ($keys[0],'fr');
// Constructeur JsonDB
require_once "core/vendor/jsondb/Dot.php";
require_once "core/vendor/jsondb/JsonDb.php";
$db = new \Prowebcraft\JsonDb([
'name' => $keys[0] . '.json',
'dir' => $folder,
'template' => self::TEMP_DIR . 'data.template.json'
]);
switch(count($keys)) {
case 1:
$tempData = $db->get($keys[0]);
break;
case 2:
$tempData = $db->get($keys[0].'.'.$keys[1]);
break;
case 3:
$tempData = $db->get($keys[0].'.'.$keys[1].'.'.$keys[2]);
break;
case 4:
$tempData = $db->get($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3]);
break;
case 5:
$tempData = $db->get($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4]);
break;
case 6:
$tempData = $db->get($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4].'.'.$keys[5]);
break;
case 7:
$tempData = $db->get($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4].'.'.$keys[5].'.'.$keys[6]);
break;
}
// Décent dans les niveaux de la variable $data
$data = $this->data;
foreach($keys as $key) {
// Si aucune donnée n'existe retourne null
if(isset($data[$key]) === false) {
return null;
return $tempData;
}
// Sinon décent dans les niveaux
else {
$data = $data[$key];
}
}
// Retourne les données
return $data;
}
/**
@ -523,31 +513,51 @@ class common {
}
/**
* Enregistre les données dans deux fichiers séparés
* Import des données de la version 9
* Convertit un fichier de données data.json puis le renomme
*/
public function saveData() {
// Save config core page module et user
// 5 premières clés principales
// Trois tentatives
public function importData($keepUsers = false) {
// Trois tentatives de lecture
for($i = 0; $i < 3; $i++) {
if(file_put_contents(self::DATA_DIR.'core.json', json_encode(array_slice($this->getData(),0,5)) , LOCK_EX) !== false) {
$tempData=json_decode(file_get_contents(self::DATA_DIR.'core.json'), true);
$tempTheme=json_decode(file_get_contents(self::DATA_DIR.'theme.json'), true);
if($tempData && $tempTheme) {
// Backup
rename (self::DATA_DIR.'core.json',self::DATA_DIR.'imported_core.json');
rename (self::DATA_DIR.'theme.json',self::DATA_DIR.'imported_theme.json');
break;
}
elseif($i === 2) {
exit('Impossible de lire les données à importer.');
}
// Pause de 10 millisecondes
usleep(10000);
}
// Save theme
// dernière clé principale
// Trois tentatives
for($i = 0; $i < 3; $i++) {
if(file_put_contents(self::DATA_DIR.'theme.json', json_encode(array_slice($this->getData(),5)), LOCK_EX) !== false) {
break;
// Dossier de langues
if (!file_exists(self::DATA_DIR . '/fr')) {
mkdir (self::DATA_DIR . '/fr');
}
// Pause de 10 millisecondes
usleep(10000);
// Ecriture des données
$this->setData(['config',$tempData['config']]);
$this->setData(['core',$tempData['core']]);
$this->setData(['page',$tempData['page']]);
// Import des modules
$this->setData(['module',$tempData['module']]);
// Import des users sauvegardés si option active
if ($keepUsers === false) {
$this->setData(['user',$tempData['user']]);
}
// Import du theme
$this->setData(['theme',$tempTheme['theme']]);
// Nettoyage du fichier de thème pour forcer une régénération
if (file_exists(self::DATA_DIR . '/theme.css')) { // On ne sait jamais
unlink (self::DATA_DIR . '/theme.css');
}
}
/**
* Génére un fichier json avec la liste des pages
*
@ -609,11 +619,27 @@ class common {
}
}
/**
* Retourne une chemin localisé pour l'enregistrement des données
* @param $stageId nom du module
* @param $lang langue des pages
* @return string du dossier à créer
*/
public function dirData($id, $lang) {
// Sauf pour les pages et les modules
if ($id === 'page' ||
$id === 'module') {
$folder = self::DATA_DIR . $lang . '/' ;
} else {
$folder = self::DATA_DIR;
}
return ($folder);
}
/**
* Génére un fichier robots.txt à l'installation
* Si le fichier exite déjà les commandes sont ajoutées
*/
public function createRobots() {
$robotValue =
@ -772,34 +798,89 @@ class common {
}
}
/**
* Insert des données
* Sauvegarde des données
* @param array $keys Clé(s) des données
*/
public function setData($keys) {
public function setData($keys = NULL) {
// Pas d'enregistrement lorsque'une notice est présente
if (!empty(self::$inputNotices)) {
return false;
}
//Retourne une chaine contenant le dossier à créer
$folder = $this->dirData ($keys[0],'fr');
// Constructeur JsonDB
require_once "core/vendor/jsondb/Dot.php";
require_once "core/vendor/jsondb/JsonDb.php";
$db = new \Prowebcraft\JsonDb([
'name' => $keys[0] . '.json',
'dir' => $folder,
'template' => self::TEMP_DIR . 'data.template.json'
]);
switch(count($keys)) {
case 1:
$this->data = $keys[0];
break;
case 2:
$this->data[$keys[0]] = $keys[1];
$db->set($keys[0],$keys[1]);
$db->save();
break;
case 3:
$this->data[$keys[0]][$keys[1]] = $keys[2];
$db->set($keys[0].'.'.$keys[1],$keys[2]);
$db->save();
break;
case 4:
$this->data[$keys[0]][$keys[1]][$keys[2]] = $keys[3];
$db->set($keys[0].'.'.$keys[1].'.'.$keys[2],$keys[3]);
$db->save();
break;
case 5:
$this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]] = $keys[4];
$db->set($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3],$keys[4]);
$db->save();
break;
case 6:
$this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]][$keys[4]] = $keys[5];
$db->set($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4],$keys[5]);
$db->save();
break;
case 7:
$this->data[$keys[0]][$keys[1]][$keys[2]][$keys[3]][$keys[4]][$keys[5]] = $keys[6];
$db->set($keys[0].'.'.$keys[1].'.'.$keys[2].'.'.$keys[3].'.'.$keys[4].'.'.$keys[5],$keys[6]);
$db->save();
break;
}
return true;
}
/**
* Initialisation des données
* @param array $module : nom du module à générer
* choix valides : core config user theme page module
*/
public function initData($module, $lang = 'fr', $sampleSite = false) {
// Tableau avec les données vierges
require_once('core/module/install/ressource/defaultdata.php');
// Stockage dans un sous-dossier localisé
// Le dossier de langue existe t-il ?
if (!file_exists(self::DATA_DIR . '/' . $lang)) {
mkdir (self::DATA_DIR . '/' . $lang);
}
$folder = $this->dirData ($module,$lang);
// Constructeur JsonDB
require_once "core/vendor/jsondb/Dot.php";
require_once "core/vendor/jsondb/JsonDb.php";
$db = new \Prowebcraft\JsonDb([
'name' => $module . '.json',
'dir' => $folder,
'template' => self::TEMP_DIR . 'data.template.json'
]);
if ($sampleSite === true) {
$db->set($module,init::$siteData[$module]);
} else {
$db->set($module,init::$defaultData[$module]);
}
$db->save;
}
/**
@ -810,7 +891,7 @@ class common {
if($this->getData(['core', 'dataVersion']) < 810) {
$this->setData(['config', 'timezone', 'Europe/Paris']);
$this->setData(['core', 'dataVersion', 810]);
$this->saveData();
//$this->SaveData();
}
// Version 8.2.0
if($this->getData(['core', 'dataVersion']) < 820) {
@ -823,56 +904,56 @@ class common {
$this->setData(['theme', 'header', 'fontSize', '2em']);
$this->setData(['theme', 'footer', 'textColor', 'rgba(33, 34, 35, 1)']);
$this->setData(['core', 'dataVersion', 820]);
$this->saveData();
//$this->SaveData();
}
// Version 8.2.2
if($this->getData(['core', 'dataVersion']) < 822) {
$this->setData(['config', 'maintenance', false]);
$this->setData(['core', 'dataVersion', 822]);
$this->saveData();
//$this->SaveData();
}
// Version 8.2.6
if($this->getData(['core', 'dataVersion']) < 826) {
$this->setData(['theme','header','linkHome',true]);
$this->setData(['core', 'dataVersion', 826]);
$this->saveData();
//$this->SaveData();
}
// Version 8.3.1
if($this->getData(['core', 'dataVersion']) < 831) {
$this->setData(['theme','header','imageContainer','auto']);
$this->setData(['core', 'dataVersion', 831]);
$this->saveData();
//$this->SaveData();
}
// Version 8.4.0
if($this->getData(['core', 'dataVersion']) < 840) {
$this->setData(['config','itemsperPage',10]);
$this->setData(['core', 'dataVersion', 840]);
$this->saveData();
//$this->SaveData();
}
// Version 8.4.4
if($this->getData(['core', 'dataVersion']) < 844) {
$this->setData(['core', 'dataVersion', 844]);
$this->saveData();
//$this->SaveData();
}
// Version 8.4.6
if($this->getData(['core', 'dataVersion']) < 846) {
$this->setData(['config','itemsperPage',10]);
$this->setData(['core', 'dataVersion', 846]);
$this->saveData();
//$this->SaveData();
}
// Version 8.5.0
if($this->getData(['core', 'dataVersion']) < 850) {
$this->setData(['theme','menu','font','Open+Sans']);
$this->setData(['core', 'dataVersion', 850]);
$this->saveData();
//$this->SaveData();
}
// Version 8.5.1
if($this->getData(['core', 'dataVersion']) < 851) {
$this->setData(['config','itemsperPage',10]);
$this->deleteData(['config','ItemsperPage']);
$this->setData(['core', 'dataVersion', 851]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.0
if($this->getData(['core', 'dataVersion']) < 9000) {
@ -882,13 +963,13 @@ class common {
}
$this->setData(['theme', 'menu','fixed',false]);
$this->setData(['core', 'dataVersion', 9000]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.01
if($this->getData(['core', 'dataVersion']) < 9001) {
$this->deleteData(['config', 'social', 'googleplusId']);
$this->setData(['core', 'dataVersion', 9001]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.08
if($this->getData(['core', 'dataVersion']) < 9008) {
@ -897,31 +978,31 @@ class common {
$this->setData(['theme', 'footer', 'fontSize','.8em']);
$this->setData(['theme', 'footer', 'font','Open+Sans']);
$this->setData(['core', 'dataVersion', 9008]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.09
if($this->getData(['core', 'dataVersion']) < 9009) {
$this->setData(['core', 'dataVersion', 9009]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.10
if($this->getData(['core', 'dataVersion']) < 9010) {
$this->deleteData(['config', 'social', 'googleplusId']);
$this->setData(['core', 'dataVersion', 9010]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.11
if($this->getData(['core', 'dataVersion']) < 9011) {
if ($this->getData(['theme','menu','position']) === 'body')
$this->setData(['theme','menu','position','site']);
$this->setData(['core', 'dataVersion', 9011]);
$this->saveData();
//$this->SaveData();
}
// Version 9.0.17
if($this->getData(['core', 'dataVersion']) < 9017) {
$this->setData(['theme','footer','displayVersion', true ]);
$this->setData(['core', 'dataVersion', 9017]);
$this->saveData();
//$this->SaveData();
}
// Version 9.1.0
if($this->getData(['core', 'dataVersion']) < 9100) {
@ -929,7 +1010,7 @@ class common {
$this->setData(['theme','footer','displaySiteMap', true ]);
$this->setData(['theme','footer','displayCopyright', true ]);
$this->setData(['core', 'dataVersion', 9100]);
$this->saveData();
//$this->SaveData();
}
// Version 9.2.00
if($this->getData(['core', 'dataVersion']) < 9200) {
@ -939,7 +1020,7 @@ class common {
$this->setData(['theme','footer','displaySearch', false ]);
$this->setData(['config','social','githubId', '' ]);
$this->setData(['core', 'dataVersion', 9200]);
$this->saveData();
//$this->SaveData();
}
// Version 9.2.05
if($this->getData(['core', 'dataVersion']) < 9205) {
@ -956,7 +1037,7 @@ class common {
rmdir ('core/vendor/swiper/');
}
$this->setData(['core', 'dataVersion', 9205]);
$this->saveData();
//$this->SaveData();
}
// Version 9.2.10
if($this->getData(['core', 'dataVersion']) < 9210) {
@ -1007,7 +1088,7 @@ class common {
}
}
$this->setData(['core', 'dataVersion', 9210]);
$this->saveData();
//$this->SaveData();
}
// Version 9.2.11
if($this->getData(['core', 'dataVersion']) < 9211) {
@ -1015,14 +1096,14 @@ class common {
$this->setData(['core', 'lastAutoUpdate', $autoUpdate]);
$this->setData(['config','autoUpdate', true]);
$this->setData(['core', 'dataVersion', 9211]);
$this->saveData();
//$this->SaveData();
}
// Version 9.2.12
if($this->getData(['core', 'dataVersion']) < 9212) {
$this->setData(['theme','menu', 'activeColorAuto',true]);
$this->setData(['theme','menu', 'activeColor','rgba(255, 255, 255, 1)']);
$this->setData(['core', 'dataVersion', 9212]);
$this->saveData();
//$this->SaveData();
}
}
}
@ -1056,7 +1137,7 @@ class core extends common {
// Date de la dernière suppression
$this->setData(['core', 'lastClearTmp', $lastClearTmp]);
// Enregistre les données
$this->saveData();
//$this->SaveData();
}
// Backup automatique des données
$lastBackup = mktime(0, 0, 0);
@ -1070,7 +1151,7 @@ class core extends common {
// Date du dernier backup
$this->setData(['core', 'lastBackup', $lastBackup]);
// Enregistre les données
$this->saveData();
//$this->SaveData();
// Supprime les backups de plus de 30 jours
$iterator = new DirectoryIterator(self::BACKUP_DIR);
foreach($iterator as $fileInfos) {
@ -1380,7 +1461,7 @@ class core extends common {
// Enregistrement des données
if($output['state'] !== false) {
$this->setData([$module->getData()]);
$this->saveData();
//$this->SaveData();
}
// Notification
if($output['notification']) {
@ -2433,6 +2514,15 @@ class layout extends common {
* Affiche la notification
*/
public function showNotification() {
if(common::$inputNotices) {
$notification = 'Impossible de soumettre le formulaire, car il contient des erreurs';
$notificationClass = 'notificationError';
}
if (common::$coreNotices) {
$notification = 'Données absentes, restauration de <p> | ';
foreach (common::$coreNotices as $item) $notification .= $item . ' | ';
$notificationClass = 'notificationError';
}
if(common::$inputNotices) {
$notification = 'Impossible de soumettre le formulaire, car il contient des erreurs';
$notificationClass = 'notificationError';

View File

@ -19,7 +19,9 @@ class config extends common {
'configMetaImage' => self::GROUP_ADMIN,
'generateFiles' => self::GROUP_ADMIN,
'updateRobots' => self::GROUP_ADMIN,
'index' => self::GROUP_ADMIN
'index' => self::GROUP_ADMIN,
'manage' => self::GROUP_ADMIN,
'updateBaseUrl' => self::GROUP_ADMIN
];
public static $timezones = [
@ -148,7 +150,7 @@ class config extends common {
public function generateFiles() {
// Mettre à jour le site map
$successSitemap=$this->createSitemap('all');
$successSitemap=$this->createSitemap();
// Creer un fichier robots.txt
$successRobots=$this->updateRobots();
@ -199,16 +201,17 @@ class config extends common {
* Sauvegarde des données
*/
public function backup() {
// Creation du ZIP
$fileName = date('Y-m-d-h-i-s', time()) . '.zip';
$fileName = str_replace('/','',helper::baseUrl(false,false)) . '-'. date('Y-m-d-h-i-s', time()) . '.zip';
$zip = new ZipArchive();
if($zip->open(self::TEMP_DIR . $fileName, ZipArchive::CREATE) === TRUE){
foreach(configHelper::scanDir('site/') as $file) {
foreach(core::scanDir(self::DATA_DIR) as $file) {
$zip->addFile($file);
}
}
$zip->close();
// Enregistre la date de backup manuel
$this->setData(['core', 'lastBackup', mktime(0, 0, 0)]);
// Téléchargement du ZIP
header('Content-Transfer-Encoding: binary');
header('Content-Disposition: attachment; filename="' . $fileName . '"');
@ -255,6 +258,104 @@ class config extends common {
]);
}
/**
* Procédure d'importation
*/
public function manage() {
// Soumission du formulaire
if($this->isPost()) {
//if ($this->getInput('configManageImportFile'))
$fileZip = $this->getInput('configManageImportFile');
$file_parts = pathinfo($fileZip);
$folder = date('Y-m-d-h-i-s', time());
$zip = new ZipArchive();
if ($file_parts['extension'] !== 'zip') {
// Valeurs en sortie erreur
$this->addOutput([
'notification' => 'Le fichier n\'est pas une archive valide',
'redirect' => helper::baseUrl() . 'config/manage',
'state' => false
]);
}
$successOpen = $zip->open(self::FILE_DIR . 'source/' . $fileZip);
if ($successOpen === FALSE) {
// Valeurs en sortie erreur
$this->addOutput([
'notification' => 'Impossible de lire l\'archive',
'redirect' => helper::baseUrl() . 'config/manage',
'state' => false
]);
}
// Lire le contenu de l'archive dans le tableau files
for( $i = 0; $i < $zip->numFiles; $i++ ){
$stat = $zip->statIndex( $i );
$files [] = ( basename( $stat['name'] ));
}
// Détermination de la version à installer
if (in_array('theme.json',$files) === true &&
in_array('core.json',$files) === true &&
in_array ('user.json', $files) === false ) {
// V9 pas de fichier user dans l'archive
// Stocker le choix de conserver les users installées
$version = '9';
} elseif (in_array('theme.json',$files) === true &&
in_array('core.json',$files) === true &&
in_array ('user.json', $files) === true &&
in_array ('config.json', $files) === true ) {
// V10 valide
$version = '10';
// Option active, les users sont stockées
if ($this->getInput('configManageImportUser', helper::FILTER_BOOLEAN) === true ) {
$users = $this->getData(['user']);
}
} else { // Version invalide
// Valeurs en sortie erreur
$this->addOutput([
'notification' => 'Cette archive n\'est pas une sauvegarde valide',
'redirect' => helper::baseUrl() . 'config/manage',
'state' => false
]);
}
// Extraire le zip
$success = $zip->extractTo( '.' );
// Fermer l'archive
$zip->close();
// Restaurer les users originaux d'une v10 si option cochée
if (!empty($users) &&
$version === '10' &&
$this->getInput('configManageImportUser', helper::FILTER_BOOLEAN) === true) {
$this->setData(['user',$users]);
}
if ($version === '9' ) {
$this->importData($this->getInput('configManageImportUser', helper::FILTER_BOOLEAN));
$this->setData(['core','dataVersion',0]);
}
// Met à jours les URL dans les contenus de page
// Message de notification
$notification = $success === true ? 'Sauvegarde importée avec succès' : 'Erreur d\'extraction';
$redirect = $this->getInput('configManageImportUser', helper::FILTER_BOOLEAN) === true ? helper::baseUrl() . 'config/manage' : helper::baseUrl() . 'user/login/';
// Valeurs en sortie erreur
$this->addOutput([
'notification' => $notification,
'redirect' =>$redirect,
'state' => $success
]);
}
// Valeurs en sortie
$this->addOutput([
'title' => 'Sauvegarder / Restaurer',
'view' => 'manage'
]);
}
/**
@ -268,6 +369,7 @@ class config extends common {
} else {
$legalPageId = '';
}
$this->setData([
'config',
[
@ -276,8 +378,6 @@ class config extends common {
'maintenance' => $this->getInput('configMaintenance', helper::FILTER_BOOLEAN),
'cookieConsent' => $this->getInput('configCookieConsent', helper::FILTER_BOOLEAN),
'favicon' => $this->getInput('configFavicon'),
'homePageId' => $this->getInput('configHomePageId', helper::FILTER_ID, true),
'metaDescription' => $this->getInput('configMetaDescription', helper::FILTER_STRING_LONG, true),
'social' => [
'facebookId' => $this->getInput('configSocialFacebookId'),
'linkedinId' => $this->getInput('configSocialLinkedinId'),
@ -288,12 +388,15 @@ class config extends common {
'githubId' => $this->getInput('configSocialGithubId')
],
'timezone' => $this->getInput('configTimezone', helper::FILTER_STRING_SHORT, true),
'title' => $this->getInput('configTitle', helper::FILTER_STRING_SHORT, true),
'itemsperPage' => $this->getInput('itemsperPage', helper::FILTER_INT,true),
'legalPageId' => $this->getInput('configLegalPageId'),
'metaDescription' => $this->getInput('configMetaDescription', helper::FILTER_STRING_LONG, true),
'title' => $this->getInput('configTitle', helper::FILTER_STRING_SHORT, true),
'googTransLogo' => $this->getInput('configdGoogTransLogo', helper::FILTER_BOOLEAN),
'autoUpdate' => $this->getInput('configAutoUpdate', helper::FILTER_BOOLEAN)
]
]);
if(self::$inputNotices === []) {
// Ecrire les fichiers de script
file_put_contents(self::DATA_DIR . 'head.inc.html',$this->getInput('configScriptHead',null));
@ -352,30 +455,27 @@ class config extends common {
]);
}
}
class configHelper extends helper {
/**
* Scan le contenu d'un dossier et de ses sous-dossiers
* @param string $dir Dossier à scanner
* @return array
* Met à jour les données de site avec l'adresse trannsmise
*/
public static function scanDir($dir) {
$dirContent = [];
$iterator = new DirectoryIterator($dir);
foreach($iterator as $fileInfos) {
if(in_array($fileInfos->getFilename(), ['.', '..', 'backup'])) {
continue;
}
elseif($fileInfos->isDir()) {
$dirContent = array_merge($dirContent, self::scanDir($fileInfos->getPathname()));
}
else {
$dirContent[] = $fileInfos->getPathname();
public function updateBaseUrl () {
$old = $this->getInput('configManageBaseURLToConvert');
$new = $this->getInput('configManageCurrentURL');
foreach($this->getHierarchy(null,null,null) as $parentId => $childIds) {
$content = $this->getData(['page',$parentId,'content']);
$replace = str_replace( $old . '/site/' , $new . 'site/', $content) ;
$this->setData(['page',$parentId,'content', $replace ]);
foreach($childIds as $childId) {
$content = $this->getData(['page',$childId,'content']);
$replace = str_replace( $old . '/site/' , $new . 'site/', $content) ;
$this->setData(['page',$childId,'content', $replace ]);
}
}
return $dirContent;
$this->setData(['core','baseUrl',helper::baseUrl(false,false)]);
// Valeurs en sortie
$this->addOutput([
'title' => 'Sauvegarder / Restaurer',
'view' => 'manage'
]);
}
}

View File

@ -0,0 +1,16 @@
/**
* This file is part of Zwii.
*
* For full copyright and license information, please see the LICENSE
* file that was distributed with this source code.
*
* @author Frédéric Tempez <frederic.tempez@outlook.com>
* @copyright Copyright (C) 2018-2020, Frédéric Tempez
* @license GNU General Public License, version 3
* @link http://zwiicms.com/
*/
/**
* Modification de l'affichage de l'icône de langues
*/

View File

@ -1,4 +1,5 @@
<?php echo template::formOpen('configForm'); ?>
<div class="notranslate">
<div class="row">
<div class="col2">
<?php echo template::button('configBack', [
@ -8,7 +9,13 @@
'value' => 'Accueil'
]); ?>
</div>
<div class="col2 offset8">
<div class="col3 offset5">
<?php echo template::button('configManageButton', [
'href' => helper::baseUrl() . 'config/manage',
'value' => 'Sauvegarder / Restaurer'
]); ?>
</div>
<div class="col2">
<?php echo template::submit('configSubmit'); ?>
</div>
</div>
@ -20,7 +27,8 @@
<div class="col4">
<?php echo template::select('configHomePageId', helper::arrayCollumn($this->getData(['page']), 'title', 'SORT_ASC'), [
'label' => 'Page d\'accueil',
'selected' => $this->getData(['config', 'homePageId'])
'selected' =>$this->getData(['config', 'homePageId']),
'help' => 'La page d\'accueil doit être définie dans une des pages de la langue sélectionnée'
]); ?>
</div>
<div class="col8">
@ -40,7 +48,7 @@
</div>
</div>
<div class="row">
<div class="col6">
<div class="col12">
<div class="block">
<h4>Réglages</h4>
<div class="row">
@ -78,66 +86,80 @@
]); ?>
</div>
</div>
<div class="col12">
<div class="row">
<div class="col6">
<?php echo template::checkbox('configCookieConsent', true, 'Message de consentement aux cookies', [
'checked' => $this->getData(['config', 'cookieConsent'])
]); ?>
</div>
</div>
<div class="col12">
<div class="row">
<div class="col6">
<?php echo template::checkbox('rewrite', true, 'Réécriture d\'URL', [
'checked' => helper::checkRewrite(),
'help' => 'Vérifiez d\'abord que votre serveur l\'autorise : ce n\'est pas le cas chez Free.'
]); ?>
</div>
</div>
<div class="row">
<div class="col6">
<?php echo template::checkbox('configMaintenance', true, 'Site en maintenance', [
'checked' => $this->getData(['config', 'maintenance'])
]); ?>
</div>
<div class="col6">
<?php echo template::checkbox('configAutoUpdate', true, 'Mise à jour automatique', [
'checked' => $this->getData(['config', 'autoUpdate']),
'help' => 'Vérifie une fois par jour l\'existence d\'une mise à jour.'
]); ?>
</div>
</div>
</div>
</div>
</div>
<div class="row">
<div class="col6">
<div class="block">
<h4>Réseaux sociaux</h4>
<div class="row">
<div class="col4">
<div class="col6">
<?php echo template::text('configSocialFacebookId', [
'help' => 'Saisissez votre ID : https://www.facebook.com/[ID].',
'label' => 'Facebook',
'value' => $this->getData(['config', 'social', 'facebookId'])
]); ?>
</div>
<div class="col4">
<div class="col6">
<?php echo template::text('configSocialInstagramId', [
'help' => 'Saisissez votre ID : https://www.instagram.com/[ID].',
'label' => 'Instagram',
'value' => $this->getData(['config', 'social', 'instagramId'])
]); ?>
</div>
<div class="col4">
</div>
<div class="row">
<div class="col6">
<?php echo template::text('configSocialYoutubeId', [
'help' => 'Saisissez votre ID : https://www.youtube.com/channel/[ID].',
'label' => 'Youtube',
'value' => $this->getData(['config', 'social', 'youtubeId'])
]); ?>
</div>
</div>
<div class="row">
<div class="col4">
<div class="col6">
<?php echo template::text('configSocialTwitterId', [
'help' => 'Saisissez votre ID : https://twitter.com/[ID].',
'label' => 'Twitter',
'value' => $this->getData(['config', 'social', 'twitterId'])
]); ?>
</div>
<div class="col4">
</div>
<div class="row">
<div class="col6">
<?php echo template::text('configSocialPinterestId', [
'help' => 'Saisissez votre ID : https://pinterest.com/[ID].',
'label' => 'Pinterest',
'value' => $this->getData(['config', 'social', 'pinterestId'])
]); ?>
</div>
<div class="col4">
<div class="col6">
<?php echo template::text('configSocialLinkedinId', [
'help' => 'Saisissez votre ID Linkedin : https://fr.linkedin.com/in/[ID].',
'label' => 'Linkedin',
@ -146,7 +168,7 @@
</div>
</div>
<div class="row">
<div class="col4 offset4">
<div class="col6 offset3">
<?php echo template::text('configSocialGithubId', [
'help' => 'Saisissez votre ID Github : https://github.com/[ID].',
'label' => 'Github',
@ -156,36 +178,8 @@
</div>
</div>
</div>
</div>
<div class="row">
<div class="col6">
<div class="block">
<h4>Gestion et sauvegarde</h4>
<div class="col12">
<div class="row">
<?php echo template::checkbox('configMaintenance', true, 'Site en maintenance', [
'checked' => $this->getData(['config', 'maintenance'])
]); ?>
<?php echo template::checkbox('configAutoUpdate', true, 'Mise à jour automatique', [
'checked' => $this->getData(['config', 'autoUpdate']),
'help' => 'Vérifie une fois par jour l\'existence d\'une mise à jour.'
]); ?>
<?php echo template::checkbox('configAutoBackup', true, 'Sauvegarde automatique', [
'checked' => $this->getData(['config', 'autoBackup']),
'help' => 'Le fichier de données est copié quotidiennement dans le dossier \'site/backup\'. La sauvegarde est conservée pendant 30 jours.'
]); ?>
</div>
</div>
<div class="row">
<div class="col10 offset1">
<?php echo template::button('configExport', [
'href' => helper::baseUrl() . 'config/backup',
'value' => 'Exporter une copie du site<br>(données, thème et fichiers)'
]); ?>
</div>
</div>
</div>
</div>
<!--</div>
<div class="row">-->
<div class="col6">
<div class="block">
<h4>Référencement</h4>
@ -304,4 +298,5 @@
</div>
</div>
</div>
</div>
<?php echo template::formClose(); ?>

View File

@ -0,0 +1,100 @@
<?php echo template::formOpen('configManageForm'); ?>
<div class="notranslate">
<div class="row">
<div class="col2">
<?php echo template::button('configManageBack', [
'class' => 'buttonGrey',
'href' => helper::baseUrl() . 'config',
'ico' => 'left',
'value' => 'Retour'
]); ?>
</div>
<div class="col2 offset8">
<?php echo template::submit('configManageSubmit',[
'value' => 'Enregister'
]); ?>
</div>
</div>
<div class="row">
<div class="col6">
<div class="block">
<h4>Sauvegarde du site (données et thème)</h4>
<div class="row">
<div class="col10 offset1">
<?php echo template::button('configManageButton', [
'href' => helper::baseUrl() . 'config/backup',
'value' => 'Générer et télécharger <br />une archive des données de site',
]); ?>
</div>
</div>
<div class="row">
<?php echo template::checkbox('configExportAutoBackup', true, 'Sauvegarde automatique quotidienne', [
'checked' => $this->getData(['config', 'autoBackup']),
'help' => '<p>Une archive contenant le dossier /site/data est copiée dans le dossier \'site/backup\'. La sauvegarde est conservée pendant 30 jours.</p><p>Les fichiers du site ne sont pas sauvegardés automatiquement.</p>'
]); ?>
</div>
</div>
</div>
<div class="col6">
<div class="block">
<h4>Restauration ou transfert d'un site</h4>
<div class="row">
<?php echo template::file('configManageImportFile', [
'label' => 'Sélectionnez une archive au format ZIP',
'type' => 2,
'help' => 'L\'archive a été déposée dans le gestionaire de fichiers. Les archives inférieures à la version 9 ne sont pas acceptées.'
]); ?>
</div>
<div class="row">
<?php echo template::checkbox('configManageImportUser', true, 'Préserver les comptes des utilisateurs déjà installés', [
'checked' => true
]); ?>
</div>
</div>
</div>
</div>
<div class="row">
<div class="col12">
<div class="block">
<h4>Conversion des URL après transfert de site</h4>
<div class="row">
<div class="col5">
<?php
if (is_null($this->getData(['core', 'baseUrl'])) ) {
$baseUrlValue = 'Pas de donnée dans la sauvegarde';
$buttonClass = 'disabled';
} elseif ($this->getData(['core', 'baseUrl']) === '') {
$baseUrlValue = '/';
$buttonClass = (helper::baseUrl(false,false) !== $this->getData(['core', 'baseUrl']) ) ? '' : 'disabled';
} else {
$baseUrlValue = $this->getData(['core', 'baseUrl']);
$buttonClass = (helper::baseUrl(false,false) !== $this->getData(['core', 'baseUrl']) ) ? '' : 'disabled';
}
echo template::text('configManageBaseURLToConvert', [
'label' => 'Dossier d\'installation de l\'archive' ,
'value' => $baseUrlValue,
'readonly' => true,
'help' => 'Lors de la restauration d\'un backup d\'une version 9.2.10 ou supérieure, l\'URL de base est stockée dans la configuration sinon cette donnée est vide.'
]); ?>
</div>
<div class="col5">
<?php echo template::text('configManageCurrentURL', [
'label' => 'Dossier du site actuel',
'value' => helper::baseUrl(false,false),
'readonly' => true,
'help' => 'Dossier du site installé.'
]); ?>
</div>
<div class="col2 verticalAlignBottom">
<?php echo template::button('configManageUpdateBaseURLButton', [
'href' => helper::baseUrl() . 'config/updateBaseUrl',
'class' => $buttonClass,
'value' => 'convertir'
]); ?>
</div>
</div>
</div>
</div>
</div>
</div>
<?php echo template::formClose(); ?>

View File

@ -12,6 +12,7 @@
* @link http://zwiicms.com/
*/
class install extends common {
public static $actions = [
@ -40,6 +41,7 @@ class install extends common {
else {
// Soumission du formulaire
if($this->isPost()) {
//$sent = $success = false;
// Double vérification pour le mot de passe
if($this->getInput('installPassword', helper::FILTER_STRING_SHORT, true) !== $this->getInput('installConfirmPassword', helper::FILTER_STRING_SHORT, true)) {
self::$inputNotices['installConfirmPassword'] = 'Incorrect';
@ -50,35 +52,15 @@ class install extends common {
$userMail = $this->getInput('installMail', helper::FILTER_MAIL, true);
$userId = $this->getInput('installId', helper::FILTER_ID, true);
// Configure certaines données par défaut
if ($this->getInput('installDefaultData',helper::FILTER_BOOLEAN) === FALSE) {
foreach($this->getHierarchy(null, false) as $parentPageId => $childrenPageIds) {
if ( $parentPageId !== 'accueil') {
if ($this->getdata(['page',$parentPageId,'moduleId'])) {
$this->deleteData(['page',$parentPageId]);
}
}
foreach($childrenPageIds as $childKey) {
$this->deleteData(['page', $childKey]);
}
}
// Effacer les barres
$this->deleteData(['page', 'barre']);
$this->deleteData(['page', 'barrelateraleavecmenu']);
// Effacer les modules
$this->deleteData(['module']);
// Ajouter ici la liste des pages privées qui ne sont pas vues lors de l'installation.
$this->deleteData(['page', 'privee']);
// Effacer les fichiers par défaut
if (is_dir(self::FILE_DIR.'source/galerie')) {
$this->removeAll(self::FILE_DIR.'source/galerie');
$this->removeAll(self::FILE_DIR.'thumb/galerie');
}
if ($this->getInput('installDefaultData',helper::FILTER_BOOLEAN) === TRUE) {
$this->initData('page','fr',true);
$this->initData('module','fr',true);
} else {
$this->setData(['module', 'blog', 'mon-premier-article', 'userId', $userId]);
$this->setData(['module', 'blog', 'mon-deuxieme-article', 'userId', $userId]);
$this->setData(['module', 'blog', 'mon-troisieme-article', 'userId', $userId]);
}
$this->setData([
$success = $this->setData([
'user',
$userId,
[
@ -90,6 +72,7 @@ class install extends common {
'password' => $this->getInput('installPassword', helper::FILTER_PASSWORD, true)
]
]);
if ($success === true) { // Formulaire complété envoi du mail
// Envoie le mail
$sent = $this->sendMail(
$userMail,
@ -99,10 +82,12 @@ class install extends common {
'<strong>URL du site :</strong> <a href="' . helper::baseUrl(false) . '" target="_blank">' . helper::baseUrl(false) . '</a><br>' .
'<strong>Identifiant du compte :</strong> ' . $this->getInput('installId') . '<br>'
);
// Stocker le dossier d'installation
$this->setData(['core', 'baseUrl', helper::baseUrl(false,false) ]);
// Générer un fichier robots.txt
$this->createRobots();
// Créer sitemap
$this->createSitemap('all');
$this->createSitemap();
// Valeurs en sortie
$this->addOutput([
'redirect' => helper::baseUrl(false),
@ -110,6 +95,7 @@ class install extends common {
'state' => ($sent === true ? true : null)
]);
}
}
// Valeurs en sortie
$this->addOutput([

View File

@ -1,5 +1,5 @@
<?php
class install extends common {
class init extends common {
public static $defaultData = [
'config' => [
@ -9,7 +9,6 @@ class install extends common {
'favicon' => 'favicon.ico',
'homePageId' => 'accueil',
'maintenance' => false,
'metaDescription' => 'Zwii est un CMS sans base de données qui permet de créer et gérer facilement un site web sans aucune connaissance en programmation.',
'social' => [
'facebookId' => 'facebook',
'instagramId' => '',
@ -19,12 +18,13 @@ class install extends common {
'githubId' => ''
],
'timezone' => 'Europe/Paris',
'title' => 'Zwii, votre site en quelques clics !',
'itemsperPage' => 10,
'legalPageId' => ''
'legalPageId' => '',
'metaDescription' => 'Zwii est un CMS sans base de données qui permet de créer et gérer facilement un site web sans aucune connaissance en programmation.',
'title' => 'Zwii, votre site en quelques clics !'
],
'core' => [
'dataVersion' => 0,
'dataVersion' => 10000,
'lastBackup' => 0,
'lastClearTmp' => 0,
'baseUrl' => ''
@ -39,6 +39,137 @@ class install extends common {
<p>Connectez-vous dès maintenant à votre espace membre afin de créer un site à votre image ! Vous pourrez personnaliser le thème, créer des pages, ajouter des utilisateurs et bien plus encore !</p>
<p>Si vous avez besoin d\'aide ou si vous cherchez des informations sur Zwii, n\'hésitez pas à jeter un œil à notre <a title="Forum" href="https://forum.zwiicms.com/">forum</a>.</p>',
'hideTitle' => false,
'homePageId' => true,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
'moduleId' => '',
'modulePosition' => 'bottom',
'parentPageId' => '',
'position' => 1,
'group' => self::GROUP_VISITOR,
'targetBlank' => false,
'title' => 'Accueil',
'block' => '12',
'barLeft' => '',
'barRight' => '',
'displayMenu' => 'none',
'hideMenuSide' => false,
'hideMenuChildren' =>false
]
],
'module' => [],
'user' => [],
'theme' => [
'body' => [
'backgroundColor' => 'rgba(236, 239, 241, 1)',
'image' => '',
'imageAttachment' => 'scroll',
'imageRepeat' => 'no-repeat',
'imagePosition' => 'top center',
'imageSize' => 'auto'
],
'button' => [
'backgroundColor' => 'rgba(32, 59, 82, 1)'
],
'footer' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'font' => 'Open+Sans',
'fontSize' => '.8em',
'fontWeight' => 'normal',
'height' => '5px',
'loginLink' => true,
'margin' => true,
'position' => 'site',
'textColor' => 'rgba(33, 34, 35, 1)',
'copyrightPosition' => 'right',
'copyrightAlign' => 'right',
'text' => 'Pied de page personnalisé',
'textPosition' => 'left',
'textAlign' => 'left',
'textTransform' => 'none',
'socialsPosition' => 'center',
'socialsAlign' => 'center',
'displayVersion' => true,
'displayVersion' => true,
'displaySiteMap' => true,
'displayCopyright' => true,
'displayLegal' => false,
'displaySearch' => false,
'template' => '3'
],
'header' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'font' => 'Oswald',
'fontSize' => '2em',
'fontWeight' => 'normal',
'height' => '150px',
'image' => 'banniere/zwii_banniere-960px.jpg',
'imagePosition' => 'center center',
'imageRepeat' => 'no-repeat',
'margin' => false,
'position' => 'site',
'textAlign' => 'center',
'textColor' => 'rgba(33, 34, 35, 1)',
'textHide' => true,
'textTransform' => 'none',
'linkHomePage' => true,
'imageContainer' => 'auto'
],
'link' => [
'textColor' => 'rgba(74, 105, 189, 1)'
],
'menu' => [
'backgroundColor' => 'rgba(32, 59, 82, 1)',
'font' => 'Open+Sans',
'fontSize' => '1em',
'fontWeight' => 'normal',
'height' => '15px 10px',
'loginLink' => true,
'burgerTitle' => true,
'margin' => false,
'position' => 'site-second',
'textAlign' => 'left',
'textColor' => 'rgba(255, 255, 255, 1)',
'textTransform' => 'none',
'fixed' => false,
'activeColorAuto' => true,
'activeColor' => 'rgba(255, 255, 255, 1)'
],
'site' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'radius' => '0',
'shadow' => '0',
'width' => '960px'
],
'text' => [
'font' => 'Open+Sans',
'fontSize' => '13px',
'textColor' => 'rgba(33, 34, 35, 1)'
],
'title' => [
'font' => 'Oswald',
'fontWeight' => 'normal',
'textColor' => 'rgba(74, 105, 189, 1)',
'textTransform' => 'none'
],
'version' => 0,
]
];
public static $siteData = [
'page' => [
'accueil' => [
'typeMenu' => 'text',
'iconUrl' => '',
'disable' => false,
'content' => '<h3>Bienvenue sur votre nouveau site Zwii !</h3>
<p><strong>Un email contenant le récapitulatif de votre installation vient de vous être envoyé.</strong></p>
<p>Connectez-vous dès maintenant à votre espace membre afin de créer un site à votre image ! Vous pourrez personnaliser le thème, créer des pages, ajouter des utilisateurs et bien plus encore !</p>
<p>Si vous avez besoin d\'aide ou si vous cherchez des informations sur Zwii, n\'hésitez pas à jeter un œil à notre <a title="Forum" href="https://forum.zwiicms.com/">forum</a>.</p>',
'hideTitle' => false,
'homePageId' => true,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -67,6 +198,7 @@ class install extends common {
<div class="col4"><p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam interdum, neque non vulputate hendrerit, arcu turpis dapibus nisl, id scelerisque metus lectus vitae nisi. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Donec feugiat dolor et turpis finibus condimentum. Cras sit amet ligula sagittis justo.</p></div>
</div>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => true,
'metaDescription' => '',
'metaTitle' => '',
@ -94,6 +226,7 @@ class install extends common {
<div class="col6"><p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam interdum, neque non vulputate hendrerit, arcu turpis dapibus nisl, id scelerisque metus lectus vitae nisi. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Donec feugiat dolor et turpis finibus condimentum. Cras sit amet ligula sagittis justo.</p></div>
</div>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => true,
'metaDescription' => '',
'metaTitle' => '',
@ -120,6 +253,7 @@ class install extends common {
<p>Cette nouvelle fonctionnalité autorise toutes sortes d\'utilisations : texte, encadrés, images, vidéos... ou simple marge blanche. Seule restriction : on ne peut pas installer un module dans une barre latérale.</p>
<p>La liste des barres disponibles et leur emplacement s\'affichent en fonction du gabarit que vous aurez choisi.',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => true,
'metaDescription' => '',
'metaTitle' => '',
@ -145,6 +279,7 @@ class install extends common {
Deux types de menus sont disponibles : l\'un reprenant les rubriques du menu principal comme celui-ci, l\'autre listant les pages d\'une même rubrique. Le choix du type de menu se fait dans la page de configuration d\'une barre latérale.</p>
<p>Pour ajouter un menu à une page, choisissez une barre latérale avec menu dans la page de configuration. Les bulles d\'aide de la rubrique "Menu" expliquent comment masquer une page.</p>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => true,
'metaDescription' => '',
'metaTitle' => '',
@ -168,6 +303,7 @@ class install extends common {
'disable' => false,
'content' => '<p>Cette page contient une instance du module de blog. Cliquez sur un article afin de le lire et de poster des commentaires.</p>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -191,6 +327,7 @@ class install extends common {
'disable' => false,
'content' => '<p>Cette page contient une instance du module de galeries photos. Cliquez sur la galerie ci-dessous afin de voir les photos qu\'elle contient.</p>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -214,6 +351,7 @@ class install extends common {
'disable' => false,
'content' => "",
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -237,6 +375,7 @@ class install extends common {
'disable' => false,
'content' => '<p>Cette page contient un exemple de formulaire conçu à partir du module de génération de formulaires. Il est configuré pour envoyer les données saisies par mail aux administrateurs du site.</p>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -260,6 +399,7 @@ class install extends common {
'disable' => false,
'content' => '<div class="block"><h4>ZwiiCMS</h4><h3>Le CMS sans base de données à l\'installation simple et rapide</h3></div>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -283,6 +423,7 @@ class install extends common {
'disable' => false,
'content' => '<p>&nbsp;</p>',
'hideTitle' => false,
'homePageId' => false,
'breadCrumb' => false,
'metaDescription' => '',
'metaTitle' => '',
@ -351,9 +492,9 @@ class install extends common {
'directory' => self::FILE_DIR.'source/galerie/landscape'
],
'legend' => [
'desert.jpg' => 'Un désert',
'iceberg.jpg' => 'Un iceberg',
'meadow.jpg' => 'Une prairie'
'desertjpg' => 'Un désert',
'icebergjpg' => 'Un iceberg',
'meadowjpg' => 'Une prairie'
]
],
'espace' => [
@ -362,9 +503,9 @@ class install extends common {
'directory' => self::FILE_DIR.'source/galerie/space'
],
'legend' => [
'earth.jpg' => 'La Terre et la Lune',
'cosmos.jpg' => 'Le cosmos',
'nebula.jpg' => 'Une nébuleuse'
'earthjpg' => 'La Terre et la Lune',
'cosmosjpg' => 'Le cosmos',
'nebulajpg' => 'Une nébuleuse'
]
]
],
@ -405,101 +546,6 @@ class install extends common {
]
]
]
],
'user' => [],
'theme' => [
'body' => [
'backgroundColor' => 'rgba(236, 239, 241, 1)',
'image' => '',
'imageAttachment' => 'scroll',
'imageRepeat' => 'no-repeat',
'imagePosition' => 'top center',
'imageSize' => 'auto'
],
'button' => [
'backgroundColor' => 'rgba(32, 59, 82, 1)'
],
'footer' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'font' => 'Open+Sans',
'fontSize' => '.8em',
'fontWeight' => 'normal',
'height' => '5px',
'loginLink' => true,
'margin' => true,
'position' => 'site',
'textColor' => 'rgba(33, 34, 35, 1)',
'copyrightPosition' => 'right',
'copyrightAlign' => 'right',
'text' => 'Pied de page personnalisé',
'textPosition' => 'left',
'textAlign' => 'left',
'textTransform' => 'none',
'socialsPosition' => 'center',
'socialsAlign' => 'center',
'displayVersion' => true,
'displayVersion' => true,
'displaySiteMap' => true,
'displayCopyright' => true,
'displayLegal' => false,
'displaySearch' => false,
'template' => '3'
],
'header' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'font' => 'Oswald',
'fontSize' => '2em',
'fontWeight' => 'normal',
'height' => '150px',
'image' => 'banniere/zwii_banniere-960px.jpg',
'imagePosition' => 'center center',
'imageRepeat' => 'no-repeat',
'margin' => false,
'position' => 'site',
'textAlign' => 'center',
'textColor' => 'rgba(33, 34, 35, 1)',
'textHide' => true,
'textTransform' => 'none',
'linkHomePage' => true,
'imageContainer' => 'auto'
],
'link' => [
'textColor' => 'rgba(74, 105, 189, 1)'
],
'menu' => [
'backgroundColor' => 'rgba(32, 59, 82, 1)',
'font' => 'Open+Sans',
'fontSize' => '1em',
'fontWeight' => 'normal',
'height' => '15px 10px',
'loginLink' => true,
'margin' => false,
'position' => 'site-second',
'textAlign' => 'left',
'textColor' => 'rgba(255, 255, 255, 1)',
'textTransform' => 'none',
'fixed' => false,
'activeColor' => 'rgba(255, 255, 255, 1)',
'activeColorAuto' => true
],
'site' => [
'backgroundColor' => 'rgba(255, 255, 255, 1)',
'radius' => '0',
'shadow' => '0',
'width' => '960px'
],
'text' => [
'font' => 'Open+Sans',
'fontSize' => '13px',
'textColor' => 'rgba(33, 34, 35, 1)'
],
'title' => [
'font' => 'Oswald',
'fontWeight' => 'normal',
'textColor' => 'rgba(74, 105, 189, 1)',
'textTransform' => 'none'
],
'version' => 0,
]
];
}

316
core/vendor/jsondb/Dot.php vendored Normal file
View File

@ -0,0 +1,316 @@
<?php
namespace Prowebcraft;
use ArrayAccess;
/**
* Dot Notation
*
* This class provides dot notation access to arrays, so it's easy to handle
* multidimensional data in a clean way.
*/
class Dot implements ArrayAccess
{
/** @var array Data */
protected $data = [];
/**
* Constructor
*
* @param array|null $data Data
*/
public function __construct(array $data = null)
{
if (is_array($data)) {
$this->data = $data;
}
}
/**
* Get value of path, default value if path doesn't exist or all data
*
* @param array $array Source Array
* @param mixed|null $key Path
* @param mixed|null $default Default value
* @return mixed Value of path
*/
public static function getValue($array, $key, $default = null)
{
if (is_string($key)) {
// Iterate path
$keys = explode('.', $key);
foreach ($keys as $key) {
if (!isset($array[$key])) {
return $default;
}
$array = &$array[$key];
}
// Get value
return $array;
} elseif (is_null($key)) {
// Get all data
return $array;
}
return null;
}
/**
* Set value or array of values to path
*
* @param array $array Target array with data
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
*/
public static function setValue(&$array, $key, $value)
{
if (is_string($key)) {
// Iterate path
$keys = explode('.', $key);
foreach ($keys as $key) {
if (!isset($array[$key]) || !is_array($array[$key])) {
$array[$key] = [];
}
$array = &$array[$key];
}
// Set value to path
$array = $value;
} elseif (is_array($key)) {
// Iterate array of paths and values
foreach ($key as $k => $v) {
self::setValue($array, $k, $v);
}
}
}
/**
* Add value or array of values to path
*
* @param array $array Target array with data
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
* @param boolean $pop Helper to pop out last key if value is an array
*/
public static function addValue(&$array, $key, $value = null, $pop = false)
{
if (is_string($key)) {
// Iterate path
$keys = explode('.', $key);
if ($pop === true) {
array_pop($keys);
}
foreach ($keys as $key) {
if (!isset($array[$key]) || !is_array($array[$key])) {
$array[$key] = [];
}
$array = &$array[$key];
}
// Add value to path
$array[] = $value;
} elseif (is_array($key)) {
// Iterate array of paths and values
foreach ($key as $k => $v) {
self::addValue($array, $k, $v);
}
}
}
/**
* Delete path or array of paths
*
* @param array $array Target array with data
* @param mixed $key Path or array of paths to delete
*/
public static function deleteValue(&$array, $key)
{
if (is_string($key)) {
// Iterate path
$keys = explode('.', $key);
$last = array_pop($keys);
foreach ($keys as $key) {
if (!isset($array[$key])) {
return;
}
$array = &$array[$key];
}
if (isset($array[$last])) {
// Detele path
unset($array[$last]);
}
} elseif (is_array($key)) {
// Iterate array of paths
foreach ($key as $k) {
self::delete($k);
}
}
}
/**
* Get value of path, default value if path doesn't exist or all data
*
* @param mixed|null $key Path
* @param mixed|null $default Default value
* @return mixed Value of path
*/
public function get($key = null, $default = null)
{
return self::getValue($this->data, $key, $default);
}
/**
* Set value or array of values to path
*
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
*/
public function set($key, $value = null)
{
return self::setValue($this->data, $key, $value);
}
/**
* Add value or array of values to path
*
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
* @param boolean $pop Helper to pop out last key if value is an array
*/
public function add($key, $value = null, $pop = false)
{
return self::addValue($this->data, $key, $value, $pop);
}
/**
* Check if path exists
*
* @param string $key Path
* @return boolean
*/
public function has($key)
{
$keys = explode('.', (string)$key);
$data = &$this->data;
foreach ($keys as $key) {
if (!isset($data[$key])) {
return false;
}
$data = &$data[$key];
}
return true;
}
/**
* Delete path or array of paths
*
* @param mixed $key Path or array of paths to delete
*/
public function delete($key)
{
return self::deleteValue($this->data, $key);
}
/**
* Delete all data, data from path or array of paths and
* optionally format path if it doesn't exist
*
* @param mixed|null $key Path or array of paths to clean
* @param boolean $format Format option
*/
public function clear($key = null, $format = false)
{
if (is_string($key)) {
// Iterate path
$keys = explode('.', $key);
$data = &$this->data;
foreach ($keys as $key) {
if (!isset($data[$key]) || !is_array($data[$key])) {
if ($format === true) {
$data[$key] = [];
} else {
return;
}
}
$data = &$data[$key];
}
// Clear path
$data = [];
} elseif (is_array($key)) {
// Iterate array
foreach ($key as $k) {
$this->clear($k, $format);
}
} elseif (is_null($key)) {
// Clear all data
$this->data = [];
}
}
/**
* Set data
*
* @param array $data
*/
public function setData(array $data)
{
$this->data = $data;
}
/**
* Set data as a reference
*
* @param array $data
*/
public function setDataAsRef(array &$data)
{
$this->data = &$data;
}
/**
* ArrayAccess abstract methods
*/
public function offsetSet($offset, $value)
{
$this->set($offset, $value);
}
public function offsetExists($offset)
{
return $this->has($offset);
}
public function offsetGet($offset)
{
return $this->get($offset);
}
public function offsetUnset($offset)
{
$this->delete($offset);
}
/**
* Magic methods
*/
public function __set($key, $value = null)
{
$this->set($key, $value);
}
public function __get($key)
{
return $this->get($key);
}
public function __isset($key)
{
return $this->has($key);
}
public function __unset($key)
{
$this->delete($key);
}
}

138
core/vendor/jsondb/JsonDb.php vendored Normal file
View File

@ -0,0 +1,138 @@
<?php
/**
* Created by PhpStorm.
* User: Andrey Mistulov
* Company: Aristos
* Date: 14.03.2017
* Time: 15:25
*/
namespace Prowebcraft;
/**
* Class Data
* @package Aristos
*/
class JsonDb extends \Prowebcraft\Dot
{
protected $db = '';
protected $data = null;
protected $config = [];
public function __construct($config = [])
{
$this->config = array_merge([
'name' => 'data.json',
'backup' => 5,
'dir' => getcwd(),
'template' => getcwd() . DIRECTORY_SEPARATOR . 'data.template.json'
], $config);
$this->loadData();
parent::__construct();
}
/**
* Set value or array of values to path
*
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
* @param bool $save Сохранить данные в базу
* @return $this
*/
public function set($key, $value = null, $save = true)
{
parent::set($key, $value);
if ($save) $this->save();
return $this;
}
/**
* Add value or array of values to path
*
* @param mixed $key Path or array of paths and values
* @param mixed|null $value Value to set if path is not an array
* @param boolean $pop Helper to pop out last key if value is an array
* @param bool $save Сохранить данные в базу
* @return $this
*/
public function add($key, $value = null, $pop = false, $save = true)
{
parent::add($key, $value, $pop);
if ($save) $this->save();
return $this;
}
/**
* Delete path or array of paths
*
* @param mixed $key Path or array of paths to delete
* @param bool $save Сохранить данные в базу
* @return $this
*/
public function delete($key, $save = true)
{
parent::delete($key);
if ($save) $this->save();
return $this;
}
/**
* Delete all data, data from path or array of paths and
* optionally format path if it doesn't exist
*
* @param mixed|null $key Path or array of paths to clean
* @param boolean $format Format option
* @param bool $save Сохранить данные в базу
* @return $this
*/
public function clear($key = null, $format = false, $save = true)
{
parent::clear($key, $format);
if ($save) $this->save();
return $this;
}
/**
* Загрузка локальной базы данных
* @param bool $reload
* Перезагрузить данные?
* @return array|mixed|null
*/
protected function loadData($reload = false) {
if ($this->data === null || $reload) {
$this->db = $this->config['dir'] . DIRECTORY_SEPARATOR . $this->config['name'];
if (!file_exists($this->db)) {
$templateFile = $this->config['template'];
if (file_exists($templateFile)) {
copy($templateFile, $this->db);
} else {
file_put_contents($this->db, '{}');
}
} else {
if ($this->config['backup']) {
try {
//todo make backup of database
} catch (\Exception $e) {
}
}
}
$this->data = json_decode(file_get_contents($this->db), true);
if (!$this->data === null) {
throw new \InvalidArgumentException('Database file ' . $this->db
. ' contains invalid json object. Please validate or remove file');
}
}
return $this->data;
}
/**
* Сохранение в локальную базу
*/
public function save() {
file_put_contents($this->db, json_encode($this->data, JSON_UNESCAPED_UNICODE|JSON_PRETTY_PRINT));
}
}