Upgrading from Pyro 3¶
Here you can find what is different in Pyro4 compared to Pyro3. This should help with converting existing Pyro3 applications to Pyro4. It also serves as a quick overview for developers that are used to Pyro3, to see what the new API and features of Pyro4 are like.
General differences from Pyro 3.x¶
- Pyro4 requires Python 2.7 or newer. If you’re on an older Python version, you can look at Pyro 3.x instead (or upgrade your python!)
- Toplevel package name has been changed from
Pyro
intoPyro4
- Mobile code support has been removed.
- Remote attribute access (
DynamicProxyWithAttrs
) is available in the normal proxy but different (you need to use exposed properties) - Event server has been removed (slight chance it appears again in the future in a different form).
- SSL support has been removed. Likely to appear again in a future version.
- You don’t need to import the various sub packages. Just
import Pyro4
and you’re done: the main Pyro API elements are available directly in thePyro4
package. Pyro.core.PyroURI
has been renamed toPyro4.URI
- You can choose from two server types to use in your daemon, a threadpool server (that can process requests concurrently, most similar to Pyro3) and a select/poll based server (that processes requests in a single thread by multiplexing all client connections).
- Pyro objects in the daemon don’t have a forced objectId UUID anymore. They just use the name you give them, or an auto generated one if you don’t provide a name yourself.
PYROLOC
protocol has been removed. Just use thePYRO
protocol with the logical name instead of the object id in the URI.- Pyro daemon binds on a random free port by default, instead of on a fixed port. Name server still is on a fixed port by default.
- Pyro daemons (including the Name server) bind on localhost by default. This prevents exposure to the outside world in a default install. You have to explicitly tell Pyro4 to bind on another network interface. With Pyro3, it was the other way around, it would bind on all network interfaces by default (potentially exposing unwanted servers).
- Logging is done using Python’s standard logging module instead of custom logger stuff from
Pyro.util
. There is some autoconfig voodoo in the package init code that reacts to some environment variable settings. - All classes are new style classes, so you can use super() etc. (this was already the case in the later Pyro 3.x releases but not in earlier ones)
- The command line syntax of these tools has changed, just check out the new usage with ‘-h’.
- The name server doesn’t have any groups anymore. The namespace is now ‘flat’. You don’t have to use the ‘:’ in front of names, or separate parts using ‘.’ anymore. You can look up names matching a prefix string or a regular expression now, so with clever names you can still achieve mostly the same as with the old group based namespace.
- The name server doesn’t have a default group any longer. Name server proxies are regular Pyro proxies and don’t perform any voodoo magic on the names anymore.
- Config items are in
Pyro4.config
(as they were inPyro.config
in Pyro3) but have changed quite a bit. Most of them have been removed. Some may return in a later version. - Exception traceback processing:
Pyro4.util.getPyroTraceback
shouldn’t be called with an exception object anymore. Either simply call it without parameters, or supply the usual ex_type, ex_value, ex_tb objects that you can get from sys.exc_info. Or even easier, install Pyro4’s custom excepthook.
Client code differences¶
Pyro.core.initClient
was deprecated for a long time already, and has been removed.- locating the name server: instead of
locator=Pyro.naming.NameServerLocator(); ns=locator.getNS()
simply usens=Pyro4.locateNS()
- Pyro’s internal methods and attributes have been renamed and are all prefixed with
_pyro
. - getting the uri from a proxy:
proxy.URI
is nowproxy._pyroUri
- the
Pyro.core.PyroURI
object has changed quite a bit. It has been renamed toPyro4.URI
and many of its attributes are different. It knows two types of protocols:PYRO
andPYRONAME
(PYROLOC
has gone). The syntax is different too:<protocol>:<objectid>@<location>
- looking up stuff in the name server:
ns.resolve
is nowns.lookup
- there is only one proxy class:
Pyro4.Proxy
- creating proxies: use the Proxy class constructor, pass in an URI or an uri string directly.
- rebinding a disconnected proxy: instead of
obj.adapter.rebindURI
now use:obj._pyroReconnect
- proxies for ‘meta’ uris (
PYRONAME
etc) are not updated anymore with the resolved uri. If you want the old behavior, you have to callproxy._pyroBind()
explicitly to bind the proxy on the resolved PYRO uri. - You can manually resolve a ‘meta’ uri by using
Pyro4.resolve
, it will return a new normal PYRO uri. - Oneway methods:
proxy._setOneway
got replaced by theproxy._pyroOneway
attribute. That is a set (or sequence) so simply add method names to it that need to be oneway.
Server code differences¶
Pyro.core.initServer
was deprecated for a long time already, and has been removed.Pyro.core.ObjBase
is gone, just use any class directly as a Pyro object. Pyro4 injects a few magic attributes in your object. Their names start with_pyro
for easy identification.Pyro.core.SynchronizedObjBase
is gone as well, you need to create your own thread safety measures if required (locks, Queues, etc)see above for changes concerning how to locate the name server.
Daemons are created much in the same way as before. But they don’t automagically register anything in the name server anymore so you have to do that yourself (
daemon.useNameServer
is gone)Daemons now bind on a random free port by default instead of a fixed port. You need to specify a port yourself when creating a daemon if you want a fixed port.
Daemons bind on localhost by default, instead of 0.0.0.0. If you want to expose to the network, you’ll have to provide a proper hostname or ip address yourself. There is a utility method in the
Pyro4.socketutil
module that can help you with that:getIpAddress
.daemon.connect
has been renamed todaemon.register
. It still returns the URI for the object, as usual.daemon.disconnect
has been renamed todaemon.unregister
daemon.connectPersistent
is gone, just pass the existing object id as a parameter to the normal register.getting an object’s uri and registering in the name server: use the URI you got from the register call, or use
daemon.uriFor
to get a new URI for a given object. Usens.register(objName, uri)
as usual to register it in the name server.creating new pyro objects on the server and returning them (factory methods):
server.getDaemon()
is replaced by the_pyroDaemon
attribute, andobj.getProxy()
is gone. Typical pattern is now:uri=self._pyroDaemon.register(object) return Pyro4.Proxy(uri)
However Pyro4 has an ‘AUTOPROXY’ feature (on by default) that makes the above unneeded (Pyro4 will wrap pyro objects with a proxy automatically for you). You can turn this feature off to make it look more like Pyro3’s behavior.
Unregistering objects from the daemon is done with
some_pyro_object._pyroDaemon.unregister(some_pyro_object)
(or use the object’s URI).
New features¶
Pyro4 introduces several new features that weren’t available in Pyro3: batched calls, async calls, new config items, etc. This won’t impact an upgrade because these features didn’t yet exist in Pyro3.