老男孩之memcached精讲第二部

1.1Memcache 服务器的安装。

Linux,FreeBSD,Solaris,windows。这里以Centos6.4为例进行说明。

软件地址:Memcached 下载地址:
         libevent 下载地址:
         网友安装资料:http://instance.iteye.com/blog/1691705


安装memcached

安装libevent(c6.6)

安装环境:

  1. [root@lnmp tools]# tar xf libevent-1.4.13-stable.tar.gz 

  2. [root@lnmp tools]# cd libevent-1.4.13-stable

  3. [root@lnmp libevent-1.4.13-stable]# ./configure

  4. [root@lnmp libevent-1.4.13-stable]# make && make install

  5. Centos操作系统可以使用 yum直接安装libevent

安装memcached:

  1. [root@lnmp tools]# tar xf memcached-1.4.13.tar.gz 

  2. [root@lnmp tools]# cd memcached-1.4.13

  3. [root@lnmp memcached-1.4.13]# ./configure 

  4. [root@lnmp memcached-1.4.13]# make && make install


其他下载地址:

http://memcached.googlecode.com/files/memcached-1.4.15.tar.gz

http://code.google.com/p/memecached/downloads/list

提示:

memcache-2.2.5.tgz<==客户端

memcached-1.4.13.tar.gz<==服务端软件

启动Memcached:

(1)配置ld.so.conf路径防止启动memcached时报错

wKioL1iqo9eAaZUdAAEGh_HsQh4382.png-wh_50

(2)开机启动memcached

[root@lnmp memcached-1.4.13]# which memcached/usr/local/bin/memcached
[root@lnmp memcached-1.4.13]# which memcached/usr/local/bin/memcached
[root@lnmp memcached-1.4.13]# memcached -d -c 10240 -p 11211 -m 16 -P /var/run/memcached.pid -u root
[root@lnmp memcached-1.4.13]# netstat -lntup | grep 11211tcp        0      0 0.0.0.0:11211               0.0.0.0:*                   LISTEN      1040/memcached      tcp        0      0 :::11211                    :::*                        LISTEN      1040/memcached      udp        0      0 0.0.0.0:11211               0.0.0.0:*                               1040/memcached      udp        0      0 :::11211                    :::*                                    1040/memcached  需要查看memcached它的帮助是-h


[root@lnmp memcached-1.4.13]# memcached -h
memcached 1.4.13
-p <num>      TCP port number to listen on (default: 11211)
-U <num>      UDP port number to listen on (default: 11211, 0 is off)
-s <file>     UNIX socket path to listen on (disables network support)
-a <mask>     access mask for UNIX socket, in octal (default: 0700)
-l <addr>     interface to listen on (default: INADDR_ANY, all addresses)
              <addr> may be specified as host:port. If you don't specify
              a port number, the value you specified with -p or -U is
              used. You may specify multiple addresses separated by comma
              or by using -l multiple times
-d            run as a daemon
-r            maximize core file limit
-u <username> assume identity of <username> (only when run as root)
-m <num>      max memory to use for items in megabytes (default: 64 MB)
-M            return error on memory exhausted (rather than removing items)
-c <num>      max simultaneous connections (default: 1024)
-k            lock down all paged memory.  Note that there is a
              limit on how much memory you may lock.  Trying to
              allocate more than that would fail, so be sure you
              set the limit correctly for the user you started
              the daemon with (not for -u <username> user;
              under sh this is done with 'ulimit -S -l NUM_KB').
-v            verbose (print errors/warnings while in event loop)
-vv           very verbose (also print client commands/reponses)
-vvv          extremely verbose (also print internal state transitions)
-h            print this help and exit
-i            print memcached and libevent license
-P <file>     save PID in <file>, only used with -d option
-f <factor>   chunk size growth factor (default: 1.25)
-n <bytes>    minimum space allocated for key+value+flags (default: 48)
-L            Try to use large memory pages (if available). Increasing
              the memory page size could reduce the number of TLB misses
              and improve the performance. In order to get large pages
              from the OS, memcached will allocate the total item-cache
              in one large chunk.
-D <char>     Use <char> as the delimiter between key prefixes and IDs.
              This is used for per-prefix stats reporting. The default is
              ":" (colon). If this option is specified, stats collection
              is turned on automatically; if not, then it may be turned on
              by sending the "stats detail on" command to the server.
-t <num>      number of threads to use (default: 4)
-R            Maximum number of requests per event, limits the number of
              requests process for a given connection to prevent 
              starvation (default: 20)
