/** * @see SugarCacheAbstract::__destruct() * * For this backend, we'll write the SugarCacheFile::$localCache array serialized out to a file */ public function __destruct() { parent::__destruct(); if ($this->_cacheChanged) { sugar_file_put_contents_atomic(sugar_cached($this->_cacheFileName), serialize($this->_localStore)); } }
/** * Upgrade Task to Run */ public function run() { if (version_compare($this->from_version, '7.0.0', '<') && ($this->toFlavor('ent') || $this->toFlavor('ult'))) { $settings = Opportunity::getSettings(); if ($settings['opps_view_by'] !== 'RevenueLineItems') { $this->log('Not using Revenue Line Items; Skipping Upgrade Script'); return; } $filename = 'custom/Extension/modules/Opportunities/Ext/Vardefs/sugarfield_date_closed.php'; if (!is_file($filename)) { return; } require $filename; if (!empty($dictionary['Opportunity']['fields'])) { $fileString = file_get_contents($filename); // PAT-584, need to set the field Expected Close Date to false when upgrade because: // In 6.7, the field Expected Close Date is Required and no formula associated out of box. // In 7, the field Expected Close Date is Not Required and there's a formula associated out of box. // So use steps from PAT-584, it results in a Required field with a formula associated. if (isset($dictionary['Opportunity']['fields']['date_closed']['required']) && $dictionary['Opportunity']['fields']['date_closed']['required'] == true) { $this->log("Change Opportunity field date_closed to not required"); $fileString = preg_replace('/(\\$dictionary\\[\'Opportunity\'\\]\\[\'fields\'\\]\\[\'date_closed\'\\]\\[\'required\'\\]\\s*=\\s*)true\\s*;/', '${1}false;', $fileString); sugar_file_put_contents_atomic($filename, $fileString); } } } }
public function run() { if (!version_compare($this->from_version, '7.2.2', '<')) { // only needed for upgrades from pre-7.2.2 return; } foreach (glob('custom/Extension/modules/*/Ext/Vardefs/*', GLOB_BRACE) as $customFieldFile) { if (is_dir($customFieldFile)) { continue; } $dictionary = array(); require $customFieldFile; if (!empty($dictionary)) { $module = key($dictionary); if (!empty($dictionary[$module]['fields'])) { $field = key($dictionary[$module]['fields']); if (!empty($dictionary[$module]['fields'][$field]['full_text_search']) && !empty($dictionary[$module]['fields'][$field]['full_text_search']['boost']) && !isset($dictionary[$module]['fields'][$field]['full_text_search']['enabled'])) { $dictionary[$module]['fields'][$field]['full_text_search']['enabled'] = true; $strToFile = "<?php\n\n" . "/* This file was updated by 7_FixCustomFieldsForFTS */\n"; foreach ($dictionary[$module]['fields'][$field] as $key => $value) { $strToFile .= "\$dictionary['{$module}']['fields']['{$field}']['{$key}'] = " . var_export($value, true) . ";\n"; } sugar_file_put_contents_atomic($customFieldFile, $strToFile); } } } } }
public function run() { $customFieldFiles = $this->getCustomFieldFiles(); foreach ($customFieldFiles as $file) { if (is_dir($file)) { continue; } $dictionary = array(); require $file; if (empty($dictionary)) { continue; } $module = key($dictionary); if (empty($dictionary[$module]['fields'])) { continue; } $field = key($dictionary[$module]['fields']); if (empty($dictionary[$module]['fields'][$field]['type']) || $dictionary[$module]['fields'][$field]['type'] != 'multienum' || isset($dictionary[$module]['fields'][$field]['isMultiSelect'])) { continue; } $this->log("Added isMultiSelect for the file: {$file}"); $dictionary[$module]['fields'][$field]['isMultiSelect'] = true; $strToFile = "<?php\n\n"; foreach ($dictionary[$module]['fields'][$field] as $key => $value) { $strToFile .= "\$dictionary['{$module}']['fields']['{$field}']['{$key}'] = " . var_export($value, true) . ";\n"; } $this->upgrader->backupFile($file); sugar_file_put_contents_atomic($file, $strToFile); } }
/** * Removes fields' filter definition. * * More precisely we need to remove the `dbFields`, `type` and `vname` * properties from the filter definition of `relate` type fields. * * @param string $module The module name. * @param array $fields The list of fields to fix. */ private function cleanUpField($module, $fields) { $file = 'custom/modules/' . $module . '/clients/base/filters/default/default.php'; if (!file_exists($file)) { return; } $viewdefs = null; require $file; foreach ($fields as $fieldName) { if (isset($viewdefs[$module]['base']['filter']['default']['fields'][$fieldName])) { $viewdefs[$module]['base']['filter']['default']['fields'][$fieldName] = array(); } } sugar_file_put_contents_atomic($file, "<?php\n\n" . "/* This file was updated by 7_FixRelateFieldsFilterMetadata */\n" . "\$viewdefs['{$module}']['base']['filter']['default'] = " . var_export($viewdefs[$module]['base']['filter']['default'], true) . ";\n"); }
public function run() { //run only when upgrading from 7.x to 7.2.1 if (version_compare($this->from_version, '7.0', '<') || version_compare($this->from_version, '7.2.1', '>=')) { return; } foreach (glob('custom/modules/*/clients/{base,portal}/views/record/record.php', GLOB_BRACE) as $recordFile) { require $recordFile; if (!empty($viewdefs)) { $module = key($viewdefs); //make sure header panel exists and has fields if (!empty($viewdefs[$module]) && !empty($viewdefs[$module]['base']) && !empty($viewdefs[$module]['base']['view']['record']) && !empty($viewdefs[$module]['base']['view']['record']['panels']) && !empty($viewdefs[$module]['base']['view']['record']['panels'][0]['fields'])) { $newViewdefs = $this->cleanUpAvatarField($viewdefs, $module); sugar_file_put_contents_atomic($recordFile, "<?php\n\n" . "/* This file was updated by 7_CleanUpCustomRecordAvatar */\n" . "\$viewdefs['{$module}']['base']['view']['record'] = " . var_export($newViewdefs[$module]['base']['view']['record'], true) . ";\n"); } } $viewdefs = null; } }
/** * Append a array of new settings to the file "config_override.php". * @param $settings Array of settings * @return bool * @throws Exception */ public function appendOverrideConfig($settings) { $file = 'config_override.php'; $sugar_config = array(); if (file_exists($file)) { $this->upgrader->backupFile($file); include $file; } foreach ($settings as $key => $val) { $sugar_config[$key] = $val; } $out = "<?php\n // created: " . date('Y-m-d H:i:s') . "\n"; foreach (array_keys($sugar_config) as $key) { $out .= override_value_to_string_recursive2('sugar_config', $key, $sugar_config[$key]); } if (!sugar_file_put_contents_atomic($file, $out)) { throw new Exception("Failed writing to the {$file} file."); } return true; }
public function run() { if (!version_compare($this->from_version, '7.6', '<')) { return; } $customFieldFiles = $this->getCustomFieldFiles(); foreach ($customFieldFiles as $file) { if (is_dir($file)) { continue; } $dictionary = array(); require $file; if (empty($dictionary)) { continue; } $module = key($dictionary); if (empty($dictionary[$module]['fields'])) { continue; } $fields = array_keys($dictionary[$module]['fields']); if (empty($dictionary[$module]['fields']['date_entered']['required']) && empty($dictionary[$module]['fields']['date_modified']['required'])) { continue; } else { // date_entered & date_modified are read only fields, set the required to false if set if (!empty($dictionary[$module]['fields']['date_entered']['required'])) { $dictionary[$module]['fields']['date_entered']['required'] = false; } if (!empty($dictionary[$module]['fields']['date_modified']['required'])) { $dictionary[$module]['fields']['date_modified']['required'] = false; } } $strToFile = "<?php\n\n"; foreach ($fields as $field) { foreach ($dictionary[$module]['fields'][$field] as $key => $value) { $strToFile .= "\$dictionary['{$module}']['fields']['{$field}']['{$key}'] = " . var_export($value, true) . ";\n"; } } $this->upgrader->backupFile($file); sugar_file_put_contents_atomic($file, $strToFile); } }
/** * Find custom address fields added to modules in the modulebuilder that have yet to be deployed */ public function upgradeVardefsInUndeployedCustomModules() { foreach (glob('custom/modulebuilder/packages/*/modules/*/vardefs.php') as $file) { require $file; if (!empty($vardefs['fields'])) { //Save opening string so we can put it back later $fileString = file_get_contents($file); $openingString = substr($fileString, 0, strpos($fileString, '$vardefs')); //Find all custom street fields foreach ($vardefs['fields'] as $fieldName => &$field) { if ($this->validateStreetField($vardefs['fields'], $fieldName)) { //Field is an address street. Proceed to update the street vardef $field['type'] = 'text'; $field['dbType'] = 'varchar'; } } //Put the updated contents back into the file sugar_file_put_contents_atomic($file, $openingString . "\n" . '$vardefs = ' . var_export($vardefs, true) . ";\n"); } } }
public function run() { //run only when upgrading from 7.x to 7.2.1 if (version_compare($this->from_version, '7.2.2', '>=')) { return; } // this is the core modules that it's on out of the box $modules = array('Accounts', 'Bugs', 'Cases', 'Contacts', 'Leads', 'Opportunities', 'Prospects', 'RevenueLineItems'); $files = glob('custom/modules/{' . join(',', $modules) . '}/clients/base/views/record/record.php', GLOB_BRACE); foreach ($files as $recordFile) { require $recordFile; if (!empty($viewdefs)) { $module = key($viewdefs); //make sure header panel exists and has fields if (!empty($viewdefs[$module]) && !empty($viewdefs[$module]['base']) && !empty($viewdefs[$module]['base']['view']['record']) && !empty($viewdefs[$module]['base']['view']['record']['buttons'])) { $newViewdefs = $this->addHistorySummaryButton($viewdefs, $module); sugar_file_put_contents_atomic($recordFile, "<?php\n\n" . "/* This file was updated by 7_CustomRecordViewHistorySummaryButton */\n" . "\$viewdefs['{$module}']['base']['view']['record'] = " . var_export($newViewdefs[$module]['base']['view']['record'], true) . ";\n"); } } $viewdefs = null; } }
/** * Fix dict defs and attempt to overwrite record file * @param array $dictionary * @param string $file */ public function fixRelationship($dictionary, $file) { $module = key($dictionary); if (empty($dictionary[$module]['fields'])) { return; } $field = key($dictionary[$module]['fields']) . '_name'; if (isset($dictionary[$module]['fields'][$field])) { // if the _name field of this relationship is set $fieldDef = $dictionary[$module]['fields'][$field]; if (!isset($fieldDef['rname']) && $fieldDef['type'] == 'relate') { // and its type is relate $dictionary[$module]['fields'][$field]['rname'] = 'name'; // set 'rname' to default 'name' $strToFile = "<?php\n\n"; foreach ($dictionary[$module]['fields'] as $key => $value) { $strToFile .= "\$dictionary[\"{$module}\"][\"fields\"][\"{$key}\"] = " . var_export($value, true) . ";\n"; } $this->upgrader->backupFile($file); sugar_file_put_contents_atomic($file, $strToFile); } } }
/** * Fix dict defs and attempt to overwrite record file * @param array $dictionary * @param string $file */ public function fixRelationship($dictionary, $file) { $module = key($dictionary); if (empty($dictionary[$module]['fields'])) { return; } $field = key($dictionary[$module]['fields']) . '_name'; if (isset($dictionary[$module]['fields'][$field])) { // if the _name field of this relationship is set $fieldDef = $dictionary[$module]['fields'][$field]; if (isset($fieldDef['module']) && is_subclass_of(BeanFactory::getBean($fieldDef['module']), 'Person') && isset($fieldDef['db_concat_fields']) && $fieldDef['rname'] == 'name' && $fieldDef['type'] == 'relate') { // and its type is relate $dictionary[$module]['fields'][$field]['rname'] = 'full_name'; // change 'name' to 'full_name' $strToFile = "<?php\n\n"; foreach ($dictionary[$module]['fields'] as $key => $value) { $strToFile .= "\$dictionary[\"{$module}\"][\"fields\"][\"{$key}\"] = " . var_export($value, true) . ";\n"; } $this->upgrader->backupFile($file); sugar_file_put_contents_atomic($file, $strToFile); } } }
function write_array_to_file($the_name, $the_array, $the_file, $mode = "w", $header = '') { if (!empty($header) && ($mode != 'a' || !file_exists($the_file))) { $the_string = $header; } else { $the_string = "<?php\n" . '// created: ' . date('Y-m-d H:i:s') . "\n"; } $the_string .= "\${$the_name} = " . var_export_helper($the_array) . ";"; if (sugar_file_put_contents_atomic($the_file, $the_string) !== false) { if (substr($the_file, 0, 7) === 'custom/') { // record custom writes to file map SugarAutoLoader::addToMap($the_file); } return true; } return false; }
/** * Override the existing file. * * @param string $moduleName The module name. * @param string $content The content of the file. */ private function writeCustomClass($moduleName, $content) { //write sugar generated class $this->log("FixClassConstructor: Replace {$moduleName}_sugar.php for module: {$moduleName}"); sugar_file_put_contents_atomic($this->getModuleClassFile($moduleName), $content); }
function cacheQuery($queryString, $resArray) { $file = create_cache_directory('modules/AOD_Index/QueryCache/' . md5($queryString)); $out = serialize($resArray); sugar_file_put_contents_atomic($file, $out); }
function save() { $path = $this->getPackageDir(); if (mkdir_recursive($path)) { //Save all the modules when we save a package $this->updateModulesMetaData(true); sugar_file_put_contents_atomic($path . '/manifest.php', $this->getManifest()); } }
protected function buildRelationshipCache() { global $beanList, $dictionary, $buildingRelCache; if ($buildingRelCache) { return; } $buildingRelCache = true; include "modules/TableDictionary.php"; if (empty($beanList)) { include "include/modules.php"; } //Reload ALL the module vardefs.... foreach ($beanList as $moduleName => $beanName) { VardefManager::loadVardef($moduleName, BeanFactory::getObjectName($moduleName)); } $relationships = array(); //Grab all the relationships from the dictionary. foreach ($dictionary as $key => $def) { if (!empty($def['relationships'])) { foreach ($def['relationships'] as $relKey => $relDef) { if ($key == $relKey) { //Relationship only entry, we need to capture everything $relationships[$key] = array_merge(array('name' => $key), $def, $relDef); } else { $relationships[$relKey] = array_merge(array('name' => $relKey), $relDef); if (!empty($relationships[$relKey]['join_table']) && empty($relationships[$relKey]['fields']) && isset($dictionary[$relationships[$relKey]['join_table']]['fields'])) { $relationships[$relKey]['fields'] = $dictionary[$relationships[$relKey]['join_table']]['fields']; } } } } } //Save it out sugar_mkdir(dirname($this->getCacheFile()), null, true); $out = "<?php \n \$relationships = " . var_export($relationships, true) . ";"; sugar_file_put_contents_atomic($this->getCacheFile(), $out); $this->relationships = $relationships; $buildingRelCache = false; }
public function ConcatenateFiles($from_path) { global $sugar_config; // Minifying the group files takes a long time sometimes. @ini_set('max_execution_time', 0); $js_groupings = $this->getJSGroupings(); // Get the files that are not meant to be minified $excludedFiles = $this->get_exclude_files($from_path); // For each item in the $js_groupings array (from JSGroupings.php), // concatenate the source files into the target file foreach ($js_groupings as $fg) { // List of files to build into one $buildList = array(); // Default the permissions to the most restrictive to start $currPerm = 0; // Process each group array. $loc is the file to read in, $trgt is // the concatenated file foreach ($fg as $loc => $trgt) { $already_minified = preg_match('/[\\.\\-]min\\.js$/', $loc); if (preg_match('/[\\.\\-]min\\.js$/', $loc)) { $already_minified = true; } else { $minified_loc = str_replace('.js', '-min.js', $loc); if (is_file($minified_loc)) { $loc = $minified_loc; $already_minified = true; } } $relpath = $loc; $loc = $from_path . '/' . $loc; $trgt = sugar_cached($trgt); //check to see that source file is a file, and is readable. if (is_file($loc) && is_readable($loc)) { // Build a file perm based on the loosest file being read in $tPerm = fileperms($loc); if ($tPerm !== false && $tPerm > $currPerm) { $currPerm = $tPerm; } //make sure we have handles to both source and target file $content = file_get_contents($loc); //Skip minifying files in exclude list and already minified files if (!$already_minified && !isset($excludedFiles[$loc])) { try { $content = SugarMin::minify($content); } catch (RuntimeException $e) { //Use unminified $buffer instead } } $content .= "\n/* End of File {$relpath} */\n\n"; $buildList[] = $content; } } // Ensure target directory exists $targetDir = dirname($trgt); if (!file_exists($targetDir)) { mkdir_recursive($targetDir); } // Build the file now using atomic write $contents = implode("", $buildList); sugar_file_put_contents_atomic($trgt, $contents); // And handle permissions like the way we used to do it $func = function_exists('sugar_chmod') ? 'sugar_chmod' : 'chmod'; // Get a default permission, from config if possible if (isset($sugar_config['default_permissions']['file_mode'])) { $defaultPerm = $sugar_config['default_permissions']['file_mode']; } else { $defaultPerm = 0777; } // Handle permission value here $newPerm = $currPerm ? $currPerm : $defaultPerm; // Set the perms for the new file @$func($trgt, $newPerm); } }
function build_relationship_cache() { $query = "SELECT * from relationships where deleted=0"; $result = $this->db->query($query); while (($row = $this->db->fetchByAssoc($result)) != null) { $relationships[$row['relationship_name']] = $row; } sugar_mkdir($this->cache_file_dir(), null, true); $out = "<?php \n \$relationships = " . var_export($relationships, true) . ";"; sugar_file_put_contents_atomic(Relationship::cache_file_dir() . '/' . Relationship::cache_file_name_only(), $out); require_once "data/Relationships/RelationshipFactory.php"; SugarRelationshipFactory::deleteCache(); }
/** * Builds up module client cache files * * @param array $platforms A list of platforms to build for. Uses the first * platform in the list as the platform. * @param string $type The type of file to create the cache for. * @param array $modules The module to create the cache for. * @param MetaDataContextInterface|null $context Metadata context */ public static function buildModuleClientCache($platforms, $type, $modules = array(), MetaDataContextInterface $context = null, $noCache = false) { if (is_string($modules)) { // They just want one module $modules = array($modules); } elseif (count($modules) == 0) { // They want all of the modules $modules = array_keys($GLOBALS['app_list_strings']['moduleList']); } if (!$context) { $context = new MetaDataContextDefault(); } foreach ($modules as $module) { $seed = BeanFactory::getBean($module); $fileList = self::getClientFiles($platforms, $type, $module, $context, $seed); $moduleResults = self::getClientFileContents($fileList, $type, $module, $seed); if ($type == "view") { foreach ($moduleResults as $view => $defs) { if (!is_array($defs) || empty($seed) || empty($seed->field_defs)) { continue; } $meta = !empty($defs['meta']) ? $defs['meta'] : array(); $deps = array_merge(DependencyManager::getDependenciesForFields($seed->field_defs, ucfirst($view) . "View"), DependencyManager::getDependenciesForView($meta, ucfirst($view) . "View", $module)); if (!empty($deps)) { if (!isset($meta['dependencies']) || !is_array($meta['dependencies'])) { $moduleResults[$view]['meta']['dependencies'] = array(); } foreach ($deps as $dep) { $moduleResults[$view]['meta']['dependencies'][] = $dep->getDefinition(); } } } } if ($noCache) { return $moduleResults; } else { $basePath = sugar_cached('modules/' . $module . '/clients/' . $platforms[0]); sugar_mkdir($basePath, null, true); $output = "<?php\n\$clientCache['" . $module . "']['" . $platforms[0] . "']['" . $type . "'] = " . var_export($moduleResults, true) . ";\n\n"; sugar_file_put_contents_atomic($basePath . '/' . $type . '.php', $output); } } }
/** * Update file with new definition * @param string $file * @param array $var * @param string $varName */ protected function updateFile($file, $var, $varName) { $this->upgrader->backupFile($file); $out = "<?php\n// created: ' . date('Y-m-d H:i:s')\n"; foreach (array_keys($var) as $key) { $out .= override_value_to_string_recursive2($varName, $key, $var[$key]); } sugar_file_put_contents_atomic($file, $out); }
/** * Change old labels to new ones in all $module subpanels * @param $module * @return bool */ public function upgradeSubpanelModuleLabels($module) { $upgradeLabels = $this->upgradeLabels[$module]; $upgradeDriver = $this->upgrader; $upgraded = false; // upgrade viewdefs $path = "custom/modules/{$module}/clients/base/views/subpanel-for-*/subpanel-for-*.php"; foreach (glob($path) as $scanFile) { $viewdefs = array(); include $scanFile; // Modification flag $changed = false; array_walk_recursive($viewdefs, function (&$value, $key) use(&$changed, $upgradeLabels, $upgradeDriver, $scanFile) { if ('label' == $key && isset($upgradeLabels[$value])) { $upgradeDriver->log(sprintf('FixCustomLabelsForCoreModules: Fix label name from "%s" to "%s" in file "%s"', $value, $upgradeLabels[$value], $scanFile)); $value = $upgradeLabels[$value]; $changed = true; } }); if ($changed) { $this->backupFile($scanFile); $upgraded = $upgraded || $changed; $keyNames = array(); $viewdefsWrite = $viewdefs; // collect key names for array path "{module}/{platform}/{view_type}/{view}" for ($i = 0; $i < 4; $i++) { if (1 != count($viewdefsWrite)) { break; } $keyNames[] = key($viewdefsWrite); $viewdefsWrite = $viewdefsWrite[key($viewdefsWrite)]; } $out = "<?php\n// created: ' . date('Y-m-d H:i:s')\n"; $out .= override_value_to_string_recursive($keyNames, 'viewdefs', $viewdefsWrite); if (sugar_file_put_contents_atomic($scanFile, $out) !== false) { // record custom writes to file map SugarAutoLoader::addToMap($scanFile); } unset($out); unset($viewdefsWrite); } unset($viewdefs); } // upgrade subpanel_layout $path = "custom/modules/{$module}/metadata/subpanels/*.php"; foreach (glob($path) as $scanFile) { $subpanel_layout = array(); include $scanFile; // Modification flag $changed = false; array_walk_recursive($subpanel_layout, function (&$value, $key) use(&$changed, $upgradeLabels, $upgradeDriver, $scanFile) { if ('vname' == $key && isset($upgradeLabels[$value])) { $upgradeDriver->log(sprintf('FixCustomLabelsForCoreModules: Fix label name from "%s" to "%s" in file "%s"', $value, $upgradeLabels[$value], $scanFile)); $value = $upgradeLabels[$value]; $changed = true; } }); if ($changed) { $upgraded = $upgraded || $changed; $this->backupFile($scanFile); write_array_to_file('subpanel_layout', $subpanel_layout, $scanFile, 'w'); } unset($subpanel_layout); } return $upgraded; }
protected function buildRelationshipCache() { global $beanList, $buildingRelCache; if ($buildingRelCache) { return; } $buildingRelCache = true; $relationships = $this->getRelationshipData(); //Save it out sugar_mkdir(dirname($this->getCacheFile()), null, true); $out = "<?php \n \$relationships = " . var_export($relationships, true) . ";"; sugar_file_put_contents_atomic($this->getCacheFile(), $out); // There are only certain times when the relationship cache needs to be // refreshed... // // If we have a cache, but no internal relationships yet, do NOT rebuild // the api cache. This is a first load of this class. // // If there is no cache, then do NOT rebuild the api cache since there is // nothing to rebuild. // // DO rebuild the cache if there is a cache, there is an internal relationships // property and it is different than $relationships $rebuildApiCache = false; $metaCacheKey = MetaDataManager::getManager()->getCachedMetadataHash(); if (empty($metaCacheKey)) { $rebuildApiCache = !empty($this->relationships) && array_diff_key($this->relationships, $relationships) !== array(); } $this->relationships = $relationships; if ($rebuildApiCache) { MetaDataManager::refreshSectionCache(array(MetaDataManager::MM_RELATIONSHIPS)); } // set the variable back to false, as we are now going to rebuild the vardefs since we have all the // relationships are loaded $buildingRelCache = false; //Now load all vardefs a second time populating the rel_calc_fields foreach ($beanList as $moduleName => $beanName) { // need to refresh the vardef so that the related calc fields are loaded VardefManager::loadVardef($moduleName, BeanFactory::getObjectName($moduleName), true); } }
function build_relationship_cache($modulesChanged = array()) { if (!empty($modulesChanged)) { $relationships = $GLOBALS['relationships']; $module1 = $modulesChanged[0]; $module2 = !empty($modulesChanged[1]) ? $modulesChanged[1] : $modulesChanged[0]; $query = "SELECT * FROM relationships WHERE (rhs_module = '{$module1}' AND lhs_module = '{$module2}') OR (rhs_module = '{$module2}' AND lhs_module = '{$module2}')"; } else { $query = "SELECT * FROM relationships WHERE deleted=0"; $relationships = array(); } $result = $this->db->query($query); while (($row = $this->db->fetchByAssoc($result)) != null) { $row = $this->convertRow($row); $relationships[$row['relationship_name']] = $row; } sugar_mkdir($this->cache_file_dir(), null, true); $out = "<?php \n \$relationships = " . var_export($relationships, true) . ";"; sugar_file_put_contents_atomic(Relationship::cache_file_dir() . '/' . Relationship::cache_file_name_only(), $out); SugarRelationshipFactory::deleteCache(); }
/** * Builds the language javascript file if needed, else returns what is known * * @param string $language The language for this file * @param array $modules The module list * @param boolean $ordered is a flag that determines $app_list_strings should be key => value pairs or tuples * @return array Array containing the language file contents and the hash for the data */ protected function buildLanguageFile($language, $modules, $ordered = false) { sugar_mkdir(sugar_cached('api/metadata'), null, true); $filePath = $this->getLangUrl($language, $ordered); if (SugarAutoLoader::fileExists($filePath)) { // Get the contents of the file so that we can get the hash $data = file_get_contents($filePath); // Decode the json and get the hash. The hash should be there but // check for it just in case something went wrong somewhere. $array = json_decode($data, true); $hash = isset($array['_hash']) ? $array['_hash'] : ''; // Cleanup unset($array); // Return the same thing as would be returned if we had to build the // file for the first time return array('hash' => $hash, 'data' => $data); } $stringData = array(); $stringData['app_list_strings'] = $this->getAppListStrings($language, $ordered); $stringData['app_strings'] = $this->getAppStrings($language); if ($this->public) { // Exception for the AppListStrings. $app_list_strings_public = array(); $app_list_strings_public['available_language_dom'] = $stringData['app_list_strings']['available_language_dom']; // Let clients fill in any gaps that may need to be filled in $app_list_strings_public = $this->fillInAppListStrings($app_list_strings_public, $stringData['app_list_strings'], $language); $stringData['app_list_strings'] = $app_list_strings_public; } else { $modStrings = array(); foreach ($modules as $modName => $moduleDef) { $modData = $this->getModuleStrings($modName, $language); $modStrings[$modName] = $modData; } $stringData['mod_strings'] = $modStrings; } $stringData['_hash'] = $this->hashChunk($stringData); $data = json_encode($stringData); sugar_file_put_contents_atomic($filePath, $data); return array("hash" => $stringData['_hash'], "data" => $data); }
function save($key_name, $duplicate = false, $rename = false) { $header = file_get_contents('modules/ModuleBuilder/MB/header.php'); $save_path = $this->path . '/language'; mkdir_recursive($save_path); foreach ($this->strings as $lang => $values) { //Check if the module Label or Singular Label has changed. $mod_strings = return_module_language(str_replace('.lang.php', '', $lang), 'ModuleBuilder'); $required = array('LBL_LIST_FORM_TITLE' => $this->label . " " . $mod_strings['LBL_LIST'], 'LBL_MODULE_NAME' => $this->label, 'LBL_MODULE_TITLE' => $this->label, 'LBL_MODULE_NAME_SINGULAR' => $this->label_singular, 'LBL_HOMEPAGE_TITLE' => $mod_strings['LBL_HOMEPAGE_PREFIX'] . " " . $this->label, 'LNK_NEW_RECORD' => $mod_strings['LBL_CREATE'] . " " . $this->label_singular, 'LNK_LIST' => $mod_strings['LBL_VIEW'] . " " . $this->label, 'LNK_IMPORT_' . strtoupper($this->key_name) => translate('LBL_IMPORT') . " " . $this->label_singular, 'LBL_SEARCH_FORM_TITLE' => $mod_strings['LBL_SEARCH'] . " " . $this->label_singular, 'LBL_HISTORY_SUBPANEL_TITLE' => $mod_strings['LBL_HISTORY'], 'LBL_ACTIVITIES_SUBPANEL_TITLE' => $mod_strings['LBL_ACTIVITIES'], 'LBL_' . strtoupper($this->key_name) . '_SUBPANEL_TITLE' => $this->label, 'LBL_NEW_FORM_TITLE' => $mod_strings['LBL_NEW'] . " " . $this->label_singular, 'LNK_IMPORT_VCARD' => translate('LBL_IMPORT') . " " . $this->label_singular . ' vCard', 'LBL_IMPORT' => translate('LBL_IMPORT') . " " . $this->label, 'LBL_IMPORT_VCARDTEXT' => "Automatically create a new {$this->label_singular} record by importing a vCard from your file system."); foreach ($required as $k => $v) { $values[$k] = $v; } write_array_to_file('mod_strings', $values, $save_path . '/' . $lang, 'w', $header); } $app_save_path = $this->path . '/../../language/application'; sugar_mkdir($app_save_path, null, true); $key_changed = $this->key_name != $key_name; foreach ($this->appListStrings as $lang => $values) { // Load previously created modules data $app_list_strings = array(); $neededFile = $app_save_path . '/' . $lang; if (file_exists($neededFile)) { include $neededFile; } if (!$duplicate) { unset($values['moduleList'][$this->key_name]); } $values = sugarLangArrayMerge($values, $app_list_strings); $values['moduleList'][$key_name] = $this->label; $values['moduleListSingular'][$key_name] = $this->label_singular; $appFile = $header . "\n"; require_once 'include/utils/array_utils.php'; $this->getGlobalAppListStringsForMB($values); foreach ($values as $key => $array) { if ($duplicate) { //keep the original when duplicating $appFile .= override_value_to_string_recursive2('app_list_strings', $key, $array); } $okey = $key; if ($key_changed) { $key = str_replace(strtolower($this->key_name), strtolower($key_name), $key); } // if we aren't duplicating or the key has changed let's add it if (!$duplicate || $okey != $key) { if ($rename && isset($this->appListStrings[$lang][$key])) { $arr = $this->appListStrings[$lang][$key]; } else { $arr = $array; } $appFile .= override_value_to_string_recursive2('app_list_strings', $key, $arr); } } sugar_file_put_contents_atomic($app_save_path . '/' . $lang, $appFile); } }
/** * Save the dictionary object to the cache * @param string $module the name of the module * @param string $object the name of the object */ static function saveCache($module, $object, $additonal_objects = array()) { if (empty($GLOBALS['dictionary'][$object])) { $object = BeanFactory::getObjectName($module); } $file = create_cache_directory('modules/' . $module . '/' . $object . 'vardefs.php'); $out = "<?php \n \$GLOBALS[\"dictionary\"][\"" . $object . "\"]=" . var_export($GLOBALS['dictionary'][$object], true) . ";"; sugar_file_put_contents_atomic($file, $out); if (sugar_is_file($file) && is_readable($file)) { include $file; } // put the item in the sugar cache. $key = "VardefManager.{$module}.{$object}"; //Sometimes bad definitions can get in from left over extensions or file system lag(caching). We need to clean those. $data = self::cleanVardefs($GLOBALS['dictionary'][$object]); sugar_cache_put($key, $data); }
/** * clear out the cache * */ public static function flushBackendCache() { // This function will flush the cache files used for the module list and the link type lists // TeamSetCache sugar_cache_clear(TEAM_SET_CACHE_KEY); $cachefile = sugar_cached('modules/Teams/TeamSetCache.php'); if (sugar_file_put_contents_atomic($cachefile, "<?php\n\n" . '$teamSets = array();' . "\n ?>") === false) { $GLOBALS['log']->error("File {$cachefile} could not be written (flush)"); } // TeamSetMD5Cache sugar_cache_clear(TEAM_SET_MD5_CACHE_KEY); $cachefile = sugar_cached('modules/Teams/TeamSetMD5Cache.php'); if (sugar_file_put_contents_atomic($cachefile, "<?php\n\n" . '$teamSetsMD5 = array();' . "\n ?>") === false) { $GLOBALS['log']->error("File {$cachefile} could not be written (flush)"); } }
/** * puts connector data in cache * @param array $data */ public function putConnectorCache($data) { // Create the cache directory if need be // fix for the cache/api/metadata problem $cacheDir = 'api/metadata'; mkdir_recursive(sugar_cached($cacheDir)); // Handle the cache file $cacheFile = sugar_cached('api/metadata/connectors.php'); $write = "<?php\n" . '// created: ' . date('Y-m-d H:i:s') . "\n" . '$connectors = ' . var_export_helper($data) . ';'; // Write with atomic writing to prevent issues with simultaneous requests // for this file sugar_file_put_contents_atomic($cacheFile, $write); if (!empty($data['_hash'])) { $this->addToHash('connectors', $data['_hash']); } }
protected function buildRelationshipCache() { global $beanList, $dictionary, $buildingRelCache; if ($buildingRelCache) { return; } $buildingRelCache = true; include "modules/TableDictionary.php"; if (empty($beanList)) { include "include/modules.php"; } //Reload ALL the module vardefs.... foreach ($beanList as $moduleName => $beanName) { VardefManager::loadVardef($moduleName, BeanFactory::getObjectName($moduleName), false, ["ignore_rel_calc_fields" => true]); } $relationships = []; //Grab all the relationships from the dictionary. foreach ($dictionary as $key => $def) { if (!empty($def['relationships'])) { foreach ($def['relationships'] as $relKey => $relDef) { if ($key == $relKey) { $relationships[$key] = array_merge(['name' => $key], $def, $relDef); } else { $relationships[$relKey] = array_merge(['name' => $relKey], $relDef); if (!empty($relationships[$relKey]['join_table']) && empty($relationships[$relKey]['fields']) && isset($dictionary[$relationships[$relKey]['join_table']]['fields'])) { $relationships[$relKey]['fields'] = $dictionary[$relationships[$relKey]['join_table']]['fields']; } } } } } //Save it out sugar_mkdir(dirname($this->getCacheFile()), null, true); $out = "<?php \n \$relationships = " . var_export_helper($relationships) . ";"; sugar_file_put_contents_atomic($this->getCacheFile(), $out); $this->relationships = $relationships; //Now load all vardefs a second time populating the rel_calc_fields foreach ($beanList as $moduleName => $beanName) { VardefManager::loadVardef($moduleName, BeanFactory::getObjectName($moduleName)); } $buildingRelCache = false; }