• Redis Fun使用


    using Newtonsoft.Json;
    using StackExchange.Redis;
    using System;
    using System.Configuration;
    using System.Reflection;
    using System.Threading.Tasks;
    using System.Text;
    
    namespace Lemon.Common
    {
        public static class RedisUtil
        {
            //缓存失效时长
            private static TimeSpan _expiry = TimeSpan.FromMinutes(30);
            private static object _locker = new Object();
            private static ConnectionMultiplexer _instance = null;
    
            /// <summary>
            /// 使用一个静态属性来返回已连接的实例,如下列中所示。这样,一旦 ConnectionMultiplexer 断开连接,便可以初始化新的连接实例。
            /// </summary>
            public static ConnectionMultiplexer Instance
            {
                get
                {
                    if (_instance == null)
                    {
                        lock (_locker)
                        {
                            if (_instance == null || !_instance.IsConnected)
                            {
                                _instance = ConnectionMultiplexer.Connect(EnvironmentCache.ConnectionStrings["RedisConnection"]);
                            }
                        }
                    }
                    //注册如下事件
                    _instance.ConnectionFailed += MuxerConnectionFailed;
                    _instance.ConnectionRestored += MuxerConnectionRestored;
                    _instance.ErrorMessage += MuxerErrorMessage;
                    _instance.HashSlotMoved += MuxerHashSlotMoved;
                    _instance.InternalError += MuxerInternalError;
                    return _instance;
                }
            }
    
            static RedisUtil()
            {
            }
                      
            /// <summary>
            /// 
            /// </summary>
            /// <returns></returns>
            public static IDatabase GetDatabase(int db)
            {
                return Instance.GetDatabase(db);
            }
                   
            /// <summary>
            /// 异步获取缓存数据
            /// </summary>
            /// <typeparam name="T"></typeparam>
            /// <param name="dbIndex">Redis数据库索引</param>
            /// <param name="key">Redis键</param>
            /// <param name="fun">从其他地方获取数据源,并缓存到Redis中</param>
            /// <returns></returns>
            public static async Task<T> GetAsync<T>(int dbIndex, string key, Func<T> fun)
            {
                var db = GetDatabase(dbIndex);
                if (db.KeyExists(key))
                {
                    return JsonConvert.DeserializeObject<T>(db.StringGet(key));
                }
                T data = default(T);
                if (fun != null)
                {
                    data = await Task.Run(() =>
                    {
                        return fun();
                    });
                    db.Set(key, data);
                }
                return data;
            }
    
            /// <summary>
            /// 同步获取缓存数据
            /// </summary>
            /// <typeparam name="T"></typeparam>
            /// <param name="dbIndex">Redis数据库索引</param>
            /// <param name="key">Redis键</param>
            /// <param name="fun">从其他地方获取数据源,并缓存到Redis中</param>
            /// <returns></returns>
            public static T Get<T>(int dbIndex, string key, Func<T> fun)
            {
                var db = GetDatabase(dbIndex);
                if (db.KeyExists(key))
                {
                    return JsonConvert.DeserializeObject<T>(db.StringGet(key));
                }
                T data = default(T);
                if (fun != null)
                {
                    data = fun();
                    db.Set(key, data);
                }
                return data;
            }
    
            /// <summary>
            /// 设置缓存
            /// </summary>
            /// <param name="key"></param>
            /// <param name="value"></param>
            public static void Set(this IDatabase db,string key, object value)
            {
                db.StringSet(key, JsonConvert.SerializeObject(value), _expiry);
            }
    
            /// <summary>
            /// 实现递增
            /// </summary>
            /// <param name="key"></param>
            /// <returns></returns>
            //public static long Increment(string key)
            //{
            //    //三种命令模式
            //    //Sync,同步模式会直接阻塞调用者,但是显然不会阻塞其他线程。
            //    //Async,异步模式直接走的是Task模型。
            //    //Fire - and - Forget,就是发送命令,然后完全不关心最终什么时候完成命令操作。
            //    //即发即弃:通过配置 CommandFlags 来实现即发即弃功能,在该实例中该方法会立即返回,如果是string则返回null 如果是int则返回0.这个操作将会继续在后台运行,一个典型的用法页面计数器的实现:
            //    return GetDatabase().StringIncrement(key, flags: CommandFlags.FireAndForget);
            //}
    
            /// <summary>
            /// 实现递减
            /// </summary>
            /// <param name="key"></param>
            /// <param name="value"></param>
            /// <returns></returns>
            //public static long Decrement(string key, string value)
            //{
            //    return GetDatabase().HashDecrement(key, value, flags: CommandFlags.FireAndForget);
            //}
    
            /// <summary>
            /// 发生错误时
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private static void MuxerErrorMessage(object sender, RedisErrorEventArgs e)
            {
                Logger.Error(e.Message);
            }
            /// <summary>
            /// 重新建立连接之前的错误
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private static void MuxerConnectionRestored(object sender, ConnectionFailedEventArgs e)
            {
                Logger.Error(sender, e.Exception);
            }
            /// <summary>
            /// 连接失败 , 如果重新连接成功你将不会收到这个通知
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private static void MuxerConnectionFailed(object sender, ConnectionFailedEventArgs e)
            {
             //   LogHelper.WriteInfoLog("重新连接:Endpoint failed: " + e.EndPoint + ", " + e.FailureType + (e.Exception == null ? "" : (", " + e.Exception.Message)));
            }
            /// <summary>
            /// 更改集群
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private static void MuxerHashSlotMoved(object sender, HashSlotMovedEventArgs e)
            {
               // LogHelper.WriteInfoLog("HashSlotMoved:NewEndPoint" + e.NewEndPoint + ", OldEndPoint" + e.OldEndPoint);
            }
            /// <summary>
            /// redis类库错误
            /// </summary>
            /// <param name="sender"></param>
            /// <param name="e"></param>
            private static void MuxerInternalError(object sender, InternalErrorEventArgs e)
            {
                Logger.Error(sender, e.Exception);
            }
    
            //场景不一样,选择的模式便会不一样,大家可以按照自己系统架构情况合理选择长连接还是Lazy。
            //建立连接后,通过调用ConnectionMultiplexer.GetDatabase 方法返回对 Redis Cache 数据库的引用。从 GetDatabase 方法返回的对象是一个轻量级直通对象,不需要进行存储。
    
            /// <summary>
            /// 使用的是Lazy,在真正需要连接时创建连接。
            /// 延迟加载技术
            /// 微软azure中的配置 连接模板
            /// </summary>
            //private static Lazy<ConnectionMultiplexer> lazyConnection = new Lazy<ConnectionMultiplexer>(() =>
            //{
            //    //var options = ConfigurationOptions.Parse(constr);
            //    ////options.ClientName = GetAppName(); // only known at runtime
            //    //options.AllowAdmin = true;
            //    //return ConnectionMultiplexer.Connect(options);
            //    ConnectionMultiplexer muxer = ConnectionMultiplexer.Connect(Coonstr);
            //    muxer.ConnectionFailed += MuxerConnectionFailed;
            //    muxer.ConnectionRestored += MuxerConnectionRestored;
            //    muxer.ErrorMessage += MuxerErrorMessage;
            //    muxer.ConfigurationChanged += MuxerConfigurationChanged;
            //    muxer.HashSlotMoved += MuxerHashSlotMoved;
            //    muxer.InternalError += MuxerInternalError;
            //    return muxer;
            //});
    
            #region  当作消息代理中间件使用 一般使用更专业的消息队列来处理这种业务场景
            /// <summary>
            /// 当作消息代理中间件使用
            /// 消息组建中,重要的概念便是生产者,消费者,消息中间件。
            /// </summary>
            /// <param name="channel"></param>
            /// <param name="message"></param>
            /// <returns></returns>
            public static long Publish(string channel, string message)
            {
                ISubscriber sub = Instance.GetSubscriber();
                //return sub.Publish("messages", "hello");
                return sub.Publish(channel, message);
            }
    
            /// <summary>
            /// 在消费者端得到该消息并输出
            /// </summary>
            /// <param name="channelFrom"></param>
            /// <returns></returns>
            public static void Subscribe(string channelFrom)
            {
                ISubscriber sub = Instance.GetSubscriber();
                sub.Subscribe(channelFrom, (channel, message) =>
                {
                    Console.WriteLine((string)message);
                });
            }
            #endregion
        }}
     /// <summary>
            ///通过secretkey对应的平台id
            /// </summary>
            /// <param name="secretKey"></param>
            /// <returns></returns>
            public int GetChannel(string secretKey, string appKey)
            {
                string key = string.Format("{0}&{1}",secretKey,appKey);
                int channelId = RedisUtil.Get<int>(0, key, () =>
                {
                    using (var context = new MediaDBContext())
                    {
                        return context.ChannelApps.Where(a => a.AppKey == appKey && a.Channel.SecretKey == secretKey && !a.IsDel)
                            .Select(c => c.ChannelId)
                            .FirstOrDefault();
                    }
                });
                return channelId;
            }
     <add name="RedisConnection" connectionString="127.0.0.1,password=Lemon82211852" />
  • 相关阅读:
    awk去重以某列重复的行
    awk 统计文件中按照某列统计某列的和(sum)
    使用jdk压缩war包
    histoty显示时间戳
    awk统计文件中某关键词出现次数
    Jbox帮助文档,默认的属性含义
    net之session漫谈及分布式session解决方案
    StackExchange.Redis 基本使用 (一) (转)
    Sql Server 表创建以及Ef浅谈
    数据验证(自定义特性)
  • 原文地址:https://www.cnblogs.com/zoro-zero/p/5603714.html
Copyright © 2020-2023  润新知