-C            Disable use of CAS
-b            Set the backlog queue limit (default: 1024)
-B            Binding protocol - one of ascii, binary, or auto (default)
-I            Override the size of each slab page. Adjusts max item size
              (default: 1mb, min: 1k, max: 128m)
-o            Comma separated list of extended or experimental options
              - (EXPERIMENTAL) maxconns_fast: immediately close new
                connections if over maxconns limit
              - hashpower: An integer multiplier for how large the hash
                table should be. Can be grown at runtime if not big enough.
                Set this based on "STAT hash_power_level" before a 
                restart.
-d 是以进程后台进行 -c 是以多少为并发 -p 以什么端口来进行监听 -m 指定多少内存 -P 以什么什么pid文件-u指定root
memcahced 相关启动参数说明:
-p 指定memcached服务监听的TCP端口。默认为11211.
-m 指定memcached服务可以缓存数据的最大内存。默认64MB(量小的时候太大内存)。
-u 运行Memcached服务的用户
-d 作为守护进程在后台运行
-c 最大的并发连接数,默认是1024,按照服务器的并发访问量来设定。
-vv 以very vrebose 模式启动,调试信息和错误输出到控制台。
-P 设置保存Memcache的pid文件($$)
-l 指定监听的服务器IP地址。
其它选项,通过"memcached -h"命令可以显示所有可用的选项。读者可自行阅读相关资料。-f 调优因子


(3) 检查启动结果:

[root@lnmp ~]# netstat -lntup | grep 11211
tcp        0      0 0.0.0.0:11211               0.0.0.0:*                   LISTEN      1850/memcached      
tcp        0      0 :::11211                    :::*                        LISTEN      1850/memcached      
udp        0      0 0.0.0.0:11211               0.0.0.0:*                               1850/memcached      
udp        0      0 :::11211                    :::*                                    1850/memcached

  启动多个实例:

[root@lnmp ~]# memcached -d -m 16 -p 11212 -c 10240 -P /var/run/memcahed.pid -u root
[root@lnmp ~]# ps -ef | grep memcahed| grep -v grep
root         1850     1  0 23:03 ?        00:00:00 memcached -d -m 16 -p 11211 -c 10240 -P /var/run/memcahed.pid -u root

root         1866     1  0 23:12 ?        00:00:00 memcached -d -m 16 -p 11212 -c 10240 -P /var/run/memcahed.pid -u root


(  4)写入 数据检查结果:

      向memcached中添加数据:键值对

 key1->values1key2->values2
 ==============================
 管理Mysql和MC做一个对比
 Mysql insert->MC:set
 Mysql select->MC:set
 Mysql delete->MC:set


  a.通过nc写入

 添加键值对的操作:printf "set key008 0 0 10\r\noldboy0987\r\n"|nc 127.0.0.1 11211

wKiom1iqpt3T-HifAAC0oibJbJI714.png-wh_50

============>命令后面字节是10,那么后面的就要10个字符,否则添加不成功


查看键值对的操作:printf "get key008 0 0 10\r\noldboy0987\r\n"|nc 127.0.0.1 11211

删除键键值对的操作:printf "delete key008 0 0 10\r\noldboy0987\r\n"|nc 127.0.0.1 11211

wKioL1ir7EzTee26AABUh2knqJY814.png-wh_50

推荐上述测试操作memcached的方式。

 

固定的语法:printf “set/get/delete id 0 0 字节数\r\n字节\r\n”


