using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Threading;

using RedisStuy;

using StackExchange.Redis;

using Xunit;

namespace RedisStudyTest
{
    [Trait("RedisLock", "All")]
    public class RedisLockStudyTest
    {
        private IDatabase redisDatabase;
        private RedisLockStudy redisLockStudy;

        public RedisLockStudyTest()
        {
            redisDatabase = RedisHelper.GetRedisDatabase();
            redisLockStudy = new RedisLockStudy();
        }

        [Fact]
        public void RedisLockTest()
        {
            //启动50个线程
            for (int i = 0; i < 50; i++)
            {
                var cc = new Thread(new ThreadStart(MyRedisLock));
                //调用Start方法执行线程
                cc.Start();
            }
            //MyRedisLock();
        }

        private void MyRedisLock()
        {
            RedisKey lockKey = "RedisLock:Test1";
            RedisValue lockValue = Guid.NewGuid().ToString();
            TimeSpan exprit = TimeSpan.FromSeconds(10);

            //偿试获取锁的最大次数
            int retryNum = 3;
            for (int i = 1; i <= retryNum; i++)
            {
                if (redisDatabase.LockTake(lockKey, lockValue, exprit))
                {
                    try
                    {
                        //做一些其它事情
                        Thread.Sleep(new Random(Guid.NewGuid().GetHashCode()).Next(0, 30));
                    }
                    catch (Exception ex)
                    {
                        string message = ex.Message;
                    }
                    finally
                    {
                        if (!redisDatabase.LockRelease(lockKey, lockValue))
                        {
                            //释放锁失败:锁超时被其它客户端重新锁定或解锁异常

                            //基本上,进行回滚等补偿操作
                        }
                    }

                    break;
                }
            }
        }
    }
}