我有一个使用某些资源的对象,比如
class UseResources {
protected $proc_open;
public function __construct()
{
$this->proc_open = proc_open( ... );
}
public function cleanup()
{
proc_close($this->proc_open);
}
};
我试图在.unload
事件上发送ajax请求,但这不是我要找的内容。
我希望能够在用户关闭窗口或浏览器后或连接丢失后调用清理方法吗?
答案 0 :(得分:1)
当窗口关闭时,unload
事件会触发,但也会在用户刷新页面或导航到新页面时触发(即使新页面位于您的站点内)。在这种情况下,我建议不要使用unload
。例如,unload
更适用于提示用户在离开表单之前保存或丢失更改等内容。)
另外,如果你实现了一个javascript解决方案,你要么(1)要求javascript使用该站点(并向那些禁用JS的人显示<noscript></noscript>
元素),或者(2)代码使得你不是仅依靠窗口关闭/清理检测例程来释放资源。
我通常用来做这样的事情的策略是使用ping进程。基本上:客户端向服务器发送常规ping命令,当收到ping时,它会将连接/会话的idle
计数器重置为0
。根据需要,每分钟左右发生一次。一个长时间运行的循环线程(Session
管理器,如果你愿意的话)然后检查任何闲置超过idle threshhold
的客户端(比如说3分钟,但由你决定),如果超出则释放与该连接/会话相关的资源。然后,站点中的每个页面(如果适用)都会添加此ping代码,以便客户端在浏览器中打开页面时开始ping。
<强>优势强>
idle
计数器将在下一页重置<强>缺点强>
setTimeout
或setInterval
和XMLHttpRequest
)客户端页面的粗略示例代码:
function pingServer() {
var req;
if (window.XMLHttpRequest) {
req = new XMLHttpRequest();
} else {
req = new ActiveXObject("Microsoft.XMLHTTP");
}
req.onreadystatechange = function() {
if (req.readyState == 4 && req.status == 200) {
alert("Idle timer reset on server");
}
}
var url = 'ping.php'; // call php code that will reset idle timer for this client
req.open("GET", url, true);
req.send();
}
var pingFrequencyMs = 5 * 1000; // ping every 5 secs
setInterval(pingServer, pingFrequencyMs);
<noscript>Sorry, JavaScript is required for this website.</noscript>
以下是您可以在服务器端使用的一个非常粗略的流程示例,但在您提供更多详细信息之前,我只能推测您正在使用哪种Web应用程序:
服务器Ping例程(伪代码,可以是PHP,ASP,JSP等)
unique ID
(或会话ID,或其他)idle
计时器的当前值,否则默认为0
(可以从内存缓存,数据库,磁盘上的文件中获取;您的选择)max idle
(超时)idle
与max idle
idle
超过max idle
,则结束会话(无论这意味着什么;关闭连接/会话特定资源等 - 在您的情况下,这意味着调用cleanup
例程,但要确保它具有正确的对象上下文),否则将idle
重置为0