• Memcached


    1.NoSQL介绍

            NoSQL是对 Not Only SQL、非传统关系型数据库的统称。

            NoSQL一词诞生于1998年,2009年这个词汇被再次提出指非关系型、分布式、不提供ACID的数据库设计模式。

            随着互联网时代的到来,数据爆发式增长,数据库技术发展日新月异,要适应新的业务需求。

            而随着移动互联网、物联网的到来,大数据的技术中NoSQL也同样重要。

    数据库排名:https://db-engines.com/en/ranking

    NoSQL 分类

    • Key-value Store k/v数据库

      • 性能好 O(1) , 如: redis、memcached

    • Document Store 文档数据库

      • mongodb、CouchDB

    • Column Store 列存数据库,Column-Oriented DB

      • HBase、Cassandra,大数据领域应用广泛

    • Graph DB 图数据库

      • Neo4j

    • Time Series 时序数据库

      • InfluxDB、Prometheus

    2. Memcached

            Memcached 只支持能序列化的数据类型,不支持持久化,基于Key-Value的内存缓存系统

            memcached 虽然没有像redis所具备的数据持久化功能,比如RDB和AOF都没有,但是可以通过做集群同步的方式,让各memcached服务器的数据进行同步,从而实现数据的一致性,即保证各memcached的数据是一样的,即使有任何一台 memcached 发生故障,只要集群中有一台 memcached 可用就不会出现数据丢失,当其他memcached 重新加入到集群的时候,可以自动从有数据的memcached 当中自动获取数据并提供服务

            Memcached 借助了操作系统的 libevent 工具做高效的读写。libevent是个程序库,它将Linux的epoll、BSD类操作系统的kqueue等事件处理功能封装成统一的接口。即使对服务器的连接数增加,也能发挥高性能。memcached使用这个libevent库,因此能在Linux、BSD、Solaris等操作系统上发挥其高性能

            Memcached 支持最大的内存存储对象为1M,超过1M的数据可以使用客户端压缩或拆分报包放到多个key中,比较大的数据在进行读取的时候需要消耗的时间比较长,memcached 最适合保存用户的session实现session共享

            Memcached存储数据时, Memcached会去申请1MB的内存, 把该块内存称为一个slab, 也称为一个page

            Memcached 支持多种开发语言,包括:JAVA,C,Python,PHP,C#,Ruby,Perl等

    Memcached 官网:http://memcached.org/

    3.Memcached 和 Redis 比较

    比较类别Redismemcached
    支持的数据结构哈希、列表、集合、有序集合纯kev-value
    持久化支持
    高可用支持redis支持集群功能,可以实现主动复制,读写分离官方也提供了sentinel集群管理工具,能够实现主从服务监控,故障自动转移,这一切,对于客户端都是透明的,无需程序改动,也无需人工介入需要二次开发
    存储value容量最大512M最大1M
    内存分配临时申请空间,可能导致碎片预分配内存池的方式管理内存,能够省去内存分配时间
    虚拟内存使用有自己的VM机制,理论上能够存储比物理内存更多的数据,当数据超量时,会引发swap,把冷数据刷到磁盘上所有的数据存储在物理内存里
    网络类型非阻塞IO复用模型,提供一些非KV存储之外的排序聚合功能,在执行这些功能时,复杂的CPU计算,会阻塞整个IO调度非阻塞IO复用模型
    水平扩展支持redis cluster 可以横向扩展暂无
    多线程Redis6.0之前是只支持单线程Memcached支持多线程,CPU利用方面Memcache优于redis
    单机QPS约10W约60W
    源代码可读性代码清爽简洁可能是考虑了太多的扩展性,多系统的兼容性,代码不清爽
    适用场景复杂数据结构、有持久化、高可用需求、value存储内容较大纯KV,数据量非常大,并发量非常大的业务

    4 Memcached 工作机制

    4.1 内存分配机制

    应用程序运行需要使用内存存储数据,但对于一个缓存系统来说,申请内存、释放内存将十分频繁,非常容易导致大量内存碎片,最后导致无连续可用内存可用。

    Memcached采用了Slab Allocator机制来分配、管理内存。

    • Page:分配给Slab的内存空间,默认为1MB,分配后就得到一个Slab。Slab分配之后内存按照固定字节大小等分成chunk。
    • Chunk:用于缓存记录k/v值的内存空间。Memcached会根据数据大小选择存到哪一个chunk中,假设chunk有128bytes、64bytes等多种,数据只有100bytes存储在128bytes中,存在少许浪费。
    • Chunk最大就是Page的大小,即一个Page中就一个Chunk
    • Slab Class:Slab按照Chunk的大小分组,就组成不同的Slab Class, 第一个Chunk大小为 96B的Slab为Class1,Chunk 120B为Class 2,如果有100bytes要存,那么Memcached会选择下图中Slab Class 2 存储,因为它是120bytes的Chunk。Slab之间的差异可以使用Growth Factor 控制,默认1.25。

    范例:查看Slab Class 

    1. #-f, --slab-growth-factor=<num> chunk size growth factor (default: 1.25)
    2. [root@centos7 ~]#memcached -u memcached -f 2 -vv
    3. slab class   1: chunk size        96 perslab   10922
    4. slab class   2: chunk size       192 perslab    5461
    5. slab class   3: chunk size       384 perslab    2730
    6. slab class   4: chunk size       768 perslab    1365
    7. slab class   5: chunk size      1536 perslab     682
    8. slab class   6: chunk size      3072 perslab     341
    9. slab class   7: chunk size      6144 perslab     170
    10. slab class   8: chunk size     12288 perslab      85
    11. slab class   9: chunk size     24576 perslab      42
    12. slab class  10: chunk size     49152 perslab      21
    13. slab class  11: chunk size     98304 perslab      10
    14. slab class  12: chunk size    196608 perslab       5
    15. slab class  13: chunk size    524288 perslab       2
    16. <27 server listening (auto-negotiate)
    17. <28 server listening (auto-negotiate)

    4.2 懒过期 Lazy Expiration

            memcached不会监视数据是否过期,而是在取数据时才看是否过期,如果过期,把数据有效期限标识为0,并不清除该数据。以后可以覆盖该位置存储其它数据。

    4.3 LRU (最近最少使用算法)

            当内存不足时,memcached会使用LRU(Least Recently Used)机制来查找可用空间,分配给新记录使用

    4.4 集群

            Memcached集群,称为基于客户端的分布式集群,即由客户端实现集群功能,即Memcached本身不支持集群

            Memcached集群内部并不互相通信,一切都需要客户端连接到Memcached服务器后自行组织这些节点,并决定数据存储的节点。

    5.安装和启动

    官方安装说明

    Install · memcached/memcached Wiki · GitHub

    5.1 yum 安装

    yum  install  -y   memcached

    1. [root@localhost ~]#yum info memcached
    2. 已加载插件:fastestmirror, langpacks
    3. Repodata is over 2 weeks old. Install yum-cron? Or run: yum makecache fast
    4. Determining fastest mirrors
    5. * base: mirrors.nju.edu.cn
    6. * extras: mirrors.nju.edu.cn
    7. * updates: mirrors.nju.edu.cn
    8. 可安装的软件包
    9. 名称 :memcached
    10. 架构 :x86_64
    11. 版本 :1.4.15
    12. 发布 :10.el7_3.1
    13. 大小 :85 k
    14. 源 :base/7/x86_64
    15. 简介 : High Performance, Distributed Memory Object Cache
    16. 网址 :http://www.memcached.org/
    17. 协议 : BSD
    18. 描述 : memcached is a high-performance, distributed memory object caching
    19. : system, generic in nature, but intended for use in speeding up dynamic
    20. : web applications by alleviating database load.

    配置文件:

    1. [root@localhost ~]#vim /etc/sysconfig/memcached
    2. PORT="11211"     #监听端口
    3. USER="memcached" #启动用户
    4. MAXCONN="1024"  #最大连接数
    5. CACHESIZE="64"  #最大使用内存
    6. OPTIONS="" #其他选项
    7. OPTIONS="" 表示该行用于定义启动 Memcached 时附加的命令行选项。当 OPTIONS 变量为空字符串时,
    8. 意味着没有指定任何额外的启动参数。
    9. Memcached 在启动时可以通过 -o 参数或者直接在配置文件中指定一系列可选配置项,这些配置项可以包括
    10. 但不限于:
    11. 绑定监听地址(例如 -l 或 -o listen=127.0.0.1
    12. 监听端口(例如 -p 或 -o port=11211
    13. 分配给缓存的最大内存大小(例如 -m 或 -o maxmemory=64
    14. 最大并发连接数(例如 -c 或 -o maxconn=1024
    15. 如:OPTIONS="-l 192.168.1.1 -p 11212 -m 512"
    16. Memcached 监听 192.168.1.1 地址上的 11212 端口,并分配最多 512MB 内存作为缓存空间。

    5.2 编译安装

    1. yum -y install gcc libevent-devel
    2. wget http://memcached.org/files/memcached-1.6.6.tar.gz
    3. tar xvf memcached-1.6.6.tar.gz
    4. cd memcached-1.6.6/
    5. ./configure --prefix=/apps/memcached
    6. make && make install
    7. ln -s /apps/memcached/bin/memcached /usr/bin
    8. #准备用户
    9. useradd -r -s /sbin/nologin memcached
    10. cat > /etc/sysconfig/memcached << eof
    11. PORT="11211"
    12. USER="memcached"
    13. MAXCONN="1024"
    14. CACHESIZE="64"
    15. OPTIONS=""
    16. eof
    17. #准备service文件
    18. cat > /lib/systemd/system/memcached.service << eof
    19. [Unit]
    20. Description=memcached daemon
    21. Before=httpd.service
    22. After=network.target
    23. [Service]
    24. EnvironmentFile=/etc/sysconfig/memcached
    25. ExecStart=/apps/memcached/bin/memcached -p \${PORT} -u \${USER} -m \${CACHESIZE} -c \${MAXCONN} \$OPTIONS
    26. [Install]
    27. WantedBy=multi-user.target
    28. eof
    29. systemctl daemon-reload
    30. systemctl enable --now memcached.service
    31. memcached --version
    32. #在多行重定向或多行字符串中,\ 在变量名前面用来确保变量名跨越多行仍然能够被正确解析。

    增长因子的改变

    1. #默认前台执行
    2. [root@centos7 ~]#memcached -u memcached -m 1024 -c 65536 -f 2 -vv
    3. #以台方式执行
    4. [root@centos7 ~]#memcached -u memcached -m 1024 -c 65536 -d

    5.3 memcached 启动程序说明

    修改memcached 运行参数,可以使用下面的选项修改/etc/sysconfig/memcached文件

    memcached 常见选项

    1. -u username memcached运行的用户身份,必须普通用户
    2. -p 绑定的端口,默认11211
    3. -m num 最大内存,单位MB,默认64MB
    4. -c num 最大连接数,缺省1024
    5. -d 守护进程方式运行
    6. -f 增长因子Growth Factor,默认1.25
    7. -v 详细信息,-vv能看到详细信息
    8. -M 使用内存直到耗尽,不许LRU
    9. -U 设置UDP监听端口,0表示禁用UDP

    6 使用 memcached

    6.1 memcached 开发库和工具

    与memcached通信的不同语言的连接器。libmemcached提供了C库和命令行工具。 

    范例: 

    #安装工具包
    yum install  libmemcached -y

    memping    检测连接服务器

    1. [root@node2 ~]#memping --help
    2. memping v1.0
    3. Ping a server to see if it is alive
    4. Current options. A '=' means the option takes a value.
    5. --version
    6. Display the version of the application and then exit.
    7. --help
    8. Display this message and then exit.
    9. --quiet
    10. stderr and stdin will be closed at application startup.
    11. --verbose
    12. Give more details on the progression of the application.
    13. --debug
    14. Provide output only useful for debugging.
    15. --servers=
    16. List which servers you wish to connect to.
    17. --expire=
    18. Set the expire option for the object.
    19. --binary
    20. Switch to binary protocol.
    21. --username=
    22. Username to use for SASL authentication
    23. --password=
    24. Password to use for SASL authentication
    25. #有memcached
    26. [root@web1 opt]#memping --servers 192.168.80.12
    27. [root@web1 opt]#echo $?
    28. 0
    29. #无memcached
    30. [root@web1 opt]#memping --servers 192.168.80.11
    31. Failed to ping 192.168.80.11:11211 CONNECTION FAILURE
    32. [root@web1 opt]#echo $?
    33. 1

    memstat

    1. [root@web1 opt]#memstat --servers=192.168.80.12
    2. Server: 192.168.80.12 (11211)
    3. pid: 60401
    4. uptime: 1128
    5. time: 1710390057
    6. version: 1.6.6
    7. libevent: 2.0.21-stable
    8. pointer_size: 64
    9. rusage_user: 0.078410
    10. rusage_system: 0.026136
    11. max_connections: 1024
    12. curr_connections: 2
    13. total_connections: 4
    14. rejected_connections: 0
    15. connection_structures: 3
    16. response_obj_bytes: 2336
    17. response_obj_total: 2
    18. response_obj_free: 1
    19. response_obj_oom: 0
    20. read_buf_bytes: 32768
    21. read_buf_bytes_free: 16384
    22. read_buf_oom: 0
    23. reserved_fds: 20
    24. cmd_get: 0
    25. cmd_set: 0
    26. cmd_flush: 0
    27. cmd_touch: 0
    28. cmd_meta: 0
    29. get_hits: 0
    30. get_misses: 0
    31. get_expired: 0
    32. get_flushed: 0
    33. delete_misses: 0
    34. delete_hits: 0
    35. incr_misses: 0
    36. incr_hits: 0
    37. decr_misses: 0
    38. decr_hits: 0
    39. cas_misses: 0
    40. cas_hits: 0
    41. cas_badval: 0
    42. touch_hits: 0
    43. touch_misses: 0
    44. auth_cmds: 0
    45. auth_errors: 0
    46. bytes_read: 32
    47. bytes_written: 30
    48. limit_maxbytes: 67108864
    49. accepting_conns: 1
    50. listen_disabled_num: 0
    51. time_in_listen_disabled_us: 0
    52. threads: 4
    53. conn_yields: 0
    54. hash_power_level: 16
    55. hash_bytes: 524288
    56. hash_is_expanding: 0
    57. slab_reassign_rescues: 0
    58. slab_reassign_chunk_rescues: 0
    59. slab_reassign_evictions_nomem: 0
    60. slab_reassign_inline_reclaim: 0
    61. slab_reassign_busy_items: 0
    62. slab_reassign_busy_deletes: 0
    63. slab_reassign_running: 0
    64. slabs_moved: 0
    65. lru_crawler_running: 0
    66. lru_crawler_starts: 1530
    67. lru_maintainer_juggles: 1178
    68. malloc_fails: 0
    69. log_worker_dropped: 0
    70. log_worker_written: 0
    71. log_watcher_skipped: 0
    72. log_watcher_sent: 0
    73. bytes: 0
    74. curr_items: 0
    75. total_items: 0
    76. slab_global_page_pool: 0
    77. expired_unfetched: 0
    78. evicted_unfetched: 0
    79. evicted_active: 0
    80. evictions: 0
    81. reclaimed: 0
    82. crawler_reclaimed: 0
    83. crawler_items_checked: 0
    84. lrutail_reflocked: 0
    85. moves_to_cold: 0
    86. moves_to_warm: 0
    87. moves_within_lru: 0
    88. direct_reclaims: 0
    89. lru_bumps_dropped: 0

    6.2  memcached 操作命令

    memcached 操作命令

    cat  /usr/share/doc/memcached/protocol.txt 

    编译安装不在此处

    [root@web1 ~]#find / -name 'protocol.txt'
    /usr/lib64/xorg/protocol.txt
    /opt/memcached-1.6.6/doc/protocol.txt

    五种基本 memcached 命令执行最简单的操作。这些命令和操作包括:

    • set   重新设置

    • add   新加一个数据

    • get    调用

    • delete   删除数据

    1. #前三个命令是用于操作存储在 memcached 中的键值对的标准修改命令,都使用如下所示的语法:
    2. command <key> <flags> <expiration time> <bytes>
    3. <value>
    4. #参数说明如下:
    5. command set/add/replace
    6. key     key 用于查找缓存值
    7. flags     可以包括键值对的整型参数,客户机使用它存储关于键值对的额外信息
    8. expiration time     在缓存中保存键值对的时间长度(以秒为单位,0 表示永远)
    9. bytes     在缓存中存储的字节数
    10. value     存储的值(始终位于第二行)
    11. #增加key,过期时间为秒,bytes为存储数据的字节数
    12. add key flags exptime bytes  

    例子: 显示服务状态

    1. [root@wg ~]#telnet 192.168.80.12 11211
    2. Trying 192.168.80.12...
    3. Connected to 192.168.80.12.
    4. Escape character is '^]'.
    5. stats
    6. #显示服务状态
    7. stats items #显示各个 slab 中 item 的数目和存储时长(最后一次访问距离现在的秒数)。
    8. stats slabs #用于显示各个slab的信息,包括chunk的大小、数目、使用情况等
    9. quit #退出

    例子: 添加数据

    1. [root@wg ~]#telnet 192.168.80.12 11211
    2. Trying 192.168.80.12...
    3. Connected to 192.168.80.12.
    4. Escape character is '^]'.
    5. add name 1 30 4
    6. wang
    7. STORED
    8. add 添加
    9. name 键的名字
    10. 1 flages标志 描述信息
    11. 30 超时时间 默认秒 0 代表永久有效
    12. 4 字节数 数据的大小、
    13. zhou 具体的值

    例子:修改

    1. set name 1 60 5
    2. test
    3. 显示CLIENT_ERROR bad data chunk数据格式不正确或者数据内容违反了Memcached的协议规范。

    例子:调用数据

    1. get name
    2. VALUE name 1 4
    3. zhou
    4. END

    例子:删除

    1. get class
    2. VALUE class 1 4
    3. asdf
    4. END
    5. delete class
    6. DELETED
    7. get class
    8. END

    例子:清空

    1. flush_all
    2. OK
    3. get mykey
    4. END
    5. quit

    7 memcached集群部署架构

    7.1 基于 magent 的部署架构

            Magent是google开发的项目,应用端通过负载均衡服务器连接到magent,然后再由magent代理用户应用请求到memcached处理,底层的memcached为双主结构会自动同步数据,本部署方式存在magent单点问题,因此需要两个magent做高可用。

    项目站点:https://code.google.com/archive/p/memagent/

    此项目过于陈旧,且不稳定,当前已经废弃

    7.2 Repcached 实现原理

    项目站点:repcached - add data replication feature to memcached

            在 master上可以通过 -X 选项指定 replication port(默认为11212/tcp),在 slave上通过 -x 指定复制的master并连接,事实上,如果同时指定了 -x/-X, repcached先会尝试连接对端的master,但如果连接失败,它就会用 -X参数来自己 listen(成为master);如果 master坏掉, slave侦测到连接断了,它会自动 listen而成为 master;而如果 slave坏掉,master也会侦测到连接断开,它就会重新 listen等待新的 slave加入。

            从这方案的技术实现来看,其实它是一个单 master单 slave的方案,但它的 master/slave都是可读写的,而且可以相互同步,所以从功能上看,也可以认为它是双机 master-master方案

    7.3 简化后的部署架构

            magent已经有很长时间没有更新,因此可以不再使用magent,直接通过负载均衡连接到memcached,仍然有两台memcached做高可用,repcached版本的memcached之间会自动同步数据,以保持数据一致性,即使其中的一台memcached故障也不影响业务正常运行,故障的memcached修复上线后再自动从另外一台同步数据即可保持数据一致性。

    7.4 部署repcached

    haproxy:192.168.80.7

    server1:192.168.80.10

    server2:192.168.80.11

    1. server1 和 server2 可同时部署也可等server1部署好后 rsync -a /apps 192.168.80.11:/
    2. yum -y install gcc libevent libevent-devel
    3. wget https://jaist.dl.sourceforge.net/project/repcached/repcached/2.2.1-1.2.8/memcached-1.2.8-repcached-2.2.1.tar.gz
    4. tar xf memcached-1.2.8-repcached-2.2.1.tar.gz
    5. cd memcached-1.2.8-repcached-2.2.1
    6. ./configure --prefix=/apps/repcached --enable-replication
    7. make
    8. 会报错
    9. #报错如下

    解决办法:

    1. vim memcached.c
    2. 56 #ifndef IOV_MAX
    3. 57 #if defined(__FreeBSD__) || defined(__APPLE__)
    4. 58 # define IOV_MAX 1024
    5. 59 #endif
    6. 60 #endif
    7. #改为如下内容,即删除原有的原第5759
    8. 56 #ifndef IOV_MAX
    9. 57 # define IOV_MAX 1024
    10. 58 #endif

    再次编译安装:

    1. [root@localhost memcached-1.2.8-repcached-2.2.1]#make && make install
    2. 做软连接
    3. ln -s /apps/repcached/bin/memcached /usr/bin/
    4. 使用帮助
    5. [root@localhost ~]#memcached -h
    6. memcached 1.2.8
    7. repcached 2.2.1
    8. -x <ip_addr> hostname or IP address of peer repcached
    9. -X <num:num> TCP port number for replication. <listen:connect> (default: 11212)

    7.6 启动 memcached

    7.6.1 相关操作

    server1

    1. #创建用户
    2. useradd -r -s /sbin/nologin memcached
    3. memcached -d -m 1024 -p 11211 -u memcached -c 2048 -x 192.168.80.11
    4. #-x 192.168.80.11 为对端memcached的地址 -d 后台
    5. ss -ntl
    6. # 查看是否启动

    server2

    1. #在server1 上 将整个目录拷贝到 server2上(若server2已经完成部署不用拷贝)
    2. rsync -a /apps 192.168.91.101:/
    3. # apps注意不要加/
    4. #yum -y install gcc libevent libevent-devel
    5. #ln -s /apps/repcached/bin/memcached /usr/bin/
    6. useradd -r -s /sbin/nologin memcached
    7. #创建用户
    8. memcached -d -m 1024 -p 11211 -u memcached -c 2048 -x 192.168.80.10
    9. ss -ntl
    10. # 查看是否启动

    haproxy

    1. yum install -y haproxy
    2. systemctl start haproxy
    3. vim /etc/haproxy/haproxy.cfg
    4. listen mem
    5. bind 192.168.80.7:11211
    6. mode tcp
    7. server m1 192.168.80.10:11211 check
    8. server m2 192.168.80.11:11211 check
    9. systemctl restart haproxy.service

    测试:

    1. [root@localhost ~]#telnet 192.168.80.7 11211
    2. Trying 192.168.80.7...
    3. Connected to 192.168.80.7.
    4. Escape character is '^]'.
    5. set server 1 0 10
    6. hello word
    7. STORED
    8. get server
    9. VALUE server 1 10
    10. hello word
    11. END
  • 相关阅读:
    换挡周期下,谁将成为厨电品牌的进取者?
    海外流量宝是个好产品吗?
    【论文阅读】ConvNeXt:A ConvNet for the 2020s 新时代卷积网络
    星戈瑞DSPE-SS-PEG-CY7近红外花菁染料
    【HCIE考试喜报】2022年11月11日考试通过
    【kubernetes】使用CloudProvider对接云厂商的LB
    Android开发----实现登录注册页面(创建本地数据库,对注册的账户密码进行存储)
    贴片和直插型IRM红外遥控接收头引脚定义和规格参数及使用注意事项
    原数据治理平台业务架构图V1.1
    【推荐系统】ESMM:一种有效估算后点击转换率的方法
  • 原文地址:https://blog.csdn.net/fhjtg/article/details/136702756