mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-02-08 07:53:54 +00:00
Bug #252859 --> Add support for dropping RSS urls onto RSS servers and folders to automatically subscribe to the feed.
Bug #252860 --> Add error reporting to alert the user when the feed url could not be downloaded or if the feed url wasn't an rss type we could understand. sr=bienvenu
This commit is contained in:
parent
8ad0b5d01a
commit
0f6bca050a
@ -14,6 +14,12 @@ var serializer =
|
||||
.classes["@mozilla.org/xmlextras/xmlserializer;1"]
|
||||
.createInstance(Components.interfaces.nsIDOMSerializer);
|
||||
|
||||
// error codes used to inform the consumer about attempts to download a feed
|
||||
|
||||
const kNewsBlogSuccess = 0;
|
||||
const kNewsBlogInvalidFeed = 1; // usually means there was an error trying to parse the feed...
|
||||
const kNewsBlogRequestFailure = 2; // generic networking failure when trying to download the feed.
|
||||
|
||||
// Hash of feeds being downloaded, indexed by URL, so the load event listener
|
||||
// can access the Feed objects after it finishes downloading the feed files.
|
||||
var gFzFeedCache = new Object();
|
||||
@ -57,19 +63,27 @@ Feed.prototype.name getter = function() {
|
||||
}
|
||||
|
||||
Feed.prototype.download = function(parseItems, aCallback) {
|
||||
this.downloadCallback = aCallback; // may be null
|
||||
|
||||
// Whether or not to parse items when downloading and parsing the feed.
|
||||
// Defaults to true, but setting to false is useful for obtaining
|
||||
// just the title of the feed when the user subscribes to it.
|
||||
this.parseItems = parseItems == null ? true : parseItems ? true : false;
|
||||
|
||||
// Before we do anything...make sure the url is an http url. This is just a sanity check
|
||||
// so we don't try opening mailto urls, imap urls, etc. that the user may have tried to subscribe to
|
||||
// as an rss feed..
|
||||
var uri = Components.classes["@mozilla.org/network/standard-url;1"].
|
||||
createInstance(Components.interfaces.nsIURI);
|
||||
uri.spec = this.url;
|
||||
if (!uri.schemeIs("http"))
|
||||
return this.onParseError(this); // simulate an invalid feed error
|
||||
|
||||
this.request = Components.classes["@mozilla.org/xmlextras/xmlhttprequest;1"]
|
||||
.createInstance(Components.interfaces.nsIXMLHttpRequest);
|
||||
this.request.onprogress = Feed.onProgress; // must be set before calling .open
|
||||
this.request.open("GET", this.url, true);
|
||||
|
||||
this.downloadCallback = aCallback; // may be null
|
||||
|
||||
this.request.overrideMimeType("text/xml");
|
||||
this.request.onload = Feed.onDownloaded;
|
||||
this.request.onerror = Feed.onDownloadError;
|
||||
@ -100,17 +114,13 @@ Feed.onProgress = function(event) {
|
||||
}
|
||||
|
||||
Feed.onDownloadError = function(event) {
|
||||
// XXX add error message if available and notify the user?
|
||||
var request = event.target;
|
||||
var url = request.channel.originalURI.spec;
|
||||
var feed = gFzFeedCache[url];
|
||||
if (feed)
|
||||
{
|
||||
debug(feed.title + " download failed");
|
||||
if (feed.downloadCallback)
|
||||
feed.downloaded(feed, false);
|
||||
}
|
||||
throw("error downloading feed " + url);
|
||||
if (feed.downloadCallback)
|
||||
feed.downloadCallback.downloaded(feed, kNewsBlogRequestFailure);
|
||||
}
|
||||
|
||||
Feed.prototype.onParseError = function(feed) {
|
||||
if (feed && feed.downloadCallback)
|
||||
feed.downloadCallback.downloaded(feed, kNewsBlogInvalidFeed);
|
||||
}
|
||||
|
||||
Feed.prototype.url getter = function() {
|
||||
@ -159,8 +169,7 @@ Feed.prototype.parse = function() {
|
||||
debug("parsing feed " + this.url);
|
||||
|
||||
if (!this.request.responseText) {
|
||||
throw("error parsing feed " + this.url + ": no data");
|
||||
return;
|
||||
return this.onParseError(this);
|
||||
}
|
||||
else if (this.request.responseText.search(/="http:\/\/purl\.org\/rss\/1\.0\/"/) != -1) {
|
||||
debug(this.url + " is an RSS 1.x (RDF-based) feed");
|
||||
@ -192,12 +201,12 @@ Feed.prototype.parse = function() {
|
||||
|
||||
Feed.prototype.parseAsRSS2 = function() {
|
||||
if (!this.request.responseXML || !(this.request.responseXML instanceof Components.interfaces.nsIDOMXMLDocument))
|
||||
throw("error parsing RSS 2.0 feed " + this.url + ": data not parsed into XMLDocument object");
|
||||
return this.onParseError(this);
|
||||
|
||||
// Get the first channel (assuming there is only one per RSS File).
|
||||
var channel = this.request.responseXML.getElementsByTagName("channel")[0];
|
||||
if (!channel)
|
||||
throw("error parsing RSS 2.0 feed " + this.url + ": channel element missing");
|
||||
return this.onParseError(this);
|
||||
|
||||
this.title = this.title || getNodeValue(channel.getElementsByTagName("title")[0]);
|
||||
this.description = getNodeValue(channel.getElementsByTagName("description")[0]);
|
||||
@ -311,12 +320,12 @@ Feed.prototype.parseAsRSS1 = function() {
|
||||
|
||||
Feed.prototype.parseAsAtom = function() {
|
||||
if (!this.request.responseXML || !(this.request.responseXML instanceof Components.interfaces.nsIDOMXMLDocument))
|
||||
throw("error parsing Atom feed " + this.url + ": data not parsed into XMLDocument object");
|
||||
return this.onParseError(this);
|
||||
|
||||
// Get the first channel (assuming there is only one per Atom File).
|
||||
var channel = this.request.responseXML.getElementsByTagName("feed")[0];
|
||||
if (!channel)
|
||||
throw("channel missing from Atom feed " + request.channel.name);
|
||||
return this.onParseError(this);
|
||||
|
||||
this.title = this.title || getNodeValue(channel.getElementsByTagName("title")[0]);
|
||||
this.description = getNodeValue(channel.getElementsByTagName("tagline")[0]);
|
||||
@ -443,6 +452,7 @@ Feed.prototype.removeInvalidItems = function() {
|
||||
|
||||
var gItemsToStore;
|
||||
var gItemsToStoreIndex = 0;
|
||||
var gStoreItemsTimer;
|
||||
|
||||
// gets the next item from gItemsToStore and forces that item to be stored
|
||||
// to the folder. If more items are left to be stored, fires a timer for the next one.
|
||||
@ -463,20 +473,16 @@ function storeNextItem()
|
||||
|
||||
if (gItemsToStoreIndex < gItemsToStore.length)
|
||||
{
|
||||
if ('setTimeout' in this)
|
||||
setTimeout(storeNextItem, 50); // fire off a timer for the next item to store
|
||||
else
|
||||
{
|
||||
debug('set timeout is not defined if this call originated from newsblog.js\n');
|
||||
storeNextItem();
|
||||
}
|
||||
if (!gStoreItemsTimer)
|
||||
gStoreItemsTimer = Components.classes["@mozilla.org/timer;1"].createInstance(Components.interfaces.nsITimer);
|
||||
gStoreItemsTimer.initWithCallback(storeNextItemTimerCallback, 50, Components.interfaces.nsITimer.TYPE_ONE_SHOT);
|
||||
}
|
||||
else
|
||||
{
|
||||
item.feed.removeInvalidItems();
|
||||
|
||||
if (item.feed.downloadCallback)
|
||||
item.feed.downloadCallback.downloaded(item.feed, true);
|
||||
item.feed.downloadCallback.downloaded(item.feed, kNewsBlogSuccess);
|
||||
|
||||
item.feed.request = null; // force the xml http request to go away. This helps reduce some
|
||||
// nasty assertions on shut down of all things.
|
||||
@ -485,3 +491,17 @@ function storeNextItem()
|
||||
gItemsToStoreIndex = 0;
|
||||
}
|
||||
}
|
||||
|
||||
var storeNextItemTimerCallback = {
|
||||
notify: function(aTimer) {
|
||||
storeNextItem();
|
||||
},
|
||||
|
||||
QueryInterface: function(aIID) {
|
||||
if (aIID.equals(Components.interfaces.nsITimerCallback) || aIID.equals(Components.interfaces.nsISupports))
|
||||
return this;
|
||||
|
||||
Components.returnCode = Components.results.NS_ERROR_NO_INTERFACE;
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
@ -34,7 +34,6 @@
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
|
||||
var kFeedUrlDelimiter = '|'; // the delimiter used to delimit feed urls in the msg folder database "feedUrl" property
|
||||
var gRSSServer = null;
|
||||
|
||||
function doLoad() {
|
||||
@ -74,10 +73,10 @@ function clearStatusInfo()
|
||||
}
|
||||
|
||||
var feedDownloadCallback = {
|
||||
downloaded: function(feed, aSuccess)
|
||||
downloaded: function(feed, aErrorCode)
|
||||
{
|
||||
// feed is null if our attempt to parse the feed failed
|
||||
if (aSuccess)
|
||||
if (aErrorCode == kNewsBlogSuccess)
|
||||
{
|
||||
updateStatusItem('progressMeter', 100);
|
||||
|
||||
@ -91,10 +90,10 @@ var feedDownloadCallback = {
|
||||
// it also flushes the subscription datasource
|
||||
addFeed(feed.url, feed.name, null, folder);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Add some code to alert the user that the feed was not something we could understand...
|
||||
}
|
||||
else if (aErrorCode == kNewsBlogInvalidFeed) // the feed was bad...
|
||||
window.alert(document.getElementById('bundle_newsblog').getFormattedString('newsblog-invalidFeed', [feed.url]));
|
||||
else // we never even downloaded the feed...(kNewsBlogRequestFailure)
|
||||
window.alert(document.getElementById('bundle_newsblog').getFormattedString('newsblog-networkError', [feed.url]));
|
||||
|
||||
// our operation is done...clear out the status text and progressmeter
|
||||
setTimeout(clearStatusInfo, 1000);
|
||||
@ -116,23 +115,6 @@ var feedDownloadCallback = {
|
||||
},
|
||||
}
|
||||
|
||||
// updates the "feedUrl" property in the message database for the folder in question.
|
||||
function updateFolderFeedUrl(aFolder, aFeedUrl, aRemoveUrl)
|
||||
{
|
||||
var msgdb = aFolder.QueryInterface(Components.interfaces.nsIMsgFolder).getMsgDatabase(null);
|
||||
var folderInfo = msgdb.dBFolderInfo;
|
||||
var oldFeedUrl = folderInfo.getCharPtrProperty("feedUrl");
|
||||
|
||||
if (aRemoveUrl)
|
||||
{
|
||||
// remove our feed url string from the list of feed urls
|
||||
var newFeedUrl = oldFeedUrl.replace(kFeedUrlDelimiter + aFeedUrl, "");
|
||||
folderInfo.setCharPtrProperty("feedUrl", newFeedUrl);
|
||||
}
|
||||
else
|
||||
folderInfo.setCharPtrProperty("feedUrl", oldFeedUrl + kFeedUrlDelimiter + aFeedUrl);
|
||||
}
|
||||
|
||||
function doAdd() {
|
||||
var userAddedFeed = false;
|
||||
var feedProperties = { feedName: "", feedLocation: "", serverURI: gRSSServer.serverURI, folderURI: "", result: userAddedFeed};
|
||||
|
@ -88,6 +88,25 @@ function addFeed(url, title, quickMode, destFolder) {
|
||||
ds.Flush();
|
||||
}
|
||||
|
||||
// updates the "feedUrl" property in the message database for the folder in question.
|
||||
|
||||
var kFeedUrlDelimiter = '|'; // the delimiter used to delimit feed urls in the msg folder database "feedUrl" property
|
||||
|
||||
function updateFolderFeedUrl(aFolder, aFeedUrl, aRemoveUrl)
|
||||
{
|
||||
var msgdb = aFolder.QueryInterface(Components.interfaces.nsIMsgFolder).getMsgDatabase(null);
|
||||
var folderInfo = msgdb.dBFolderInfo;
|
||||
var oldFeedUrl = folderInfo.getCharPtrProperty("feedUrl");
|
||||
|
||||
if (aRemoveUrl)
|
||||
{
|
||||
// remove our feed url string from the list of feed urls
|
||||
var newFeedUrl = oldFeedUrl.replace(kFeedUrlDelimiter + aFeedUrl, "");
|
||||
folderInfo.setCharPtrProperty("feedUrl", newFeedUrl);
|
||||
}
|
||||
else
|
||||
folderInfo.setCharPtrProperty("feedUrl", oldFeedUrl + kFeedUrlDelimiter + aFeedUrl);
|
||||
}
|
||||
|
||||
function getNodeValue(node) {
|
||||
if (node && node.textContent)
|
||||
|
@ -51,7 +51,7 @@ var nsNewsBlogFeedDownloader =
|
||||
var rdf = Components.classes["@mozilla.org/rdf/rdf-service;1"]
|
||||
.getService(Components.interfaces.nsIRDFService);
|
||||
|
||||
progressNotifier.init(aMsgWindow.statusFeedback);
|
||||
progressNotifier.init(aMsgWindow.statusFeedback, false);
|
||||
|
||||
var index = 0;
|
||||
for (url in feedUrlArray)
|
||||
@ -68,6 +68,23 @@ var nsNewsBlogFeedDownloader =
|
||||
}
|
||||
},
|
||||
|
||||
subscribeToFeed: function(aUrl, aFolder, aMsgWindow)
|
||||
{
|
||||
if (!gExternalScriptsLoaded)
|
||||
loadScripts();
|
||||
var rdf = Components.classes["@mozilla.org/rdf/rdf-service;1"]
|
||||
.getService(Components.interfaces.nsIRDFService);
|
||||
|
||||
var itemResource = rdf.GetResource(aUrl);
|
||||
var feed = new Feed(itemResource);
|
||||
feed.server = aFolder.server;
|
||||
if (!aFolder.server.isServer) // if the root server, create a new folder for the feed
|
||||
feed.folder = aFolder; // user must want us to add this subscription url to an existing RSS folder.
|
||||
|
||||
progressNotifier.init(aMsgWindow.statusFeedback, true);
|
||||
feed.download(true, progressNotifier);
|
||||
},
|
||||
|
||||
QueryInterface: function(aIID)
|
||||
{
|
||||
if (aIID.equals(Components.interfaces.nsINewsBlogFeedDownloader) ||
|
||||
@ -222,33 +239,52 @@ function loadScripts()
|
||||
var gNumPendingFeedDownloads = 0;
|
||||
|
||||
var progressNotifier = {
|
||||
|
||||
mSubscribeMode: false,
|
||||
mStatusFeedback: null,
|
||||
mFeeds: new Array,
|
||||
|
||||
init: function(aStatusFeedback)
|
||||
init: function(aStatusFeedback, aSubscribeMode)
|
||||
{
|
||||
if (!gNumPendingFeedDownloads) // if we aren't already in the middle of downloading feed items...
|
||||
{
|
||||
this.mStatusFeedback = aStatusFeedback;
|
||||
this.mSubscribeMode = aSubscribeMode;
|
||||
this.mStatusFeedback.startMeteors();
|
||||
this.mStatusFeedback.showStatusString(GetString('newsblog-getNewMailCheck'));
|
||||
|
||||
this.mStatusFeedback.showStatusString(aSubscribeMode ? GetNewsBlogStringBundle().GetStringFromName('subscribe-validating')
|
||||
: GetNewsBlogStringBundle().GetStringFromName('newsblog-getNewMailCheck'));
|
||||
}
|
||||
},
|
||||
|
||||
downloaded: function(feed)
|
||||
downloaded: function(feed, aErrorCode)
|
||||
{
|
||||
if (this.mSubscribeMode && aErrorCode == kNewsBlogSuccess)
|
||||
{
|
||||
// if we get here...we should always have a folder by now...either
|
||||
// in feed.folder or FeedItems created the folder for us....
|
||||
var folder = feed.folder ? feed.folder : feed.server.rootMsgFolder.getChildNamed(feed.name);
|
||||
updateFolderFeedUrl(folder, feed.url, false);
|
||||
addFeed(feed.url, feed.name, null, folder); // add feed just adds the feed to the subscription UI and flushes the datasource
|
||||
}
|
||||
else if (aErrorCode == kNewsBlogInvalidFeed)
|
||||
this.mStatusFeedback.showStatusString(GetNewsBlogStringBundle().formatStringFromName("newsblog-invalidFeed",
|
||||
[feed.url], 1));
|
||||
else if (aErrorCode == kNewsBlogRequestFailure)
|
||||
this.mStatusFeedback.showStatusString(GetNewsBlogStringBundle().formatStringFromName("newsblog-networkError",
|
||||
[feed.url], 1));
|
||||
|
||||
this.mStatusFeedback.stopMeteors();
|
||||
gNumPendingFeedDownloads--;
|
||||
if (!gNumPendingFeedDownloads)
|
||||
{
|
||||
this.mFeeds = new Array;
|
||||
|
||||
// no more pending actions...clear the status bar text...should we do this on a timer
|
||||
// so the text sticks around for a little while? It doesnt look like we do it on a timer for
|
||||
// newsgroups so we'll follow that model.
|
||||
this.mSubscribeMode = false;
|
||||
|
||||
this.mStatusFeedback.showStatusString("");
|
||||
// should we do this on a timer so the text sticks around for a little while?
|
||||
// It doesnt look like we do it on a timer for newsgroups so we'll follow that model.
|
||||
if (aErrorCode == kNewsBlogSuccess) // don't clear the status text if we just dumped an error to the status bar!
|
||||
this.mStatusFeedback.showStatusString("");
|
||||
}
|
||||
},
|
||||
|
||||
@ -259,6 +295,12 @@ var progressNotifier = {
|
||||
{
|
||||
// we currently don't do anything here. Eventually we may add
|
||||
// status text about the number of new feed articles received.
|
||||
|
||||
if (this.mSubscribeMode) // if we are subscribing to a feed, show feed download progress
|
||||
{
|
||||
this.mStatusFeedback.showStatusString(GetNewsBlogStringBundle().formatStringFromName("subscribe-fetchingFeedItems", [aCurrentFeedItems, aMaxFeedItems], 2));
|
||||
this.onProgress(feed, aCurrentFeedItems, aMaxFeedItems);
|
||||
}
|
||||
},
|
||||
|
||||
onProgress: function(feed, aProgress, aProgressMax)
|
||||
@ -292,10 +334,10 @@ var progressNotifier = {
|
||||
}
|
||||
}
|
||||
|
||||
function GetString(name)
|
||||
function GetNewsBlogStringBundle(name)
|
||||
{
|
||||
var strBundleService = Components.classes["@mozilla.org/intl/stringbundle;1"].getService();
|
||||
strBundleService = strBundleService.QueryInterface(Components.interfaces.nsIStringBundleService);
|
||||
var strBundle = strBundleService.createBundle("chrome://messenger-newsblog/locale/newsblog.properties");
|
||||
return strBundle.GetStringFromName(name);
|
||||
return strBundle;
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
# Status strings used in the subscribe dialog
|
||||
|
||||
subscribe-validating=Verifying the feed...
|
||||
subscribe-validating=Verifying the RSS feed...
|
||||
|
||||
# when downloading new feed items from the subscribe dialog.
|
||||
# LOCALIZATION NOTE: Do not translate %d in the following line.
|
||||
@ -8,4 +8,6 @@ subscribe-validating=Verifying the feed...
|
||||
# the second %S will receive the total number of messages
|
||||
subscribe-fetchingFeedItems=Downloading feed articles (%S of %S)
|
||||
|
||||
newsblog-invalidFeed=%S is not a valid RSS feed.
|
||||
newsblog-networkError=%S could not be found. Please check the name and try again.
|
||||
newsblog-getNewMailCheck=Checking RSS feeds for new items
|
||||
|
@ -69,6 +69,7 @@ function CanDropOnFolderTree(index, orientation)
|
||||
|
||||
trans.addDataFlavor("text/x-moz-message");
|
||||
trans.addDataFlavor("text/x-moz-folder");
|
||||
trans.addDataFlavor("text/x-moz-url");
|
||||
|
||||
var folderTree = GetFolderTree();
|
||||
var targetResource = GetFolderResource(folderTree, index);
|
||||
@ -121,33 +122,43 @@ function CanDropOnFolderTree(index, orientation)
|
||||
if (hdr.folder == targetFolder)
|
||||
return false;
|
||||
break;
|
||||
} else if (dataFlavor.value == "text/x-moz-folder") {
|
||||
|
||||
// we should only get here if we are dragging and dropping folders
|
||||
dragFolder = true;
|
||||
sourceResource = RDF.GetResource(sourceUri);
|
||||
var sourceFolder = sourceResource.QueryInterface(Components.interfaces.nsIMsgFolder);
|
||||
sourceServer = sourceFolder.server;
|
||||
|
||||
if (targetUri == sourceUri)
|
||||
return false;
|
||||
|
||||
//don't allow drop on different imap servers.
|
||||
if (sourceServer != targetServer && targetServer.type == "imap")
|
||||
return false;
|
||||
|
||||
//don't allow immediate child to be dropped to it's parent
|
||||
if (targetFolder.URI == sourceFolder.parent.URI)
|
||||
{
|
||||
debugDump(targetFolder.URI + "\n");
|
||||
debugDump(sourceFolder.parent.URI + "\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
var isAncestor = sourceFolder.isAncestorOf(targetFolder);
|
||||
// don't allow parent to be dropped on its ancestors
|
||||
if (isAncestor)
|
||||
return false;
|
||||
} else if (dataFlavor.value == "text/x-moz-url") {
|
||||
// eventually check to make sure this is an http url before doing anything else...
|
||||
var uri = Components.classes["@mozilla.org/network/standard-url;1"].
|
||||
createInstance(Components.interfaces.nsIURI);
|
||||
var url = sourceUri.split("\n")[0];
|
||||
uri.spec = url;
|
||||
|
||||
if (uri.schemeIs("http") && targetServer && targetServer.type == 'rss')
|
||||
return true;
|
||||
}
|
||||
|
||||
// we should only get here if we are dragging and dropping folders
|
||||
dragFolder = true;
|
||||
sourceResource = RDF.GetResource(sourceUri);
|
||||
var sourceFolder = sourceResource.QueryInterface(Components.interfaces.nsIMsgFolder);
|
||||
sourceServer = sourceFolder.server;
|
||||
|
||||
if (targetUri == sourceUri)
|
||||
return false;
|
||||
|
||||
//don't allow drop on different imap servers.
|
||||
if (sourceServer != targetServer && targetServer.type == "imap")
|
||||
return false;
|
||||
|
||||
//don't allow immediate child to be dropped to it's parent
|
||||
if (targetFolder.URI == sourceFolder.parent.URI)
|
||||
{
|
||||
debugDump(targetFolder.URI + "\n");
|
||||
debugDump(sourceFolder.parent.URI + "\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
var isAncestor = sourceFolder.isAncestorOf(targetFolder);
|
||||
// don't allow parent to be dropped on its ancestors
|
||||
if (isAncestor)
|
||||
return false;
|
||||
}
|
||||
|
||||
if (dragFolder)
|
||||
@ -198,6 +209,8 @@ function DropOnFolderTree(row, orientation)
|
||||
|
||||
var folderTree = GetFolderTree();
|
||||
var targetResource = GetFolderResource(folderTree, row);
|
||||
var targetFolder = targetResource.QueryInterface(Components.interfaces.nsIMsgFolder);
|
||||
var targetServer = targetFolder.server;
|
||||
|
||||
var targetUri = targetResource.Value;
|
||||
debugDump("***targetUri = " + targetUri + "\n");
|
||||
@ -209,6 +222,7 @@ function DropOnFolderTree(row, orientation)
|
||||
var trans = Components.classes["@mozilla.org/widget/transferable;1"].createInstance(Components.interfaces.nsITransferable);
|
||||
trans.addDataFlavor("text/x-moz-message");
|
||||
trans.addDataFlavor("text/x-moz-folder");
|
||||
trans.addDataFlavor("text/x-moz-url");
|
||||
|
||||
var list = Components.classes["@mozilla.org/supports-array;1"].createInstance(Components.interfaces.nsISupportsArray);
|
||||
|
||||
@ -248,6 +262,24 @@ function DropOnFolderTree(row, orientation)
|
||||
}
|
||||
else if (flavor.value == "text/x-moz-message")
|
||||
dropMessage = true;
|
||||
else if (flavor.value == "text/x-moz-url")
|
||||
{
|
||||
var uri = Components.classes["@mozilla.org/network/standard-url;1"].
|
||||
createInstance(Components.interfaces.nsIURI);
|
||||
var url = sourceUri.split("\n")[0];
|
||||
uri.spec = url;
|
||||
|
||||
if (uri.schemeIs("http") && targetServer && targetServer.type == 'rss')
|
||||
{
|
||||
var rssService = Components.classes["@mozilla.org/newsblog-feed-downloader;1"].getService().
|
||||
QueryInterface(Components.interfaces.nsINewsBlogFeedDownloader);
|
||||
if (rssService)
|
||||
rssService.subscribeToFeed(url, targetFolder, msgWindow);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (!dropMessage)
|
||||
@ -273,9 +305,6 @@ function DropOnFolderTree(row, orientation)
|
||||
|
||||
var isSourceNews = false;
|
||||
isSourceNews = isNewsURI(sourceUri);
|
||||
|
||||
var targetFolder = targetResource.QueryInterface(Components.interfaces.nsIMsgFolder);
|
||||
var targetServer = targetFolder.server;
|
||||
|
||||
if (dropMessage) {
|
||||
var sourceMsgHdr = list.GetElementAt(0).QueryInterface(Components.interfaces.nsIMsgDBHdr);
|
||||
|
@ -46,5 +46,9 @@ interface nsINewsBlogFeedDownloader : nsISupports
|
||||
void downloadFeed(in string aUrl, in nsIMsgFolder aFolder,
|
||||
in boolean aQuickMode, in wstring aTitle,
|
||||
in nsIUrlListener aUrlListener, in nsIMsgWindow aMsgWindow);
|
||||
|
||||
/* A convient method to subscribe to feeds without going through the subscribe UI
|
||||
used by drag and drop */
|
||||
void subscribeToFeed(in string aUrl, in nsIMsgFolder aFolder, in nsIMsgWindow aMsgWindow);
|
||||
};
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user