首页 > ServiceStack.Redis的问题与修正

ServiceStack.Redis的问题与修正

Redis是开源、高性能的Key-value存储引擎。

最近我们在一个日访问量约1kw的网站上使用redis替换以前的memcache,成功将CPU从30%下降到15%,效果相当显著。

ServiceStackRedis是最受欢迎的C#驱动之一。关于如何使用ServiceStackRedis请参见这里——使用ServiceStackRedis链接Redis简介

不过我们在使用ServiceStackRedis的线程池(PooledRedisClientManager)还是碰到了不少问题。

 1 链接数异常。

 一个webserver会占用80个链接。当15台webserver就过千了,这时会出现有些客户端链接不上的情况。

 解决方案:

 GetInActiveWriteClient方法中

//找下一个目标

//从当前读写指针的后面开始查找,而不是从0开始

var nextIndex = (WritePoolIndex + i) % writeClients.Length;

更改为

var nextIndex = i;

同时修改DisposeClient方法中将readClient.Active == false将DisposeConnection一下。线程就能很好的回收了。



效果:

在我们这样一个网站下,单台webserver大约会占用10个~15个链接,比之前的80个少了不少。



分析:



从代码上来看,作者的初衷是为了更快的找到空闲的线程,但是却认所有线程都不间断的使用,没有一个线程可能空闲。

如果站点较小,webserver不太多,不改问题也不大。不过我认为用长链接并不划算,因为与redis建立一个链接还是相对比较“便宜”的。



2 多台redis存储相同的内容。



相同的内容会冗余在所有redis中



解决方案



在GetInActiveWriteClient中加入int型参数来标识出使用那台redis



var start = 0;

var step = 1;

if (index > -1 && index < ReadWriteHosts.Count)

{

  start = index;

  step = ReadWriteHosts.Count;

}

//遍历读写池

//这个时候池是锁定的

for (var i = start; i < writeClients.Length; i += step)

{

  省略



这样线程池中就会按ReadWriteHosts的个数来顺序分配。



效果:



在进行读写时只需要使用key.GetHashCode方法获得一个hash值就能准确分配到其中一台redis上。保证所有的redis的数据不重复。







更多相关:

  • 今天,小编给大家带来的教程为:前嗅ForeSpider脚本教程中,链接抽取的应用场景,以及链接在源码的html标签里写脚本的实战教程。具体内容如下:一.应用场景当需要手动添加链接时,可添加链接脚本。在“链接脚本处”,可能用到的类为extractor 、result、url、grabDoc、dom。二.链接在源码的html标签里链接地址...

  • 问题 项目中需要链接多个静态库,在编译的时候报错如下 sdi_io.cpp:(.text._ZN13sdi_H264EncIO7DataPopEPm+0x30):对‘H264ENC_StatusGet(H264ENC_Status_t&)’未定义的引用 可能原因是符号确实没有定义,而本文出现这个问题的原因是,链接的静态库有前后...

  • 上一篇文章里大概描述linux下静态链接库的编译与使用,下面讲动态链接库的编译与使用方法。 1. 什么是动态链接库     所谓动态链接库,是指编译的时候不会把程序引用到的库插入到执行程序里,而是在执行时候才会去加载相关的库,所有用到此库的程序可以共享一份代码。     这样带来的好处是可执行程序所占的空间变小了,同时,如果库需要升...

  • 人们总喜欢在帖子中加上各种有用的URL链接或Email地址。而笔者当初设计时没有考虑到这一点,使得这些URL链接或Email地址只能以文字的形式而并不是以超链接的形式显示,其它浏览帖子的人还必须把这些URL链接拷贝到浏览器中或把Email地址拷贝到Outlook中才能转到相应的链接地址或发送电子邮件到相应的Email地址。   发现这...

  • iPhone上的Safari(还有些webkit android手机浏览器)会自动对看起来像是电话号码的数字串(包括已经加入连字符或括号格式化过的)添加电话链接,点击之后会询问用户是否想要拨打该号码。如果你不希望开启这个自动识别,可以将它关闭:

    如何理解numpy.nan_to_num

    nan 是not a number ,inf是无穷大 numpy.nan_to_num(x): 使用0代替数组x中的nan元素,使用有限的数字代替inf元素...

  • 简介 Simple Reference  基础CUDA示例,适用于初学者, 反映了运用CUDA和CUDA runtime APIs的一些基本概念.Utilities Reference  演示如何查询设备能力和衡量GPU/CPU 带宽的实例程序。Graphics Reference  图形化示例展现的是 CUDA, OpenGL,...

  • 在做开发的过程中难免需要给内核及下载的一些源码打补丁,所以我们先学习下Linux下使用如如何使用diff制作补丁以及如何使用patch打补丁。...

  • 我在调研ATS 4.2.3挂载SSD的过程中,遇到很多坑,特此详细记录我摸索的主要过程,以便大家以后避免之。 基本思路可以完全照搬参考文献[2][3] 下面的安装假定是以root用户身份进行的,Linux服务器已经安装好系统,磁盘已经做好分区。 首先需要认识我们的Linux服务器的硬件配置和软件情况 硬件配置: DELL...

  • 该博文整理一些在使用stl编程过程中遇到的小经验: 1.在多线程环境下面打印调试,如何使用cout及时刷新到屏幕上? 在C中我们经常这样使用: printf("Hello World "); fflush(stdout); 如果使用stl,我们可以这样使用: cout << "Hello World" << endl <...

  • 多线程有什么好处?提高CPU的利用率,更好地利用系统资源,使用Monitor类可以同步静态/实例化的方法的全部代码或者部分代码段,使用不同的同步类创建自己的同步机制。多线程指从软件或者硬件上实现多个线程并发执行的技术。具有多线程能力的计算机因有硬件支持而能够在同一时间执行多于一个线程提升整体处理性能。多线程是指程序中包含多个执行流,即...

  • Step1:在界面主函数的构造函数中初始化多线程 auto mythread = new QThread(); //新建connect(mythread , &QThread::finished, mythread, &QObject::deleteLater);//线程运行结束后释放内存object1->moveToThread...

  • 一、thread的基本用法 参见C++使用thread类多线程编程 。 二、类外使用多线程,访问类的成员 这几种方式,新建线程都是在类外,然后通过把友元函数或者成员函数作为thread参数。 #include #include #include using namesp...

  • 本博文是根据中科大信息学院谭立湘老师的课件加上自己的理解整理出来的 ************************************************************************************ NVIDIA在2007年推出CUDA这个统一计算架构 CUDA的基本思想是支持大量的线程级并...

  • 一、parallel communication patterns   并行通信模式 Map:映射,在特定的位置读取和写入。 Gather:收集,从多个不同的位置读入,写入一个位置。 Scatter:分发,写入多个位置。 Transpose转置 结构数组缩写为AOS,数组结构缩写为SOA 转置运算是指任务重新排序内存中的数...