From: Panagiotis Atmatzidis Date: 2013-05-31T04:45:41+09:00 Subject: Re: Advice for simple client/server application Hello, On 18 Νοε 2012, at 09:04 , Carlo E. Prelz wrote: > Subject: Advice for simple client/server application > Date: Sun 18 Nov 12 06:09:42AM +0900 > > Quoting Panagiotis Atmatzidis (atma@convalesco.org): > >> I need to write a client/server application and I'd like to some >> advice from more experienced users. >> >> There will be multiple clients and one server. Every client should >> automatically identify to the server and give some details >> (client_id, date, time, etc). The identification needs to be at very >> basic level, just to avoid *strange things* from happening, since >> the server is going to listen on the internet (firewall rules will >> be applied, but some clients may have dynamic ip's, so some subnets >> might be able to connect). >> >> The server will dig for data from a database, at each client's >> request will send an array (list of words) to the client. Then the >> server will receive a hash with detailed info from the client about >> the each element of the array and will dump the results into the >> database. These arrays will be formed only when requested by >> clients. The server will make sure clients don't get the same arrays >> and make a check to the given results and that's about it. >> >> It's a fairly simple application. I was thinking of using sinatra + >> routes, to create the list in 'txt' format to the client but I'm not >> sure how to send the results back to the sinatra server yet. >> >> So I'd like to ask more advanced users if there's any protocol, gem >> and/or framework that would make this task easier since I've never >> done anything similar before. I know there's a variety of protocols >> which can be used. I'd like to keep things simple & clean as much as >> possible. > > You do not specify if the clients are also written in Ruby. When I > have to do inter-process communications, on the same machine or > between remote machines, I use DRb (Distributed Ruby), which is > included in MRI. I certainly had to pour some sweat to gain confidence > with it, but it was worth the effort. You can even set it up to use > SSL, so the traffic will be encrypted. > > Let's say you have a server based on this scaffold (engine.rb): > > --8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<-- > require 'drb/drb' > require 'drb/ssl' > > class Engine > HOST='yourhost.xxx' > PORT=21212 > URI="drbssl://#{HOST}:#{PORT}" > CERTNAME=[['C',HOST.split('.')[-1]],['O',HOST],['CN',self.to_s]] > > def initialize > config={:verbose=>false,:SSLCertName=>CERTNAME} > @srv=DRb::start_service(URI,self,config) > > # > # Your inits > # > > @para1=rand(1000) > @para2=rand(1000) > end > > def runme > DRb::thread.join() > end > > # > # Remote-callable methdos > # > > def method1(a) > "#{@para1} #{@para2} method 1 returns #{a.to_s}" > end > > def method2(a) > "#{@para1} #{@para2} method 2 returns #{a.to_s} #{a.to_s}" > end > > def Engine::remote > config={:verbose=>false} > > DRb.start_service(nil,nil,config) > DRbObject.new(nil,URI) > end > end > > if($0==__FILE__) > Engine::new.runme > end > --8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<-- > > Your client may be something like this: > > --8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<-- > require 'engine.rb' > > class Client > def initialize > @engine=Engine::remote > end > > def runme > puts @engine.method1(rand(1000)) > puts @engine.method1('test') > puts @engine.method2(rand(1000)) > puts @engine.method2('test') > end > end > > Client::new.runme > --8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<----8<-- > > Your engine can provide an identify method (you may have a hash of > user ids/passwords associated to one or more address, for > example). Then, you would have a 'dig' method that would provide the > desired list of words. > > For me, DRb has cut the cake several times (you can also base it on > Unix sockets, for intra-machine communications). > > There are some snags. The biggest is that methods of the DRb-exported > objects are executed remotely, but if your client receives remote > objects, it will receive LOCAL COPIES of them. Let's say your engine > has object @ob, which has method meth. If your engine has this method > > def m > @ob.meth > end > > meth is executed remotely, by the engine process. But if your > methods just returns @ob: > > def m > @ob > end > > and in your client you have > > ob=@engine.m > ob.meth > > meth is executed in the client's thread (and thus, for example, it > won't be able to access the database opened by the remote engine). > > I hope this is of help. > > Carlo > > -- > * Se la Strada e la sua Virtu' non fossero state messe da parte, > * K * Carlo E. Prelz - fluido@fluido.as che bisogno ci sarebbe > * di parlare tanto di amore e di rettitudine? (Chuang-Tzu) > I'm playing with druby. Some concepts are hard to grasp for now. What I'm trying to do is: 1) Send results to server 2) Run some methods with these results from the server 3) Return the values to the server so it can perform the final operation. I don't get how can I get results from the client back to the server...? How can I send back data to the server? :-/ Thanks Panagiotis (atmosx) Atmatzidis email: atma@convalesco.org URL: http://www.convalesco.org GnuPG ID: 0x1A7BFEC5 gpg --keyserver pgp.mit.edu --recv-keys 1A7BFEC5 -- The wise man said: "Never argue with an idiot. They bring you down to their level and beat you with experience."