Thứ Hai, 16 tháng 6, 2014

Identifying Expensive Pages [Optimizing Drupal]

To find out which pages are the most resource intensive, enable the statistics module that is included with Drupal. Although the
statistics module increases the load on your server  (since it records access statistics for your site into your database), it can
beuseful  to see which pages are the most frequently viewed  and  thus the most ripe for query optimization. It also tracks total  pagegeneration time  over a period, which you can specify in Configuration -> Statistics. This is useful  for identifying out-of-control
web crawlerthat are eating up system resources, which you can then ban  on the spot  by visiting Reports -> Top visitors and
clicking “ban.” Be careful, though—its just as easy to ban  a good crawler that drives traffic to your site as a bad one. Make sure
you investigate the origin  of the crawler before banning it.

Identifying  Expensive Code

Consider the following resource-hogging code:

// Very expensive, silly way to  get  node titles.  First we get  the  node IDs
// of  all published   nodes.
$query  = db_select('node', 'n');
$query->fields('n', array('nid'));
$query->condition("n.status", 1);
$query->addTag('node_access');
$result = $query->execute();
// Now  we do a node_load() on each  individual node and save  the  title.
foreach($result as  $row)  {
$node = node_load($row->nid);
$titles[] = check_plain($node->title);
}
Fully loading a node is an expensive operation: hooks run,  modules perform database queries to add  or modify the node, and memory is used to cache the node in node_load()’s internal cache. If yoare not depending on modification to the node by a module, it’s
much faster  to do your own query of the node table directly. Certainly this is a contrived example, but the same pattern can often befound, thais, often data is retrieved via multiple queries that could be combined into a single query, or needless node loading is
performed.

Optimizing Tables

SQL slowness can result from poor implementation of SQL tables in contributed modules. For example, columns without indices may
result in slow queries. A quick way to see how queries are executed by MySQL is to take one of the queries you’ve captured in
your slow query log, prepend the word EXPLAIN to it, and  issue the query to MySQL. The result will be a table showing which indices were used. Consult a good book on MySQL for details.

Caching Queries Manually

If you have very expensive queries that must be performed, perhaps the results can be manually cached by your module. See
Chapter 16 for details on Drupal’s cache API.

Changing the Table Type from MyISAM to InnoDB

Two common choices for MySQL storage engines, often called  table types, are MyISAM and  InnoDB. Drupal uses InnoDB by
default. 
MyISAM uses table-level locking, while InnoDB uses row-level locking.  Locking  is important to preserve database integrity; it
prevents two database processes from trying to update the same data at the same time.  In practice, the difference in locking
strategies means that access to an entire table is blocked during writes  for MyISAM. Therefore, on a busy Drupal site when many
comments are being added, all comment reads are blocked while a new comment is inserted. On InnoDB, this is less of a problem,
since  only the row(s) being written get locked, allowing other server  threads to continue to operate on the remaining rows.However, with MyISAM,table  reads are faster, and  data maintenance and  recovery tools are more mature. See http://dev.mysql.com/tech-resources/articles/storage- engine/part_1.html or http://dev.mysql.com/doc/refman/5.1/en/storage-engines.html for more
information on MySQL’s table  storage architectures. To test whether table-locking issues are the cause of slow performance, you
can analyze lock contention by checking the Table_locks_immediate and  Table_locks_waited status variables within MySQL.

mysql> SHOW STATUS   LIKE   'Table%';

+-----------------------+---------+
| Variable_name                  | Value      |
+-----------------------+---------+
| Table_locks_immediate | 1151552  |
| Table_locks_waited          | 15324      |
+-----------------------+---------+

Table_locks_immediate is the number of times that a table  lock was acquired immediately, and Table_locks_waited is the number of times a table  lock could not be acquired immediately and  a wait was needed. If the Table_locks_waited value is high,and  you
are having performance problems, yomay want  to split up large tables; for example, you might create a dedicated cache table for acustom module or consider ways to reduce the sizes or the frequency of the table  lock commands. One way treduce table  sizes
for some tables, such as the cache_*, watchdog, and  accesslog tables, is by reducing the lifetime of the data. This can be done within the Drupal administrative interface. Also, making sure cron is being run  as often as once an hour will keepthese tables pruned.
Because Drupal can be used in many different ways, it is impossible to give an across-the-board recommendation as to which tables
should use which engine. However, in general, good candidates for conversion to InnoDB are the cache, watchdog, sessions, and
accesslog tables. Fortunately, the conversion to InnoDB is very simple:
ALTER  TABLE  accesslog TYPE='InnoDB';
Of course, this conversion should be done when the site is offline and  your data has been backed up, and  you should be informed about the different characteristics of InnoDB tablesFor MySQL performance tuning, check  out the performance tuning script at www.day32.com/MySQL/which provides suggestions for tuning MySQL server  variables.

Summary

In this chapter, you learned the following:

     How to troubleshoot performance bottlenecks.
     How to optimize a web server.
     How to optimize a database.
     Drupal-specific optimizations.
     Possible multi server architectures.

Không có nhận xét nào:

Đăng nhận xét