ls4 0.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/AUTHORS +1 -0
- data/COPYING +661 -0
- data/ChangeLog +9 -0
- data/NOTICE +8 -0
- data/README.rdoc +61 -0
- data/bin/ls4-cs +3 -0
- data/bin/ls4-ds +3 -0
- data/bin/ls4-gw +3 -0
- data/bin/ls4-standalone +3 -0
- data/bin/ls4cmd +3 -0
- data/bin/ls4ctl +3 -0
- data/bin/ls4rpc +3 -0
- data/bin/ls4stat +3 -0
- data/bin/ls4top +3 -0
- data/lib/ls4/command/cmd.rb +241 -0
- data/lib/ls4/command/cs.rb +190 -0
- data/lib/ls4/command/ctl.rb +278 -0
- data/lib/ls4/command/ds.rb +335 -0
- data/lib/ls4/command/gw.rb +256 -0
- data/lib/ls4/command/rpc.rb +172 -0
- data/lib/ls4/command/standalone.rb +318 -0
- data/lib/ls4/command/stat.rb +244 -0
- data/lib/ls4/command/top.rb +291 -0
- data/lib/ls4/default.rb +26 -0
- data/lib/ls4/lib/cclog.rb +220 -0
- data/lib/ls4/lib/ebus.rb +553 -0
- data/lib/ls4/lib/vbcode.rb +228 -0
- data/lib/ls4/logic/fault_detector.rb +212 -0
- data/lib/ls4/logic/membership.rb +253 -0
- data/lib/ls4/logic/node.rb +66 -0
- data/lib/ls4/logic/okey.rb +45 -0
- data/lib/ls4/logic/tsv_data.rb +81 -0
- data/lib/ls4/logic/weight.rb +166 -0
- data/lib/ls4/service/balance.rb +62 -0
- data/lib/ls4/service/base.rb +29 -0
- data/lib/ls4/service/bus.rb +37 -0
- data/lib/ls4/service/config.rb +63 -0
- data/lib/ls4/service/config_cs.rb +33 -0
- data/lib/ls4/service/config_ds.rb +56 -0
- data/lib/ls4/service/config_gw.rb +42 -0
- data/lib/ls4/service/data_client.rb +122 -0
- data/lib/ls4/service/data_server.rb +168 -0
- data/lib/ls4/service/data_server_url.rb +83 -0
- data/lib/ls4/service/gateway.rb +375 -0
- data/lib/ls4/service/gateway_ro.rb +91 -0
- data/lib/ls4/service/gw_http.rb +821 -0
- data/lib/ls4/service/heartbeat.rb +182 -0
- data/lib/ls4/service/log.rb +81 -0
- data/lib/ls4/service/master_select.rb +148 -0
- data/lib/ls4/service/mds.rb +292 -0
- data/lib/ls4/service/mds_cache.rb +294 -0
- data/lib/ls4/service/mds_cache_mem.rb +63 -0
- data/lib/ls4/service/mds_cache_memcached.rb +65 -0
- data/lib/ls4/service/mds_ha.rb +176 -0
- data/lib/ls4/service/mds_memcache.rb +209 -0
- data/lib/ls4/service/mds_tc.rb +508 -0
- data/lib/ls4/service/mds_tt.rb +472 -0
- data/lib/ls4/service/membership.rb +331 -0
- data/lib/ls4/service/process.rb +90 -0
- data/lib/ls4/service/rpc.rb +50 -0
- data/lib/ls4/service/rpc_cs.rb +101 -0
- data/lib/ls4/service/rpc_ds.rb +96 -0
- data/lib/ls4/service/rpc_gw.rb +255 -0
- data/lib/ls4/service/rts.rb +94 -0
- data/lib/ls4/service/rts_file.rb +76 -0
- data/lib/ls4/service/rts_memory.rb +55 -0
- data/lib/ls4/service/slave.rb +132 -0
- data/lib/ls4/service/stat.rb +91 -0
- data/lib/ls4/service/stat_cs.rb +25 -0
- data/lib/ls4/service/stat_ds.rb +40 -0
- data/lib/ls4/service/stat_gw.rb +25 -0
- data/lib/ls4/service/storage.rb +116 -0
- data/lib/ls4/service/storage_dir.rb +201 -0
- data/lib/ls4/service/sync.rb +206 -0
- data/lib/ls4/service/time_check.rb +80 -0
- data/lib/ls4/service/ulog.rb +159 -0
- data/lib/ls4/service/ulog_file.rb +398 -0
- data/lib/ls4/service/ulog_memory.rb +53 -0
- data/lib/ls4/service/weight.rb +134 -0
- data/lib/ls4/version.rb +5 -0
- data/test/01_add_get_remove.rt +84 -0
- data/test/02_read.rt +61 -0
- data/test/03_getd_readd.rt +69 -0
- data/test/04_version_time.rt +170 -0
- data/test/05_version_name.rt +161 -0
- data/test/06_http_get_set_remove_1.rt +119 -0
- data/test/07_http_get_set_remove_2.rt +116 -0
- data/test/08_read_only_time.rt +177 -0
- data/test/09_read_only_name.rt +173 -0
- data/test/10_http_get_set_remove_3.rt +73 -0
- data/test/11_mds_cache_memcached.rt +88 -0
- data/test/12_mds_cache_local_memory.rt +86 -0
- data/test/13_memcache_mds.rt +84 -0
- data/test/14_delete.rt +63 -0
- data/test/15_standalone.rt +71 -0
- data/test/chukan.rb +516 -0
- data/test/common.rb +250 -0
- data/test/load_test.rb +79 -0
- data/test/load_test_offload.rb +86 -0
- metadata +295 -0
@@ -0,0 +1,182 @@
|
|
1
|
+
#
|
2
|
+
# LS4
|
3
|
+
# Copyright (C) 2010-2011 FURUHASHI Sadayuki
|
4
|
+
#
|
5
|
+
# This program is free software: you can redistribute it and/or modify
|
6
|
+
# it under the terms of the GNU Affero General Public License as
|
7
|
+
# published by the Free Software Foundation, either version 3 of the
|
8
|
+
# License, or (at your option) any later version.
|
9
|
+
#
|
10
|
+
# This program is distributed in the hope that it will be useful,
|
11
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
# GNU Affero General Public License for more details.
|
14
|
+
#
|
15
|
+
# You should have received a copy of the GNU Affero General Public License
|
16
|
+
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
#
|
18
|
+
module LS4
|
19
|
+
|
20
|
+
|
21
|
+
class HeartbeatResponse
|
22
|
+
def initialize(term=nil, sync_needed=nil)
|
23
|
+
@term = term
|
24
|
+
@sync_needed = sync_needed
|
25
|
+
end
|
26
|
+
|
27
|
+
attr_accessor :term
|
28
|
+
attr_accessor :sync_needed
|
29
|
+
|
30
|
+
public
|
31
|
+
def to_msgpack(out = '')
|
32
|
+
[@term, @sync_needed].to_msgpack(out)
|
33
|
+
end
|
34
|
+
def from_msgpack(obj)
|
35
|
+
@term = obj[0]
|
36
|
+
@sync_needed = obj[1]
|
37
|
+
self
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
|
42
|
+
class HeartbeatServerService < Service
|
43
|
+
def initialize
|
44
|
+
super
|
45
|
+
@syncs = []
|
46
|
+
end
|
47
|
+
|
48
|
+
def rpc_heartbeat(nid, sync_hash)
|
49
|
+
hbres = HeartbeatResponse.new
|
50
|
+
|
51
|
+
if nid
|
52
|
+
hbres.term = MembershipBus.reset_fault_detector(nid)
|
53
|
+
end
|
54
|
+
|
55
|
+
if sync_hash
|
56
|
+
if SyncBus.check_hash(sync_hash)
|
57
|
+
hbres.sync_needed = false
|
58
|
+
else
|
59
|
+
hbres.sync_needed = true
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
hbres
|
64
|
+
end
|
65
|
+
|
66
|
+
ebus_connect :CSRPCBus,
|
67
|
+
:heartbeat => :rpc_heartbeat
|
68
|
+
end
|
69
|
+
|
70
|
+
|
71
|
+
class HeartbeatClientService < Service
|
72
|
+
def initialize
|
73
|
+
@heartbeat_nid = nil
|
74
|
+
end
|
75
|
+
|
76
|
+
#def get_cs_session
|
77
|
+
# ProcessBus.get_session(ConfigBus.get_cs_address)
|
78
|
+
#end
|
79
|
+
#
|
80
|
+
#def on_timer
|
81
|
+
# do_heartbeat
|
82
|
+
#end
|
83
|
+
#
|
84
|
+
#def do_heartbeat
|
85
|
+
# sync_hash = SyncBus.get_hash
|
86
|
+
# get_cs_session.callback(:heartbeat, @heartbeat_nid, sync_hash) do |future|
|
87
|
+
# begin
|
88
|
+
# hbres = HeartbeatResponse.new.from_msgpack(future.get)
|
89
|
+
# ack_heartbeat(hbres)
|
90
|
+
# rescue
|
91
|
+
# $log.error "heartbeat error: #{$!}"
|
92
|
+
# $log.error_backtrace $!.backtrace
|
93
|
+
# end
|
94
|
+
# end
|
95
|
+
#end
|
96
|
+
#
|
97
|
+
#def ack_heartbeat(hbres)
|
98
|
+
# if hbres.sync_needed
|
99
|
+
# SyncBus.try_sync
|
100
|
+
# end
|
101
|
+
#end
|
102
|
+
#
|
103
|
+
#ebus_connect :ProcessBus,
|
104
|
+
# :on_timer
|
105
|
+
#
|
106
|
+
#def heartbeat_blocking!
|
107
|
+
# do_heartbeat.join
|
108
|
+
#end
|
109
|
+
|
110
|
+
def run
|
111
|
+
@cs = MessagePack::RPC::Client.new(*ConfigBus.get_cs_address)
|
112
|
+
@end = false
|
113
|
+
@thread = Thread.new do
|
114
|
+
while !@end
|
115
|
+
sleep 1
|
116
|
+
do_heartbeat_blocking
|
117
|
+
end
|
118
|
+
end
|
119
|
+
end
|
120
|
+
|
121
|
+
def shutdown
|
122
|
+
@end = true
|
123
|
+
#@thread.join
|
124
|
+
@cs.close
|
125
|
+
end
|
126
|
+
|
127
|
+
def do_heartbeat_blocking
|
128
|
+
sync_hash = SyncBus.get_hash
|
129
|
+
begin
|
130
|
+
res = @cs.call(:heartbeat, @heartbeat_nid, sync_hash)
|
131
|
+
hbres = HeartbeatResponse.new.from_msgpack(res)
|
132
|
+
if hbres.sync_needed
|
133
|
+
ProcessBus.submit {
|
134
|
+
SyncBus.try_sync
|
135
|
+
}
|
136
|
+
end
|
137
|
+
rescue
|
138
|
+
$log.error "heartbeat error: #{$!}"
|
139
|
+
$log.error_backtrace $!.backtrace
|
140
|
+
end
|
141
|
+
nil
|
142
|
+
end
|
143
|
+
|
144
|
+
def heartbeat_blocking!
|
145
|
+
do_heartbeat_blocking
|
146
|
+
end
|
147
|
+
|
148
|
+
ebus_connect :ProcessBus,
|
149
|
+
:run,
|
150
|
+
:shutdown
|
151
|
+
end
|
152
|
+
|
153
|
+
|
154
|
+
class HeartbeatMemberService < HeartbeatClientService
|
155
|
+
def initialize
|
156
|
+
super
|
157
|
+
@heartbeat_nid = ConfigBus.self_nid
|
158
|
+
end
|
159
|
+
|
160
|
+
#def ack_heartbeat(hbres)
|
161
|
+
# super
|
162
|
+
#
|
163
|
+
# if hbres.term
|
164
|
+
# # do nothing
|
165
|
+
# else
|
166
|
+
# # MembershipMemberService
|
167
|
+
# #register_self
|
168
|
+
# end
|
169
|
+
#
|
170
|
+
# MembershipBus.try_register_node
|
171
|
+
#end
|
172
|
+
|
173
|
+
def on_timer
|
174
|
+
MembershipBus.try_register_node
|
175
|
+
end
|
176
|
+
|
177
|
+
ebus_connect :ProcessBus,
|
178
|
+
:on_timer
|
179
|
+
end
|
180
|
+
|
181
|
+
|
182
|
+
end
|
@@ -0,0 +1,81 @@
|
|
1
|
+
#
|
2
|
+
# LS4
|
3
|
+
# Copyright (C) 2010-2011 FURUHASHI Sadayuki
|
4
|
+
#
|
5
|
+
# This program is free software: you can redistribute it and/or modify
|
6
|
+
# it under the terms of the GNU Affero General Public License as
|
7
|
+
# published by the Free Software Foundation, either version 3 of the
|
8
|
+
# License, or (at your option) any later version.
|
9
|
+
#
|
10
|
+
# This program is distributed in the hope that it will be useful,
|
11
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
# GNU Affero General Public License for more details.
|
14
|
+
#
|
15
|
+
# You should have received a copy of the GNU Affero General Public License
|
16
|
+
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
#
|
18
|
+
module LS4
|
19
|
+
|
20
|
+
|
21
|
+
$log = CCLog.new(CCLog::LEVEL_INFO)
|
22
|
+
|
23
|
+
|
24
|
+
class LogService < Service
|
25
|
+
def initialize
|
26
|
+
@out = nil
|
27
|
+
end
|
28
|
+
|
29
|
+
def self.open!
|
30
|
+
init.open
|
31
|
+
end
|
32
|
+
|
33
|
+
def open
|
34
|
+
if path = ConfigBus.get_log_path
|
35
|
+
out = File.open(path, "a")
|
36
|
+
@out = $log.out = out
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def on_sighup
|
41
|
+
if path = ConfigBus.get_log_path
|
42
|
+
out = File.open(path, "a")
|
43
|
+
if @out
|
44
|
+
@out.close
|
45
|
+
@out = nil
|
46
|
+
end
|
47
|
+
@out = $log.out = out
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
def shutdown
|
52
|
+
if @out
|
53
|
+
@out.close
|
54
|
+
@out = nil
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
def log_event_bus
|
59
|
+
$log.on_trace do
|
60
|
+
LS4.constants.each {|const|
|
61
|
+
klass = LS4.const_get(const)
|
62
|
+
if klass.is_a?(Class) && klass < Bus
|
63
|
+
bus = klass
|
64
|
+
name = bus.name.gsub('LS4::','')
|
65
|
+
$log.trace name
|
66
|
+
bus.ebus_all_slots.each {|s|
|
67
|
+
s = s.to_s.gsub('LS4::','')
|
68
|
+
$log.trace " #{s}"
|
69
|
+
}
|
70
|
+
end
|
71
|
+
}
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
ebus_connect :ProcessBus,
|
76
|
+
:shutdown,
|
77
|
+
:on_sighup
|
78
|
+
end
|
79
|
+
|
80
|
+
|
81
|
+
end
|
@@ -0,0 +1,148 @@
|
|
1
|
+
#
|
2
|
+
# LS4
|
3
|
+
# Copyright (C) 2010-2011 FURUHASHI Sadayuki
|
4
|
+
#
|
5
|
+
# This program is free software: you can redistribute it and/or modify
|
6
|
+
# it under the terms of the GNU Affero General Public License as
|
7
|
+
# published by the Free Software Foundation, either version 3 of the
|
8
|
+
# License, or (at your option) any later version.
|
9
|
+
#
|
10
|
+
# This program is distributed in the hope that it will be useful,
|
11
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
# GNU Affero General Public License for more details.
|
14
|
+
#
|
15
|
+
# You should have received a copy of the GNU Affero General Public License
|
16
|
+
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
#
|
18
|
+
module LS4
|
19
|
+
|
20
|
+
|
21
|
+
class MasterSelectBus < Bus
|
22
|
+
call_slot :select_master
|
23
|
+
call_slot :select_master_static
|
24
|
+
signal_slot :update_nodes
|
25
|
+
end
|
26
|
+
|
27
|
+
|
28
|
+
class LocationAwareMasterSelectService < Service
|
29
|
+
def initialize
|
30
|
+
@map = {} # { rsid => [nids] }
|
31
|
+
@self_location = ConfigBus.self_location
|
32
|
+
end
|
33
|
+
|
34
|
+
def update_nodes(nodes=nil)
|
35
|
+
nodes ||= MembershipBus.get_all_nodes
|
36
|
+
|
37
|
+
rsid_nodes = {}
|
38
|
+
nodes.each {|node|
|
39
|
+
node.rsids.each {|rsid|
|
40
|
+
(rsid_nodes[rsid] ||= []) << node
|
41
|
+
}
|
42
|
+
}
|
43
|
+
|
44
|
+
rsid_loc_nids = {}
|
45
|
+
rsid_nodes.each_pair {|rsid,nodes|
|
46
|
+
loc_grouped = nodes.group_by {|node| node.location }
|
47
|
+
|
48
|
+
sorted = loc_grouped.to_a.sort_by {|loc,nodes| loc }
|
49
|
+
if idx = sorted.find_index {|loc,nodes| loc == @self_location }
|
50
|
+
sorted = rotate(sorted, idx)
|
51
|
+
end
|
52
|
+
|
53
|
+
loc_nids = sorted.map {|loc,nodes|
|
54
|
+
nids = nodes.map {|node| node.nid }
|
55
|
+
nids.sort
|
56
|
+
}
|
57
|
+
|
58
|
+
rsid_loc_nids[rsid] = loc_nids
|
59
|
+
}
|
60
|
+
|
61
|
+
@map = rsid_loc_nids
|
62
|
+
end
|
63
|
+
|
64
|
+
def select_master(rsid, key)
|
65
|
+
loc_nodes = @map[rsid]
|
66
|
+
unless loc_nodes
|
67
|
+
raise "no such rsid: #{rsid}"
|
68
|
+
end
|
69
|
+
digest = Digest::MD5.digest(key)
|
70
|
+
i = digest.unpack('C')[0]
|
71
|
+
loc_nodes.map {|nodes| rotate(nodes, i) }.flatten
|
72
|
+
end
|
73
|
+
|
74
|
+
def select_master_static(rsid)
|
75
|
+
loc_nodes = @map[rsid]
|
76
|
+
unless loc_nodes
|
77
|
+
raise "no such rsid: #{rsid}"
|
78
|
+
end
|
79
|
+
loc_nodes.flatten
|
80
|
+
end
|
81
|
+
|
82
|
+
ebus_connect :MasterSelectBus,
|
83
|
+
:select_master,
|
84
|
+
:select_master_static,
|
85
|
+
:update_nodes
|
86
|
+
|
87
|
+
private
|
88
|
+
def rotate(array, i)
|
89
|
+
n = i % array.size
|
90
|
+
return array[-n,n] + array[0, array.size-n]
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
|
95
|
+
class FlatMasterSelectService < Service
|
96
|
+
def initialize
|
97
|
+
@map = {} # { rsid => nids }
|
98
|
+
end
|
99
|
+
|
100
|
+
def update_nodes(nodes=nil)
|
101
|
+
nodes ||= MembershipBus.get_all_nodes
|
102
|
+
|
103
|
+
rsid_nids = {}
|
104
|
+
nodes.each {|node|
|
105
|
+
node.rsids.each {|rsid|
|
106
|
+
(rsid_nids[rsid] ||= []) << node.nid
|
107
|
+
}
|
108
|
+
}
|
109
|
+
|
110
|
+
rsid_nids.values.each {|nids|
|
111
|
+
nids.sort!
|
112
|
+
}
|
113
|
+
|
114
|
+
@map = rsid_nids
|
115
|
+
end
|
116
|
+
|
117
|
+
def select_master(rsid, key)
|
118
|
+
nids = @map[rsid]
|
119
|
+
unless nids
|
120
|
+
raise "no such rsid: #{rsid}"
|
121
|
+
end
|
122
|
+
digest = Digest::MD5.digest(key)
|
123
|
+
i = digest.unpack('C')[0]
|
124
|
+
rotate(nids, i)
|
125
|
+
end
|
126
|
+
|
127
|
+
def select_master_static(rsid)
|
128
|
+
nids = @map[rsid]
|
129
|
+
unless nids
|
130
|
+
raise "no such rsid: #{rsid}"
|
131
|
+
end
|
132
|
+
nids.dup
|
133
|
+
end
|
134
|
+
|
135
|
+
ebus_connect :MasterSelectBus,
|
136
|
+
:select_master,
|
137
|
+
:select_master_static,
|
138
|
+
:update_nodes
|
139
|
+
|
140
|
+
private
|
141
|
+
def rotate(array, i)
|
142
|
+
n = i % array.size
|
143
|
+
return array[-n,n] + array[0, array.size-n]
|
144
|
+
end
|
145
|
+
end
|
146
|
+
|
147
|
+
|
148
|
+
end
|
@@ -0,0 +1,292 @@
|
|
1
|
+
#
|
2
|
+
# LS4
|
3
|
+
# Copyright (C) 2010-2011 FURUHASHI Sadayuki
|
4
|
+
#
|
5
|
+
# This program is free software: you can redistribute it and/or modify
|
6
|
+
# it under the terms of the GNU Affero General Public License as
|
7
|
+
# published by the Free Software Foundation, either version 3 of the
|
8
|
+
# License, or (at your option) any later version.
|
9
|
+
#
|
10
|
+
# This program is distributed in the hope that it will be useful,
|
11
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
# GNU Affero General Public License for more details.
|
14
|
+
#
|
15
|
+
# You should have received a copy of the GNU Affero General Public License
|
16
|
+
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
#
|
18
|
+
module LS4
|
19
|
+
|
20
|
+
|
21
|
+
class MDSBus < Bus
|
22
|
+
# @return
|
23
|
+
# found: ObjectKey
|
24
|
+
# not found: nil
|
25
|
+
call_slot :get_okey
|
26
|
+
|
27
|
+
# @return
|
28
|
+
# found: Hash (may be {})
|
29
|
+
# not found: nil
|
30
|
+
call_slot :get_attrs
|
31
|
+
|
32
|
+
# @return
|
33
|
+
# found: [ObjectKey, Hash (may be {})]
|
34
|
+
# not found: [nil, nil]
|
35
|
+
call_slot :get_okey_attrs
|
36
|
+
|
37
|
+
# @return new ObjectKey
|
38
|
+
call_slot :add
|
39
|
+
|
40
|
+
# @return
|
41
|
+
# found: updated ObjectKey
|
42
|
+
# not found: nil
|
43
|
+
call_slot :update_attrs
|
44
|
+
|
45
|
+
# @return
|
46
|
+
# found: removed ObjectKey
|
47
|
+
# not found: nil
|
48
|
+
call_slot :remove
|
49
|
+
|
50
|
+
# @return
|
51
|
+
# found: removed ObjectKey
|
52
|
+
# not found: nil
|
53
|
+
call_slot :delete
|
54
|
+
|
55
|
+
# @return
|
56
|
+
# found: array of [ObjectKey, vtime, vname]
|
57
|
+
# not found: []
|
58
|
+
call_slot :util_locate
|
59
|
+
end
|
60
|
+
|
61
|
+
|
62
|
+
class MDSConfigService < Service
|
63
|
+
def run
|
64
|
+
@uri = ConfigBus.get_initial_mds_uri
|
65
|
+
on_change
|
66
|
+
end
|
67
|
+
|
68
|
+
def rpc_get_mds_uri
|
69
|
+
@uri
|
70
|
+
end
|
71
|
+
|
72
|
+
def rpc_set_mds_uri(uri)
|
73
|
+
@uri = uri
|
74
|
+
on_change
|
75
|
+
nil
|
76
|
+
end
|
77
|
+
|
78
|
+
def self.hash_uri(uri)
|
79
|
+
Digest::SHA1.digest(uri)
|
80
|
+
end
|
81
|
+
|
82
|
+
def on_change
|
83
|
+
SyncBus.update(SYNC_MDS_URI,
|
84
|
+
@uri, MDSConfigService.hash_uri(@uri))
|
85
|
+
end
|
86
|
+
|
87
|
+
ebus_connect :ProcessBus,
|
88
|
+
:run
|
89
|
+
|
90
|
+
ebus_connect :CSRPCBus,
|
91
|
+
:get_mds_uri => :rpc_get_mds_uri,
|
92
|
+
:set_mds_uri => :rpc_set_mds_uri
|
93
|
+
end
|
94
|
+
|
95
|
+
|
96
|
+
class MDSService < Service
|
97
|
+
def initialize
|
98
|
+
@uri = ""
|
99
|
+
@mds = NullMDS.new
|
100
|
+
end
|
101
|
+
|
102
|
+
def run
|
103
|
+
SyncBus.register_callback(SYNC_MDS_URI,
|
104
|
+
MDSConfigService.hash_uri(@uri)) do |obj|
|
105
|
+
uri = obj
|
106
|
+
reopen(uri)
|
107
|
+
@uri = uri
|
108
|
+
MDSConfigService.hash_uri(@uri)
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
def shutdown
|
113
|
+
if @mds
|
114
|
+
@mds.close rescue nil
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
def reopen(uri)
|
119
|
+
klass, expr = MDSSelector.select_class(uri)
|
120
|
+
|
121
|
+
mds = klass.new
|
122
|
+
mds.open(expr)
|
123
|
+
|
124
|
+
old_mds = @mds
|
125
|
+
@mds = mds
|
126
|
+
|
127
|
+
$log.info "using MDS: #{@mds}"
|
128
|
+
|
129
|
+
begin
|
130
|
+
old_mds.close
|
131
|
+
rescue
|
132
|
+
$log.error "MDS close error: #{$!}"
|
133
|
+
$log.error_backtrace $!.backtrace
|
134
|
+
end
|
135
|
+
end
|
136
|
+
|
137
|
+
ebus_connect :ProcessBus,
|
138
|
+
:run,
|
139
|
+
:shutdown
|
140
|
+
|
141
|
+
ebus_connect :MDSBus,
|
142
|
+
:get_okey,
|
143
|
+
:get_attrs,
|
144
|
+
:get_okey_attrs,
|
145
|
+
:add,
|
146
|
+
:update_attrs,
|
147
|
+
:remove,
|
148
|
+
:delete,
|
149
|
+
:util_locate
|
150
|
+
|
151
|
+
extend Forwardable
|
152
|
+
|
153
|
+
def_delegators :@mds,
|
154
|
+
:get_okey,
|
155
|
+
:get_attrs,
|
156
|
+
:get_okey_attrs,
|
157
|
+
:add,
|
158
|
+
:update_attrs,
|
159
|
+
:remove,
|
160
|
+
:delete,
|
161
|
+
:util_locate
|
162
|
+
end
|
163
|
+
|
164
|
+
|
165
|
+
module MDSSelector
|
166
|
+
IMPLS = {}
|
167
|
+
|
168
|
+
def self.register(name, klass)
|
169
|
+
IMPLS[name.to_sym] = klass
|
170
|
+
nil
|
171
|
+
end
|
172
|
+
|
173
|
+
def self.select_class(uri)
|
174
|
+
if m = /^(\w{1,8})\:(.*)/.match(uri)
|
175
|
+
type = m[1].to_sym
|
176
|
+
expr = m[2]
|
177
|
+
else
|
178
|
+
type = :tt
|
179
|
+
expr = uri
|
180
|
+
end
|
181
|
+
|
182
|
+
klass = IMPLS[type]
|
183
|
+
unless klass
|
184
|
+
raise "unknown MDS type: #{type}"
|
185
|
+
end
|
186
|
+
|
187
|
+
return klass, expr
|
188
|
+
end
|
189
|
+
end
|
190
|
+
|
191
|
+
|
192
|
+
class MDS
|
193
|
+
module Query
|
194
|
+
QC_EQ = 0
|
195
|
+
QC_NOT_EQ = 1
|
196
|
+
QC_LESS_THAN = 2
|
197
|
+
QC_LESS_THAN_EQ = 3
|
198
|
+
QC_GRATER_THAN = 4
|
199
|
+
QC_GRATER_THAN_EQ = 5
|
200
|
+
QC_NULL = 6
|
201
|
+
QC_NOT_NULL = 8
|
202
|
+
|
203
|
+
ORDER_NONE = 0
|
204
|
+
ORDER_STR_ASC = 1
|
205
|
+
ORDER_STR_DESC = 2
|
206
|
+
ORDER_NUM_ASC = 3
|
207
|
+
ORDER_NUM_DESC = 4
|
208
|
+
end
|
209
|
+
|
210
|
+
#def open(expr)
|
211
|
+
#end
|
212
|
+
|
213
|
+
#def close
|
214
|
+
#end
|
215
|
+
|
216
|
+
# @param version vname:String or vtime:Integer
|
217
|
+
#def get_okey(key, version=nil, &cb)
|
218
|
+
#end
|
219
|
+
|
220
|
+
# @param version vname:String or vtime:Integer
|
221
|
+
#def get_attrs(key, version=nil, &cb)
|
222
|
+
#end
|
223
|
+
|
224
|
+
# @param version vname:String or vtime:Integer
|
225
|
+
#def get_okey_attrs(key, version=nil, &cb)
|
226
|
+
#end
|
227
|
+
|
228
|
+
#def add(key, attrs={}, vname=nil, &cb)
|
229
|
+
#end
|
230
|
+
|
231
|
+
#def update_attrs(key, attrs, &cb)
|
232
|
+
#end
|
233
|
+
|
234
|
+
#def remove(key, &cb)
|
235
|
+
#end
|
236
|
+
|
237
|
+
#def delete(key, version=nil, &cb)
|
238
|
+
#end
|
239
|
+
|
240
|
+
def util_locate(key, &cb)
|
241
|
+
get_okey(key) {|okey|
|
242
|
+
if okey
|
243
|
+
cb.call([okey, nil], nil) rescue nil
|
244
|
+
else
|
245
|
+
cb.call([], nil) rescue nil
|
246
|
+
end
|
247
|
+
}
|
248
|
+
end
|
249
|
+
|
250
|
+
protected
|
251
|
+
def get_current_vtime(at_least=0)
|
252
|
+
now = Time.now.utc.to_i
|
253
|
+
if now <= at_least
|
254
|
+
return at_least + 1
|
255
|
+
else
|
256
|
+
return now
|
257
|
+
end
|
258
|
+
end
|
259
|
+
|
260
|
+
def new_okey(key, vtime=get_current_vtime, rsid=nil)
|
261
|
+
rsid ||= BalanceBus.select_next_rsid(key)
|
262
|
+
ObjectKey.new(key, vtime, rsid)
|
263
|
+
end
|
264
|
+
end
|
265
|
+
|
266
|
+
|
267
|
+
class NullMDS < MDS
|
268
|
+
extend Forwardable
|
269
|
+
|
270
|
+
[
|
271
|
+
:get_okey,
|
272
|
+
:get_attrs,
|
273
|
+
:get_okey_attrs,
|
274
|
+
:add,
|
275
|
+
:remove,
|
276
|
+
:delete,
|
277
|
+
:util_locate,
|
278
|
+
:open
|
279
|
+
].each {|method|
|
280
|
+
def_delegator :self, :raise_error, method
|
281
|
+
}
|
282
|
+
|
283
|
+
def raise_error(*args)
|
284
|
+
raise "mds is not configured"
|
285
|
+
end
|
286
|
+
|
287
|
+
def close
|
288
|
+
end
|
289
|
+
end
|
290
|
+
|
291
|
+
|
292
|
+
end
|