From: m_seki@... Date: 2002-02-05T12:31:22+09:00 Subject: Re: Controlling access to (druby's) ExtServ#stop_service > > I think, the owner alone knows reference of ExtServ (= DRbObject). > > How do others get the reference of ExtServ ? > What does this do (from drb package: sample/extserv_test.rb)? > if (cmd == 'quit') > s.service('itest1').stop_service > s.service('itest2').stop_service > end > > It does not seem to do anything: the server process keeps running and > subsequent access to that server still returns itest1 and itest2. Ooops, he is too talkative. > Any idea how to prevent local user from stopping the service? * DRb protocol do not care about user authentication. I think, it is application domain. * My idea is ..., keep your DRbObjects confidential. * I wrote experimental module called DRbAuth. -> http://www2a.biglobe.ne.jp/~seki/ruby/drbauth-0.9.tar.gz == using DRbAuth * start sign_server.rb * patch extserv.rb * start ExtServManager * inovke/quit ExtServ === start ticket_server.rb % ruby ticket_server.rb require 'drb/drb' require 'drbauth' class TicketServer include DRbUndumped def initialize(dict); @dict = dict; end def check_sign(ticket) salt = Time.now.to_s name, g_sign, opt = ticket.sign(salt) if @dict[name].nil? or DRbAuth::digest(@dict[name], salt) != g_sign raise DRbAuth::DRbAuthError end [name, opt] end end if __FILE__ == $0 users = { 'mas'=>'mas00', 'seki'=>'seki00' , 'ys' => 'santoso'} users.keys.each do |k| users[k] = DRbAuth.digest(k, users[k]) end ts = TicketServer.new(users) DRb.start_service(ARGV.shift || 'druby://:8472', ts) puts DRb.uri gets exit end === patch drb/extserv.rb Apply this patch. @@ -13,8 +13,8 @@ def initialize(there, name, server=nil) @server = server || DRb::primary_server @name = name - @invoker = DRbObject.new(nil, there) - @invoker.regist(name, DRbObject.new(self, @server.uri)) + ro = DRbObject.new(nil, there) + @invoker = ro.regist(name, DRbObject.new(self, @server.uri)) end attr_reader :server === start ExtServManager % ruby extserv_test2.rb server require 'drb/drb' require 'drbauth' class Foo include DRbUndumped def initialize(str); @str = str; end def hello(it); "#{it}: #{self}"; end def to_s; @str; end end class MyFront < DRbAuth::Front include DRbUndumped def initialize(ticket_server, extserv, allow_users=nil) super(ticket_server) @extserv = extserv @user = allow_users end def regist(name, ro) @extserv.regist(name, ro) return @extserv end private def fetch(service, user) if @user raise(DRbAuth::DRbAuthError) unless @user.include?(user) end return @extserv.service(service) end end cmd = ARGV.shift case cmd when 'itest1', 'itest2' require 'drb/extserv' front = Foo.new(cmd) server = DRb::DRbServer.new(nil, front) es = DRb::ExtServ.new(ARGV.shift, ARGV.shift, server) server.thread.join when 'server' require 'drb/extservm' ts_uri = ARGV.shift || 'druby://localhost:8472' DRb::ExtServManager.command['itest1'] = "ruby -I. #{$0} itest1" DRb::ExtServManager.command['itest2'] = "ruby -I. #{$0} itest2" s = DRb::ExtServManager.new front = MyFront.new(DRbObject.new(nil, ts_uri), s, ['seki', 'ys']) DRb.start_service(nil, front) puts DRb.uri DRb.thread.join else uri = (cmd == 'quit') ? ARGV.shift : cmd print "user: " user = gets.chomp print "pass: " pass = gets.chomp DRb.start_service s = DRbObject.new(nil, uri) ticket = DRbAuth::Ticket.new(user, pass, 'itest1') s.checkout(ticket) s1 = ticket.retrieve f1 = s1.front puts f1 ticket = DRbAuth::Ticket.new(user, pass, 'itest2') s.checkout(ticket) s2 = ticket.retrieve f2 = s2.front puts f2 puts f1.hello(f2) if (cmd == 'quit') s1.stop_service s2.stop_service end end === invoke/quit ExtServ % ruby extserv_test2.rb druby://..... user: seki pass: seki00 .... % ruby extserv_test2.rb quit druby://..... user: seki pass: seki00 .... seki.