PageRenderTime 51ms CodeModel.GetById 21ms RepoModel.GetById 1ms app.codeStats 0ms

/core/application/controllers/BackupperController.php

http://vlc-shares.googlecode.com/
PHP | 392 lines | 283 code | 85 blank | 24 comment | 65 complexity | 7e744b496dad5cd2758ca34b7aa3eb76 MD5 | raw file
Possible License(s): GPL-2.0
  1. <?php
  2. require_once 'X/Controller/Action.php';
  3. require_once 'Zend/Config.php';
  4. require_once 'Zend/Config/Xml.php';
  5. require_once 'Zend/Config/Writer/Xml.php';
  6. class BackupperController extends X_Controller_Action
  7. {
  8. function init() {
  9. parent::init();
  10. if ( !X_VlcShares_Plugins::broker()->isRegistered('backupper') ) {
  11. $this->_helper->flashMessenger(X_Env::_('p_backupper_err_pluginnotregistered'));
  12. $this->_helper->redirector('index', 'manage');
  13. }
  14. }
  15. public function indexAction() {
  16. // i need to generate a list of backupable items
  17. // reading plugin list
  18. // Core settings must be insered in first position
  19. $backuppables = array(
  20. 'backupper' => X_Env::_('p_backupper_backup_core')
  21. );
  22. $pluginList = X_VlcShares_Plugins::broker()->getPlugins();
  23. foreach ($pluginList as $pluginId => $plugin) {
  24. if ($plugin instanceof X_VlcShares_Plugins_BackuppableInterface) {
  25. // plugin is backupable
  26. $translationKey = explode('_', get_class($plugin));
  27. $translationKey = strtolower(array_pop($translationKey));
  28. $backuppables[$pluginId] = X_Env::_("p_{$translationKey}_backupper_itemlabel");
  29. }
  30. }
  31. // i need the list of backup files
  32. $restorables = array();
  33. try {
  34. $backupDir = new DirectoryIterator(APPLICATION_PATH . "/../data/backupper/");
  35. foreach ($backupDir as $entry) {
  36. if ( $entry->isFile() && pathinfo($entry->getFilename(), PATHINFO_EXTENSION) == 'xml' && X_Env::startWith($entry->getFilename(), 'backup_') ) {
  37. $restorables[$entry->getFilename()] = $entry->getFilename();
  38. X_Debug::i("Valid backup file: $entry");
  39. }
  40. }
  41. } catch ( Exception $e) {
  42. X_Debug::e("Error while parsing backupper data directory: {$e->getMessage()}");
  43. }
  44. krsort($restorables);
  45. // look in plugin config for alert.enabled status
  46. $showConfig = new Application_Model_Config();
  47. Application_Model_ConfigsMapper::i()->fetchByKey("backupper.alert.enabled", $showConfig);
  48. if ( $showConfig->getId() == null ) {
  49. $showActiveAlert = true;
  50. } else {
  51. $showActiveAlert = !((bool) $showConfig->getValue());
  52. }
  53. $this->view->showActiveAlert = $showActiveAlert;
  54. $this->view->backuppables = $backuppables;
  55. $this->view->restorables = $restorables;
  56. $this->view->messages = $this->_helper->flashMessenger->getMessages();
  57. }
  58. function backupAction() {
  59. //$message = var_export($this->getRequest()->getPost(), true);
  60. ignore_user_abort();
  61. /* @var $request Zend_Controller_Request_Http */
  62. $request = $this->getRequest();
  63. $fastAction = $request->getParam('a', false);
  64. if ( $request->isPost() || $fastAction !== false ) {
  65. $components = $request->getPost('components', array());
  66. $plugins = X_VlcShares_Plugins::broker()->getPlugins();
  67. $items = array();
  68. foreach ($plugins as $pId => $plugin ) {
  69. if (( array_key_exists($pId, $components) && ((bool) $components[$pId]) ) || $fastAction == 'all' || $fastAction == $pId) {
  70. if ( $plugin instanceof X_VlcShares_Plugins_BackuppableInterface ) {
  71. //$toBackup[$pId] = $plugin;
  72. $items[$pId] = $plugin->getBackupItems();
  73. X_Debug::i('Backuppable plugin: '.$pId);
  74. } elseif ($fastAction != 'all') {
  75. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_backup_invalidplugin'). ": $pId", 'type' => 'error' ));
  76. }
  77. } else {
  78. //X_Debug::i('Discarded plugin: '.$pId);
  79. }
  80. }
  81. //$this->_helper->flashMessenger(var_export($items, true));
  82. if ( count($items) ) {
  83. $writer = new Zend_Config_Writer_Xml();
  84. $date = date("Y-m-d_H-i-s");
  85. $type = $fastAction !== false ? $fastAction : 'custom';
  86. $data['metadata'] = array(
  87. 'version' => X_VlcShares::VERSION,
  88. 'created' => date('d/m/Y H:i:s'),
  89. 'decrypt' => 'backupper_decodevalues_0_5_5'
  90. );
  91. $data['plugins'] = $items;
  92. $filename = APPLICATION_PATH . "/../data/backupper/backup_{$date}_{$type}.xml";
  93. $data['plugins'] = array_map('backupper_encodevalues', $data['plugins']);
  94. $configs = new Zend_Config($data);
  95. $writer->setFilename($filename);
  96. try {
  97. $writer->write(null, $configs, true);
  98. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_backup_done'), 'type' => 'info' ));
  99. } catch (Exception $e) {
  100. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_writefile').": {$e->getMessage()}", 'type' => 'error' ));
  101. }
  102. } else {
  103. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_backup_nobackupactionneeded'), 'type' => 'warning' ));
  104. }
  105. }
  106. //$this->_helper->flashMessenger($message);
  107. $this->_helper->redirector('index', 'backupper');
  108. }
  109. function rinfoAction() {
  110. /* @var $request Zend_Controller_Request_Http */
  111. $request = $this->getRequest();
  112. //$fastAction = $request->getParam('a', false);
  113. if ( ! ( $request->isPost()
  114. && ($file = $request->getPost('file', false)) !== false
  115. && X_Env::startWith(realpath(APPLICATION_PATH . "/../data/backupper/$file"), realpath(APPLICATION_PATH . "/../data/backupper/")) // this ensure no ../
  116. && file_exists(APPLICATION_PATH . "/../data/backupper/$file") ) ) {
  117. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_invalidrestorefile'), 'type' => 'error' ));
  118. $this->_helper->redirector('index', 'backupper');
  119. }
  120. //$data = file_get_contents(APPLICATION_PATH . "/../data/backupper/$file");
  121. //@$data['plugins'] = array_map('backupper_decodevalues_0_5_3', $data['plugins']);
  122. //$backup = new Zend_Config_Xml($data);
  123. try {
  124. /* @var $backuppedData Zend_Config_Xml */
  125. $backup = new Zend_Config_Xml(APPLICATION_PATH . "/../data/backupper/$file");
  126. $decryptFunction = $backup->metadata->get('decrypt', false);
  127. if ( $decryptFunction !== false ) {
  128. if ( function_exists($decryptFunction) ) {
  129. $arrayBackuppedData = $backup->toArray();
  130. $arrayBackuppedData['plugins'] = array_map($decryptFunction, $arrayBackuppedData['plugins']);
  131. } else {
  132. throw new Exception("Unknown decryption function: $decryptFunction");
  133. }
  134. $backup = new Zend_Config($arrayBackuppedData);
  135. }
  136. } catch (Exception $e) {
  137. X_Debug::e("Error while restoring: {$e->getMessage()}");
  138. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_malformedrestorefile'), 'type' => 'error' ));
  139. $this->_helper->redirector('index', 'backupper');
  140. }
  141. try {
  142. $plugins = array();
  143. $pluginList = X_VlcShares_Plugins::broker()->getPlugins();
  144. $backupPlugins = $backup->plugins->toArray();
  145. foreach ($pluginList as $pluginId => $plugin) {
  146. if ($plugin instanceof X_VlcShares_Plugins_BackuppableInterface) {
  147. // plugin is backupable
  148. $translationKey = explode('_', get_class($plugin));
  149. $translationKey = strtolower(array_pop($translationKey));
  150. if ( array_key_exists($pluginId, $backupPlugins) ) {
  151. $plugins[$pluginId] = X_Env::_("p_{$translationKey}_backupper_itemlabel");
  152. }
  153. }
  154. }
  155. $this->view->components = $plugins;
  156. $this->view->file = $file;
  157. $this->view->created = $backup->metadata->created;
  158. $this->view->version = $backup->metadata->version;
  159. } catch (Exception $e) {
  160. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_malformedrestorefile'), 'type' => 'error' ));
  161. }
  162. }
  163. function restoreAction() {
  164. ignore_user_abort();
  165. /* @var $request Zend_Controller_Request_Http */
  166. $request = $this->getRequest();
  167. if ( $request->isPost() ) {
  168. $file = $request->getPost('file', false);
  169. if ( $file === false
  170. || !X_Env::startWith(realpath(APPLICATION_PATH . "/../data/backupper/$file"), realpath(APPLICATION_PATH . "/../data/backupper/")) // this ensure no ../
  171. || !file_exists(APPLICATION_PATH . "/../data/backupper/$file")) {
  172. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_invalidrestorefile'), 'type' => 'warning' ));
  173. $this->_helper->redirector('index', 'backupper');
  174. }
  175. try {
  176. /* @var $backuppedData Zend_Config_Xml */
  177. $backuppedData = new Zend_Config_Xml(APPLICATION_PATH . "/../data/backupper/$file");
  178. $decryptFunction = $backuppedData->metadata->get('decrypt', false);
  179. if ( $decryptFunction !== false ) {
  180. if ( function_exists($decryptFunction) ) {
  181. $arrayBackuppedData = $backuppedData->toArray();
  182. $arrayBackuppedData['plugins'] = array_map($decryptFunction, $arrayBackuppedData['plugins']);
  183. } else {
  184. throw new Exception("Unknown decryption function: $decryptFunction");
  185. }
  186. $backuppedData = new Zend_Config($arrayBackuppedData);
  187. }
  188. } catch (Exception $e) {
  189. X_Debug::e("Error while restoring: {$e->getMessage()}");
  190. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_malformedrestorefile'), 'type' => 'error' ));
  191. $this->_helper->redirector('index', 'backupper');
  192. }
  193. //die('<pre>'.var_export($backuppedData->toArray(), true).'</pre>');
  194. $components = $request->getPost('components', array());
  195. if ( count($components) ) {
  196. $plugins = X_VlcShares_Plugins::broker()->getPlugins();
  197. $items = array();
  198. foreach ($plugins as $pId => $plugin ) {
  199. if ( array_key_exists($pId, $components) && ((bool) $components[$pId]) ) {
  200. if ( $plugin instanceof X_VlcShares_Plugins_BackuppableInterface ) {
  201. //$toBackup[$pId] = $plugin;
  202. try {
  203. $data = $backuppedData->plugins->$pId;
  204. if ( !is_object($data) || !method_exists($data, 'toArray') ) {
  205. $data = array();
  206. } else {
  207. $data = $data->toArray();
  208. }
  209. $returned = $plugin->restoreItems($data);
  210. X_Debug::i("Plugins $pId restored");
  211. if ( $returned ) {
  212. $this->_helper->flashMessenger(array('text' => $returned, 'type' => 'info' ));
  213. } else {
  214. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_restore_done_plugin').": $pId", 'type' => 'info' ));
  215. }
  216. } catch (Exception $e) {
  217. X_Debug::e("Error restoring $pId: {$e->getMessage()}");
  218. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_pluginnotrestored').": $pId, {$e->getMessage()}", 'type' => 'error' ));
  219. }
  220. }
  221. }
  222. }
  223. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_restore_done'), 'type' => 'info' ));
  224. } else {
  225. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_restore_norestoreactionneeded'), 'type' => 'warning' ));
  226. }
  227. }
  228. $this->_helper->redirector('index', 'backupper');
  229. }
  230. function alertAction() {
  231. $status = $this->getRequest()->getParam('status', false);
  232. $config = new Application_Model_Config();
  233. Application_Model_ConfigsMapper::i()->fetchByKey("backupper.alert.enabled", $config);
  234. if ( $config->getId() == null ) {
  235. // i need to add a new config, yeah!
  236. $config->setKey('backupper.alert.enabled')
  237. ->setValue(1)
  238. ->setDefault(1)
  239. ->setSection('plugins')
  240. ->setType(Application_Model_Config::TYPE_BOOLEAN);
  241. }
  242. switch ($status) {
  243. case 'on':
  244. $config->setValue(1);
  245. break;
  246. case 'off':
  247. $config->setValue(0);
  248. break;
  249. default:
  250. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_unknownstatus'), 'type' => 'error' ));
  251. $this->_helper->redirector('index', 'backupper');
  252. break;
  253. }
  254. try {
  255. Application_Model_ConfigsMapper::i()->save($config);
  256. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_alertstatuschanged'), 'type' => 'info' ));
  257. } catch (Exception $e) {
  258. X_Debug::e('Unable to store alert.enabled status: '.$e->getMessage());
  259. $this->_helper->flashMessenger(array('text' => X_Env::_('p_backupper_err_dberror').": {$e->getMessage()}", 'type' => 'error' ));
  260. }
  261. $this->_helper->redirector('index', 'backupper');
  262. }
  263. }
  264. if ( !function_exists('backupper_encodevalues') ) {
  265. function backupper_encodevalues($value) {
  266. if ( is_array($value) ) {
  267. $_changed = array();
  268. foreach ($value as $k => $v) {
  269. if ( preg_match('/^[^a-z].*/i', $k) > 0 ) {
  270. $k = "_$k";
  271. }
  272. $_changed[$k] = backupper_encodevalues($v);
  273. }
  274. return $_changed;
  275. } else {
  276. return base64_encode($value);
  277. }
  278. }
  279. }
  280. if ( !function_exists('backupper_decodevalues_0_5_5') ) {
  281. function backupper_decodevalues_0_5_5($value) {
  282. if ( is_array($value) ) {
  283. $_changed = array();
  284. foreach ($value as $k => $v) {
  285. if ( X_Env::startWith($k, '_') ) {
  286. $k = substr($k, 1);
  287. }
  288. $_changed[$k] = backupper_decodevalues_0_5_5($v);
  289. }
  290. return $_changed;
  291. } else {
  292. return base64_decode($value);
  293. }
  294. }
  295. }
  296. if ( !function_exists('backupper_decodevalues_0_5_3') ) {
  297. function backupper_decodevalues_0_5_3($value) {
  298. if ( is_array($value) ) {
  299. foreach ($value as $k => $v) {
  300. $value[$k] = backupper_decodevalues_0_5_3($v);
  301. }
  302. return $value;
  303. } else {
  304. return base64_decode($value);
  305. }
  306. }
  307. }