python RPyC user count - python

I wish to use RPyC to provide an API for a hardware board as a service.
The board can only cater for a single user at a time.
Is there any way I can get RPyC to enforce that only a single user can get access at a time?

I'm not sure if this would work (or work well), but you can try starting a OneShotServer inside a loop, thus at any given moment only one connection is served. When the connection is closed, the server terminates, and you start another one for the next client.
Something like:
is_aborting = False
while not is_aborting:
server = OneShotServer(myservice, *args, **kwargs)
# serve the next client:
server.start()
# done serving the client
If this doesn't work, your best bet is to subclass ThreadedServer, and override the _accept_method method to keep track if there's already a connection open, and return an error if there is.

Related

Is there a python equivalent for .isConnected functionality in C#

I have been looking for the equivalent of [isConnected() functionality] of C# in PYTHON. https://learn.microsoft.com/en-us/dotnet/api/system.net.sockets.socket.connected?view=net-5.0
What I basically need is to check if the socket connection is still open on another end (primary server). If not, move the connection to a new socket(backup server).
I have been quite blank as to how I can move the existing connection to another server without having to reconnect again. Any kind of guidance and help will be really appreciated.
Right now, my connection to server is done at Login(). I want that just in case primary disconnects, the existing username moves to secondary. He just should perform file and word operations. What changes should I do in my code to achieve this.
My current code structure is:
Client side:
def file_operation():
do_something
def word_addition():
do_something
def login():
s.connect(host,port)
if __name__ == "__main__":
Server side:
def accept_client():
s.accept
do_something
def GUI():
accept_client()
if __name__ == "__main__":
According to the Python Sockets documentation, no, there isn't. Python sockets are merely a wrapper around the Berkeley Sockets API, so whatever is in that API, that's what's in the Python API.
If you look at the source code for Microsoft's Socket.cs class, you'll see that they maintain a boolean flag field m_IsConnected to indicate the socket's current connection status. You could potentially do the same with your own custom sockets class, using Microsoft's code as a model for writing your Python code.
Or, you could simply use the socket as you normally would, and switch to a different server when a socket error occurs.

How to close a SolrClient connection?

I am using SolrClient for python with Solr 6.6.2. It works as expected but I cannot find anything in the documentation for closing the connection after opening it.
def getdocbyid(docidlist):
for id in docidlist:
solr = SolrClient('http://localhost:8983/solr', auth=("solradmin", "Admin098"))
doc = solr.get('Collection_Test',doc_id=id)
print(doc)
I do not know if the client closes it automatically or not. If it doesn't, wouldn't it be a problem if several connections are left open? I just want to know if it there is any way to close the connection. Here is the link to the documentation:
https://solrclient.readthedocs.io/en/latest/
The connections are not kept around indefinitely. The standard timeout for any persistent http connection in Jetty is five seconds as far as I remember, so you do not have to worry about the number of connections being kept alive exploding.
The Jetty server will also just drop the connection if required, as it's not required to keep it around as a guarantee for the client. solrclient uses a requests session internally, so it should do pipelining for subsequent queries. If you run into issues with this you can keep a set of clients available as a pool in your application instead, then request an available client instead of creating a new one each time.
I'm however pretty sure you won't run into any issues with the default settings.

How python socket detect the server is closed when continue sending data to server?

I use python socket to send data to server, and the code like:
When I close the server, it will send the data twice, and then, it will go to the "except" code. If I set the SEND_INTERVAL too long, it will be a disaster. So, how to get the error immediately when the server is closed or downtime?
Nothing happens immediatly over the network. That's one thing.
Secondly the underlying OS will detect broken connections (and Python gets that info in the form of an exception), but usually this takes time. And that's why you still send messages even though the connection is already dead. But since OS operates on network layer (as opposed to the application layer) then there's an issue: the connection may be dead but OS may never detect this. For example this will happen when the server is dead but behind alive proxy.
Thirdly the most reliable way to know that a server is alive is when it sends something back to the client. So you should always .recv() (with timeout) after .sendall() call and the server should always .sendall() after .recv() (the request-response pattern, even when the response is a simple "I received message"). If you can't modify the server side and (in worst case) if the server doesn't send anything back to the client then there's no reliable way to know this.
That's why you need some form of framing/correctness protocol. Simple .sendall() won't do.

