Tokyo Tyrant教程
1) 基础使用
安装Tokyo Tyrant后,可以通过在终端执行命令'ttserver'来立即启动服务器。默认,服务器在1978端口监听,为on-memory hash database(适合存储缓存数据)提供访问服务。
[terminal-1]$ttserver
在另外一个终端中执行下面的命令以测试存储操作,'tcrmgr put'调用函数'tcrdbput':
[terminal-2]$tcrmgrputlocalhostonefirst [terminal-2]$tcrmgrputlocalhosttwosecond [terminal-2]$tcrmgrputlocalhostthreethird
执行下面的命令来一次获取多条记录。'tcrmgr mget' 调用函数 'tcrdbget3':
[terminal-2]$tcrmgrmgetlocalhostonetwothree
在服务器的终端中按Ctrl-C来终止服务器。
通过指定后缀为'.tch'的文件名,我们运行服务器来处理 hash database:
[terminal-1]$ttservercasket.tch
保存一些记录
[terminal-2]$tcrmgrputlocalhostonefirst [terminal-2]$tcrmgrputlocalhosttwosecond [terminal-2]$tcrmgrputlocalhostthreethird
用Ctrl-C终止服务器,然后重新启动服务器:
[terminal-1]$ttservercasket.tch
检查保存的记录的一致性。
[terminal-2]$tcrmgrmgetlocalhostonetwothree
[terminal-1]$rmcasket.tch
2) 后台进程
指定选项"-dmn"以后台进程的方式运行服务器。此外,可以指定"-pid"选项来指定文件以记录进程ID。注意后台进程的当前工作目录被修改到root目录。因此,文件路径参数需要用绝对路径来表示。
[terminal-1]$ttserver-dmn-pid/tmp/ttserver.pid/tmp/casket.tch
为了终止服务器,查看'_pid'指定的进程Id文件并发送SIGTERM 信号给进程。
[terminal-1]$kill-TERM`cat/tmp/ttserver.pid`
为了通过操作系统的RC脚本运行服务器,请使用'ttservctl'。对于Linux发型版本,添加下面的行到/etc/rc.local.
/etc/rc.local
默认,数据库文件和相关文件被放置在'/var/ttserver'下。因为'ttservctl'是一个很小的shell脚本,您可以随意的复制并编辑它。同样,也可以安装修改后的脚本到'/etc/init.d'并设置符号链接/etc/rc3.d/S98ttserver' and `/etc/rc5.d/S98ttserver'.
3) 备份和恢复
让我们再次运行服务器以继续这个教程。
[terminal-1]$ttservercasket.tch
保存一些记录。
[terminal-2]$tcrmgrputlocalhostonefirst [terminal-2]$tcrmgrputlocalhosttwosecond [terminal-2]$tcrmgrputlocalhostthreethird
为了备份数据库文件,使用命令'tcrmgr copy'并指定目标路径。注意备份文件将在服务器上的本地文件系统中创建(不是在客户端这边).
[terminal-2]$tcrmgrcopylocalhostbackup.tch
[terminal-1]$rmcasket.tch
[terminal-1]$cpbackup.tchcasket.tch [terminal-1]$ttservercasket.tch
检查存储的记录的一致性。
[terminal-2]$tcrmgrmgetlocalhostonetwothree
[terminal-1]$rmcasket.tchbackup.tch
4) 更新日志
让我们开启更新日志来运行服务器。选项'-ulog'指定包含更新日志文件的目录。
[terminal-1]$mkdirulog [terminal-1]$ttserver-ulogulogcasket.tch
存储一些记录.
[terminal-2]$tcrmgrputlocalhostonefirst [terminal-2]$tcrmgrputlocalhosttwosecond [terminal-2]$tcrmgrputlocalhostthreethird
[terminal-1]$rmcasket.tch
备份更新日志目录并重新启动服务器。
[terminal-1]$mvulogulog-back [terminal-1]$mkdirulog [terminal-1]$ttserver-ulogulogcasket.tch
在客户端使用'tcrmgr restore'命令从备份的更新日志中恢复数据库
[terminal-2]$tcrmgrrestorelocalhostulog-back
检查存储的记录的一致性。
[terminal-2]$tcrmgrmgetlocalhostonetwothree
[terminal-1]$rm-rfcasket.tchulogulog-back
5) 复制
复制是同步两台或更多数据库服务器的机制,实现高可用性和高完整性。复制源服务器被称为"master"而所有目标服务器都被称为"slave"。复制需要以下前提条件:
1. master必须记录更新日志
2. master必须指定唯一的服务器ID
3. 每个slave必须记录更新日志,因为在master当机时它将成为master
4. 每个slave必须指定唯一的服务器ID,因为在master当机时它将成为master
5. 每个slave必须指定它的master服务器的地址和端口号
6. 每个slave必须指定复制时间戳文件
这个章节将描述何如建立一个master(使用端口1978)和一个slave(使用端口1979)的复制。首先,让我们运行master服务器。
[terminal-1]$mkdirulog-1 [terminal-1]$ttserver-port1978-ulogulog-1-sid1casket-1.tch
下一步,在另一个终端运行slave服务器。
[terminal-2]$mkdirulog-2 [terminal-2]$ttserver-port1979-ulogulog-2-sid2-mhostlocalhost-mport1978-rts2.rtscasket-2.tch
在master中存储一些记录。
[terminal-3]$tcrmgrput-port1978localhostonefirst [terminal-3]$tcrmgrput-port1978localhosttwosecond [terminal-3]$tcrmgrput-port1978localhostthreethird
在master和slave中检查存储记录的一致性。
[terminal-2]$tcrmgrmget-port1978localhostonetwothree [terminal-2]$tcrmgrmget-port1979localhostonetwothree
让我们模拟master崩溃的情况。Ctrl-C终止master并删除数据库文件。
[terminal-1]$rmcasket-1.tch
Ctrl-C终止slave并重启作为master。
[terminal-2]$ttserver-port1979-ulogulog-2-sid2casket-2.tch
添加新的slave(使用端口1980)。
[terminal-1]$mkdirulog-3 [terminal-1]$ttserver-port1980-ulogulog-3-sid3-mhostlocalhost-mport1979-rts3.rtscasket-3.tch
在新的master和新的slave中检查存储记录的一致性。
[terminal-2]$tcrmgrmget-port1979localhostonetwothree [terminal-2]$tcrmgrmget-port1980localhostonetwothree
[terminal-1]$rm-rfcasket-1.tchulog-11.rts [terminal-2]$rm-rfcasket-2.tchulog-22.rts [terminal-1]$rm-rfcasket-3.tchulog-33.rts
Tokyo Tyrant支持"双master"复制可以提供更高的可用性。要实现它,运行两个服务器各自复制对方。注意同时更新两个master可能导致数据库不一致。默认,服务器不报错即使检测到不一致。'-rcc'选项将使得服务器检查一致性并在检测到不一致时停止服务。
6) 按需设置复制
可以为正在运行的数据库服务设置复制而不必停工。首先,为备份操作准备下面的脚本并保存为"ttbackup.sh",设置好可执行权限(0755)。
#!/bin/sh srcpath="$1" destpath="$1.$2" rm-f"$destpath" cp-f"$srcpath""$destpath"
下一步,让我们开启更新日志来启动master。
[terminal-1]$mkdirulog-1 [terminal-1]$ttserver-port1978-ulogulog-1-sid1casket-1.tch
往master中存入一些记录。
[terminal-2]$tcrtestwrite-port1978localhost10000
检查存储的记录的一致性。
[terminal-2]$tcrmgrlist-port1978-pvlocalhost
备份数据库
[terminal-2]$tcrmgrcopy-port1978localhost'@./ttbackup.sh'
确认备份文件被保存为"casket-1.tch.xxxxx"("xxxxx"为备份文件的时间戳)。然后,使用备份文件运行slave。
[terminal-2]$ls [terminal-2]$cpcasket-1.tch.xxxxxcasket-2.tch [terminal-2]$echoxxxxx>2.rts [terminal-2]$mkdirulog-2 [terminal-2]$ttserver-port1979-ulogulog-2-sid2-rts2.rtscasket-2.tch
注意上面的操作并不是指定master为slave。作为教程,让我们模拟当你正在设置复制时,有一些记录被用户存储进master。
[terminal-3]$tcrmgrput-port1978localhostonefirst [terminal-3]$tcrmgrput-port1978localhosttwosecond [terminal-3]$tcrmgrput-port1978localhostthreethird
检查master和slave的差异。
[terminal-3]$tcrmgrinform-port1978localhost [terminal-3]$tcrmgrinform-port1979localhost
给slave指定master,这样将启动复制并解决这个差异。
[terminal-3]$tcrmgrsetmst-port1979-mport1978localhostlocalhost
确认slave知道master并且解决了差异。
[terminal-3]$tcrmgrinform-port1979-stlocalhost
[terminal-1]$rm-rfcasket-1.tchcasket-1.tch.*ulog-11.rtsttbackup.sh [terminal-2]$rm-rfcasket-2.tchulog-22.rts
7) 调整
如果使用hash database,设置调增参数"#bnum=xxx"来改进性能。它指定bucket 数量,应该要比存储的记录数多。
如果使用B+ tree database,设置调整参数"#lcnum=xxx#bnum=yyy"来改进性能。前一个参数指定缓存的叶节点的最大数量,应该和系统容许的内存容量一样大。后一个参数指定bucket 的数量,应该比要存储的记录数的1/128大。
如果有非常大量的客户端访问服务器,确认已清除每个进程的文件描述符数量的限制。在大多数系统中默认设置为1024。如果没有,使用'ulimit'来清理它。
为了处理服务波峰时间的突发请求,可以用复制来联合使用on-memory hash/tree database和file hash/tree database。master服务器处理on-memory database,它可以从容处理波峰时间的突发请求。但是on-memory database不保证数据的持久化,用于复制的slave通过将记录存储到文件数据库中来弥补这个缺陷。
8) Lua扩展
如果你需要比已有更加复杂的数据库操作,请使用Lua扩展。举例,准备下列脚本并保存为"test.lua"。这里有一个名为"fibonacci"的函数,返回key的费伯那其数字(注:数列中每个数字是前两个数字的和)
functionfibonacci(key,value) localnum=tonumber(key) locallarge=math.pow((1+math.sqrt(5))/2,num) localsmall=math.pow((1-math.sqrt(5))/2,num) return(large-small)/math.sqrt(5) end
让我们启动服务器,让它读取这个脚本文件
[terminal-1]$ttserver-exttest.lua
[terminal-2]$tcrmgrextlocalhostfibonacci1 [terminal-2]$tcrmgrextlocalhostfibonacci2 [terminal-2]$tcrmgrextlocalhostfibonacci3 [terminal-2]$tcrmgrextlocalhostfibonacci4 [terminal-2]$tcrmgrextlocalhostfibonacci5 [terminal-2]$tcrmgrextlocalhostfibonacci6
Fibonacci可以通过其他算法来产生。添加下列脚本到"test.lua"。这里有函数"fibnext"可以从数据库中返回下一个费伯那其数字。状态信息被保存在数据库中。
functionfibnext(key,value) localcur=tonumber(_get("fibcur")) ifnotcurthen _put("fibold",0) _put("fibcur",1) return1 end localold=tonumber(_get("fibold")) _put("fibold",cur) cur=old+cur _put("fibcur",cur) returncur end
然后,重启服务器并测试新的算法。
[terminal-2]$tcrmgrextlocalhostfibnext [terminal-2]$tcrmgrextlocalhostfibnext [terminal-2]$tcrmgrextlocalhostfibnext [terminal-2]$tcrmgrextlocalhostfibnext [terminal-2]$tcrmgrextlocalhostfibnext [terminal-2]$tcrmgrextlocalhostfibnext
As you see,the called function receives two string parameters of the key and the value. The return value is sent back to the client. You can use such built-in functions for database operations as "_put","_out","_get",and so on. There is a sample file `ext/senatus.lua'.
如你所见,被调用的函数接收两个字符串参数,key和value。返回值被发送回客户端。你可以始终诸如"_put","_get"等内建函数来进行数据库操作。这里有一个实例文件'ext/senatus.lua'。
9) 使用memcached 客户端
这个章节描述如何使用Perl的mamcached客户端类库(Cache::Memcached)来访问Tokyo Tyrant。和平常一样运行Tokyo Tyrant服务器,下面的脚本是一个典型例子。
useCache::Memcached; my$memd=Cache::Memcached->new(); $memd->set_servers(['localhost:1978']); $memd->set('one','first'); $memd->set('two','second'); $memd->set('three','third'); my$val=$memd->get('one'); printf("one:%s\n",$val); $val=$memd->get_multi('one','two','three'); printf("one:%s\n",$val->{one}); printf("two:%s\n",$val->{two}); printf("three:%s\n",$val->{three}); $memd->delete('one');
10) 使用HTTP 客户端
这个章节介绍如何使用Perl的HTTP客户端类库(LWP::UserAgent)来访问Tokyo Tyrant。和平常一样运行Tokyo Tyrant服务器,下面的脚本是一个典型例子。
useLWP::UserAgent; my$ua=LWP::UserAgent->new(keep_alive=>1); my$baseurl='http://localhost:1978/'; my$req; $req=HTTP::Request->new(PUT=>$baseurl.'one',[],'first'); $ua->request($req); $req=HTTP::Request->new(PUT=>$baseurl.'two',["X-TT-PDMODE"=>1],'second'); $ua->request($req); $req=HTTP::Request->new(PUT=>$baseurl.'three',["X-TT-PDMODE"=>2],'third'); $ua->request($req); $req=HTTP::Request->new(GET=>$baseurl.'one'); my$res=$ua->request($req); if($res->is_success()){ printf("%s\n",$res->content()); } $req=HTTP::Request->new(DELETE=>$baseurl.'one'); $res=$ua->request($req); $req=HTTP::Request->new(POST=>$baseurl.'foo',["X-TT-XNAME"=>"echo","X-TT-XOPTS"=>1],'bar'); $res=$ua->request($req); if($res->is_success()){ printf("%s\n",$res->content()); }
11) 持久化而支持过期的缓存
如果你想位你的web应用缓存类似session信息这样的数据,但是想避免因服务器当机而造成的数据丢失,Tokyo Tyrant是一个方案,也就是说,持久化而支持过期的缓存。它需要下面的前提条件:
1. 服务器必须开启table database
2. 客户端保存每条记录时要使用过期数据列
3. 数据库在过期数据列上要有索引
5. 服务器必须周期性的调用通过Lua扩展提供的用户自定义函数
首先,为过期准备下面的脚本并保存为"ttexpire.lua"。当"X"列的数值超过当前日期时将使记录过期。
functionexpire() localargs={} localcdate=string.format("%d",_time()) table.insert(args,"addcond\0x\0NUMLE\0"..cdate) table.insert(args,"out") localres=_misc("search",args) ifnotresthen _log("expirationwasFailed",2) end end
启动服务器,table database方式,其中有一个"x"列是有索引的,并计划每秒钟调用一次expiration 函数。
[terminal-1]$ttserver-extttexpire.lua-extpcexpire1.0"casket.tct#idx=x:dec#dfunit=8"
在另外一个终端中存储测试记录。
[terminal-2]$now=`date+%s` for((i=1;i<=60;i++));do tcrmgrput-sep'|'localhost"$i""x|$((now+i))" done
确认数据正在被过期机制删除:
[terminal-2]$tcrmgrlist-pv-sep'|'localhost原文链接:https://www.f2er.com/nosql/203908.html