2010-02-27 68 views
4

我需要一些帮助来理解PHP的内部运作。请记住,在过去,我们曾经写过TSR(终止并保持常驻)例程(Pre-windows era)吗?一旦该程序执行完毕,它将保留在内存中,并可以通过某个热键(alt或ctrl-键组合)重新执行。PHP架构:我该怎么做?

我想在Web服务器/应用程序中使用类似的概念。比如说,我有common_functions.php,它由普通函数(如Generate_City_Combo()或Check_Permission()或Generate_User_Permission_list()等)组成,并运行在该apache/php服务器上运行的所有Web应用程序中。

在所有的模块或应用程序的PHP文件,我可以写:
require_once(common_functions.php);

它将在所有模块和应用程序中包含该通用文件,并且工作正常。

我的问题是:如何在内部处理这个问题?假设我有: 两个应用程序AppOne和AppTwo。
AppOne有两种菜单选项AppOne_Menu_PQR和AppOne_Menu_XYZ
AppTwo有两种菜单选项AppTwo_Menu_ABC和APPTwo_Menu_DEF

这四个菜单项的调用函数{像Generate_City_Combo(),或Check_Permission()或Generate_User_Permission_list()}从common_functions。 php

现在考虑以下情况: A)用户XXX登录并从他的个性化仪表板中点击AppOne_Menu_PQR,然后按照所有屏幕和说明进行操作。这是一系列8-10页的请求(屏幕),它是交互式的。结束后,用户XXX从他的个性化仪表板中点击AppTwo_Menu_DEF,并再次像早先的他/他通过所有屏幕和说明(约8-10页/屏幕)一样。然后用户XXX注销。

在B)用户XXX日志和为所欲为的情况下A.提到的同时,用户也YYY登录(从其他客户机)并执行情景A.

提到的场景类似的事情A,它是同一届会议。对于情景B,有两个不同的会话。

假设所有菜单选项都调用Generate_User_Permission_list()和Generate_Footer()或许多菜单选项调用Generate_City_Combo()。

那么PHP会每页执行/包含common_functions.php多少次?每个会话?或每个PHP启动/关闭?我的理解是common_functions.php将被执行一次每页请求/循环/加载/屏幕,对不对?基本上每一次互动都有一次。

记住像Generate_City_Combo()或Generate_Footer()这样的函数会产生相同的输出或做同样的事情,而不管谁或什么时候调用。

我想限制一次,每个应用程序启动和关闭。

这些只是例子。我的实际问题要复杂得多。在我的应用程序中,我想只调用一次Application_Startup()例程,这将创建理想的环境(如所有查找和参考数据结构,只读数据,安全矩阵,菜单选项,上下文相关的业务执行逻辑等。 )。之后,所有来服务器的请求不必花费任何时间或资源来创建环境,但可以立即指“已创建环境”。

这是不是可行的PHP?怎么样?你能指点我到某个地方或一些解释PHP内部工作的书吗?

在此先感谢。

回答

2

PHP在一个完全独立的执行框架中处理每个HTTP请求 - 没有持续的进程运行来为它们提供服务。 (您的网络服务器正在运行,但每次加载PHP页面时,都会调用一个单独的PHP解释器实例。)

如果您希望生成所需持久区域的时间很长,您可能希望考虑缓存磁盘从这些脚本输出和第一加载缓存的版本,如果它是可用的(而不是过时的)。

+0

谢谢戴维。 有没有办法有一个? 很多次,我已经看到php应用程序创建对象实例左右中心与每个http请求。作为老C开发人员,我觉得它非常高效。有出路吗? 谢谢 Shailesh。 – 2010-02-27 04:36:42

+0

这是PHP工作方式的固有特性 - 它在技术上被设计为一个预处理器(尽管它自创建以来已经有所改进)。 PHP解释器无法同时处理多个请求,因为它旨在由单独的服务器调用(而不是单独运行)。 – Amber 2010-02-27 06:21:06

1

PHP(在几乎所有情况下)是面向页。没有Application_Startup()会维护HTTP请求的状态。

您有时可以通过从数据库或$ _SESSION加载/卸载序列化数据来模拟此过程,但会涉及开销。另外,还有一些其他的情况下,一个memcached服务器可以优化这个为好,但你通常不能使用那些与你典型的虚拟主机服务,如的cPanel。

如果我不得不建立一个像你所说的应用程序,我会将用户选择序列化到会话中,然后保存在数据库中的会话之间持续存在的任何需要。

PHP有几个ORM模块,如Doctrine,它简化了对象到数据库的序列化。

+0

没有相应的global.aspx或global.asa? – 2010-02-27 04:44:51

+0

nope有没有,但你可以用php创建类似的东西:http://sarfraznawaz.wordpress.com/2009/09/08/application-variables-in-php/ – Sarfraz 2010-02-27 05:24:21

+0

Sarfraz是正确的,没有像全球.aspx/global.asa在php中,他在链接中提出的建议使用序列化,并且存在与此相关的非序列化开销。 这是PHP开发人员必须处理的事情。 – 2010-02-27 17:20:33

1

我会说你可能会过早地优化,但有希望。

由于您希望每个请求的稳定性,您经常需要在内存中多次复制已编译的代码;您不希望单独的请求在相同的内存空间中运行并且存在竞争条件或数据损坏的风险!

这就是说,有numerous PHP Accelerators那里将预编译PHP代码,大大加快包括和要求调用。

+0

有没有办法,可以像TomCat一样开发Application Server? – 2010-02-27 04:47:31

0

在这里,我很坏,但是随着PThread的出现,似乎可能会出现针对实际解决方案刺伤的可能性,而不仅仅是实际上说“不,你不能用PHP来完成。“

一个人基本上可以使用CLI工具,socket_ *函数和PThreads在PHP中创建自己的多线程Web服务器。只听端口80,添加请求,请求队列,并启动工作线程的一些数字来处理队列。

可以根据请求队列长度和操作系统的运行队列长度来管理工作人员的数量。每隔几秒,主线程就可以通过一个函数来管理工作池的大小。如果Web请求队列长度大于某个常量时间,则操作系统的运行队列长度和工作数量小于配置的最大值,则可以实例化另一个工作线程。如果Web请求队列长度小于某个其他(较低)常量时间,则操作系统的运行队列长度和工作数量大于配置的最小值,它可以告诉其中一个工作线程在完成当前请求时死亡。然后可以调整常量和配置的值以最大化服务器的所有吞吐量。类似的东西。

你必须做所有你自己的uri解析,你必须自己拼凑HTTP响应等,但工作线程可以实例化扩展Threaded的对象,或者重用先前实例化的Threaded对象。

Voila - PHP TomCat。