Releasing resources when Pyro4 client disconnects unexpectedly

I have a Pyro4 distributed system with multiple clients connecting to a single server. These clients connect to a remote object, and that object may allocate some resources in the system (virtual devices, in my case).
Once a client disconnects (let's say because of a crash), I need to release those resources. What is the proper way to detect that an specific client has disconnected from an specific object?
I've tried different things:
Overriding the Daemon.clientDisconnected method. I get a connection parameter from this method. But I can't correlate that to an object, because I have no access to which remote object that connection refers to.
Using Pyro4.current_context in Daemon.clientDisconnected. This doesn't work because that is a thread-local object. That in place, if I have more clients connected than threads in my pool, I get repeated contexts.
Using Proxy._pyroAnnotations as in the "usersession" example available by the Pyro4 project, doesn't help me, because again, I get the annotation from the Pyro4.core.current_context.annotations attribute, which shows me wrong annotations when Daemon.clientDisconnected is called (I imagine due to a thread related issues).
Using instance_mode="session" and the __del__ method in the remote class (as each client would have a separate instance of the class, so the instance is supposed to be destroyed once the client disconnects). But this relies on the __del__ method, which has some problems as some Python programmers would point out.
I added my current solution as an answer, but I really would like to know if there's a more elegant way of doing this with Pyro4, as this scenario is a recurrent pattern in network programming.
Pyro 4.63 will probably have some built-in support for this to make it easier to do. You can read about it here http://pyro4.readthedocs.io/en/latest/tipstricks.html#automatically-freeing-resources-when-client-connection-gets-closed and try it out if you clone the current master from Github. Maybe you can take a look and see if that would make your use case simpler?
I use the Proxy._pyroHandshake attribute as a client ID in the client side and override the Daemon.validateHandshake and Daemon.clientDisconnected. This way, on every new connection I map the handshake data (unique per client) to a connection. But I really wanted to know if there's an elegant way to do that in Pyro4, which is pattern that happens very often in network programming.
Notice that instead of using the Proxy as an attribute of Client, Client can also extends Pyro4.Proxy and use _pyroAnnotations to send the client ID to all the remote calls.
class Client:
def __init__(self):
self._client_id = uuid.uuid4()
self._proxy = Pyro4.Proxy("PYRO:server#127.0.0.1")
self._proxy._pyroHandshake = self._client_id
self._proxy._pyroBind()
def allocate_resource(self, resource_name):
self._proxy.allocate_resource(self._client_id, resource_name)
class Server:
def __init__(self):
self._client_id_by_connection = {}
self._resources_by_client_id = {}
def client_connected(self, connection, client_id):
self._client_id_by_connection[client_id] = connection
self._resources_by_client_id[client_id] = []
def client_disconnected(self, connection):
client_id = self._client_id_by_connection[connection]
for resource in self._resources_by_client_id[client_id]
resource.free()
#Pyro4.expose
def allocate_resource(self, client_id, resource_name)
new_resource = Resource(resource_name)
self._resources_by_client_id[client_id].append(new_resource)
server = Server()
daemon.register(server, objectId="server")
daemon.clientDisconnect = server.client_disconnected
daemon.validateHandshake = server.client_connected
daemon.requestLoop()

Disconnect from Openstack?

I am writing python code on top of the openstack shade library.
Connecting to a stack is pretty straight forward:
return shade.openstack_cloud(cloud='mycloud', **auth_data)
Now I am simply wondering: is there a canonical way to disconnect when I am done?
Or is the assumption that my script ending will do a "graceful" shutdown of that connection; not leaving anything behind?
OpenStack works on a RESTful api model. This means the connections are stateless, i.e. it makes a HTTP connection when you do your request, and closes that connection when the request is finished.
The above code simply initialises things by reading your config, authentication data, etc. A connection is not made until you do something with that object, e.g. create an image:
image = cloud.create_image( 'ubuntu-trusty',
filename='ubuntu-trusty.qcow2', wait=True)
In summary, no, you don't need to disconnect, shade's underlying code will take care of closing connections.

Categories

Resources