From: Guido De Rosa Date: 2010-10-19T20:18:36+09:00 Subject: Re: su {block of code.} Tony Arcieri wrote in post #955286: > I guess my question is what exactly are you trying to accomplish? Do you > want a small DSL of commands to work with files as root, or are you > expecting everything to be executed in the context of the setuid root > VM? My immediate, practical need is to deal with files; but in the longer term it would be nice to develop something more general, as I wrote in my first post. Or something intermediate, as you will read later. > If it's the former, try this: > > include FileUtils > cp "somefile", "anotherfile" Actually this works fine: # server.rb, run as root # ... DRb.start_service(URI, File) # client.rb, non-root # ... module Sudo File = DRbObject.new_with_uri(SERVER_URI) end puts Sudo::File.read '/etc/shadow' # only readable by root It also works with FileUtils instead of Files and probably other classes and modules. But what if I want to distribute multiple classes/modules? In general, what is the proper way to distribute multiple dRuby front objects? The most obvious solution, to me, was an Array of objects as a front object. I tried this: # server.rb DRb.start_service(URI, [File, FileUtils]) # client.rb module Sudo File, FileUtils = DRbObject.new_with_uri(SERVER_URI) end but, again, It doesn't work: client.rb:8:in `': can't convert DRb::DRbObject to Array (DRb::DRbObject#to_ary gives DRb::DRbUnknown) (TypeError) from client.rb:7:in `
' So I am compelled to run several DRb server instances? > That should operate as expected. Beyond that, you would need to use > ParseTree or ripper to extract the Ruby code you want executed on the > remote > VM or something like that, but then you need to ensure that all the > classes/objects it's using are actually loaded on the new VM. I see... looks like *a lot* of work... > For practicality's sake I'd suggest exposing a small DSL for doing what > you > want to do as root. FileUtils provides everything I'd think you need, > but > perhaps you have a use case I'm not envisioning. As a more flexible alternative, you should be able to say if you want to Sudo-ize FileUtils or other modules/classes. A possible API might look like this: Sudo.autoload :MyClass, 'mygem/myclass' Sudo.require 'fileutils' Sudo.enable :File, :FileUtils, :MyClass my_super_object = Sudo::MyClass.new Sudo::File.open ... Sudo::FileUtils.cp So you use superuser powers only explicitly when you really need them. -- Posted via http://www.ruby-forum.com/.