Re: opening new diffs in existing window



On 11/22/06, Stephen Kennedy <stevek gnome org> wrote:
> I just noticed that my patch will cause two problems:
> 1) The dbus binding class MeldDbus is a child of dbus.service.Object,
> which is not defined if the python-dbus module is not installed and
> will therefore lead to a ValueError exception
> 2) in the case that the python-dbus module is installed while dbus
> itself isn't, meld will print a stacktrace instead of launching.
> > http://kacper.doesntexist.org/hacks/meld-dbus.patch

Hi Kacper, thanks for the work. It's something that is long overdue.
This week is very hectic, so it could be a while before review/merge.
Meanwhile...

No problem, I know how it is.

In the past I've used fake stubs for optional modules. e.g.

Attached is an improved patch that handles the above cases using a
dummy dbus interface as suggested.

Attached patch applies over previous patch and can be found at:
http://kacper.doesntexist.org/hacks/meld-dbus-improvement-diff.patch
I've also prepared a patch against meld 1.1.3:
http://kacper.doesntexist.org/hacks/meld-dbus-improved.patch

Also, it would be really nice if the three-way-merge command could
return an exit status. Right now, because of the tabbed interface,
there's no single return value from the program. But there could be
from the dbus invocation which would make interfacing with source
control much easier.

I'm not sure how to do this. My dbus stuff just calls the arg parsing
which in turn calls one of the MeldApp.append_* methods, then returns
to caller.

 I think that what you're suggesting requires an async method that
blocks until the opened diff tab is closed (and hence has a return
value). I say async because it can't block the gui application, just
the client calling over dbus. Or a callback to the client that says
"ok, the tab you opened was just closed with retval X".

If it's simpler than that, do let me know :-) otherwise I'll leave it
to someone who knows what they're doing with this gui stuff.

-Kacper

diff -Naurp meld-1.1.3/dummydbus.py meld-1.1.3-kw/dummydbus.py
--- meld-1.1.3/dummydbus.py	1970-01-01 01:00:00.000000000 +0100
+++ meld-1.1.3-kw/dummydbus.py	2006-11-24 01:13:36.046227404 +0100
@@ -0,0 +1,14 @@
+# Replacement dummy classes in case dbus isn't available
+class DBusObject:
+    def __init__(self, bus_name, object_path):
+        pass
+
+class DBusException:
+    def __init__(self):
+        pass
+
+def method(iface):
+    def decorator(func):
+        return func
+    return decorator
+
diff -Naurp meld-1.1.3/meldapp.py meld-1.1.3-kw/meldapp.py
--- meld-1.1.3/meldapp.py	2006-11-24 01:23:32.057619900 +0100
+++ meld-1.1.3-kw/meldapp.py	2006-11-24 01:15:41.967084524 +0100
@@ -40,16 +40,19 @@ dbus_available = 0
try:
    import dbus
    import dbus.service
+    # following may be too implementation-dependent
+    from dbus.service import Object as DBusObject
+    from dbus.decorators import method
+    from dbus import DBusException
    if getattr(dbus, 'version', (0,0,0)) >= (0,41,0):
        import dbus.glib
        dbus_available = 1
    else:
        pass # dbus version too old
 except ImportError:
-    pass
-    # FIXME: Do I print this error or give the silent treatement?
-    #print "Oops, no dbus. Please install the python-dbus package."
-    #print "Meld will not be able to launch new diffs in existing window."
+    # @method decorator, DBusException, DBusObject
+    from dummydbus import *
+    print "meld: python-dbus not installed. Can't talk with running instances."

 # sourceview
sourceview_available = 0
@@ -874,19 +877,19 @@ Written by Stephen Kennedy <stevek gnome
#
################################################################################

-class MeldDbus(dbus.service.Object):
+class MeldDBus(DBusObject):
    def __init__(self, bus_name, app, object_path='/net/sf/meld'):
        dbus.service.Object.__init__(self, bus_name, object_path)
        self.app = app

-    @dbus.service.method('net.sf.meld')
+    @method('net.sf.meld')
    def diff(self, args):
        self.app.parseargs(args)

def register_dbus(app):
    session_bus = dbus.SessionBus()
    bus_name = dbus.service.BusName('net.sf.meld', bus=session_bus)
-    remotemeld = MeldDbus(bus_name, app)
+    remotemeld = MeldDBus(bus_name, app)

def try_dbus():
    bus = dbus.SessionBus()
@@ -902,7 +905,17 @@ def pass_args_dbus(args):
    bus = dbus.SessionBus()
    proxy = bus.get_object('net.sf.meld','/net/sf/meld')
    iface = dbus.Interface(proxy, 'net.sf.meld')
+    # Following (proxy) call will fail with UnknownMethodException
+    # if the python-dbus bindings are installed while dbus itself isn't.
+    # Maybe there is a cleaner way detect this earlier?
    iface.diff(args)
+    try:
+        pass
+    except DBusException:
+        print "meld: pydbus modules exist, but dbus itself is not available."
+        return 0
+    return 1
+



@@ -940,8 +953,8 @@ def main():
        running_already = try_dbus()
        if running_already:
            if args and not force_new_window:
-                pass_args_dbus(args)
-                return
+                if pass_args_dbus(args):
+                    return
    # either you're forcing a new window or it ain't running yet
    app = MeldApp()
    if dbus_available and not running_already:



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]