b.通过telnet写入

  1. root@localhost ~]# telnet 192.168.1.200 11211

  2. Trying 192.168.1.200...

  3. Connected to 192.168.1.200.

  4. Escape character is '^]'.

  5. set user01 0 0 6

  6. abcdef

  7. STORED

  8. get user01

  9. VALUE user01 0 6

  10. abcdef

  11. END


  1. [root@localhost ~]# telnet 192.168.1.200 11211

  2. Trying 192.168.1.200...

  3. Connected to 192.168.1.200.

  4. Escape character is '^]'.

  5. set k 0 0 1

  6. v

  7. STORED

  8. get k

  9. VALUE k 0 1

  10. v

  11. END

  12. delete k

  13. DELETED

  14. get k

  15. END


  16. stats  

  17. STAT pid 1850

  18. STAT uptime 4893

  19. STAT time 1427819110

  20. STAT version 1.4.13

  21. STAT libevent 1.4.13-stable

  22. STAT pointer_size 64

  23. STAT rusage_user 0.041993

  24. STAT rusage_system 0.487925

  25. STAT curr_connections 10

  26. STAT total_connections 12

  27. STAT connection_structures 11

  28. STAT reserved_fds 20

  29. STAT cmd_get 4

  30. STAT cmd_set 3

  31. STAT cmd_flush 0

  32. STAT cmd_touch 0

  33. STAT get_hits 3

  34. STAT get_misses 1

  35. STAT delete_misses 0

  36. STAT delete_hits 1

  37. STAT incr_misses 0

  38. STAT incr_hits 0

  39. STAT decr_misses 0

  40. STAT decr_hits 0

  41. STAT cas_misses 0

  42. STAT cas_hits 0 命中

  43. STAT cas_badval 0

  44. STAT touch_hits 0

  45. STAT touch_misses 0

  46. STAT auth_cmds 0

  47. STAT auth_errors 0

  48. STAT bytes_read 131

  49. STAT bytes_written 153

  50. STAT limit_maxbytes 16777216

  51. STAT accepting_conns 1

  52. STAT listen_disabled_num 0

  53. STAT threads 4

  54. STAT conn_yields 0

  55. STAT hash_power_level 16

  56. STAT hash_bytes 524288


  57. 这个是查看状态。

  58. 可以这样子进行监控写脚本。

  59. [root@localhost ~]# printf "stats\r\noldboy\r\n"|nc 192.168.1.200 11211 | grep hit

  60. STAT get_hits 3

  61. STAT delete_hits 1

  62. STAT incr_hits 0

  63. STAT decr_hits 0

  64. STAT cas_hits 0

  65. STAT touch_hits 0

  66. Memcached状态查看:

  67. stats 整体

  68. stats setting 可以查看一些memcached设置 例如:线程数。。。一些参数是什么。

  69. stats slabs 查看slabs相关情况

  70. stats items 查看Items相关情况

  71. stats sizes 查看存在的Items 个数和大小

  72. stats cachedump 查看key value

  73. stats reset 清理统计数据

关闭memcached:

先测试插入数据

[root@localhost ~]# printf "set L001 0 0 6\r\noldboy\r\n"|nc 192.168.1.200 11211
STORED
[root@localhost ~]# printf "get L001 0 0 6\r\n"
get L001 0 0 6


一重启就会消失

[root@lnmp ~]# kill 1850
[root@lnmp ~]# kill 1866
[root@lnmp ~]# memcached -d -m 16 -p 11212 -c 10240 -P /var/run/memcahed.pid -u root
[root@localhost ~]# printf "get L001 0 0 6\r\n" |nc 192.168.1.200 11211

操作memcahed命令语法:

  1. set     key 0   0   10

  2. <command name><key><flags><exptime><bytes>\r\n

  3. 命令        标记    过期时间  字节数 

  4. <command name> setadd,或者 repalce   -<command name>

  5. # set 意思是“存储此数据”

  6. # add 意思是 “存储此数据,只在服务器*未*保留此键值的数据时”

  7. # replace意思是“存储此数据,只在服务器*曾*保留此键值的数据时”

  8. #<key> 是接下来的客户端索要求储存的数据的键值

  9. #<flags>是在取回内容时,与数据和发送块一同保存服务器上的任意16位无符号×××(用十进制来书写)。客户端可以用它作为“位域”来储存一些特定的信息;它对服务器是不透明的。

  10. #<exptime>是终止时间。如果为0,该项永不过期(虽然他可能被删除,以便为其他缓存项目腾出位置)。如果非0(Unix时间戳或当前时刻的秒偏移),到达终止时间后,客户端无法在获取这项内容。

  11. #<bytes> 是随后的数据区块的字节长度,不包括用于份野的“\r\n”。它可以是0(这时后面跟随一个空的数据区块)。

  12. 在这一行以后,客户端发送数据区块。

  13. #<data block>\r\n

  14. -<data block>是大段的8位数据,其长度由前面的命令行的<bytes>指定。


  15. 发送命令行和数据块以后,客户端等待回复,可能的回复如下:

  16. -“STORED\r\n

  17. -NOT_S1

表明成功

表明数据没有被存储,但不是因为发生错误。这通常以为这add或者replace命令条件不成立,或者,项目已经位列删除队列(参考后文的”delete“命令)。

1.2.2关闭memcached

pkill memcahed
netstat -lntup | grep 11211
kill `cat /var/run/11211.pid`
ps -ef|grep memcached|grep -v grep |awk '{print $2}' |xagrs kill


企业工作场景中如何配置memcached?

在企业实际工作中一般是开发人员提出要求,说要部署一个memcached缓存。

我们运维接到了需求,内存指定多大是根据业务有多少数据要缓存来确定业务重要性,进而采取负载均衡,分布式架构,最后确定并发连接数。

实际的部署,一般就是安装memcached服务端,把服务启动,并确保客户访问上就O了,客户端PHP安装都安装好了。

