当我们有一个发送确认电子邮件一旦完成注册类型的系统。系统在几分钟内有大约3000个注册,我们注意到一个错误。如果用户A在用户B注册后注册了几ms,用户A将通过电子邮件获取用户B的详细信息。我们确实设法解决了这个问题,并将其缩小到了从缓存中获取电子邮件模板的这段代码,只是在占位符上替换了一个字符串。奇怪C#错误替换文本字符串
private string ProcessEmailBody(MyRegistrationModel registration)
{
var content = CacheHelper.GetContent("REGISTRATIONEMAIL");
if (content != null)
{
content.Text = context.Text.Replace("@@[email protected]@", registration.FullName);
return content.Text;
}
else return null;
}
的CacheHelper.GetContent()
方法是静态的,我做这个固定的这个“错误”:
private string ProcessEmailBody(MyRegistrationModel registration)
{
var content = CacheHelper.GetContent("REGISTRATIONEMAIL");
if (content != null)
{
string body = content.Text;
body = body.Replace("@@[email protected]@", registration.FullName);
return body;
}
else return null;
}
我想不出我的生活为什么这个有固定的问题。任何人都可以解释这一点吗?
编辑:这是我的getContent()方法(我知道的签名比上面不同,我被短暂)
public static Content GetContent(string key, int partnerSiteId, int? version, IContentRepository contentRepository, out string cacheKey)
{
cacheKey = string.Format("{0}_{1}_{2}", key, partnerSiteId, version);
var content = CacheManager.Get(cacheKey,() => contentRepository.GetContent(key, partnerSiteId, version), WebConfig.GetCacheDuration(CacheProfile.Short));
return content;
}
private static DataCache _Cache = null; // DataCache is from AppFabric (Microsoft.ApplicationServer.Caching)
public static T Get<T>(string objectKey, Func<T> reloadItemExpresion, TimeSpan cacheDuration) where T : class
{
if (_Cache == null)
{
if (reloadItemExpresion != null)
{
return reloadItemExpresion.Invoke();
}
return null;
}
object cachedObject = null;
try
{
cachedObject = _Cache.Get(objectKey);
}
catch (Exception ex)
{
if (ex is FileNotFoundException)
{
_Cache.Remove(objectKey);
}
}
if (cachedObject != null)
{
return cachedObject as T;
}
if (reloadItemExpresion != null && cacheDuration > TimeSpan.Zero)
{
T item = reloadItemExpresion.Invoke();
if (item != null)
{
Insert(item, objectKey, cacheDuration);
}
return item;
}
return null;
}
contentRepository.GetContent
刚刚熄灭到数据库并获取实际的内容了。
显示'CacheHelper.GetContent'的代码...很可能它提供了多个线程间的实例*共享*,因此您在修改'content.Text'时创建了竞争条件。 – 2012-02-08 11:07:29
没有足够的信息; “内容”的实际类型是什么?GetContent方法是如何实现的?你总是发出同样的“内容”实例吗?此代码是否运行多线程?在这种情况下,这可能只是一个竞争条件,您需要确保正确的线程同步。 – 2012-02-08 11:11:58
我编辑了我的问题。 – eth0 2012-02-08 11:24:31