Index: branches/5.1.x/core/install/install_data.sql =================================================================== diff -u -N -r14364 -r14402 --- branches/5.1.x/core/install/install_data.sql (.../install_data.sql) (revision 14364) +++ branches/5.1.x/core/install/install_data.sql (.../install_data.sql) (revision 14402) @@ -962,5 +962,5 @@ #INSERT INTO PageContent VALUES (DEFAULT, 1, 1, 'In-portal is a revolutionary Web Site management system that allows you to automate and facilitate management of large portal and community web sites. Regardless of whether you are running a directory site or a content news portal, a community site or an online mall, In-portal will enhance your web site management experience with innovative.

We are proud to present our newly developed "default" theme that introduces a fresh look as well totally new approach in the template system.
', NULL, NULL, NULL, NULL, 0, 0, 0, 0, 0); -INSERT INTO Modules VALUES ('Core', 'core/', 'adm', DEFAULT, 1, 1, '', 0, NULL); -INSERT INTO Modules VALUES ('In-Portal', 'core/', 'm', DEFAULT, 1, 0, '', 0, NULL); \ No newline at end of file +INSERT INTO Modules VALUES ('Core', 'core/', 'adm', DEFAULT, 1, 1, '', 0, NULL, NULL); +INSERT INTO Modules VALUES ('In-Portal', 'core/', 'm', DEFAULT, 1, 0, '', 0, NULL, NULL); \ No newline at end of file Index: branches/5.1.x/core/admin_templates/tools/system_tools.tpl =================================================================== diff -u -N -r14241 -r14402 --- branches/5.1.x/core/admin_templates/tools/system_tools.tpl (.../system_tools.tpl) (revision 14241) +++ branches/5.1.x/core/admin_templates/tools/system_tools.tpl (.../system_tools.tpl) (revision 14402) @@ -115,6 +115,29 @@
+ +
+
+
+

+
+ +
+ "/> +
+ +
+

