使用 Cloudfront 将 S3 子文件夹重定向到另一个域

Redirect S3 subfolder to another domain with Cloudfront

我有一个托管在 S3 上并使用 CloudFront 的静态展示网站,以及一个在线商店 (Prestashop) 和一个博客 (Wordpress),它们都托管在 OVH 服务器上。

我想在我的静态网站的两个子文件夹上进行隐藏重定向,这样就好像我的 3 个网站在同一台主机上一样,使用以下模式:

当然,我需要以这种方式处理每个请求,最终得到类似的东西:

我的网站.com/store/fr/1-myproduct.html

returns什么

mystore.com/fr/1-myproduct.html

会回来的。

这看起来真的很棘手,因为我没有找到真正解决我的问题的方法,在这一点上我怀疑是否有可能做这样的事情。 我考虑过使用代理,但那不是像用大锤打苍蝇一样吗?

我已经搜索了任何可能的重定向,但我只能找到 subdomain/domain 个重定向...

所以我的问题是"How can I do that ?" 但现在我想知道 "Can one do that ?"


P.S : 这是我第一次 post ,我习惯在 posting 之前搜索很长时间,我总是最终找到解决方案,除了现在.欢迎任何建议。

I'll check about proxies since it's my last hope

等等。

I have a static showcase website hosted on S3 and using CloudFront

CloudFront 是反向代理

根据您对其他两个站点的灵活性,CloudFront 可以将您带到您想去的地方,将多个独立站点组合在一个主机名下。

这是通过为您的分发创建额外的源服务器,然后创建额外的缓存行为来完成的,路径模式与额外的路径相匹配,例如 /blog/blog/* 将请求发送到备用起源。

但是,有一个问题。 CloudFront 无法删除匹配的模式,因此 mainsite.example.com/blog/hello-world,匹配模式 /blog/* 将被转发到 blog.example.com/blog/hello-world -- 而不是 blog.example.com/hello-world.¹ 这将需要更改其他站点以便以这种方式集成它们。

除非……

如果您已经拥有独特的路径模式,那没问题,但如果额外站点的内容位于每个单独站点的根目录中,您就会在此处看到问题。并非无法克服,但仍然是一个问题。

您唯一的选择是在 CloudFront 后面使用反向代理来重写这些路径并将请求发送到备用服务器。这也没什么大不了的,因为 HAProxy、Nginx 和 Varnish 都提供了这样的功能,并且可以在非常小的硬件上处理大量代理请求。

最近(2017 年)发布的 Lambda@Edge 服务允许您在必要时在处理请求时即时重写路径。

但最重要的是,除了代理之外,您还没有找到真正的解决方案的原因是别无选择——给定主机名的每条路径都必须在一个逻辑位置处理——一组一个或多个相同配置的端点。在 CloudFront 的情况下,逻辑位置在物理上分布在全球范围内。


¹ CloudFront 实际上可以在转发请求之前预先添加到路径中,因此 mainsite.example.com/bar/fizz 的请求可以转发到 foosite.example.com/foo/bar/fizz通过在配置源时将源路径设置为 /foo。但如果不使用 Lambda@Edge,它也无法删除路径部分或以其他方式修改路径。在上面讨论的场景中,您可以在配置其他源服务器时将源路径留空。

具有以下行为的单个 S3 存储桶:

domain.com-> 从存储桶的根目录提供文件

域。com/blog -> 提供 S3 存储桶中子文件夹中的文件(这不是默认行为)

如何:

https://aws.amazon.com/ru/blogs/compute/implementing-default-directory-indexes-in-amazon-s3-backed-amazon-cloudfront-origins-using-lambdaedge/

Lambda边缘代码:

'use strict'; exports.handler =(事件、上下文、回调)=> {

// Extract the request from the CloudFront event that is sent to Lambda@Edge 
var request = event.Records[0].cf.request;

// Extract the URI from the request
var olduri = request.uri;

// Match any '/' that occurs at the end of a URI. Replace it with a default index
var newuri = olduri.replace(/\/$/, '\/index.html');

// Log the URI as received by CloudFront and the new URI to be used to fetch from origin
console.log("Old URI: " + olduri);
console.log("New URI: " + newuri);

// Replace the received URI with the URI that includes the index page
request.uri = newuri;

// Return to CloudFront
return callback(null, request);

};

代码总结更高:

  • lambda edge 将路径“/blog/”重写为“/blog/index.html”