Configuration Magento:为任何特定存储禁用模块
假设我有3家商店 我想禁用存储2中的模块。我只希望在存储1和存储3中启用它 我明白我可以通过以下方式做到:Configuration Magento:为任何特定存储禁用模块,configuration,magento,module,Configuration,Magento,Module,假设我有3家商店 我想禁用存储2中的模块。我只希望在存储1和存储3中启用它 我明白我可以通过以下方式做到: 进入系统->配置->高级 从当前配置范围的下拉列表中选择所需的存储 但这并不完全有效 而且,我也不想检查模块代码本身中的存储,也不想为模块创建系统配置字段,以便选中/取消选中存储以启用/禁用 我所期望的是在app/etc/modules/MyNamespace\u MyModule.xml中添加一些代码。我们可以这样做吗?此配置只是在前端布局中禁用模块输出,但模块控制器、事件观察器、管
- 进入系统->配置->高级
- 从当前配置范围的下拉列表中选择所需的存储
我所期望的是在app/etc/modules/MyNamespace\u MyModule.xml中添加一些代码。我们可以这样做吗?此配置只是在前端布局中禁用模块输出,但模块控制器、事件观察器、管理页面等仍在工作 另外,不要忘记在布局文件定义中指定模块名称,否则将为特定存储加载所有布局文件内容:
<config>
<layout>
<module_alias module="Module_Name">
<file>yourlayoutfile.xml</file>
</module_alias>
</layout>
</config>
yourlayoutfile.xml
如果您正在开发一个模块,并且希望在frontent上为特定存储禁用其全部功能,那么您应该创建一个“是/否”类型的配置字段,并通过模块代码中的Mage::getStoreConfigFlag('config/field/path')检查其值 要禁用存储范围上的模块,我发现可以这样做:
<?xml version="1.0"?>
<config>
<modules>
<MyPackage_MyModule>
<active>false</active>
<restricted>mystore1,mystore4,mystore5</restricted>
<codePool>local</codePool>
</MyPackage_MyModule>
</modules>
</config>
将app/code/core/Mage/core/Model/Config.php移动到app/code/local/Mage/core/Model/Config.php
在Config.php中找到“LoadModuleConfiguration”方法,不做任何更改,但添加以下代码使该方法如下所示
public function loadModulesConfiguration($fileName, $mergeToObject = null, $mergeModel=null)
{
$disableLocalModules = !$this->_canUseLocalModules();
if ($mergeToObject === null) {
$mergeToObject = clone $this->_prototype;
$mergeToObject->loadString('<config/>');
}
if ($mergeModel === null) {
$mergeModel = clone $this->_prototype;
}
$modules = $this->getNode('modules')->children();
foreach ($modules as $modName=>$module) {
if ($module->is('active')) {
// Begin additional code
if((bool)$module->restricted) {
$restricted = explode(',', (string)$module->restricted);
$runCode = (isset($_SERVER['MAGE_RUN_CODE']) ? $_SERVER['MAGE_RUN_CODE'] : 'default');
if(in_array($runCode, $restricted)) {
continue;
}
}
// End additional code
if ($disableLocalModules && ('local' === (string)$module->codePool)) {
continue;
}
if (!is_array($fileName)) {
$fileName = array($fileName);
}
foreach ($fileName as $configFile) {
$configFile = $this->getModuleDir('etc', $modName).DS.$configFile;
if ($mergeModel->loadFile($configFile)) {
$mergeToObject->extend($mergeModel, true);
}
}
}
}
return $mergeToObject;
}
公共函数加载模块配置($fileName,$mergeToObject=null,$mergeModel=null)
{
$disableLocalModules=!$this->_canUseLocalModules();
if($mergeToObject==null){
$mergeToObject=克隆$this->\u原型;
$mergeToObject->loadString(“”);
}
如果($mergeModel==null){
$mergeModel=clone$this->\u原型;
}
$modules=$this->getNode('modules')->children();
foreach($modName=>$module形式的模块){
如果($module->is('active')){
//开始附加代码
如果((bool)$模块->受限){
$restricted=分解(“,”,(字符串)$module->restricted);
$runCode=(isset($服务器['MAGE\U运行\U代码])?$服务器['MAGE\U运行\U代码]:'default');
if(在数组中($runCode,$restricted)){
继续;
}
}
//结束附加代码
if($disableLocalModules&('local'==(字符串)$module->codePool)){
继续;
}
如果(!是_数组($fileName)){
$fileName=数组($fileName);
}
foreach($configFile文件名){
$configFile=$this->getModuleDir('etc',$modName).DS.$configFile;
如果($mergeModel->loadFile($configFile)){
$mergeToObject->extend($mergeModel,true);
}
}
}
}
返回$mergeToObject;
}
新代码将使该方法也检查模块xml文件中的新节点。如果该节点存在,则该值将是一个以逗号分隔的存储代码列表,您不希望在其中加载模块。如果有多个存储,则应使用当前存储代码设置$服务器变量“MAGE\u RUN\u CODE”。如果未设置,脚本将回退到假定存储代码为“default”,这是默认情况下的代码,除非出于某种奇怪的原因,您决定在后端更改该代码
模块xml文件可能如下所示:
<?xml version="1.0"?>
<config>
<modules>
<MyPackage_MyModule>
<active>false</active>
<restricted>mystore1,mystore4,mystore5</restricted>
<codePool>local</codePool>
</MyPackage_MyModule>
</modules>
</config>
假的
mystore1、mystore4、mystore5
地方的
这样,在存储代码为mystore1、mystore4或mystore5的存储上,模块甚至不会加载。标签是完全可选的,如果您忽略它,模块将按正常方式加载。也是一个有趣的解决方案
我的客户端安装的Magento 1.8.1.0有一个有问题的模块,在多商店设置中会破坏另一个站点的菜单。Eric Hainer发布的上述解决方案不适用于此安装,因此我对其进行了轻微修改: 我没有使用
$\u服务器['MAGE\u RUN\u code']
,而是使用$\u服务器['SERVER\u NAME']
。工作很有魅力。:)
因此,不是:
$runCode = (isset($_SERVER['MAGE_RUN_CODE']) ? $_SERVER['MAGE_RUN_CODE'] : 'default');
<restricted>mystore1,mystore4,mystore5</restricted>
使用:
而不是:
$runCode = (isset($_SERVER['MAGE_RUN_CODE']) ? $_SERVER['MAGE_RUN_CODE'] : 'default');
<restricted>mystore1,mystore4,mystore5</restricted>
mystore1、mystore4、mystore5
使用:
www.site2.com,www.site3.com
显然,将“www.site1.com”、“www.site2.com”和“www.site3.com”更改为您自己的位置
谢谢你的主意,Eric:)我使用Eric解决方案有一段时间了。在我的例子中,我在我的一个商店中禁用了负责分层导航的特定模块,从而返回到默认的分层导航行为 它看起来很有效,但过了一段时间我注意到分层导航选项停止出现在它们应该出现的地方。很快我就注意到,事实上,这个不应该在这个商店工作的模块继续工作。然后我意识到,当我禁用配置缓存时,Eric的解决方案可以工作,但再次启用后,它就停止了 过了一会儿,我意识到它必须以这种方式工作,启用配置缓存,因为Eric的解决方案仅在生成此xml时才在全局xml中包含(或不包含)指定的配置文件。然后将其缓存并仅从缓存调用。所以当它从应该使用某些模块的站点生成时,它被包括在内,然后在不应该使用它的站点上也被使用 无论如何,我根据Eric的代码(在模块配置中使用受限)制定了另一个解决方案。我认为Magento应该决定在请求类时加载什么。然后它可以检查什么是当前的MAGE_RUN_代码
// Second - if entity is not rewritten then use class prefix to form class name
if (empty($className)) {
if (!empty($config)) {
$className = $config->getClassName();
}
if (empty($className)) {
$className = 'mage_'.$group.'_'.$groupType;
}
if (!empty($class)) {
$className .= '_'.$class;
}
$className = uc_words($className);
}
$this->_classNameCache[$groupRootNode][$group][$class] = $className;
return $className;
public function getGroupedClassName($groupType, $classId, $groupRootNode=null)
{
if (empty($groupRootNode)) {
$groupRootNode = 'global/'.$groupType.'s';
}
$classArr = explode('/', trim($classId));
$group = $classArr[0];
$class = !empty($classArr[1]) ? $classArr[1] : null;
if (isset($this->_classNameCache[$groupRootNode][$group][$class])) {
return $this->_classNameCache[$groupRootNode][$group][$class];
}
$config = $this->_xml->global->{$groupType.'s'}->{$group};
// First - check maybe the entity class was rewritten
$className = null;
if (isset($config->rewrite->$class)) {
$className = (string)$config->rewrite->$class;
} else {
/**
* Backwards compatibility for pre-MMDB extensions.
* In MMDB release resource nodes <..._mysql4> were renamed to <..._resource>. So <deprecatedNode> is left
* to keep name of previously used nodes, that still may be used by non-updated extensions.
*/
if (isset($config->deprecatedNode)) {
$deprecatedNode = $config->deprecatedNode;
$configOld = $this->_xml->global->{$groupType.'s'}->$deprecatedNode;
if (isset($configOld->rewrite->$class)) {
$className = (string) $configOld->rewrite->$class;
}
}
}
//START CHECKING IF CLASS MODULE IS ENABLED
if (strpos($className, 'Pneumatig_') !== false) {
$var = substr($className, 0, strpos($className, '_', strpos($className, '_') + 1));
if (isset($this->_xml->modules->$var)) {
if ((bool)$this->_xml->modules->$var->restricted === true) {
$code = isset($_SERVER['MAGE_RUN_CODE']) ? $_SERVER['MAGE_RUN_CODE'] : 'default';
if (strpos((string)$this->_xml->modules->$var->restricted, $code) !== false) {
$className = '';
}
}
}
}
//END CHECKING IF CLASS MODULE IS ENABLED
// Second - if entity is not rewritten then use class prefix to form class name
if (empty($className)) {
if (!empty($config)) {
$className = $config->getClassName();
}
if (empty($className)) {
$className = 'mage_'.$group.'_'.$groupType;
}
if (!empty($class)) {
$className .= '_'.$class;
}
$className = uc_words($className);
}
$this->_classNameCache[$groupRootNode][$group][$class] = $className;
return $className;
}