初入公司,了解业务,了解架构,加缓存。

思想:给公司或提出方法前,要写好方案。

1.2.3安装memcached的客户端

以下安装PHPLNMP的环境,要求页面能出来phpinfo,才能继续操作

wKiom1i04ASAsKtrAADmFFO28Sw230.png-wh_50

php的memcached模块(memcache客户端)编译安装

本文以php程序为例,讲解安装memcache的php的客户端及memcache的扩展在

http://pecl.php.net/packpage/memcache选择想要下载的Memcache版本。这里以memcache-2.2.5版本为例来安装PHP的Memcache扩展:JAVA程序一样需要客户端(resin,tomcat),但不会像php一样编译。在客户端php的服务器上:

1、解压缩并编译安装。

wKiom1i07VDz0zE-AAEQ1fh3LO8451.png-wh_50

memcache.so的路径

安装完后会有类似这样的提示:

[root@lnmp lib]# cd /application/php/lib/
[root@lnmp lib]# grep mem php.ini
;Maximum amount of memory a script may consume (128MB)
;http://php.net/memory-limit
memory_limit = 128M
;If this parameter is set to Off, then memory leaks will not be shown (on
;http://php.net/report-memleaks
report_memleaks = On
;enabled, registering these variables consumes CPU cycles and memory each time
;Enable / Disable collection of memory usage statistics by mysqlnd which can be
;http://php.net/mysqlnd.collect_memory_statistics
mysqlnd.collect_memory_statistics = Off
;A default size of the shared memory segment
;sysvshm.init_mem = 10000

wKioL1i079qht93-AAC9NswH58E631.png-wh_50

2.修改php.ini文件

wKioL1i08A6wu_C4AACYHuQ19hA052.png-wh_50

3.重启apache服务使php的配置生效

wKioL1i08EHwHb3HAACAcRjhfr0727.png-wh_50

如果是nginx则:

wKioL1i08HTiWwrHAAFEmb99rqY954.png-wh_50

4)打开浏览器访问phpinfo页面,出现如下内容表示memcache客户端安装成功

wKiom1i08KWxXBW8AAHTwQqprBE529.png-wh_50

5.编写测试PHP脚本

php程序连接memcached测试

wKioL1i08NKRxwJUAAIJaNYnYPg990.png-wh_50

New多个对象连接不通的memcached.

wKioL1i08QCCrw_eAADW7NXSXKA377.png-wh_50

作业:

wKiom1i08T_imFLTAAFN8rT1vEY478.png-wh_50

1.3.2集群中的session共享存储

http://oldboy.blog.51cto.com/2561410/1331316

1.3.3如何实现集群中的session共享存储实战

wKioL1i08ZfAgp85AABvZxuZv9g492.png-wh_50

  1. vim /applications/php/lib/php.ini

  2. 把上面的参数给改掉。

  3. 保存,然后重新启动PHP,/applications/php/lib/php-fpm 重启新启动的命令

1.4Memcached分布式集群

前面已经介绍过,Memcached的分布式使用通过客户端的程序库来实现的,下面举例描述其工作流程。Tokyo_Tyrant(持久化存储)

3.通过程序实现URL一致性HASH

wKioL1i08evCpGr7AAGCIiIjK1k705.png-wh_50

假设有node1、node2、node3三台Memcached服务器,应用程序套实现保存名为"tokyo"、"tokyo1""tokyo2""tokyo3"的数据如图所示:

wKiom1i08h7hx6C4AADLMfq9CHM363.png-wh_50

图上方Memcached中存入数据的初始状态

向Memcached中存入"tokyo",将"tokyo"传给客户端程序后,客户端实现的算法就会根据这个"键"来决定保存数据的Memcached服务器,选定服务器后,就命令该服务器保存"tokyo"及其值,如下图:

wKiom1i08suwM2JCAADUSyuKvO8350.png-wh_50

同样,存入"tokyo1"、"tokyo2"和"tokyo3"的过程都是先通过客户端的算法选择服务器在保存数据。

接下来获取保存数据。获取保存的key/value对时也要将要获取的键"toyko"传递给函数库。函数库通过与存取数据操作相同的算法,根据"键"来选择服务器。只要使用的算法相同,就能确定存入在哪一台服务器,然后发送get命令。只要数据没有因为某些原因被删除,就能获得保存的值如图:

wKioL1i08wmCaMpbAAEgzJp9yZ8601.png-wh_50

