Changes

Jump to: navigation, search

User:Jminta/Account Manager Notes

5,608 bytes added, 17:35, 21 January 2008
brain dump
'''Warning:''' These are simply random thoughts and are not any sort of prediction of what will come. Nor are they a commitment to make these kinds of changes in the near future.

The account manager currently serves several related functions:
*Creates/Destroys nsIMsgAccount objects
*Initializes nsIMsgAccount objects on startup
*Provides a entry-point to the organization structure of TB's data objects.

This proposal aims to separate these three tasks, in order to make extending various parts of TB easier. Some renaming is intentional, in order to make it easier to break existing mental models about the code.

=== msgIDataStore ===
The <code>msgIDataStore</code> service is in charge of persisting data-objects across Thunderbird restarts. It is somewhat analogous to the session-store object in Firefox.

The <code>msgIDataStore</code> service initializes registered accounts on startup. While it does provide an access point to these datasources, it will generally not be used directly by front-end callers.

Note that this allows for temporary data-sources to be created and used within a TB session. This means that things like Google Reader's feed-preview will be easy to implement.

Proposed interface:
<pre>
[scriptable, uuid(xxx)]
interface msgIDataStore : nsISupports {
/**
* Registers a data source that should be initializes at application startup
*
* @param contractId the contract-id for the XPCOM object that is being
* registered
* @param source the msgIDataSource being registered
*
* @returns a unique id for this datasource. This id will be identical across
* restarts.
*/
AString registerDataSource(in AString contractId, in msgIDataSource source);

/**
* Unregisters a datasource, so that it will no longer be created on startup
*
* @param id The id returned when the data source was registered.
*/
void unregisterDataSource(in AString id);
};

/**
* All objects intending to provide data to be displayed in the main TB window
* should implement this interface, if they wish to persist across sessions.
*/
[scriptable, uuid(xxx)]
interface msgIDataSource : nsISupports {
/**
* Called by the msgIDataStore on startup to initialize this object.
*
* @param id the datastore's id for this object
* @param properties the properties this datasource stored last shutdown
*/
void initialize(in AString id, in nsIPropertyBag properties);

/**
* Called when Thunderbird is shutting down. The datasource should return a
* property bag containing all of the information it needs to re-initialize
* itself next startup.
*/
nsIPropertyBag onShutdown();
};
</pre>

=== msgIFolderTreeService ===
The <code>msgIFolderTreeService</code> handles the display of data-sources within the main TB window. Front-end callers should use this service's methods to create their displays, since temporary data-sources may have been created.

Proposed interfaces:
<pre>
[scriptable, uuid(xxx)]
interface msgIFolderTreeService : nsISupports {
/**
* Adds a new source that this service should query in building the folder
* tree. Also fires a notification that a new source has been registered so
* that other displays can update themselves.
*
* @param source the new source to query for display information
*
* @note Each data-source must re-add themselves on startup.
*/
void addDataSource(in msgIFolderItem source);

/**
* Removes a previously added source of display data.
*
* @param source the data source to remove
*/
void removeDataSource(in msgIFolderItem source);
};

/**
* This interface should be implemented by any data-source wishing to be shown
* in the folder-tree or otherwise displayed in the main TB window.
*/
[scriptable, uuid(xxx)]
interface msgIFolderTreeItem : nsISupports {
void getChildren();
void onSelected();
readonly attribute AString displayText;
//xxx icon
//xxx styling
void addObserver()
void removeObserver()
};
</pre>

==== code snippets ====
The current "account manager" UI would do something like the following to create a new mail account.
<pre>
var acct = Cc["acct-contractid"].createInstance(Ci.msgIDataSource);
acct.email = "foo@bar.com"
acct.server = whateverObject;
var ds = Cc["data-store-contract-id"].getService(Ci.msgIDataStore);
ds.registerDataSource("acct-contractid", acct);
var folderDisplay = Cc["folder-display-contract-id"].getService(Ci.msgIFolderTreeService);
folderDisplay.addDataSource(acct);
</pre>
The previously mentioned temporary data-sources (like feed preview) would omit the two lines dealing with "ds".

Notice that this allows several new degrees of flexibility. First, a non-account can register with the folder service.
<pre>
var calendarDataSource = {
getChildren: function() { return calendarManager.getCalendars({}); },
onSelected: function() {
// toggle into calendar view
},
// blah blah rest of interface
};

var folderDisplay = Cc["folder-display-contract-id"].getService(Ci.msgIFolderTreeService);
folderDisplay.addDataSource(calendarDataSource);
</pre>

A session-store service (preserving emails being composed during crash) can register.
<pre>
var crashStore = {
initialize: function(aId, aProps) {
var savedDataFile = aProps.getProperty("fileurl");
//reload data
},
onShutdown: function() { return {"fileurl": this._fileurl}; }
};
var ds = Cc["data-store-contract-id"].getService(Ci.msgIDataStore);
ds.registerDataSource("crash-contractid", crashStore);
</pre>
289
edits

Navigation menu