[英]custom module slowing drupal
I have worked on a custom shipping module to match my commerce module shipping needs. 我已经开发了一个自定义的运输模块,以满足我的商务模块运输需求。 I have noticed that the module is slowing drupal a lot on a lot the pages even-though I am basically my module should only be hooking to drupal commerce checkout.
我注意到,即使在很多页面上,该模块也使很多Drupal变慢了,尽管我基本上是将我的模块仅挂接到Drupal Commerce Checkout。
Here is my module code: 这是我的模块代码:
function myips_commerce_shipping_method_info() {
$shipping_methods = array();
$shipping_methods['IPS'] = array(
'title' => t('IPS'),
'description' => t('Quote rates from IPS'),
);
return array($shipping_methods);
}
function myips_commerce_shipping_service_info() {
$shipping_services = array();
$shipping_services['myips_shipping_service'] = array( //arbitrary name w/ 'service' in there
'title' => t('Custom Shipping Service'), //title for the interface
'description' => t('Variable rates based on the book origin '),
'display_title' => t('IPS Shipping'),
'shipping_method' => 'IPS',
'price_component' => 'shipping', //from commerce_shipping
'callbacks' => array(
'rate' => 'myips_service_rate_order'),
);
return $shipping_services;
}
function myips_service_rate_order($shipping_service, $order) {
$order_number=$order->order_number;
$currency_code='USD';
$shipping_total=getordershipmentvalue($order_number);
$rates['myips_shipping_service']=array(
'amount' => commerce_currency_decimal_to_amount($shipping_total, $currency_code),
'currency_code' =>$currency_code,
'data' => array(),
);
return $rates[$shipping_service['name']];
}
function getcustomershippingcountry($order_id) {
$order=commerce_order_load($order_id);
$profile_id=$order->commerce_customer_shipping['und']['0']['profile_id'];
$profile=commerce_customer_profile_load($profile_id);
$country= $profile->commerce_customer_address[LANGUAGE_NONE]['0']['country'];
return $country;
}
function getordershipmentvalue($order_id) {
$order=commerce_order_load($order_id);
$total=0;
foreach($order->commerce_line_items[LANGUAGE_NONE] as $line) {
$line_item_id=$line['line_item_id'];
$total=$total+getitemshipmentvalue($line_item_id);
}
return $total;
}
function getitemshipmentvalue($line_item_id){
$line_item=commerce_line_item_load($line_item_id);
$line_quantity=$line_item->quantity;
$order_id= $line_item->order_id;
$destination= getcustomershippingcountry($order_id);
$product_id=$line_item->commerce_product[LANGUAGE_NONE]['0']['product_id'];
$product=commerce_product_load($product_id);
$product_weight=$product->field_book_weight[LANGUAGE_NONE]['0']['weight'];
$product_origin=$product->field_book_origin[LANGUAGE_NONE]['0']['value'];
$line_total=getshippingrates($destination, $product_origin, $product_weight*$line_quantity);
return $line_total;
}
function calculateshippment($shipping_type, $zone, $product_weight) {
$query=new EntityFieldQuery();
$query->entityCondition('entity_type', 'node');
$query->entityCondition('bundle', $shipping_type);
$query->fieldCondition('field_up_to_weight', 'value',$product_weight,'>=');
$query->fieldCondition('field_zone_number', 'value',$zone);
$query->fieldorderby('field_up_to_weight','value','ASC');
$query->range(0,1);
$result=$query->execute();
if(!empty($result)){
$nodes=node_load_multiple(array_keys($result['node']));
foreach($nodes as $node) {
$price=$node->field_shipment_price[LANGUAGE_NONE][0]['value'];
}
}
return $price;
}
function getdestinationzone($destination, $shipping_type) {
$query=new EntityFieldQuery();
$query->entityCondition('entity_type', 'node');
$query->entityCondition('bundle', 'countries_zones');
$query->fieldCondition('field_country_abbreviation', 'value',$destination);
$result=$query->execute();
if(!empty($result)) {
$nodes=node_load_multiple(array_keys($result['node']));
foreach($nodes as $node) {
if($shipping_type=='out_us_zone_prices') {
$zone=$node->field_us_zone[LANGUAGE_NONE]['0']['value'];
}elseif($shipping_type=='mail_zone_prices') {
$zone=$node->field_mail_zone[LANGUAGE_NONE]['0']['value'];
}elseif($shipping_type=='dhl_zone_prices') {
$zone=$node->field_dhl_zone[LANGUAGE_NONE]['0']['value'];
}
}
}
return $zone;
}
function getshippingrates($destination, $product_origin, $product_weight) {
if($product_origin=='US') {
if($destination==$product_origin) {
$shipping_type='us_zone_prices';
}else {
$shipping_type='out_us_zone_prices';
}
/* End of Product Origin US */
}elseif($product_origin=='LB'){
if($destination==$product_origin) {
$shipping_type='mail_zone_prices';
}else {
$shipping_type='dhl_zone_prices';
}
}
$zone=getdestinationzone($destination,$shipping_type);
return calculateshippment($shipping_type, $zone, $product_weight);
}
Why would my module slowing drupal performance? 为什么我的模块会降低Drupal性能?
I think the main problem of your module is that your database queries are in a foreach-loop (in getordershipmentvalue()
) 我认为您模块的主要问题是数据库查询位于foreach循环中(在
getordershipmentvalue()
)
Ok you maybe can't see it immediately, but if you look behind the getitemshipmentvalue()
-call, you can see, that there are many other function calls there. 好的,您也许无法立即看到它,但是如果您查看
getitemshipmentvalue()
call的背后,您会看到那里还有许多其他函数调用。
And over multiple corners the functions calculateshippment()
and getdestinationzone()
will be called. 并在多个角落调用了
calculateshippment()
和getdestinationzone()
函数。 In these functions there are database-queries. 在这些功能中,有数据库查询。
Thats the reason, why your module is so slow: Because over multiple corners you query the database in a loop. 这就是为什么模块如此缓慢的原因:因为您在多个角落中循环查询数据库。 This is similar to a DOS-Attack on the database-server (A bigger problem with great arrays of "commerce_line_items").
这类似于数据库服务器上的DOS攻击(较大的“ commerce_line_items”数组问题更大)。
The solution: Think about your code-design. 解决方案:考虑您的代码设计。 Try to put your database-query-code outside of the foreach-loop.
尝试将数据库查询代码放在foreach循环之外。
I would also prefer to cache the data after the first request. 我也希望在第一个请求之后缓存数据。 (For example with
variable_set()
) (例如,使用
variable_set()
)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.