1: <?php
2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15:
16:
17: defined('CON_FRAMEWORK') || die('Illegal call: Missing framework initialization - request aborted.');
18:
19: cInclude('includes', 'functions.api.string.php');
20: cInclude('includes', 'functions.con.php');
21:
22: 23: 24: 25: 26: 27: 28: 29:
30: class cModuleSynchronizer extends cModuleHandler {
31:
32: 33: 34: 35: 36:
37: private $_lastIdMod = 0;
38:
39: 40: 41: 42: 43: 44: 45: 46:
47: private function _syncModule($dir, $oldModulName, $newModulName) {
48: global $client;
49:
50: if ($this->_isExistInTable($oldModulName, $client) == false) {
51:
52: $this->_addModul($newModulName, $client);
53: cRegistry::appendLastInfoMessage(sprintf(i18n('Module %s successfully synchronized'), $newModulName));
54: } else {
55:
56: if ($oldModulName != $newModulName) {
57: $this->_updateModulnameInDb($oldModulName, $newModulName, $client);
58: }
59: }
60: }
61:
62: 63: 64: 65: 66: 67: 68:
69: private function _renameFiles($dir, $oldModulName, $newModulName) {
70: if (cFileHandler::exists($dir . $newModulName . '/' . $this->_directories['php'] . $oldModulName . '_input.php') == true) {
71: rename($dir . $newModulName . '/' . $this->_directories['php'] . $oldModulName . '_input.php', $dir . $newModulName . '/' . $this->_directories['php'] . $newModulName . '_input.php');
72: }
73:
74: if (cFileHandler::exists($dir . $newModulName . '/' . $this->_directories['php'] . $oldModulName . '_output.php') == true) {
75: rename($dir . $newModulName . '/' . $this->_directories['php'] . $oldModulName . '_output.php', $dir . $newModulName . '/' . $this->_directories['php'] . $newModulName . '_output.php');
76: }
77:
78: if (cFileHandler::exists($dir . $newModulName . '/' . $this->_directories['css'] . $oldModulName . '.css') == true) {
79: rename($dir . $newModulName . '/' . $this->_directories['css'] . $oldModulName . '.css', $dir . $newModulName . '/' . $this->_directories['css'] . $newModulName . '.css');
80: }
81:
82: if (cFileHandler::exists($dir . $newModulName . '/' . $this->_directories['js'] . $oldModulName . '.js') == true) {
83: rename($dir . $newModulName . '/' . $this->_directories['js'] . $oldModulName . '.js', $dir . $newModulName . '/' . $this->_directories['js'] . $newModulName . '.js');
84: }
85: }
86:
87: 88: 89: 90: 91: 92: 93: 94: 95:
96: private function _renameFileAndDir($dir, $dirNameOld, $dirNameNew, $client) {
97: if (rename($dir . $dirNameOld, $dir . $dirNameNew) == FALSE) {
98: return false;
99: } else {
100: $this->_renameFiles($dir, $dirNameOld, $dirNameNew);
101: }
102: return true;
103: }
104:
105: 106: 107: 108: 109: 110:
111: public function compareFileAndModuleTimestamp() {
112: global $cfg, $cfgClient;
113:
114: $synchLock = 0;
115:
116: $sql = sprintf('SELECT UNIX_TIMESTAMP(mod1.lastmodified) AS lastmodified,mod1.idclient,description,type, mod1.name, mod1.alias, mod1.idmod FROM %s AS mod1 WHERE mod1.idclient = %s', $this->_cfg['tab']['mod'], $this->_client);
117: $notification = new cGuiNotification();
118:
119: $db = cRegistry::getDb();
120: $db->query($sql);
121: $retIdMod = 0;
122:
123: while ($db->nextRecord()) {
124: $showMessage = false;
125:
126: $modulePath = $cfgClient[$db->f('idclient')]['module']['path'] . $db->f('alias') . '/';
127: $modulePHP = $modulePath . $this->_directories['php'] . $db->f('alias');
128:
129: $lastmodified = $db->f('lastmodified');
130:
131: $lastmodInput = $lastmodOutput = 0;
132:
133: if (cFileHandler::exists($modulePHP . '_input.php')) {
134: $lastmodInput = filemtime($modulePHP . '_input.php');
135: }
136:
137: if (cFileHandler::exists($modulePHP . '_output.php')) {
138: $lastmodOutput = filemtime($modulePHP . '_output.php');
139: }
140:
141: if (cFileHandler::exists($modulePath . "info.xml")) {
142: $lastModInfo = filemtime($modulePath . "info.xml");
143: if ($lastModInfo > $lastmodified) {
144: $modInfo = cXmlBase::xmlStringToArray(cFileHandler::read($modulePath . "info.xml"));
145: $mod = new cApiModule($db->f("idmod"));
146: if ($modInfo["description"] != $mod->get("description")) {
147: $mod->set("description", $modInfo["description"]);
148: $this->setLastModified($lastModInfo, $db->f('idmod'));
149: }
150: if ($modInfo["type"] != $mod->get("type")) {
151: $mod->set("type", $modInfo["type"]);
152: $this->setLastModified($lastModInfo, $db->f('idmod'));
153: }
154:
155: if ($modInfo["name"] != $mod->get("name")) {
156: $mod->set("name", $modInfo["name"]);
157: $this->setLastModified($lastModInfo, $db->f('idmod'));
158: }
159:
160: if ($modInfo["alias"] != $mod->get("alias")) {
161: $mod->set("alias", $modInfo["alias"]);
162: $this->setLastModified($lastModInfo, $db->f('idmod'));
163: }
164: $mod->store();
165: $synchLock = 1;
166: $showMessage = true;
167: }
168: }
169:
170: $lastmodabsolute = max($lastmodInput, $lastmodOutput);
171: if ($lastmodified < $lastmodabsolute) {
172:
173: $synchLock = 1;
174: $this->setLastModified($lastmodabsolute, $db->f('idmod'));
175: conGenerateCodeForAllArtsUsingMod($db->f('idmod'));
176: $showMessage = true;
177: }
178:
179: if (($idmod = $this->_synchronizeFilesystemAndDb($db)) != 0) {
180: $retIdMod = $idmod;
181: }
182:
183: if ($showMessage) {
184: cRegistry::appendLastInfoMessage(sprintf(i18n('Module %s successfully synchronized'), $db->f('name')));
185: }
186: }
187:
188: if ($synchLock == 0) {
189: cRegistry::addInfoMessage(i18n('All modules are already synchronized'));
190: }
191:
192:
193: return $retIdMod;
194: }
195:
196: 197: 198: 199: 200: 201: 202: 203: 204: 205:
206: private function _synchronizeFilesystemAndDb($db) {
207: $returnIdMod = 0;
208: $this->initWithDatabaseRow($db);
209:
210: if ($this->modulePathExists() == false) {
211: $modul = new cApiModule($db->f('idmod'));
212: $returnIdMod = $db->f('idmod');
213: if ($modul->moduleInUse($db->f('idmod')) == true) {
214:
215: if ($this->createModule() == false) {
216: $notification = new cGuiNotification();
217: $notification->displayNotification('error', i18n("Can not create module") . " " . $db->f('name'));
218: }
219: } else {
220:
221: $sql = sprintf('DELETE FROM %s WHERE idmod = %s AND idclient = %s', $this->_cfg['tab']['mod'], $db->f('idmod'), $this->_client);
222: $myDb = cRegistry::getDb();
223: $myDb->query($sql);
224: }
225: }
226: return $returnIdMod;
227: }
228:
229: 230: 231: 232: 233: 234:
235: private function _isValidFirstChar($file) {
236: if (substr($file, 0, 1) == '.') {
237: return false;
238: } else {
239: return true;
240: }
241: }
242:
243: 244: 245: 246: 247: 248: 249: 250:
251: public function synchronize() {
252: global $cfg, $cfgClient;
253:
254:
255: $dir = $cfgClient[$this->_client]['module']['path'];
256:
257: if (is_dir($dir)) {
258: if ($dh = opendir($dir)) {
259: while (($file = readdir($dh)) !== false) {
260:
261: if ($this->_isValidFirstChar($file) && is_dir($dir . $file . '/')) {
262: $newFile = cApiStrCleanURLCharacters($file);
263:
264: if ($newFile == $file) {
265: $this->_syncModule($dir, $file, $newFile);
266: } else {
267: if (is_dir($dir . $newFile)) {
268:
269:
270: $newDirName = $newFile . substr(md5(time() . rand(0, time())), 0, 4);
271:
272:
273: if ($this->_renameFileAndDir($dir, $file, $newDirName, $this->_client) != false) {
274: $this->_syncModule($dir, $file, $newDirName);
275: }
276: } else {
277:
278: if ($this->_renameFileAndDir($dir, $file, $newFile, $this->_client) != false) {
279: $this->_syncModule($dir, $file, $newFile);
280: }
281: }
282: }
283: }
284: }
285: }
286:
287:
288: closedir($dh);
289: }
290:
291:
292: return $this->_lastIdMod;
293: }
294:
295: 296: 297: 298: 299: 300: 301: 302: 303: 304: 305:
306: private function _isExistInTable($alias, $idclient) {
307: $db = cRegistry::getDb();
308:
309:
310: $sql = sprintf("SELECT * FROM %s WHERE alias='%s' AND idclient=%s", $this->_cfg['tab']['mod'], $alias, $idclient);
311:
312: $db->query($sql);
313:
314:
315: if ($db->nextRecord()) {
316: return true;
317: } else {
318: return false;
319: }
320: }
321:
322: 323: 324: 325: 326: 327: 328:
329: private function _updateModulnameInDb($oldName, $newName, $idclient) {
330: $db = cRegistry::getDb();
331:
332:
333: $sql = sprintf("SELECT * FROM %s WHERE alias='%s' AND idclient=%s", $this->_cfg['tab']['mod'], $oldName, $idclient);
334:
335: $db->query($sql);
336:
337:
338: if ($db->nextRecord()) {
339: $sqlUpdateName = sprintf("UPDATE %s SET alias='%s' WHERE idmod=%s", $this->_cfg['tab']['mod'], $newName, $db->f('idmod'));
340: $db->query($sqlUpdateName);
341: return;
342: }
343: }
344:
345: 346: 347: 348: 349: 350:
351: private function _addModul($name, $idclient) {
352:
353: $oModColl = new cApiModuleCollection();
354: $oMod = $oModColl->create($name, $idclient, $name);
355: if (is_object($oMod)) {
356:
357: $this->_lastIdMod = $oMod->get('idmod');
358: }
359: }
360:
361: 362: 363: 364: 365: 366:
367: public function setLastModified($timestamp, $idmod) {
368: $oMod = new cApiModule((int) $idmod);
369: if ($oMod->isLoaded()) {
370: $oMod->set('lastmodified', date('Y-m-d H:i:s', $timestamp));
371: $oMod->store();
372: }
373: }
374:
375: }
376: