我使用memcached作为ExpressJS会话的后备存储-通过应用程序配置设置选择。如果无法联系memcached主机,我希望从memcached回退到内存。(这不一定是一种生产策略,因为memcached是非常可靠的-当我忘记在dev中引导Docker实例时,它更适合使用,但它仍然可以是一种生产故障安全机制。)
我首先想到我可以"app.use“一个新的会话实例,并尝试删除第一个实例,但我读到很难(如果可能)”不使用“Express中间件,即在链中就地交换中间件,或者通常在链设置完成后对链进行修补。
这里的问题是在连接超时后,应用程序中间件已经被设置,在会话中间件之后安装了许多其他服务。
我的第二个想法是,我可以重新配置Express会话实例本身,并在创建后更改存储吗?我在the documentation中看不到任何方法。
我的第三个想法是将express-session包装在一个新的“可交换存储”类中,但我对包装整个接口的范围很谨慎。
例如,在我的应用程序设置中:
app.use(services.session.middleware());
// then a lot of other middleware...
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: false}));
app.use(cookieParser());
app.use(express.static(path.join(rootPath, 'public')));
...etc在会话服务中,选择并配置会话实例:
function middleware() {
// default / Memory Store options
const opts = {
resave: false,
saveUninitialized: false,
...etc
}
};
// Install any configured backing store
if(config.session.storage === "memcached"){
const MemcachedStore = require('connect-memcached')(session);
opts.proxy = 'true';
opts.store = new MemcachedStore({
hosts: ...,
secret: ...
});
const errorHandler = (type, details)=> {
/* HERE I WOULD LIKE TO RE-MAKE THE SESSION USING MEMORY
* AND DISCARD THE MEMCACHED ONE
* (THIS HAPPENS AFTER APP BOOT HAS FINISHED)
*/
console.error( String.format("Memcached {3} with host:{0} details:{1}.", details.server, details.messages.join( '' ), type));
}
opts.store.client.on('failure', details => errorHandler('failure', details));
opts.store.client.on('issue', details => errorHandler('issue', details));
}
return session(opts);
}发布于 2018-07-06 18:20:30
我认为你可以尝试几种方法来解决这个问题。第一种方法是根据您在启动时提供的配置来配置存储系统(可能是通过config或nconf之类的模块)。第二种方法是在启动应用程序时运行一次快速检查,以确保它可以访问memcache服务,如果不能访问memcache服务,则返回到内存并返回错误。
我已经厌倦了做这两件事,因为你使用的是docker,而且启动memcache应该很容易。这是因为你将引入一些代码,这些代码可能会在生产中触发,如果有一些连接问题,然后你可能会发现自己意外地服务于内存之外的会话,而不是像memcache这样的东西,可能没有意识到。
我将在这里详细介绍这两种策略,并提供第三种可能更好的选择。
1.根据配置选择缓存系统
这应该相当简单,只需将您的配置提取到某种配置管理器/环境变量(checkout config或nconf)中即可。当启动应用程序并连接您的会话中间件时,您可以提取所有可能的配置,查看存在哪些配置,并在此基础上附加一个。这类似于您的if (config.session.storage === 'memcache")目前的外观。只需使用不配置的回退,express-session中间件就会回退到内存中。这样,您可以完全省略配置,只需始终使用内存进行开发即可。
2.在连接到所需的服务之前运行测试
结合以上几点,如果提供了memcache的详细信息,您可以在启动时尝试在memcache中存储一些内容,从而快速运行测试。也许是在应用程序启动时发出信号的new Date();?如果这抛出一个错误,那么只要不将MemcachedStore附加到快速会话选项,就可以安全地销毁MemcachedStore。
如果无法连接到Memcached,则会抛出错误
这是对#2的进一步组合。如果您确定提供了memcache配置,那么我会亲自检查您是否可以联系服务,如果不能,则抛出错误并停止应用程序。这意味着,在开发过程中,您可以立即了解问题所在,而在生产环境中,您也可以立即了解问题所在,并且可以根据应用程序无法启动的事实为自己触发自动警报。
这可能是最好和最健壮的解决方案,在谈论连接的服务时,通常情况下,进行静默回退不是一个好主意,因为事情可能会出错,而您根本不知道。我很欣赏这是为了开发的目的,你需要实用,但如果它节省了你意外地从你的服务器内存服务所有会话,那么这将是非常有益的。
https://stackoverflow.com/questions/51201653
复制相似问题