我刚刚阅读了这个 SO 问题,哪种设计最可取:test-create、try-create、create-catch?
关于答案,似乎开发人员更喜欢“Try-Create”模式,其中一些人提到TryCreate(user, out resultCode)可以是线程安全的,但其他模式不是。
尝试创建
enum CreateUserResultCode
{
Success,
UserAlreadyExists,
UsernameAlreadyExists
}
if (!TryCreate(user, out resultCode))
{
switch(resultCode)
{
case UserAlreadyExists: act on user exists error;
case UsernameAlreadyExists: act on username exists error;
}
}
我在想如果tryCreate方法涉及多个数据库调用,那么在实际实践中使其线程安全的正确方法是什么?
说tryCreate会做两件事:
检查数据库中是否存在用户名
如果名称不存在,则创建一个新名称
很有可能一个线程完成了 1 而不是 2,另一个线程开始调用这个方法tryCreate并且也完成了 1,这是一个竞争条件。
当然,在tryCreate我可以添加一个锁或某事,但它会使tryCreate成为热点。如果我有一个高知名度的网站,所有新注册都必须等待tryCreate中的锁定。
我从其他网站看到的是当你输入你的用户名时,它会触发一个ajax调用来检查它是否存在于当前数据库中,然后你去下一步创建它。(不确定是否创建了一个锁此刻。)
关于如何在现实生活中实现涉及多个数据库调用的适当安全tryCreate的任何想法?
更新 1:TryCreate的逻辑可能非常复杂,而不仅仅是 2 个 db 调用