如果URL具有某些文件扩展名,RackSpace Cloud会删除$ _SESSION [英] RackSpace Cloud Strips $_SESSION if URL Has Certain File Extensions

查看:394
本文介绍了如果URL具有某些文件扩展名,RackSpace Cloud会删除$ _SESSION的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用传统的LAMP堆栈为RackSpace云上的客户创建了一个视频培训网站(RackSpace的云具有Windows和LAMP堆栈)。我在这个网站上服务的视频和其他媒体文件需要保护,因为我的客户收取钱访问他们。没有DRM或有趣的业务,基本上我们存储的文件以外的web根目录和使用PHP验证用户的,他们能够访问文件之前使用mod_rewrite通过PHP运行请求。

I am creating a video training site for a client on the RackSpace Cloud using the traditional LAMP stack (RackSpace's cloud has both Windows and LAMP stacks). The videos and other media files I'm serving on this site need to be protected as my client charges money for access to them. There is no DRM or funny business like that, essentially we store the files outside of the web root and use PHP to authenticate user's before they are able to access the files by using mod_rewrite to run the request through PHP.

所以让我们假设用户在这个URL请求一个文件:

So let's say the user requests a file at this URL:

http://www.example.com/uploads/preview_image/29.jpg

我使用mod_rewrite重写网址:

I am using mod_rewrite to rewrite that url to:

http://www.example.com/files.php?path=%2Fuploads%2Fpreview_image%2F29.jpg

以下是files.php脚本的简化版本:

Here is a simplified version of the files.php script:

<?php
// Setups the environment and sets $logged_in
// This part requires $_SESSION
require_once('../../includes/user_config.php');

if (!$logged_in) {
    // Redirect non-authenticated users
    header('Location: login.php');
}

// This user is authenticated, continue

$content_type = "image/jpeg";

// getAbsolutePathForRequestedResource() takes 
// a Query Parameter called path and uses DB
// lookups and some string manipulation to get
// an absolute path. This part doesn't have
// any bearing on the problem at hand
$file_path = getAbsolutePathForRequestedResource($_GET['path']);

// At this point $file_path looks something like
// this: "/path/to/a/place/outside/the/webroot"

if (file_exists($file_path) && !is_dir($file_path)) {
    header("Content-Type: $content_type");
    header('Content-Length: ' . filesize($file_path));
    echo file_get_contents($file_path);
} else {
    header('HTTP/1.0 404 Not Found'); 
    header('Status: 404 Not Found');
    echo '404 Not Found';
}
exit();

?>



问题



说这对我完美。在本地测试机器上它像一个魅力。但是一旦部署到云,它停止工作。在一些调试之后,结果是如果对云的请求具有诸如.JPG,.PNG或.SWF(即通常是静态媒体文件的扩展)的某些文件扩展名,请求被路由到称为Varnish的高速缓存系统。这个路由的最终结果是,整个过程使我的PHP脚本会话不存在。

The Problem

Let me start by saying this works perfectly for me. On local test machines it works like a charm. However once deployed to the cloud it stops working. After some debugging it turns out that if a request to the cloud has certain file extensions like .JPG, .PNG, or .SWF (i.e. extensions of typically static media files.) the request is routed to a cache system called Varnish. The end result of this routing is that by the time this whole process makes it to my PHP script the session is not present.

如果我更改URL中的扩展名.PHP或者如果我甚至添加一个查询参数Varnish被绕过,PHP脚本可以获得会话。没问题吧?

If I change the extension in the URL to .PHP or if I even add a query parameter Varnish is bypassed and the PHP script can get the session. No problem right? I'll just add a meaningless query parameter to my requests!

这里是rub:我通过这个系统提供的媒体文件通过编译的SWF文件请求,我有零控制。它们是由第三方软件生成的,我不希望添加或更改他们请求的网址。

Here is the rub: The media files I am serving through this system are being requested through compiled SWF files that I have zero control over. They are generated by third-party software and I have no hope of adding or changing the URLs that they request.

我有这个项目吗?

更新:我应该注意,我已经验证了这种行为与RackSpace支持,他们说他们没有什么能做的。 >

Update: I should note that I have verified this behavior with RackSpace support and they have said there is nothing they can do about it.

推荐答案

如果请求的Flash应用程序遵循重定向,我会尝试在第一个请求时使用重定向回答,并重写第二个,例如

If the requesting flash app is following redirects, I would try to answer with a redirect on the first request and rewrite the second one, e.g.

GET .../29.jpg

header("Status: 302 Moved temporarily");
header("Location: .../r.php?i=29.jpg&random=872938729348");

然后您的r.php会在第二个请求中提交文件。

Then your r.php delivers the file on the second request.

如果不是(btw。always),我会明确地发送头,并提供静态文件,Varnish接受和相应的行为,像

If not (btw. always), I would explicitly send headers along with delivering the static files that Varnish accepts and acts accordingly, something like

header("Cache-Control: no-cache, must-revalidate, max-age=0, post-check=0, pre-check=0");
header("Expires: Sat, 26 Jul 1997 05:00:00 GMT");

和:
我会将 / code>语句,以确保脚本的其余部分不被执行。 header()只发送标头。

我发现使用 ob_start ()作为您的PHP文件中的空格可能会导致在添加标题时出现恼人的错误。

I find it also more reliable to use ob_start() as whitespace in your PHP file may lead to annoying errors when adding headers.

这篇关于如果URL具有某些文件扩展名,RackSpace Cloud会删除$ _SESSION的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