Moving on from CCTray
In my last post on CCTray (here) I mentioned a number of what I saw as limitations on CCTray in its current implementation. In this post, it is time to start look at an alternate design for CCTray. Over time I will work on this design and eventually produce a prototype of what I think would be a replacement for CCTray.
Design Goals
Before I begin on the design, the question is what should this application do, what are the constraints and expectations and what is the basic philosophy behind the design.
The basic goal of this application is to provide the ability to monitor, in real time, what is happening on one or more servers that hosts the CruiseControl.Net server. It should also be able interact with the servers to provide a rudimentary level of control. This includes:
- Forcing builds
- Aborting builds
- Stopping and starting projects
- Clearing queues
- Sending messages to be viewed by other users (e.g. fix notifications)
Where possible the application should be extendible. This means that no assumptions should be made about what will implement any part of the application. It should also be robust (handle failures without crashing), informative (let the user know what is happening) and easily usable (be easy to setup and run). Some nice to have features include automatic updates and international.
With this requirements list, what are the limitations? First it will require .Net 2.0 or higher. It will (at least initially) require Windows to run on (since I don’t know enough about Mono/Linux). And finally it must not require any changes to the server side. This also means it should be able to monitor older versions of CruiseControl.Net (I’m thinking at least 1.3 or later).
Components
Since one of the objectives of the new design is modularity, the new application will consist of a number of different interacting components. The following diagram provides a logical view of these components:
These break down into three categories – infrastructure, UI and monitor. The infrastructure components are common to all parts of the application and include items like interfaces, configuration and the bootstrap (more on this to come). The UI components are display components – they provide the actual interface that a user will see. Finally the monitor components do the actual monitoring of the remote server.
They are deliberately separate from the UI components, allowing them to be instantiated and used without requiring any UI components at all. If these three categories are implemented in separate projects (my plan) then it will be possible to build a wide variety of applications with only changing some of the modules.
The core component provides functionality that can be used by all other components. As such I envisage that it will be referenced by all components.
The bootstrap is a process launcher. It can take in a variety of command-line arguments and launch different configurations as required. When I talk about the interactions below this should become clearer.
The UI will contain the shell for the user interface. It can either be a complete interface in itself, or it can rely on optional display components (I will provide some default components).
Finally the monitor is the actual heart of the new application. This will be a standard interface that allows people to implement any transport protocol they like (initially I’ll build protocols for .Net Remoting, HTTP and WCF). The actual transport is called a listener – this merely monitors the remote server and passes on events. Therefore the other half of a monitor is a set of listeners. These can do any type of processing they like – X10, speech, notification icons, etc.
Interactions
The above model showed the various components, now it’s time to look at how this components will interact. The following diagram shows a logical view of this:
These different components work together in the following way:
- The user starts up the application. This is call to the bootstrap component, which starts up the default UI component.
- The bootstrap initialises an instance of the UI component and starts it running.
- The UI component then iterates through the configuration and calls the bootstrap component to start up an instance of each monitor. The new instance will run in a separate process.
- The bootstrap component initialises an instance of the server monitor and starts it running.
- Finally all the separate processes communicates via a standard communications channel (also changeable).
This model means each monitor is running in its own process – if a problem happens with a monitor it won’t take down the entire application! It also simplifies development as it removes needing to worry about threading and locking issues (well, also removes). Plus it does open a possibility for hot-swapping in the future (if desired).
The downside is there will be a slightly larger memory hit (since each monitor is its own process), plus some more processing is required for passing messages to the communications channel and picking up messages.
While this may appear to be a more complex model, it is possible for implement a threaded version of the UI that doesn’t have separate processes, or even a version that doesn’t run monitors at all (e.g. for a command-line version). In a future post I’ll look into this some more.
UI Design
For the UI I thought it would be good to move the design closer to a typical windows application. The following mock-up shows the rough areas for the main UI:
Most of these are self-explanatory. The menu bar, toolbar and status bar are the same as in a typical windows application. It should be possible to add commands to the first two and additional statuses as required.
The bottom part of the mockup shows an area for message history. This allows the UI to display any relevant messages that the user might be interested in. These would be things like status updates, user commands and results, and any errors. The user will have the ability to turn this area off if not desired (or perhaps it should default to off and they can turn it on).
On the left is something I’m calling a server explorer (for the moment). This would list all the servers and their queues (similar to the current queues display), plus the projects for each server. Over time more information may be added to the explorer (e.g. extra views, wizards, editors, etc.)
The final components are the tab selector and display. The user would be able to configure what project/server/queue displays they want, and they would appear in this area. As the user clicks on different items in the server explorer, this area would be updated. The selected tab display would also have the ability to interact with the menu bar, toolbar and status bar.
I’m envisaging a UI interface that looks something similar to the management console that comes with Windows (or at least some versions of Windows). The various bars would be consistent, but the other areas would be configurable by the user.
Summary
I’ve covered a bit in this post about what I see as a future (re)design for the CCTray application. I’ve covered what the modules, the interactions between the components and (very quickly) the UI.
This gives me enough to start on for a quick prototype of how the application will work. During my holiday in China I used some of my spare time to do just this, and over my next few posts I’ll start to cover some of what I have implemented.
However, be warned, this is still very much in a proof of concept stage. I haven’t ironed out all the issues (or all the errors) and it still needs a lot of work. But it should be enough to see whether it is worthwhile continuing the project or not
Stay tuned…



[...] the first in a series of posts of building a prototype replacement for CCTray (my basic design is here). This series will mainly be about what I have done and why. At the end of the series I’ll [...]
Pingback by Starting the Monitor « Automated Coder — 12 November, 2008 @ 9:11 pm