Ale*_*lex 37 php sorting graph-theory magento
在Magento中,有一个功能,您可以通过指定在运行总计之前和之后来定义总计算的顺序.
我添加了一个自定义总计,如果我将以下行添加到config.xml,则排序错误.错误的意思是:tax_shipping来之前 shipping.这会导致运费的税费增加两倍.
但这违反了这一条件
tax_shipping
after: shipping
Run Code Online (Sandbox Code Playgroud)
我的猜测:整套规则必定存在一些矛盾.但我怎么能找到它呢?
这是我添加的唯一规则.没有这个规则,tax_shipping就会排序shipping.
<shippingprotectiontax>
<class>n98_shippingprotection/quote_address_total_shippingprotectionTax</class>
<after>subtotal,discount,shipping,tax</after>
<before>grand_total</before>
</shippingprotectiontax>
Run Code Online (Sandbox Code Playgroud)
下面我粘贴usort调用返回的已排序数组.Mage_Sales_Model_Quote_Address_Total_Collector::_getSortedCollectorCodes()
对于那些没有安装Magento的人,代码如下:
/**
* uasort callback function
*
* @param array $a
* @param array $b
* @return int
*/
protected function _compareTotals($a, $b)
{
$aCode = $a['_code'];
$bCode = $b['_code'];
if (in_array($aCode, $b['after']) || in_array($bCode, $a['before'])) {
$res = -1;
} elseif (in_array($bCode, $a['after']) || in_array($aCode, $b['before'])) {
$res = 1;
} else {
$res = 0;
}
return $res;
}
protected function _getSortedCollectorCodes()
{
...
uasort($configArray, array($this, '_compareTotals'));
Mage::log('Sorted:');
// this produces the output below
$loginfo = "";
foreach($configArray as $code=>$data) {
$loginfo .= "$code\n";
$loginfo .= "after: ".implode(',',$data['after'])."\n";
$loginfo .= "before: ".implode(',',$data['before'])."\n";
$loginfo .= "\n";
}
Mage::log($loginfo);
...
Run Code Online (Sandbox Code Playgroud)
日志输出:
nominal
after:
before: subtotal,grand_total
subtotal
after: nominal
before: grand_total,shipping,freeshipping,tax_subtotal,discount,tax,weee,giftwrapping,cashondelivery,cashondelivery_tax,shippingprotection,shippingprotectiontax
freeshipping
after: subtotal,nominal
before: tax_subtotal,shipping,grand_total,tax,discount
tax_shipping
after: shipping,subtotal,freeshipping,tax_subtotal,nominal
before: tax,discount,grand_total,grand_total
giftwrapping
after: subtotal,nominal
before:
tax_subtotal
after: freeshipping,subtotal,subtotal,nominal
before: tax,discount,shipping,grand_total,weee,customerbalance,giftcardaccount,reward
weee
after: subtotal,tax_subtotal,nominal,freeshipping,subtotal,subtotal,nominal
before: tax,discount,grand_total,grand_total,tax
shipping
after: subtotal,freeshipping,tax_subtotal,nominal
before: grand_total,discount,tax_shipping,tax,cashondelivery,cashondelivery_tax,shippingprotection,shippingprotectiontax
discount
after: subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee
before: grand_total,tax,customerbalance,giftcardaccount,reward,cashondelivery,cashondelivery_tax,shippingprotection,shippingprotectiontax
cashondelivery
after: subtotal,discount,shipping,nominal,subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee,subtotal,freeshipping,tax_subtotal,nominal
before: tax,grand_total,grand_total,customerbalance,giftcardaccount,tax_giftwrapping,reward,customerbalance,giftcardaccount,reward
shippingprotection
after: subtotal,discount,shipping,nominal,subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee,subtotal,freeshipping,tax_subtotal,nominal
before: tax,grand_total,grand_total,customerbalance,giftcardaccount,tax_giftwrapping,reward,cashondelivery_tax,customerbalance,giftcardaccount,reward
tax
after: subtotal,shipping,discount,tax_subtotal,freeshipping,tax_shipping,nominal,weee,cashondelivery,shippingprotection
before: grand_total,customerbalance,giftcardaccount,tax_giftwrapping,reward,cashondelivery_tax,shippingprotectiontax
shippingprotectiontax
after: subtotal,discount,shipping,tax,nominal,subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee,subtotal,freeshipping,tax_subtotal,nominal,subtotal,shipping,discount,tax_subtotal,freeshipping,tax_shipping,nominal,weee,cashondelivery,shippingprotection
before: grand_total,customerbalance,giftcardaccount,reward
cashondelivery_tax
after: subtotal,discount,shipping,tax,nominal,subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee,subtotal,freeshipping,tax_subtotal,nominal,subtotal,shipping,discount,tax_subtotal,freeshipping,tax_shipping,nominal,weee,cashondelivery
before: grand_total,customerbalance,giftcardaccount,reward
tax_giftwrapping
after: tax,subtotal,shipping,discount,tax_subtotal,freeshipping,tax_shipping,nominal,weee
before: grand_total,customerbalance,giftcardaccount
grand_total
after: subtotal,nominal,shipping,freeshipping,tax_subtotal,discount,tax,tax_giftwrapping,cashondelivery,cashondelivery_tax,shippingprotection,shippingprotectiontax
before: customerbalance,giftcardaccount,reward
reward
after: wee,discount,tax,tax_subtotal,grand_total,subtotal,shipping,nominal,freeshipping,tax_subtotal,tax_shipping,weee,subtotal,shipping,discount,tax_subtotal,freeshipping,tax_shipping,nominal,weee,freeshipping,subtotal,subtotal,nominal,subtotal,nominal,shipping,freeshipping,tax_subtotal,discount,tax,tax_giftwrapping
before: giftcardaccount,customerbalance,customerbalance
giftcardaccount
after: wee,discount,tax,tax_subtotal,grand_total,reward,subtotal,shipping,nominal,freeshipping,tax_shipping,weee
before: customerbalance
customerbalance
after: wee,discount,tax,tax_subtotal,grand_total,reward,giftcardaccount,subtotal,shipping,nominal,freeshipping,tax_shipping,weee
before:
Run Code Online (Sandbox Code Playgroud)
编辑:
在Vinai的回答后,我添加了更多的调试代码
$fp = fopen('/tmp/dotfile','w');
fwrite($fp,"digraph TotalOrder\n");
fwrite($fp,"{\n");
foreach($configArray as $code=>$data) {
$_code = $data['_code'];
foreach($data['before'] as $beforeCode) {
fwrite($fp,"$beforeCode -> $_code;\n");
}
foreach($data['after'] as $afterCode) {
fwrite($fp,"$_code -> $afterCode;\n");
}
}
fwrite($fp,"}\n");
fclose($fp);
Run Code Online (Sandbox Code Playgroud)
并用graphviz将其可视化:dot -Tpng dotfile > viz.png.这是第一次尝试的结果.排序后调用.

EDIT2:
我觉得这很没用.
所以我在合并after/before条目之前对数组进行了可视化.(紧接着$configArray = $this->_modelsConfig;)
这是没有我的shippingprotectiontax条目:

这是我的shippingprotectiontax条目:

我没有看到任何明显的矛盾.
EDIT3:
在uasort之前的配置数组:
array (
'nominal' =>
array (
'class' => 'sales/quote_address_total_nominal',
'before' =>
array (
0 => 'subtotal',
1 => 'grand_total',
),
'renderer' => 'checkout/total_nominal',
'after' =>
array (
),
'_code' => 'nominal',
),
'subtotal' =>
array (
'class' => 'sales/quote_address_total_subtotal',
'after' =>
array (
0 => 'nominal',
),
'before' =>
array (
0 => 'grand_total',
1 => 'shipping',
2 => 'freeshipping',
3 => 'tax_subtotal',
4 => 'discount',
5 => 'tax',
6 => 'weee',
7 => 'giftwrapping',
8 => 'cashondelivery',
9 => 'cashondelivery_tax',
10 => 'shippingprotection',
11 => 'shippingprotectiontax',
),
'renderer' => 'tax/checkout_subtotal',
'admin_renderer' => 'adminhtml/sales_order_create_totals_subtotal',
'_code' => 'subtotal',
),
'shipping' =>
array (
'class' => 'sales/quote_address_total_shipping',
'after' =>
array (
0 => 'subtotal',
1 => 'freeshipping',
2 => 'tax_subtotal',
3 => 'nominal',
),
'before' =>
array (
0 => 'grand_total',
1 => 'discount',
2 => 'tax_shipping',
3 => 'tax',
4 => 'cashondelivery',
5 => 'cashondelivery_tax',
6 => 'shippingprotection',
7 => 'shippingprotectiontax',
),
'renderer' => 'tax/checkout_shipping',
'admin_renderer' => 'adminhtml/sales_order_create_totals_shipping',
'_code' => 'shipping',
),
'grand_total' =>
array (
'class' => 'sales/quote_address_total_grand',
'after' =>
array (
0 => 'subtotal',
1 => 'nominal',
2 => 'shipping',
3 => 'freeshipping',
4 => 'tax_subtotal',
5 => 'discount',
6 => 'tax',
7 => 'tax_giftwrapping',
8 => 'cashondelivery',
9 => 'cashondelivery_tax',
10 => 'shippingprotection',
11 => 'shippingprotectiontax',
),
'renderer' => 'tax/checkout_grandtotal',
'admin_renderer' => 'adminhtml/sales_order_create_totals_grandtotal',
'before' =>
array (
0 => 'customerbalance',
1 => 'giftcardaccount',
2 => 'reward',
),
'_code' => 'grand_total',
),
'freeshipping' =>
array (
'class' => 'salesrule/quote_freeshipping',
'after' =>
array (
0 => 'subtotal',
1 => 'nominal',
),
'before' =>
array (
0 => 'tax_subtotal',
1 => 'shipping',
2 => 'grand_total',
3 => 'tax',
4 => 'discount',
),
'_code' => 'freeshipping',
),
'discount' =>
array (
'class' => 'salesrule/quote_discount',
'after' =>
array (
0 => 'subtotal',
1 => 'shipping',
2 => 'nominal',
3 => 'freeshipping',
4 => 'tax_subtotal',
5 => 'tax_shipping',
6 => 'weee',
),
'before' =>
array (
0 => 'grand_total',
1 => 'tax',
2 => 'customerbalance',
3 => 'giftcardaccount',
4 => 'reward',
5 => 'cashondelivery',
6 => 'cashondelivery_tax',
7 => 'shippingprotection',
8 => 'shippingprotectiontax',
),
'renderer' => 'tax/checkout_discount',
'admin_renderer' => 'adminhtml/sales_order_create_totals_discount',
'_code' => 'discount',
),
'tax_subtotal' =>
array (
'class' => 'tax/sales_total_quote_subtotal',
'after' =>
array (
0 => 'freeshipping',
1 => 'subtotal',
2 => 'subtotal',
3 => 'nominal',
),
'before' =>
array (
0 => 'tax',
1 => 'discount',
2 => 'shipping',
3 => 'grand_total',
4 => 'weee',
5 => 'customerbalance',
6 => 'giftcardaccount',
7 => 'reward',
),
'_code' => 'tax_subtotal',
),
'tax_shipping' =>
array (
'class' => 'tax/sales_total_quote_shipping',
'after' =>
array (
0 => 'shipping',
1 => 'subtotal',
2 => 'freeshipping',
3 => 'tax_subtotal',
4 => 'nominal',
),
'before' =>
array (
0 => 'tax',
1 => 'discount',
2 => 'grand_total',
3 => 'grand_total',
),
'_code' => 'tax_shipping',
),
'tax' =>
array (
'class' => 'tax/sales_total_quote_tax',
'after' =>
array (
0 => 'subtotal',
1 => 'shipping',
2 => 'discount',
3 => 'tax_subtotal',
4 => 'freeshipping',
5 => 'tax_shipping',
6 => 'nominal',
7 => 'weee',
8 => 'cashondelivery',
9 => 'shippingprotection',
),
'before' =>
array (
0 => 'grand_total',
1 => 'customerbalance',
2 => 'giftcardaccount',
3 => 'tax_giftwrapping',
4 => 'reward',
5 => 'cashondelivery_tax',
6 => 'shippingprotectiontax',
),
'renderer' => 'tax/checkout_tax',
'admin_renderer' => 'adminhtml/sales_order_create_totals_tax',
'_code' => 'tax',
),
'weee' =>
array (
'class' => 'weee/total_quote_weee',
'after' =>
array (
0 => 'subtotal',
1 => 'tax_subtotal',
2 => 'nominal',
3 => 'freeshipping',
4 => 'subtotal',
5 => 'subtotal',
6 => 'nominal',
),
'before' =>
array (
0 => 'tax',
1 => 'discount',
2 => 'grand_total',
3 => 'grand_total',
4 => 'tax',
),
'_code' => 'weee',
),
'customerbalance' =>
array (
'class' => 'enterprise_customerbalance/total_quote_customerbalance',
'after' =>
array (
0 => 'wee',
1 => 'discount',
2 => 'tax',
3 => 'tax_subtotal',
4 => 'grand_total',
5 => 'reward',
6 => 'giftcardaccount',
7 => 'subtotal',
8 => 'shipping',
9 => 'nominal',
10 => 'freeshipping',
11 => 'tax_shipping',
12 => 'weee',
),
'renderer' => 'enterprise_customerbalance/checkout_total',
'before' =>
array (
),
'_code' => 'customerbalance',
),
'giftcardaccount' =>
array (
'class' => 'enterprise_giftcardaccount/total_quote_giftcardaccount',
'after' =>
array (
0 => 'wee',
1 => 'discount',
2 => 'tax',
3 => 'tax_subtotal',
4 => 'grand_total',
5 => 'reward',
6 => 'subtotal',
7 => 'shipping',
8 => 'nominal',
9 => 'freeshipping',
11 => 'tax_shipping',
12 => 'weee',
),
'before' =>
array (
0 => 'customerbalance',
),
'renderer' => 'enterprise_giftcardaccount/checkout_cart_total',
'_code' => 'giftcardaccount',
),
'giftwrapping' =>
array (
'class' => 'enterprise_giftwrapping/total_quote_giftwrapping',
'after' =>
array (
0 => 'subtotal',
1 => 'nominal',
),
'renderer' => 'enterprise_giftwrapping/checkout_totals',
'before' =>
array (
),
'_code' => 'giftwrapping',
),
'tax_giftwrapping' =>
array (
'class' => 'enterprise_giftwrapping/total_quote_tax_giftwrapping',
'after' =>
array (
0 => 'tax',
1 => 'subtotal',
2 => 'shipping',
3 => 'discount',
4 => 'tax_subtotal',
5 => 'freeshipping',
6 => 'tax_shipping',
7 => 'nominal',
8 => 'weee',
),
'before' =>
array (
0 => 'grand_total',
1 => 'customerbalance',
2 => 'giftcardaccount',
),
'_code' => 'tax_giftwrapping',
),
'reward' =>
array (
'class' => 'enterprise_reward/total_quote_reward',
'after' =>
array (
0 => 'wee',
1 => 'discount',
2 => 'tax',
3 => 'tax_subtotal',
4 => 'grand_total',
5 => 'subtotal',
6 => 'shipping',
7 => 'nominal',
8 => 'freeshipping',
9 => 'tax_subtotal',
10 => 'tax_shipping',
11 => 'weee',
12 => 'subtotal',
13 => 'shipping',
14 => 'discount',
15 => 'tax_subtotal',
16 => 'freeshipping',
17 => 'tax_shipping',
18 => 'nominal',
19 => 'weee',
20 => 'freeshipping',
21 => 'subtotal',
22 => 'subtotal',
23 => 'nominal',
24 => 'subtotal',
25 => 'nominal',
26 => 'shipping',
27 => 'freeshipping',
28 => 'tax_subtotal',
29 => 'discount',
30 => 'tax',
31 => 'tax_giftwrapping',
),
'before' =>
array (
0 => 'giftcardaccount',
1 => 'customerbalance',
2 => 'customerbalance',
),
'renderer' => 'enterprise_reward/checkout_total',
'_code' => 'reward',
),
'cashondelivery' =>
array (
'class' => 'cashondelivery/quote_total',
'after' =>
array (
0 => 'subtotal',
1 => 'discount',
2 => 'shipping',
3 => 'nominal',
4 => 'subtotal',
5 => 'shipping',
6 => 'nominal',
7 => 'freeshipping',
8 => 'tax_subtotal',
9 => 'tax_shipping',
10 => 'weee',
11 => 'subtotal',
12 => 'freeshipping',
13 => 'tax_subtotal',
14 => 'nominal',
),
'before' =>
array (
0 => 'tax',
1 => 'grand_total',
2 => 'grand_total',
3 => 'customerbalance',
4 => 'giftcardaccount',
5 => 'tax_giftwrapping',
6 => 'reward',
7 => 'customerbalance',
8 => 'giftcardaccount',
9 => 'reward',
),
'renderer' => 'cashondelivery/checkout_cod',
'admin_renderer' => 'cashondelivery/adminhtml_sales_order_create_totals_cod',
'_code' => 'cashondelivery',
),
'cashondelivery_tax' =>
array (
'class' => 'cashondelivery/quote_taxTotal',
'after' =>
array (
0 => 'subtotal',
1 => 'discount',
2 => 'shipping',
3 => 'tax',
4 => 'nominal',
5 => 'subtotal',
6 => 'shipping',
7 => 'nominal',
8 => 'freeshipping',
9 => 'tax_subtotal',
10 => 'tax_shipping',
11 => 'weee',
12 => 'subtotal',
13 => 'freeshipping',
14 => 'tax_subtotal',
15 => 'nominal',
16 => 'subtotal',
17 => 'shipping',
18 => 'discount',
19 => 'tax_subtotal',
20 => 'freeshipping',
21 => 'tax_shipping',
22 => 'nominal',
23 => 'weee',
24 => 'cashondelivery',
),
'before' =>
array (
0 => 'grand_total',
1 => 'customerbalance',
2 => 'giftcardaccount',
3 => 'reward',
),
'_code' => 'cashondelivery_tax',
),
'shippingprotection' =>
array (
'class' => 'n98_shippingprotection/quote_address_total_shippingprotection',
'after' =>
array (
0 => 'subtotal',
1 => 'discount',
2 => 'shipping',
3 => 'nominal',
4 => 'subtotal',
5 => 'shipping',
6 => 'nominal',
7 => 'freeshipping',
8 => 'tax_subtotal',
9 => 'tax_shipping',
10 => 'weee',
11 => 'subtotal',
12 => 'freeshipping',
13 => 'tax_subtotal',
14 => 'nominal',
),
'before' =>
array (
0 => 'tax',
1 => 'grand_total',
2 => 'grand_total',
3 => 'customerbalance',
4 => 'giftcardaccount',
5 => 'tax_giftwrapping',
6 => 'reward',
7 => 'cashondelivery_tax',
8 => 'customerbalance',
9 => 'giftcardaccount',
10 => 'reward',
),
'_code' => 'shippingprotection',
),
'shippingprotectiontax' =>
array (
'class' => 'n98_shippingprotection/quote_address_total_shippingprotectionTax',
'after' =>
array (
0 => 'subtotal',
1 => 'discount',
2 => 'shipping',
3 => 'tax',
4 => 'nominal',
5 => 'subtotal',
6 => 'shipping',
7 => 'nominal',
8 => 'freeshipping',
9 => 'tax_subtotal',
10 => 'tax_shipping',
11 => 'weee',
12 => 'subtotal',
13 => 'freeshipping',
14 => 'tax_subtotal',
15 => 'nominal',
16 => 'subtotal',
17 => 'shipping',
18 => 'discount',
19 => 'tax_subtotal',
20 => 'freeshipping',
21 => 'tax_shipping',
22 => 'nominal',
23 => 'weee',
24 => 'cashondelivery',
25 => 'shippingprotection',
),
'before' =>
array (
0 => 'grand_total',
1 => 'customerbalance',
2 => 'giftcardaccount',
3 => 'reward',
),
'_code' => 'shippingprotectiontax',
),
)
更新: Magento Bug Ticket:https : //jira.magento.com/browse/MCACE-129
Vin*_*nai 20
感谢持久的@Alex,这是一个更好的答案,更好的解释:)我的第一个答案是错误的.
PHP 为所有数组排序函数实现快速排序(引用zend_qsort.c).
如果数组中的两个记录相同,则它们的位置将被交换.
问题是礼品包装总记录,据说,它_compareTotals()大于小计和名义,但等于所有其他总数.
根据$confArray输入数组的原始顺序和枢轴元素的位置,将礼品包装与折扣交换是合法的,因为两者是相等的,即使折扣大于运费.
从排序算法的角度来看,这可能会使问题更加清晰:
有几种可能的解决方案,即使最初的问题是选择快速排序来构建有向非循环依赖图
有趣的是,没有很多PHP软件包可供使用.有一个孤立的PEAR包Structures_Graph.使用它可能是快速解决方案,但这意味着将其$confArray转换为Structures_Graph结构(所以可能不那么快).
维基百科很好地解释了这个问题,因此滚动自己的解决方案可能是一个有趣的挑战.在德国Wikipedia拓扑排序页面打破了问题转化为逻辑步骤,并且还具有PERL一个很好的例子算法.
Ale*_*lex 17
最后,这是我对这个问题的补丁.
它实现了Vinai建议的拓扑排序.
app/code/core/Mage/Sales/Model/Config/Ordered.php到app/code/local/Mage/Sales/Model/Config/Ordered.phptotal-sorting.patch并调用patch -p0 app/code/local/Mage/Sales/Model/Config/Ordered.php如果是升级,请务必重新应用这些步骤.
该补丁经过测试可与Magento 1.7.0.2配合使用
--- app/code/core/Mage/Sales/Model/Config/Ordered.php 2012-08-14 14:19:50.306504947 +0200
+++ app/code/local/Mage/Sales/Model/Config/Ordered.php 2012-08-15 10:00:47.027003404 +0200
@@ -121,6 +121,78 @@
return $totalConfig;
}
+// [PATCHED CODE BEGIN]
+
+ /**
+ * Topological sort
+ *
+ * Copyright: http://www.calcatraz.com/blog/php-topological-sort-function-384
+ * And fix see comment on http://stackoverflow.com/questions/11953021/topological-sorting-in-php
+ *
+ * @param $nodeids Node Ids
+ * @param $edges Array of Edges. Each edge is specified as an array with two elements: The source and destination node of the edge
+ * @return array|null
+ */
+ function topological_sort($nodeids, $edges) {
+ $L = $S = $nodes = array();
+ foreach($nodeids as $id) {
+ $nodes[$id] = array('in'=>array(), 'out'=>array());
+ foreach($edges as $e) {
+ if ($id==$e[0]) { $nodes[$id]['out'][]=$e[1]; }
+ if ($id==$e[1]) { $nodes[$id]['in'][]=$e[0]; }
+ }
+ }
+ foreach ($nodes as $id=>$n) { if (empty($n['in'])) $S[]=$id; }
+ while ($id = array_shift($S)) {
+ if (!in_array($id, $L)) {
+ $L[] = $id;
+ foreach($nodes[$id]['out'] as $m) {
+ $nodes[$m]['in'] = array_diff($nodes[$m]['in'], array($id));
+ if (empty($nodes[$m]['in'])) { $S[] = $m; }
+ }
+ $nodes[$id]['out'] = array();
+ }
+ }
+ foreach($nodes as $n) {
+ if (!empty($n['in']) or !empty($n['out'])) {
+ return null; // not sortable as graph is cyclic
+ }
+ }
+ return $L;
+ }
+
+ /**
+ * Sort config array
+ *
+ * public to be easily accessable by test
+ *
+ * @param $configArray
+ * @return array
+ */
+ public function _topSortConfigArray($configArray)
+ {
+ $nodes = array_keys($configArray);
+ $edges = array();
+
+ foreach ($configArray as $code => $data) {
+ $_code = $data['_code'];
+ if (!isset($configArray[$_code])) continue;
+ foreach ($data['before'] as $beforeCode) {
+ if (!isset($configArray[$beforeCode])) continue;
+ $edges[] = array($_code, $beforeCode);
+ }
+
+ foreach ($data['after'] as $afterCode) {
+ if (!isset($configArray[$afterCode])) continue;
+ $edges[] = array($afterCode, $_code);
+ }
+ }
+ return $this->topological_sort($nodes, $edges);
+ }
+
+// [PATCHED CODE END]
+
+
/**
* Aggregate before/after information from all items and sort totals based on this data
*
@@ -138,38 +210,16 @@
// invoke simple sorting if the first element contains the "sort_order" key
reset($configArray);
$element = current($configArray);
+ // [PATCHED CODE BEGIN]
if (isset($element['sort_order'])) {
uasort($configArray, array($this, '_compareSortOrder'));
+ $sortedCollectors = array_keys($configArray);
+
} else {
- foreach ($configArray as $code => $data) {
- foreach ($data['before'] as $beforeCode) {
- if (!isset($configArray[$beforeCode])) {
- continue;
- }
- $configArray[$code]['before'] = array_unique(array_merge(
- $configArray[$code]['before'], $configArray[$beforeCode]['before']
- ));
- $configArray[$beforeCode]['after'] = array_merge(
- $configArray[$beforeCode]['after'], array($code), $data['after']
- );
- $configArray[$beforeCode]['after'] = array_unique($configArray[$beforeCode]['after']);
- }
- foreach ($data['after'] as $afterCode) {
- if (!isset($configArray[$afterCode])) {
- continue;
- }
- $configArray[$code]['after'] = array_unique(array_merge(
- $configArray[$code]['after'], $configArray[$afterCode]['after']
- ));
- $configArray[$afterCode]['before'] = array_merge(
- $configArray[$afterCode]['before'], array($code), $data['before']
- );
- $configArray[$afterCode]['before'] = array_unique($configArray[$afterCode]['before']);
- }
- }
- uasort($configArray, array($this, '_compareTotals'));
+ $sortedCollectors = $this->_topSortConfigArray($configArray);
}
- $sortedCollectors = array_keys($configArray);
+ // [PATCHED CODE END]
+
if (Mage::app()->useCache('config')) {
Mage::app()->saveCache(serialize($sortedCollectors), $this->_collectorsCacheKey, array(
Mage_Core_Model_Config::CACHE_TAG
@@ -196,27 +246,6 @@
}
/**
- * Callback that uses after/before for comparison
- *
- * @param array $a
- * @param array $b
- * @return int
- */
- protected function _compareTotals($a, $b)
- {
- $aCode = $a['_code'];
- $bCode = $b['_code'];
- if (in_array($aCode, $b['after']) || in_array($bCode, $a['before'])) {
- $res = -1;
- } elseif (in_array($bCode, $a['after']) || in_array($aCode, $b['before'])) {
- $res = 1;
- } else {
- $res = 0;
- }
- return $res;
- }
-
- /**
* Callback that uses sort_order for comparison
*
* @param array $a
编辑:还有另一个建议的变化(对于Magento 2):https://github.com/magento/magento2/pull/49
| 归档时间: |
|
| 查看次数: |
11572 次 |
| 最近记录: |