This site has been retired. For up to date information, see handbook.gnome.org or gitlab.gnome.org.


[Home] [TitleIndex] [WordIndex

What I have learned

This is a kind of general report of SoC. The idea is to share all the things I have done until now, what I have learned.

Pre-SoC

I had a pretty good idea of what I wanted to do, just didn't know how to do it yet. My idea for what I was planning to do you can read here.
At this point I thought if I was going to work with Geoclue I would get my hands into it. I took some time to read about Geoclue, see how it works, its properties, learn about the providers, get up to date with it.
So my first step was compiling Geoclue. I dind't have any trouble compiling Geoclue, I had to compile Gypsy first to have that provider and I also had to install some developer packages (I use Ubuntu and except for Gypsy they were all in the repositories).
I checked the examples that were provided with Geoclue but they were all written in C. They where a good help to see how the different providers worked.

I was also reading about SoC and looking into the community. IRC was a starting point and it was easy to talk to other people there. At this point I was receiving lots of e-mails on the SoC list, hundreds of e-mails a day and of course I wanted to read all of them. I confess, it wasn't possible. I started to filter the important ones and reading those only. Only after a few weeks was I able to read all or most of all the e-mail.

SoC

By the end of the "bonding with the community" period I started to code. Lionel (my mentor) was excited in seeing some code and I also wanted to "get my hands dirty" so I started to code some examples in python to show and learn how Geoclue could be used. This wasn't that easy at start because I had never used D-Bus and there were no Geoclue + python examples available.
I went to google and quickly found this python-dbus tutorial. I also had to go thru the Geoclue API (D-BUS). I then managed to make some examples, four to be exact that are available here.
I learned the importance of the Geoclue Master provider, internally the Master provider uses the best Geoclue provider (based on client requirements and provider availability, accuracy and resource requirements). The provider that is actually used may change over time as conditions change, but the client can just ignore this. This was exactly what I wanted.

I was prepared to start changing GTG! and had a (more) serious meeting with Lionel to discuss how this would be done. It was his idea and he suggested a plugin. Of course to do the plugin the plugin support needed to be done. This would be good for me as I had never done such a thing and for GTG! that would be supporting plugins.

So I started to implement the plugin system/engine on GTG!. This was hard at start because I didn't understand how a plugin system worked and I didn't find nothing explaining, generically, how these systems worked. I did in fact find some specific information that helped me:

These two pages helped allot, I had a better idea but I was still a little confused on how the plugin would change the GTK+ interface. The answer was easier than I imagined and I took more time searching and looking into other applications code trying to understand this. I also got a precious help from Jonathan Barnoud (aka Pititjo) who mailed me some info and pointed me in the right direction for importing python files as modules.

The Plugin Engine

The general understanding of a plugin engine wasn't a problem, but the specific understanding of how plugins would interact with GTK+ was hard for me. At the end it was allot easier than I initially thought.
A plugin engine has to load plugins, that's the idea right?! The first thing is to decide how these plugins are going to be structured. GTG! is written in python and the contributers are python developers so it only made sense for the plugins to be python modules.
So I decided that the plugins for GTG! would have the following structure/properties:

   1 class ExamplePlugin:
   2     PLUGIN_NAME = 'Example'
   3     PLUGIN_AUTHORS = 'Paulo Cabido <paulo.cabido@gmail.com>'
   4     PLUGIN_VERSION = '0.1'
   5     PLUGIN_DESCRIPTION = 'Plugin Description goes here.'
   6     PLUGIN_ENABLED = True
   7 
   8     def activate(self, plugin_api):
   9         pass
  10         
  11     def onTaskOpened(self, plugin_api):
  12         pass
  13                 
  14     def deactivate(self, plugin_api):
  15         pass

The plugin engine handles the loading of the modules and also the unloading (when a plugin is deactivated) and when it should happen. The LoadPlugins method does the tricky part. As I mentioned before, Jonathan Barnoud pointed me in the right way. He mailed me the code (those three lines of the first for) that would load python files as modules. The modules pkgutil and imp are used to discover modules in the plugins directory.

   1  def LoadPlugins(self):
   2         plugins = {}
   3         try:
   4             for loader, name, ispkg in pkgutil.iter_modules(self.plugin_path):
   5                 file, pathname, desc = imp.find_module(name, self.plugin_path)
   6                 plugins[name] = imp.load_module(name, file, pathname, desc)
   7         except Exception, e:
   8             print "Error: %s" % e
   9             
  10         for name, plugin in plugins.items():
  11             self.Plugins.append(self.loadPlugin(plugin))
  12                         
  13         return self.Plugins

I have talked about the plugins, how they are structured, how they are loaded but another important part is how they interact with GTG!. This is done thru the Plugin API. It would be easy to pass the GTK+ window to the plugin and let the plugin developers do what they want, but that's not a very good practice. So I created this API, that has the methods that the plugins can use to interact with GTG!. The API supports the following methods:

The API is a work in progress and things may change with time, some methods can be altered and some new ones can be included. If you have any suggestions, feel free to let me know.

The last part there is to talk about is the Plugin Manager. This is the GUI to select witch plugins are enabled or disabled. The manager uses the engine to activate/deactivate the plugins. It is accessible under the Plugin menu (Preferences).

python-geoclue

I have mentioned the examples I made to show how Geoclue can be used. After writing those examples, I decided to write a module to help python developers use Geoclue.
The idea of the module is to facilitate as much as possible, for a developer to use Geoclue without having to reinvent the wheel or help a developer who lacks the time to learn about Geoclue from zero. This way the only thing a developer needs is to import the module on their project and with a minimum code effort they can get addresses and positions.
While coding this module (and the examples also) I learned about Geoclue and D-Bus, witch I had never used. It's really easy to use.
I also used signal/slots for the first time with the traditional connect(function) method. This way it's possible to detect changes to the address or position and automatically process those changes. I thought about using D-Bus to make this but my idea was to have as less dependencies as possible for the programmer.
Currently this module is working with the following features:

There is a test file in the test folder that I created to show how to use each of these features. You can see for yourselves how easy it is to use Geoclue now!
Any suggestion or idea, as usual, is welcome.

GTG

I have also learned allot about Getting Things Gnome!. It is a well structured application with a high potential!
As you know, Getting Things Gnome! is an organizer for the GNOME desktop environment. You create tasks to organize what you have to do and each task can have subtasks and so on. For a task to be completed all the subtasks (if they exist) also have to be completed. GTG! has a view called "Work View" that lists the tasks that are possible to be completed at that moment. So if a task with several subtasks exists, the subtasks have to be completed before the main task will appear in the "Work View". This is a great concept that lets one keep in mind the priority of the tasks that are to be done.

So how does GTG! work?


2024-10-23 10:58