+
+ +
+ "/> +
+
+
+ +
+
Index: branches/5.1.x/core/install/install_schema.sql =================================================================== diff -u -N -r14332 -r14402 --- branches/5.1.x/core/install/install_schema.sql (.../install_schema.sql) (revision 14332) +++ branches/5.1.x/core/install/install_schema.sql (.../install_schema.sql) (revision 14402) @@ -1,7 +1,7 @@ CREATE TABLE PermissionConfig ( PermissionConfigId int(11) NOT NULL auto_increment, PermissionName varchar(30) NOT NULL default '', - Description varchar(255) NOT NULL default '', + Description varchar(255) NOT NULL default '', ModuleId varchar(20) NOT NULL default '0', PRIMARY KEY (PermissionConfigId), KEY PermissionName (PermissionName) @@ -155,16 +155,17 @@ ); CREATE TABLE Modules ( - `Name` varchar(255) NOT NULL default '', - Path varchar(255) NOT NULL default '', - `Var` VARCHAR(100) NOT NULL DEFAULT '', - Version varchar(10) NOT NULL default '0.0.0', - Loaded tinyint(4) NOT NULL default '1', - LoadOrder tinyint(4) NOT NULL default '0', - TemplatePath varchar(255) NOT NULL default '', - RootCat int(11) NOT NULL default '0', - BuildDate int(10) unsigned default NULL, - PRIMARY KEY (`Name`), + `Name` varchar(255) NOT NULL DEFAULT '', + Path varchar(255) NOT NULL DEFAULT '', + Var varchar(100) NOT NULL DEFAULT '', + Version varchar(10) NOT NULL DEFAULT '0.0.0', + Loaded tinyint(4) NOT NULL DEFAULT '1', + LoadOrder tinyint(4) NOT NULL DEFAULT '0', + TemplatePath varchar(255) NOT NULL DEFAULT '', + RootCat int(11) NOT NULL DEFAULT '0', + BuildDate int(10) unsigned DEFAULT NULL, + AppliedDBRevisions text, + PRIMARY KEY (`Name`), KEY Loaded (Loaded), KEY LoadOrder (LoadOrder) ); Index: branches/5.1.x/core/install/upgrades.sql =================================================================== diff -u -N -r14364 -r14402 --- branches/5.1.x/core/install/upgrades.sql (.../upgrades.sql) (revision 14364) +++ branches/5.1.x/core/install/upgrades.sql (.../upgrades.sql) (revision 14402) @@ -2020,4 +2020,7 @@ # ===== v 5.1.3-B1 ===== ALTER TABLE FormSubmissions CHANGE ReferrerURL ReferrerURL TEXT NULL; -INSERT INTO ConfigurationValues VALUES (DEFAULT, 'UserEmailActivationTimeout', '', 'In-Portal:Users', 'in-portal:configure_users', 'la_title_General', 'la_config_UserEmailActivationTimeout', 'text', NULL, NULL, 10.051, 0, 0, NULL); \ No newline at end of file +INSERT INTO ConfigurationValues VALUES (DEFAULT, 'UserEmailActivationTimeout', '', 'In-Portal:Users', 'in-portal:configure_users', 'la_title_General', 'la_config_UserEmailActivationTimeout', 'text', NULL, NULL, 10.051, 0, 0, NULL); + +# ===== v 5.1.3-B2 ===== +ALTER TABLE Modules ADD AppliedDBRevisions TEXT NULL; \ No newline at end of file Index: branches/5.1.x/core/units/helpers/deployment_helper.php =================================================================== diff -u -N --- branches/5.1.x/core/units/helpers/deployment_helper.php (revision 0) +++ branches/5.1.x/core/units/helpers/deployment_helper.php (revision 14402) @@ -0,0 +1,386 @@ +Conn->qstr( $this->moduleName ); + $revisions = $this->Conn->GetOne($sql); + + $this->appliedRevisions = $revisions ? explode(',', $revisions) : Array (); + } + + private function saveAppliedRevisions() + { + // maybe optimize + sort($this->appliedRevisions); + + $fields_hash = Array ( + 'AppliedDBRevisions' => implode(',', $this->appliedRevisions), + ); + + $this->Conn->doUpdate($fields_hash, TABLE_PREFIX . 'Modules', '`Name` = ' . $this->Conn->qstr($this->moduleName)); + } + + public function deployAll($dry_run = false) + { + $this->dryRun = $dry_run; + $this->lineEnding = $dry_run ? '
' . PHP_EOL : PHP_EOL; + + $ret = true; + + foreach ($this->Application->ModuleInfo as $module_name => $module_info) { + $this->moduleName = $module_name; + + if ( !file_exists($this->getModuleFile('project_upgrades.sql')) ) { + continue; + } + + $ret = $ret && $this->deploy($module_name); + } + + if (!$this->dryRun) { + $this->resetCaches(); + $this->refreshThemes(); + } + + return $ret; + } + + /** + * Deploys pending changes to a site + * + */ + private function deploy($module_name) + { + echo 'Deploying Module "' . $module_name . '":' . $this->lineEnding; + + echo 'Upgrading Database ... '; + if ( !$this->upgradeDatabase() ) { + return false; + } + + echo 'OK' . $this->lineEnding; + + $this->importLanguagePack(); + + echo 'Done.' . $this->lineEnding; + + return true; + } + + /** + * Import latest languagepack (without overwrite) + * + */ + private function importLanguagePack() + { + $language_import_helper =& $this->Application->recallObject('LanguageImportHelper'); + /* @var $language_import_helper LanguageImportHelper */ + + echo 'Importing LanguagePack ... '; + $filename = $this->getModuleFile('english.lang'); + $language_import_helper->performImport($filename, '|0|1|2|', $this->moduleName, LANG_SKIP_EXISTING); + echo 'OK' . $this->lineEnding; + } + + /** + * Resets unit and section cache + * + */ + private function resetCaches() + { + // 2. reset unit config cache (so new classes get auto-registered) + echo 'Resetting Unit Config Cache ... '; + $admin_event = new kEvent('adm:OnResetConfigsCache'); + $this->Application->HandleEvent($admin_event); + echo 'OK' . $this->lineEnding; + + // 3. reset sections cache + echo 'Resetting Sections Cache ... '; + $admin_event = new kEvent('adm:OnResetSections'); + $this->Application->HandleEvent($admin_event); + echo 'OK' . $this->lineEnding; + } + + /** + * Rebuild theme files + * + */ + private function refreshThemes() + { + echo 'Rebuilding Theme Files ... '; + $admin_event = new kEvent('adm:OnRebuildThemes'); + $this->Application->HandleEvent($admin_event); + echo 'OK' . $this->lineEnding; + } + + /** + * Runs database upgrade script + * + * @return bool + */ + private function upgradeDatabase() + { + $this->loadAppliedRevisions(); + $this->Conn->errorHandler = Array(&$this, 'handleSqlError'); + + if ( !$this->collectDatabaseRevisions() || !$this->checkRevisionDependencies() ) { + return false; + } + + $applied = $this->applyRevisions(); + $this->saveAppliedRevisions(); + + return $applied; + } + + /** + * Collects database revisions from "project_upgrades.sql" file. + * + * @return bool + */ + private function collectDatabaseRevisions() + { + $filename = $this->getModuleFile('project_upgrades.sql'); + + if ( !file_exists($filename) ) { + return true; + } + + $sqls = file_get_contents($filename); + preg_match_all("/# r([\d]+)([^\:]*):.*?(\n|$)/s", $sqls, $matches, PREG_SET_ORDER + PREG_OFFSET_CAPTURE); + + if (!$matches) { + echo 'No Database Revisions Found' . $this->lineEnding; + + return false; + } + + foreach ($matches as $index => $match) { + $revision = $match[1][0]; + + if ( $this->revisionApplied($revision) ) { + // skip applied revisions + continue; + } + + if ( isset($this->revisionSqls[$revision]) ) { + // duplicate revision among non-applied ones + echo 'Duplicate revision ' . $revision . ' found' . $this->lineEnding; + + return false; + } + + // get revision sqls + $start_pos = $match[0][1] + strlen($match[0][0]); + $end_pos = isset($matches[$index + 1]) ? $matches[$index + 1][0][1] : strlen($sqls); + $revision_sqls = substr($sqls, $start_pos, $end_pos - $start_pos); + + if (!$revision_sqls) { + // resision without sqls + continue; + } + + $this->revisionSqls[$revision] = $revision_sqls; + $revision_lependencies = $this->parseRevisionDependencies($match[2][0]); + + if ($revision_lependencies) { + $this->revisionDependencies[$revision] = $revision_lependencies; + } + } + + ksort($this->revisionSqls); + ksort($this->revisionDependencies); + + return true; + } + + /** + * Checks that all dependent revisions are either present now OR were applied before + * + * @return bool + */ + private function checkRevisionDependencies() + { + foreach ($this->revisionDependencies as $revision => $revision_dependencies) { + foreach ($revision_dependencies as $revision_dependency) { + if ( $this->revisionApplied($revision_dependency) ) { + // revision dependend upon already applied -> depencency fulfilled + continue; + } + + if ($revision_dependency >= $revision) { + echo 'Revision ' . $revision . ' has incorrect dependency to revision ' . $revision_dependency . '. Only dependencies to older revisions are allowed!' . $this->lineEnding; + + return false; + } + + if ( !isset($this->revisionSqls[$revision_dependency]) ) { + echo 'Revision ' . $revision . ' depends on missing revision ' . $revision_dependency . '!' . $this->lineEnding; + + return false; + } + } + } + + return true; + } + + /** + * Runs all pending sqls + * + * @return bool + */ + private function applyRevisions() + { + if (!$this->revisionSqls) { + return true; + } + + if ($this->dryRun) { + $this->appliedRevisions = array_merge($this->appliedRevisions, array_keys($this->revisionSqls)); + + return true; + } + + echo $this->lineEnding; + + foreach ($this->revisionSqls as $revision => $sqls) { + echo 'Processing DB Revision: #' . $revision . ' ... '; + + $sqls = str_replace("\r\n", "\n", $sqls); // convert to linux line endings + $no_comment_sqls = preg_replace("/#\s([^;]*?)\n/is", '', $sqls); // remove all comments "#" on new lines + + $sqls = explode(";\n", $no_comment_sqls . "\n"); // ensures that last sql won't have ";" in it + $sqls = array_map('trim', $sqls); + + foreach ($sqls as $index => $sql) { + if (!$sql || (substr($sql, 0, 1) == '#')) { + continue; // usually last line + } + + $this->Conn->Query($sql); + + if ( $this->Conn->hasError() ) { + // consider revisions with errors applied + $this->appliedRevisions[] = $revision; + + return false; + } + } + + $this->appliedRevisions[] = $revision; + echo 'OK' . $this->lineEnding; + } + + return true; + } + + /** + * Error handler for sql errors + * + * @param int $code + * @param string $msg + * @param string $sql + * @return bool + */ + public function handleSqlError($code, $msg, $sql) + { + echo 'Error (#' . $code . ': ' . $msg . ') during SQL processing:' . $this->lineEnding . $sql . $this->lineEnding; + echo 'Please execute rest of sqls in this revision by hand and run deployment script again.' . $this->lineEnding; + + return true; + } + + /** + * Checks if given revision was already applied + * + * @param int $revision + * @return bool + */ + private function revisionApplied($revision) + { + foreach ($this->appliedRevisions as $applied_revision) { + // revision range + $applied_revision = explode('-', $applied_revision, 2); + + if ( !isset($applied_revision[1]) ) { + // convert single revision to revision range + $applied_revision[1] = $applied_revision[0]; + } + + if ( $revision >= $applied_revision[0] && $revision <= $applied_revision[1] ) { + return true; + } + } + + return false; + } + + /** + * Returns path to given file in current module install folder + * + * @param string $filename + * @return string + */ + private function getModuleFile($filename) + { + $module_folder = $this->Application->findModule('Name', $this->moduleName, 'Path'); + + return FULL_PATH . DIRECTORY_SEPARATOR . $module_folder . 'install/' . $filename; + } + + /** + * Extracts revisions from string in format "(1,3,5464,23342,3243)" + * + * @param string $string + * @return Array + */ + private function parseRevisionDependencies($string) + { + if (!$string) { + return Array (); + } + + $string = explode(',', substr($string, 1, -1)); + + return array_map('trim', $string); + } +} \ No newline at end of file Index: branches/5.1.x/tools/run_event.php =================================================================== diff -u -N --- branches/5.1.x/tools/run_event.php (revision 0) +++ branches/5.1.x/tools/run_event.php (revision 14402) @@ -0,0 +1,50 @@ +Init(); + +$application->StoreVar('user_id', USER_ROOT, true); +$application->HandleEvent($ev, $argv[1]); // event name in form "prefix[.special]:event_name" + +$application->Done(); + +$end = getmicrotime(); + +function getmicrotime() +{ + list($usec, $sec) = explode(" ", microtime()); + return ((float)$usec + (float)$sec); +} Index: branches/5.1.x/core/units/admin/admin_events_handler.php =================================================================== diff -u -N -r14326 -r14402 --- branches/5.1.x/core/units/admin/admin_events_handler.php (.../admin_events_handler.php) (revision 14326) +++ branches/5.1.x/core/units/admin/admin_events_handler.php (.../admin_events_handler.php) (revision 14402) @@ -1,6 +1,6 @@ array('self' => true), 'OnClosePopup' => array('self' => true), @@ -44,8 +45,8 @@ $system_events = Array ( 'OnResetModRwCache', 'OnResetSections', 'OnResetConfigsCache', 'OnResetParsedData', 'OnResetMemcache', - 'OnDeleteCompiledTemplates', 'OnCompileTemplates', 'OnGenerateTableStructure', - 'OnRebuildThemes', 'OnCheckPrefixConfig', 'OnMemoryCacheGet', 'OnMemoryCacheSet' + 'OnDeleteCompiledTemplates', 'OnCompileTemplates', 'OnGenerateTableStructure', 'OnSynchronizeDBRevisions', + 'OnDeploy', 'OnRebuildThemes', 'OnCheckPrefixConfig', 'OnMemoryCacheGet', 'OnMemoryCacheSet' ); if (in_array($event->Name, $system_events)) { @@ -1320,6 +1321,41 @@ echo $json_helper->encode($ret); } + + /** + * Deploy changes + * + * Usage: "php tools/run_event.php adm:OnDeploy b674006f3edb1d9cd4d838c150b0567d" + * + * @param kEvent $event + */ + function OnDeploy(&$event) + { + if ( isset($GLOBALS['argv']) ) { + // command line invocation -> don't perform redirect + $event->status = erSTOP; + } + + $deployment_helper =& $this->Application->recallObject('DeploymentHelper'); + /* @var $deployment_helper DeploymentHelper */ + + $deployment_helper->deployAll(); + } + + /** + * Synchronizes database revisions from "project_upgrades.sql" file + * + * @param kEvent $event + */ + function OnSynchronizeDBRevisions(&$event) + { + $deployment_helper =& $this->Application->recallObject('DeploymentHelper'); + /* @var $deployment_helper DeploymentHelper */ + + if ( !$deployment_helper->deployAll(true) ) { + $event->status = erFAIL; + } + } } Index: branches/5.1.x/core/install/english.lang =================================================================== diff -u -N -r14364 -r14402 --- branches/5.1.x/core/install/english.lang (.../english.lang) (revision 14364) +++ branches/5.1.x/core/install/english.lang (.../english.lang) (revision 14402) @@ -24,6 +24,7 @@ Q29udGVudCBNb2Rl RGVsZXRl RGVsZXRl + RGVwbG95 RGVzaWduIE1vZGU= RG93bg== RWRpdA== @@ -46,6 +47,7 @@ U2VsZWN0IEFsbA== U2V0IFZhbHVl U2hvdyBTdHJ1Y3R1cmU= + U3luY2hyb25pemU= VW5zZWxlY3Q= VXA= VXNl @@ -708,6 +710,7 @@ Q2FjaGUgS2V5KHMp PHVsPg0KICA8bGk+RGVsZXRlcyBhbGwgY29tcGlsZWQgdGVtcGxhdGVzIGZyb20gQWRtaW4gQ29uc29sZSBhbmQgRnJvbnQtZW5kIHRoZW1lcy48L2xpPg0KICA8bGk+UmVjb21tZW5kZWQgZm9yIHRoZSBtYWludGVuYW5jZSBwdXJwb3Nlcywgc2luY2UgZG9lcyBub3QgcHJvdmlkZSBhbnkgYWR2YW50YWdlcyBleGNlcHQgZm9yIHRlbXBvcmFyeSBsb3dlcmluZyB1c2FnZSBvZiB0aGUgZGlzayBzcGFjZS4gQWxsIHRlbXBsYXRlcyB3aWxsIGJlIGF1dG9tYXRpY2FsbHkgcmVjb21waWxlZCBhdCB0aGUgdGltZSBvZiB2aXNpdC48L2xpPg0KPC91bD4= ZGF0YWJhc2UgY2FjaGU= + PHVsPg0KPGxpPlRoaXMgZGVwbG95IHNjcmlwdCB3aWxsIGFwcGx5IGFsbCBEYXRhYmFzZSBDaGFuZ2VzIHN0b3JlZCBpbiA8Yj48dT5bbW9kdWxlXS9wcm9qZWN0X3VwZ3JhZGVzLnNxbDwvdT48L2I+IHRvIHRoZSBjdXJyZW50IHdlYnNpdGUgYW5kIHNhdmUgYXBwbGllZCBSZXZpc2lvbnMgaW4gQXBwbGllZERCUmV2aXNpb25zLjwvbGk+DQo8bGk+VGhpcyBkZXBsb3kgc2NyaXB0IHdpbGwgY3JlYXRlIGFsbCBuZXcgbGFuZ3VhZ2UgcGhyYXNlcyBieSByZS1pbXBvcnRpbmcgPGI+PHU+Y3VzdG9tL2luc3RhbGwvZW5nbGlzaC5sYW5nPC91PjwvYj4gZmlsZS48L2xpPg0KPGxpPlRoaXMgZGVwbG95IHNjcmlwdCB3aWxsIHJlc2V0IGFsbCBjYWNoZXMgYXQgb25jZTwvbGk+DQo8L3VsPg== PHVsPg0KICA8bGk+TmFtZSBvZiB0aGUgS2V5IHVzZWQgdG8gZ2V0IG9yIHNldCB0aGUgZGF0YSAodmFsdWUpIGluIHRoZSBtZW1vcnkgY2FjaGUgKDxzdHJvbmc+PGk+a0FwcGxpY2F0aW9uOjpzZXRDYWNoZTwvaT48L3N0cm9uZz4gYW5kIDxzdHJvbmc+PGk+a0FwcGxpY2F0aW9uOjpnZXRDYWNoZTwvaT48L3N0cm9uZz4gbWV0aG9kcykuPC9saT4NCjwvdWw+ Q3VycmVudCB2YWx1ZSBvciBhIG5ldyB2YWx1ZSAoZm9yIHNldHRpbmcpIG9mIHRoZSBrZXkgbmFtZSBzcGVjaWZpZWQgYWJvdmUu PHVsPg0KICA8bGk+U2hvd3MgdGhlIGxvY2F0aW9uIG9mIDxzdHJvbmc+PGk+VW5pdCBDb25maWc8L2k+PC9zdHJvbmc+IGZpbGUsIGFzc29jaWF0ZWQgd2l0aCB0aGUgZ2l2ZW4gPHN0cm9uZz48aT5Vbml0IENvbmZpZyBQcmVmaXg8L2k+PC9zdHJvbmc+IChpZS4gImFkbSIsICJ1IiwgImxhbmciIGFuZCBvdGhlcnMpLjwvbGk+DQo8L3VsPg== @@ -722,6 +725,7 @@ PHVsPg0KICA8bGk+UmVzZXRzIHZhcmlvdXMgY2FjaGVkIHN5c3RlbSBkYXRhIHN1Y2ggYXMgZGVmaW5lZCBQSFAgQ2xhc3NlcyAobWFwcGluZyBiZXR3ZWVuIHRoZSBjbGFzcyBuYW1lIGFuZCBwaHlzaWNhbCBmaWxlbmFtZSBhbmQgbG9jYXRpb24gb2YgdGhlIGNsYXNzKSwgSG9va3MsIEFnZW50cywgQ2FjaGVkIENvbmZpZ3VyYXRpb24gVmFyaWFibGVzLCBSZXBsYWNlbWVudCBUZW1wbGF0ZXMsIFJld3JpdGUgTGlzdGVuZXJzIGFuZCBMb2FkZWQgTW9kdWxlcy4gRGF0YSBpcyByZWFkIGFuZCBjb2xsZWN0ZWQgZnJvbSA8c3Ryb25nPjxpPlVuaXQgQ29uZmlnPC9pPjwvc3Ryb25nPiBmaWxlcyB0aGF0IGFscmVhZHkgYmVlbiBzY2FubmVkIGFuZCBjYWNoZWQgYnkgdGhlIHN5c3RlbS48L2xpPg0KPC91bD4= PHVsPg0KICA8bGk+RGVsZXRlcyB0aGUgY2FjaGVkIHZlcnNpb24gb2YgRnJvbnQtZW5kIG1lbnUgKGRpc3BsYXllZCB2aWEgPHN0cm9uZz48aT4mbHQ7aW5wMjpzdF9DYWNoZWRNZW51IC4uLi8mZ3Q7PC9pPjwvc3Ryb25nPiB0YWcpLiBUaGlzIGNhY2hlIGlzIHVwZGF0ZWQgYXV0b21hdGljYWxseSwgd2hlbiB0aGUgd2Vic2l0ZSBzdHJ1Y3R1cmUgb3Igc2VjdGlvbnMgYXJlIGNoYW5nZWQuPC9saT4NCiAgPGxpPlVzZSB0aGlzIG9wdGlvbiBvbmx5IGluIGNhc2UgaWYgZGlzcGxheWVkIG1lbnUgb24gdGhlIEZyb250LWVuZCBkb2Vzbid0IG1hdGNoIHRoZSBtZW51IGRlZmluZWQgaW4gQWRtaW4gQ29uc29sZS48L2xpPg0KPC91bD4= PHVsPg0KICA8bGk+U2hvd3MgdGhlIHN0cnVjdHVyZSBvZiB0aGUgZGF0YWJhc2UgdGFibGUgbG9hZGluZyBpdCBieSB0aGUgVGFibGUgTmFtZSAodGFibGUgcHJlZml4IGlzIG9wdGlvbmFsKSBvciA8c3Ryb25nPjxpPlVuaXQgQ29uZmlnIFByZWZpeDwvaT48L3N0cm9uZz4gYXNzb2NpYXRlZCB3aXRoIHRoaXMgdGFibGUuPC9saT4NCjwvdWw+ + PHVsPg0KPGxpPkFzIGEgcmVzdWx0LCBzY3JpcHQgd2lsbCBWYWxpZGF0ZSBjdXJyZW50IDxiPjx1PnByb2plY3RfdXBncmFkZXMuc3FsPC91PjwvYj4gZmlsZSBhbmQgb3V0bGluZSBhbnkgZXJyb3JzIG9yIGluY29uc2lzdGVuY2llcywgYW5kIGF1dG8tcG9wdWxhdGUgYWxsIG1pc3NpbmcgREIgUmV2aXNpb25zIGZyb20gdGhlIGZpbGUgaW50byBBcHBsaWVkREJSZXZpc2lvbnMuPC9saT4NCjxsaT48YiBzdHlsZT0iY29sb3I6cmVkIj5OT1RFOjwvYj4gRGV2ZWxvcGVycyBzaG91bGQgT05MWSBydW4gdGhpcyBiZWZvcmUgdGhleSBwZXJmb3JtIFJlcG9zaXRvcnkgVXBkYXRlcyBvbiB0aGVpIHdvcmtpbmcgY29weSE8L2xpPg0KPC91bD4= VXNpbmcgUmVndWxhciBFeHByZXNzaW9u SG90 SFRNTA== @@ -1064,6 +1068,7 @@ U2VjdGlvbiBPdmVydmlldw== U2VjdGlvbiBQcm9wZXJ0aWVz U2VjdGlvbiBDYWNoaW5n + UHJvamVjdCBEZXBsb3ltZW50 UHJvcGVydGllcw== UXVpY2sgTGlua3M= UmVjaXBpZW50cyBJbmZvcm1hdGlvbg== @@ -1385,6 +1390,7 @@ U3lzdGVtIFRvb2xz Q2xlYXIgVGVtcGxhdGVzIENhY2hl Q29tbW9ubHkgVXNlZCBLZXlz + RGVwbG95IENoYW5nZXM= S2V5IE5hbWU= S2V5IFZhbHVl TG9jYXRlIFVuaXQgQ29uZmlnIEZpbGU= @@ -1398,6 +1404,7 @@ UmVzZXQgUGFyc2VkIGFuZCBDYWNoZWQgU3lzdGVtIERhdGE= UmVzZXQgU01TIE1lbnUgQ2FjaGU= U2hvdyBEYXRhYmFzZSBUYWJsZSBTdHJ1Y3R1cmU= + U3luY2hyb25pemUgRGF0YWJhc2UgUmV2aXNpb25z VGhlbWUgRmlsZXM= VGhlc2F1cnVz VXBkYXRpbmcgU2VjdGlvbnM= Index: branches/5.1.x/core/units/helpers/helpers_config.php =================================================================== diff -u -N -r14241 -r14402 --- branches/5.1.x/core/units/helpers/helpers_config.php (.../helpers_config.php) (revision 14241) +++ branches/5.1.x/core/units/helpers/helpers_config.php (.../helpers_config.php) (revision 14402) @@ -1,6 +1,6 @@ 'MimeDecodeHelper', 'class' => 'MimeDecodeHelper', 'file' => 'mime_decode_helper.php', 'build_event' => '', 'require_classes' => 'kHelper'), Array ('pseudo' => 'UserHelper', 'class' => 'UserHelper', 'file' => 'user_helper.php', 'build_event' => '', 'require_classes' => 'kHelper'), Array ('pseudo' => 'SiteHelper', 'class' => 'SiteHelper', 'file' => 'site_helper.php', 'build_event' => '', 'require_classes' => 'kHelper'), + + Array ('pseudo' => 'DeploymentHelper', 'class' => 'DeploymentHelper', 'file' => 'deployment_helper.php', 'build_event' => '', 'require_classes' => 'kHelper'), ), ); \ No newline at end of file