简介
Wikipedia、Facebook 和 Yahoo! 等主要 web 属性使用 LAMP 架构来为每天数百万的请求提供服务,而 Wordpress、Joomla、Drupal 和 SugarCRM 等 web 应用程序软件使用其架构来让组织轻松部署基于 web 的应用程序。
该架构的优势在于其简单性。而 .NET 这样的堆栈和 Java™ 技术可能使用大量硬件、昂贵的软件栈和复杂的性能调优,LAMP 堆栈可以运行于商品硬件之上,使用开源软件栈。由于软件栈是一个松散的组件集,而非一个整体堆栈,性能调优是一大挑战,因为需要分析和调优每个组件。
然而,这有几个个简单性能任务会对任何规模的网站的性能产生巨大的影响。在本文中,我们将探讨旨在优化 LAMP 应用程序性能的 5 个这样的任务。这些项目应当很少需要对您的应用程序进行架构更改,使其成为最大化您的 web 应用程序所需的响应能力和硬件需求的安全、便捷的选择。
回页首
使用操作码缓存
提高任何 PHP 应用程序(当然是 LAMP 中的 “P”)的性能的最简单方式是利用一个操作码缓存。对于我使用的任何网站,它是我确保存在的一项内容,因为性能影响很大(很多时候有了操作码缓存,响应时间可减少一半)。但是对 PHP 不熟悉的大部分人的一个很大的疑问是,为何改进会如此之大。答案在于 PHP 如何处理 web 请求。图 1 概览了 PHP 请求的流程。
图 1. PHP 请求
由于 PHP 是一种解释语言,而非 C 或 Java 等编译语言,对每个请求执行了 “解析-编译-执行” 的整个步骤。您可以看到为何这会耗时、耗资源,特别是当脚本在请求之间很少变化时。解析和编译脚本之后,脚本作为一系列操作码处于机器可解析状态。这是操作码缓存发挥效用的地方。它作为一系列操作码缓存这些编译脚本,以避免为解析和编译每个请求步骤。您将在图 2 中看到这样的工作流是如何运作的。
图 2. PHP 请求使用操作码缓存
因此当 PHP 脚本的缓存操作码存在时,我们可以跳过 PHP 请求流程的解析和编译步骤,直接执行缓存操作码并输出结果。检查算法负责处理您可能对脚本文件进行了更改的情况,因此在已变更脚本的第一个请求后,会为随后的请求自动重新编译和缓存操作码,替换缓存的脚本。
操作码缓存对于 PHP 流行已久,其中早期的一些要追溯到 PHP V4 的全盛期。目前有一些流行选项正在积极开发和使用中:
- 替代 PHP 缓存(APC)可能是 PHP 最流行的操作码缓存(参见 参考资料)。它由若干核心 PHP 开发人员所开发,做出了很大贡献,Facebook 和 Yahoo! 的工程师赋予了其速度和稳定性。它还支持用于处理 PHP 请求的若干其他速度改进,包括一个用户缓存组件,这将在本文后面探讨。
- Wincache 是主要由 Microsoft® 的 Internet Information Services (IIS) 团队积极开发的一个操作码缓存,仅供在使用 IIS web 服务器的 Windows® 上使用(参见 参考资料)。开发它的主要动力在于使 PHP 成为 Windows-IIS-PHP 堆栈上的一流开发平台,因为据知 APC 在该堆栈上运作的不是很好。它在功能上非常类似于 APC,且支持一个用户缓存组件,以及一个内置会话处理程序,以将 Wincache 作为一个会话处理程序直接加以利用。
- eAccelerator 是原始 PHP 缓存之一 Turck MMCache 操作码缓存(参见 参考资料)的一个派生。不同于 APC 和 Wincache,它仅是一个操作码缓存和优化器,因此它不包含用户缓存组件。它在 UNIX® 和 Windows 堆栈上完全兼容,且对于不打算利用 APC 或 Wincache 提供的其他功能的站点很流行。如果您要使用 memcache 这样的解决方案来为多 web 服务器环境提供一个单独的用户缓存服务器,那么这就是常见情况。
毫无疑问,一个操作码缓存是通过在每次请求后消除解析和编译脚本的需要来加速 PHP 的第一步。完成第一步之后,您应当看到响应时间和服务器负载方面的改进。但是优化 PHP 可以做的不止这些,我们接下来将加以讨论。
回页首
优化您的 PHP 设置
虽然实现操作码缓存是性能改进的一大创举,不过也有大量其他优化选项可供您基于 php.ini 文件中的设置优化您的 PHP 设置。这些设置更适合于生产实例;在开发或测试实例上,您可能不希望做这些变更,因为它会使得应用程序问题的调试变得更难。
让我们看一下对于性能提升很重要的一些项目。
应当禁用的选项
有若干 php.ini 设置应当予以禁用,因为它们常用作向后兼容性:
-
register_globals
— 在 PHP V4.2 之前该功能常常是默认值,其中传入的请求变量被自动赋给普通 PHP 变量。这样做除了引起重大安全问题之外(使未过滤的传入请求数据与普通 PHP 变量内容相混),对每一个请求这样做还会产生开销。因此禁用这一设置使您的应用程序更安全且能提高性能。
-
magic_quotes_*
— 这是 PHP V4 的另一遗留项,其中传入的数据会自动避开有风险的表单数据。它旨在作为一个安全特性,在将传入的数据发送到数据库之前对其进行整理,但不是很有效,因为它不能帮助用户预防常见的 SQL 注入攻击。由于大部分数据库层支持能更好地处理该风险的准备语句,禁用该设置会再次消除这个烦人的性能问题。
-
always_populate_raw_post_data
— 这仅当您出于某些原因需要查看传入的未过滤 POST
数据的整个负载时才需要。否则,它仅在内存中存储 POST 数据的一个副本,而这没有必要。
然而,在遗留代码上禁用这些选项会有风险,因为它们可能取决于其设置来实现正确执行。不应当基于被设置的这些选项来开发任何新代码,而且可能的话,您应当寻求方法来重构您的现有代码,避免使用它们。
应当禁用或调整设置的选项
您可以启用 php.ini 文件的一些优秀性能选项,来提升您的脚本速度:
-
output_buffering
— 您应当确保启用该选项,因为它会以块为单位将输出刷回到浏览器,而非以每个 echo
或 print
语句为单位,而后者会大大减缓您的请求响应时间。
-
variables_order
— 这个指令控制传入请求的 EGPCS(Environment
、Get
、Post
、Cookie
和 Server
)变量解析顺序。如果您没有使用某种超全局变量(比如环境变量),您可以安全地删除它们来获得一点加速,从而避免在每一个请求上解析它们。
-
date.timezone
— 这是在 PHP V5.1 中添加的一个指令,用于设置默认时区,然后用于后面将要介绍的 DateTime
函数。如果您不在 php.ini 文件中设置该选项,PHP 会执行大量系统请求来弄清它是什么,且在 PHP V5.3 中,对每一个请求会发出一个警告。
就以应当在您的生产实例上配置的设置而言,这些被看作是 “唾手可得”。就 PHP 而言,还有一件事需要考虑。这就是您的应用程序中 require()
和 include()
(以及其同级 require_once()
和 include_once()
)的使用。这些函数优化您的 PHP 配置和代码,以防止对每个请求进行不必要的文件状态检查,从而减少响应时间。
回页首
管理您的 require()
和 include()
从性能来看,文件状态调用(即为检查一个文件是否存在而对底层文件系统进行的调用)相当昂贵。文件状态的最大元凶之一以 require()
和 include()
语句的形式出现,这两个语句用于将代码带到脚本中。require_once()
和 include_once()
的同级调用更成问题,因为它们不仅需要验证文件是否存在,而且它之前没有包含在内。
那么解决这个问题的最好方式是什么?您可以做一些事来加快解决。
- 为所有
require()
和 include()
调用使用绝对路径。这将使 PHP 更清楚您希望包含的确切文件,因此无需为您的文件检查整个 include_path
。
- 保持
include_path
中的条目数较低。这在很难为每个 require()
和 include()
调用提供绝对路径的情况(通常在大型遗留应用程序中会出现这种情况)下很有用,方法就是不检查您包含的文件不在的位置。
APC 和 Wincache 还有用于缓存 PHP 进行的文件状态检查结果的机制,因此无需进行反复的文件系统检查。当您将 include 文件名保留为静态而非变量驱动的时,它们最有效,因此尽可能尝试这样做很有用。
回页首
优化您的数据库
数据库优化很快会成为一个前沿话题,我几乎没有空间在这里完全公正地做这个话题。但是如果您在寻求优化您的数据库的速度,首先应当采取一些步骤,这应当对常见问题有所帮助。
将数据库放在自己的机器上
数据库查询自身可以变得相当激烈,通常在对大小合理的数据集执行简单的 SELECT
语句时限定在 100% 的 CPU。如果您的 web 服务器和数据库服务器都在竟用单一机器上的 CPU 时间,这无疑将减慢您的请求速度。因此我想第一步最好是将 web 服务器和数据库服务器放在单独的机器上,确保您的数据库服务器是两者中更强健的(数据库服务器喜欢大量内存和多个 CPU)。
合理设计和编制表索引
数据库性能的最大问题可能源自于不良数据库设计和缺失索引。SELECT
语句通常是运行在典型 web 应用程序中的最常见的查询类型。它们也是在数据库服务器上运行的最耗时的查询。此外,这些类型的 SQL 语句对适当的索引和数据库设计最敏感,因此查看以下指示,获取实现最优性能的技巧。
- 确保每个表都有一个主键。这为表提供一个默认顺序和快速方式来联接其他表。
- 确保一个表中的任何外键(即链接记录到另一个表中的记录的键)的索引得到合理编制。许多数据库会自动对这些键施加约束,以便值真正匹配另一个表中的一条记录,这有助于摆脱这一困难。
- 试图限制一个表中的列数。一个表中有太多列比仅有一些列时进行查询所需的扫描时间要长。此外,如果您有不常用的含多个列的一个表,您也在通过
NULL
值字段浪费磁盘空间。文本或 blob 等可变大小字段也是如此,其中表大小的增长可以远超过需求。在这种情况下,您应当考虑将其他栏分成不同的表,在记录的主键上将其联合起来。
分析在服务器上运行的查询
改进数据库性能的最佳方法是分析在您的数据库服务器上运行什么查询,且运行它们需要多长时间。几乎每个数据库都有具有这种功能的工具。对于 MySQL,您可以利用慢查询日志来查找有问题的查询。要使用它,在 MySQL 配置文件中将 slow_query_log
设置为 1,然后将 log_output 设置为 FILE,将它们记录到文件 hostname-slow.log 中。您可以设置 long_query_time
阈值,确定查询必须运行多少秒才被看作是 “慢查询”。我想建议将该阈值首先设置为 5 秒,随着时间的推移将其缩减为 1 秒,具体取决于您的数据集。如果您探究该文件,您会看到类似于清单 1 的详细查询。
清单 1. MySQL 慢查询日志
/usr/local/mysql/bin/mysqld, Version: 5.1.49-log, started with:
Tcp port: 3306 Unix socket: /tmp/mysql.sock
Time Id Command Argument
# Time: 030207 15:03:33
# User@Host: user[user] @ localhost.localdomain [127.0.0.1]
# Query_time: 13 Lock_time: 0 Rows_sent: 117 Rows_examined: 234
use sugarcrm;
select * from accounts inner join leads on accounts.id = leads.account_id;
|
我们想要考虑的关键对象是 Query_time
,显示查询需要的时间。另一项要考虑的是 Rows_sent
和 Rows_examined
的数量,因为这些可指这样的情况:其中如果一个查询察看太多行或返回太多行,就会被错误地书写。您可以更深入地钻研如何写查询,即在查询开始处加上 EXPLAIN
,它会返回查询计划,而非结果集,如清单 2 所示。
清单 2. MySQL EXPLAIN
结果
mysql> explain select * from accounts inner join leads on accounts.id = leads.account_id;
+----+-------------+----------+--------+--------------------------+---------+---
| id | select_type | table | type | possible_keys
| key | key_len | ref | rows | Extra |
+----+-------------+----------+--------+--------------------------+---------+--------
| 1 | SIMPLE | leads | ALL | idx_leads_acct_del | NULL | NULL
| NULL | 200 | |
| 1 | SIMPLE | accounts | eq_ref | PRIMARY,idx_accnt_id_del | PRIMARY | 108
| sugarcrm.leads.account_id | 1 | |
+----+-------------+----------+--------+--------------------------+---------+---------
2 rows in set (0.00 sec)
|
MySQL 手册更深入探究 EXPLAIN
输出的主题(参见 参考资料),但是我考虑的一项重要内容是 ‘type’ 列为 ‘ALL’ 的地方,因为这需要 MySQL 做一个全表扫描,且不需要键来执行查询。这些帮助您在添加索引时会大幅提高查询速度。
回页首
有效缓存数据
正如我们在上一节看到的,数据库往往容易成为您 web 应用程序性能的最大痛点。但是如果您要查询的数据不经常改变怎么办?在这种情况下,一个好的选择就是在本地存储这些结果,而非针对每个请求调用查询。
我们之前探究的两个操作码缓存 APC 和 Wincache 具有实现上述操作的工具,其中您可以将 PHP 数据直接存储到一个共享内存段中,便于快速查询。清单 3 提供了具体示例。
清单 3. 使用 APC 缓存数据库结果的示例
<?php
function getListOfUsers()
{
$list = apc_fetch('getListOfUsers');
if ( empty($list) ) {
$conn = new PDO('mysql:dbname=testdb;host=127.0.0.1', 'dbuser', 'dbpass');
$sql = 'SELECT id, name FROM users ORDER BY name';
foreach ($conn->query($sql) as $row) {
$list[] = $row;
}
apc_store('getListOfUsers',$list);
}
return $list;
}
|
我们仅需一次执行查询。之后,我们将结果推送到 getListOfUsers
键下的 APC 缓存中。从这里开始,直到缓存到期,您就能够直接从缓存中获取结果数组,跳过 SQL 查询。
APC 和 Wincache 并非一个用户缓存的惟一选择;memcache 和 Redis 是不需要您在与 Web 服务器相同的服务器上运行用户缓存的其他流行选择。这就提高了性能和灵活性,特别是当您的 web 应用程序跨多个 Web 服务器向外扩展时。
回页首
结束语
在本文中,我们探究了调优您的 LAMP 性能的 5 种简单方法。我们不仅通过利用一个操作码缓存和优化 PHP 配置探究了 PHP 级别的技术,而且探究了如何优化您的数据库设计来实现合理的索引编制。我们还探讨了如何利用一个用户缓存(以 APC 为例)来展示如何在数据不经常改变时避免重复的数据库调用。
<!-- CMA ID: 629653 --><!-- Site ID: 10 --><!-- XSLT stylesheet used to transform this file: dw-document-html-6.0.xsl -->
回页首
下载
描述
名字
大小
下载方法
源代码 |
os-5waystunelamp.zip |
|
HTTP |
关于下载方法的信息
分享到:
相关推荐
**LAMP系统性能调优** 是针对基于Linux、Apache、MySQL和PHP/Perl架构的Web应用程序进行优化的过程,以提高其效率和响应速度。LAMP架构广泛用于各种规模的Web应用,从简单的待办事项列表到大型电子商务平台,如...
MySQL是一种关系型数据库管理系统,广泛应用于各种Web应用程序中。由于其高效的数据处理能力和稳定性,MySQL成为了LAMP架构中不可或缺的一部分。 **1.4 PHP(或Perl)脚本语言** PHP是一种用于Web开发的脚本语言,...
【LAMP架构优化】LAMP(Linux,Apache,MySQL,PHP)是许多知名网站和流行的Web应用程序的基础,如Wikipedia、...对于任何规模的LAMP应用程序来说,实施这些策略都可以在不大幅改动架构的情况下,实现性能的最大化。
MySQL 服务器调优 MySQL 服务器调优是提高 MySQL ...许多 LAMP 应用程序都严重依赖于缓存来提高性能。 MySQL 服务器调优是一个复杂的过程,需要对服务器的硬件和软件进行调整,以提高 MySQL 服务器的性能和效率。
- **错误处理:** 可以使用`set_error_handler`来自定义错误处理逻辑,这对于提高应用程序的健壮性非常重要。 - **关闭函数注册:** `register_shutdown_function`可以在脚本结束执行时执行某些操作,例如记录日志、...
随着LAMP(Linux、Apache、MySQL 和 PHP/Perl)架构的广泛应用,开发人员不断开发和部署新的应用程序,但服务器管理员往往对应用程序本身的控制有限。为了达到最高效率,对数据库层进行调优变得至关重要。本文将详细...
在LAMP系统中,Apache、PHP和MySQL是关键组成部分,它们共同构建了一个强大的Web应用程序平台。本文主要关注Apache和PHP的性能调优,以提升整个系统的响应速度和效率。 首先,Apache的性能优化主要涉及其多处理模块...
同时,应持续跟踪和分析系统性能,根据实际情况进行微调,以确保MySQL服务器始终处于最佳运行状态,满足应用程序的需求。 总的来说,LAMP系统性能调优中的MySQL数据库服务器优化是一个涉及硬件、配置和查询逻辑的...
LAMP是一种流行的开源Web服务器软件堆栈组合,适用于运行动态网站或Web应用程序。 #### 一、准备工作 在开始之前,请确保已经具备以下条件: 1. 已安装Redhat5操作系统。 2. 具备基本的Linux命令行操作技能。 3. ...
- **灵活性**:PHP不仅可以用于Web开发,还可以用于命令行脚本和桌面应用程序开发。 - **强大的社区支持**:PHP拥有庞大的开发者社区,提供了大量的框架、类库和教程资源。 #### 三、LAMP的优势 - **成本效益**:...
该书深入探讨了如何使用LAMP技术栈来构建高效的Web应用程序和服务。 #### 主要内容 - **Linux系统管理**: 包括安装配置、安全性设置等。 - **Apache服务器配置**: 如何优化性能、实现负载均衡等。 - **MySQL数据库...
- **时尚组合**:LAMP平台提供了构建现代Web应用程序所需的完整工具链,能够满足从简单的静态网页到复杂的动态网站的各种需求。 - **免费与开源**:所有组件都是免费且开源的,这降低了开发成本,并允许开发者根据...
Linux作为操作系统,Apache是服务器软件,MySQL是数据库管理系统,而PHP则是一种服务器端脚本语言,广泛用于创建动态网页和应用程序。 在【Lamp兄弟连细说PHP全部课件和代码】中,我们可以期待以下内容: 1. **PHP...
LAMP(Linux, Apache, MySQL, PHP)是一种常见的开源软件堆栈,用于构建动态网站和Web应用程序。该架构在IT领域广泛应用,因其免费、高效和可扩展性而受到青睐。以下是对LAMP系统架构实现方案的详细说明。 **一、...
LAMP(Linux、Apache、MySQL、PHP)是一个流行的开源Web服务器解决方案,用于在Linux系统上构建动态网站和web应用程序。这个“LAMP所需部署安装的压缩包”可能包含所有或部分构成LAMP环境的组件,以及可能的配置文件...
在IT行业中,Linux、Apache、MySQL和PHP(简称LAMP)是构建动态网站和Web应用程序的常用基础架构。本文将详细讲解如何在Red Hat Enterprise Linux 4(RHEL4)上部署这一组合,以实现一个高效且可靠的Web服务器环境。...
LAMP环境是指Linux操作系统下的Apache(HTTP服务器)、MySQL(数据库服务器)和PHP(脚本语言)的集成环境,是搭建Web应用程序的基础。在Linux系统中,有RPM包安装和源码包安装两种方法来搭建LAMP环境。 ### RPM包...