图上Memcached中存入"tokyo"的过程

 将不同的键保存到不同的服务器上,就实现Memcached的分布式算法。部署多台Memcached服务器时,键分散保存到这些服务器上,当某台Memcahed服务器发生故障无法连接时,只要分散到这台服务机器上key/values对不能访问,其他key/value对不受影响。

 目前有两种分布式算法使用的最多,一种是根据余数来计算分布,另外一种是根据一致性哈希算法来计算分布。根据余数分布式算法实现求得键的整数哈希值,再除以以服务器台数,根据余数来选择将键存放到哪台服务器上。这种方法虽然计算简单,效率很高,但在服务器增加或减少时,会导致几乎所有的缓存失败,所以在大规模部署中,很少使用这个种方法,一般采用一致性HASH算法,原理如图下首先算出Memcached服务器(节点)的哈希值,并将其分散到0~2的32次方的圆上,然后用同样的方法算出存储数据的键的哈希值并映射到圆上,然后从数据映射到位置开始顺时针查找,将数据保存到查找到的第一个服务器上。如果超过232仍然找不到服务器,就会将数据保存到第一台Memcached服务器上。

wKioL1i080nwgl-bAALPLq2v1OU376.png-wh_50

当需要添加一台Memcached服务器时,由于保存键的服务器的个数发生了变化,因此余数结果也会发生巨大的变化,几乎所有的键都找不到之前存入的服务器,导致所有的缓存失效。但在采用一致性哈希算法时,添加服务器后,只有在圆上增加服务器地点的逆时针方向的第一台服务器上的键会受到影响如图下所示:

wKiom1i084qDtQHJAAMJ_N-3PWk296.png-wh_50

wKiom1i089WjBZHoAAHedgm5kcw089.png-wh_50

 一致性哈希算法对数据的存储是不均匀的,但可以最大限度的减少缓存的失效量。在大规模部署的Memcached时,容灾和扩容一定要使用一致性哈希算法,以确保再出现故障或容量问题时减少对数据库的影响。

持久化储存工具:

1)memcachedb

wKioL1i09CLg4cOzAAIelXBlrKs947.png-wh_50

wKiom1i09FfBKblDAACzxLYuizE841.png-wh_50

2.TOKYO tyrant(2000万)

TOKYO tyrant:它是日本最大的SNS社交万展mixijp开发的Tokyo Cabinet key-value数据库网络接口,它拥有Memcache的兼容协议,也也可以通过HTTP协议进行数据交换。对任何原有Memcached客户端来讲可以将Tokyo Tyrant看成是一个Memcached,但是,它的数据是可以持久化存储的。Tokyo Tyrant 具有故障转移,日志文件体积小,大数据量下表现出色等优势,详见:

http://blog.s135.com/post/362.htm

wKioL1i09J7zxbWeAATUhj8sUrM565.png-wh_50

3.HandlerSocket(Mysql插件)

http://database.51cto.com/art/201105/261741htm



分布式memcached集群

1.一致性HASH算法分享。

2.Nginx HASH适合Mc。(mc的代理模块这样的,tengine 一致性HASH模块)。

1.5Memcached管理

1.5.1通过端口管理Memcached

(1)通过在命令行执行telnet ip port 方式可以登录到Memcached


(2)命令直接操作,nc这样的命令。

如果写脚本通过nc检查端口并监控memcache服务可以用下面的方法:

a.memcached监控脚本:

wKioL1i09RKgu30zAAIYWlWvVv0151.png-wh_50


b.通过nc查看memcached状态

wKiom1i09UPwO-2QAAD96jHi1gw103.png-wh_50

c.安装memadmin管理客户端


上传到lnmp的服务器上上传到nginx下面的服务器下面,然后在进行解压就行了

然后在uri的地方写上memadmin

wKioL1i09a3Bk3DkAAK4kOHmYp8987.png-wh_50

wKiom1i09dLxi77pAAGZE3kzBF8543.png-wh_50

1.6Memcached的监控

部署好Memcached之后,需要对Memcached的使用情况进行跟踪:监控Memcached的状态信息,内存使用情况,hit/miss值是多少。通过对Memcached监控不仅能立刻了解Memcached出现问题,还能够利用状态信息来分析业务数据的增长并为未来的容量规划提供依据。

监控Memcached的工具很多,当前的常用监控工具有:memcache.php,Nagios和cacti,下面分别对三种监控方法进行介绍

1.6.1利用memcache.php对单台memcached进行监控

利用php进行监控室最简单的监控方法,只要机器上支持PHP环境即可。这种监控的执行过程是:

把这个文件放到可以访问的目录下然后对这个memcache.php文件进行修改,下载此文件地址如下:

http://livebookmark.net/memcachephp/memcachephp.zip