ASP.NET 核心会话实现线程安全吗?
Is ASP.NET Core Session implementation thread safe?
我知道 there is an analogous question 但那是关于 ASP.NET 而不是 ASP.NET 核心。答案都是7-9岁的,混在一起说ASP.NET和ASP.NET核心未必是个好主意。
在这种情况下我的意思是线程安全的:
使用 Session
(通过 HttpContext
访问,通过注入 IHttpContextAccessor
访问)的读写方法(如 Set(...)
)是否安全属于同一会话的多个请求?
显而易见的答案是肯定的,因为如果它不安全,那么所有开发人员都应该使他们的会话访问代码线程安全...
我查看了 DistributedSession
source code,它似乎是默认值(我在调试器中按上述方式访问的会话是 DistributedSession
的一个实例)并且没有任何序列化或其他技术,如锁...甚至私有 _store
成员也是纯粹的 Dictionary
...
这个线程对于并发修改使用如何安全?我错过了什么?
DistributedSession
由 DistributedSessionStore
which is registered as a transient dependency 创建。这意味着 DistributedSessionStore
本身是隐式安全的,因为它实际上并不在请求之间共享。
会话使用字典作为基础数据源,它也是 DistributedSession
对象的本地数据源。初始化会话时,会话在访问会话时通过反序列化缓存中存储的数据来延迟初始化 _store
字典。 That looks like this:
var data = _cache.Get(_sessionKey);
if (data != null)
{
Deserialize(new MemoryStream(data));
}
所以这里访问_cache
是一次操作。 writing to the cache.
时同理
至于 IDistributedCache
实现,您通常可以期望它们是 thread-safe 以允许并行访问。 MemoryCache
例如使用 a concurrent collection as the backing store.
所有这些对于并发请求意味着基本上您不应该期望一个请求直接影响另一个请求的会话。会话通常只反序列化一次,因此不会出现在请求期间(通过其他请求)发生的更新。
我知道 there is an analogous question 但那是关于 ASP.NET 而不是 ASP.NET 核心。答案都是7-9岁的,混在一起说ASP.NET和ASP.NET核心未必是个好主意。
在这种情况下我的意思是线程安全的:
使用 Session
(通过 HttpContext
访问,通过注入 IHttpContextAccessor
访问)的读写方法(如 Set(...)
)是否安全属于同一会话的多个请求?
显而易见的答案是肯定的,因为如果它不安全,那么所有开发人员都应该使他们的会话访问代码线程安全...
我查看了 DistributedSession
source code,它似乎是默认值(我在调试器中按上述方式访问的会话是 DistributedSession
的一个实例)并且没有任何序列化或其他技术,如锁...甚至私有 _store
成员也是纯粹的 Dictionary
...
这个线程对于并发修改使用如何安全?我错过了什么?
DistributedSession
由 DistributedSessionStore
which is registered as a transient dependency 创建。这意味着 DistributedSessionStore
本身是隐式安全的,因为它实际上并不在请求之间共享。
会话使用字典作为基础数据源,它也是 DistributedSession
对象的本地数据源。初始化会话时,会话在访问会话时通过反序列化缓存中存储的数据来延迟初始化 _store
字典。 That looks like this:
var data = _cache.Get(_sessionKey);
if (data != null)
{
Deserialize(new MemoryStream(data));
}
所以这里访问_cache
是一次操作。 writing to the cache.
至于 IDistributedCache
实现,您通常可以期望它们是 thread-safe 以允许并行访问。 MemoryCache
例如使用 a concurrent collection as the backing store.
所有这些对于并发请求意味着基本上您不应该期望一个请求直接影响另一个请求的会话。会话通常只反序列化一次,因此不会出现在请求期间(通过其他请求)发生的更新。