我的网络应用程序以这种方式管理用户的个人资料:
username.mywebsite.com
我使用子域快速模块管理它,它工作正常。 (https://www.npmjs.org/package/subdomain)
var subdomain = '/subdomain/:profileurl';
app.get(subdomain+'/user-home', main.isThisProfileExist, main.getHome);
app.get(subdomain+'/user-info', main.isThisProfileExist, main.getInfo);
app.get(subdomain+'/user-data', main.isThisProfileExist, main.getData);
...
然而,很少有用户有权将自己的个人资料与自定义域名(CNAME)相关联,这就是我的问题所在:我无法找到快捷路线的工作方式。所以我在考虑一种伪造expressjs的req.host值的方法。但我不认为这是最好的方式。
例如,用户已为其域名添加了此CNAME记录:
customdomain.com CNAME username.mywebsite.com
但是在express中我会得到req.host值:
customdomain.com
这是逻辑,但它不符合我对这种情况的需要,因为我无法知道哪个档案是针对性的......
你有什么想法帮助我吗?
谢谢
答案 0 :(得分:1)
如果您不希望用户必须告诉您他们的自定义CNAME是什么,您可以在收到的主机上自行进行DNS查询。
类似的东西:
var dns = require('dns');
var domains = dns.resolveCname(req.host);
您可以使用connect:
轻松将其添加为您自己的中间件app.use(myCustomDomainLookup());
中间件模块中的实现可能是这样的:
var dns = require('dns');
module.exports = function () {
return function (req, res, next) {
if (!recognisedSubdomain(req.host)) {
var domains = dns.resolveCname(req.host);
var validProfiles = domains.map(main.ifThisProfileExists);
req._profile = validProfiles[0]; // Picking first valid profile
}
next();
}
}
修改强>:
为了清晰起见,请在此处添加评论代码。
要与您的子域中间件集成,您需要覆盖req.host。这意味着在子域中间件之前,您的中间件需要use
d 。
你应该能够适应上述'如果'阻止如下:
if (!recognisedSubdomain(req.host)) {
var domains = dns.resolveCname(req.host);
req.host = domains[0];
}
由于resolveCname的文档表明可以返回域列表,因此如果返回多个域,您必须决定要执行的操作。