I am using this JavaScript code to obtain the URI of a message selected:
var msgHdr = gFolderDisplay.selectedMessage;
var msgUri = msgHdr.folder.getUriForMsg(msgHdr);
The problem with this is that the URI changes once the message is archived (as the folder where the message is stored changes). So I have to manually archive the message, find the message in the destination folder, select it, and then execute the previous code in order to have the final URI. I would like to avoid all this process. Is there any way to perform the archiving (i.e., emulate that the user clicked on the "Archive" button) and then retrieve the URI automatically? It would be something like this:
var msgHdr = gFolderDisplay.selectedMessage;
var msgUri = magicMethodThatArchivesTheMessageAndReturnsItsURIonceArchived(msgHdr)
I'm confused about how magicMethodThatArchivesTheMessageAndReturnsItsURIonceArchived could be implemented.
Any idea would be very welcome!
Archive a message and then get its URI
-
- Posts: 196
- Joined: September 23rd, 2018, 11:07 am
-
- Posts: 6432
- Joined: February 3rd, 2009, 6:29 pm
Re: Archive a message and then get its URI
I can't get the new messageKey from the archiver object.
I tried using the nsIMsgFolderNotificationService listener, but it doesn't work.
Reference (comm-release is not available)
http://searchfox.org/comm-central/searc ... edMessages
http://searchfox.org/comm-central/sourc ... chiver.jsm
http://searchfox.org/comm-central/sourc ... ersion.txt
Testing in error console...
Similar thread: http://forums.mozillazine.org/viewtopic ... &t=3041933
ThunderKdB search results
http://github.com/cleidigh/ThunderKdB/s ... lename:.js
http://github.com/cleidigh/ThunderKdB/s ... lename:.js
I tried using the nsIMsgFolderNotificationService listener, but it doesn't work.
Reference (comm-release is not available)
http://searchfox.org/comm-central/searc ... edMessages
http://searchfox.org/comm-central/sourc ... chiver.jsm
http://searchfox.org/comm-central/sourc ... ersion.txt
Testing in error console...
Code: Select all
(function () {
console.log("old messageKey: " + gFolderDisplay.selectedMessage.messageKey);
var listener = {
msgAdded: function (aMsg) {
// MailServices.mfn.removeListener(listener);
console.log(aMsg);
},
itemEvent(aItem, aEvent, aData, aString) {
// MailServices.mfn.removeListener(listener);
console.log(aItem);
console.log(aEvent);
},
msgKeyChanged: function (aOldMsgKey, aNewMsgHdr) {
// MailServices.mfn.removeListener(listener);
console.log(aOldMsgKey);
console.log(aNewMsgHdr);
},
};
MailServices.mfn.addListener(listener,
MailServices.mfn.msgAdded | MailServices.mfn.itemEvent | MailServices.mfn.msgKeyChanged);
var archiver = new MessageArchiver();
archiver.folderDisplay = gFolderDisplay;
archiver.msgWindow = msgWindow;
archiver.oncomplete = function () {
console.log(archiver);
console.log(archiver._currentBatch.archiveFolderURI); // gmail.com IMAP All Mail folder
console.log(archiver._currentBatch.messages[0].messageKey); // old messageKey
};
archiver.archiveMessages(gFolderDisplay.selectedMessages);
})();
Code: Select all
(function () {
// show folderUri and messageId and msgUri of selected message
var msgHdr = gFolderDisplay.selectedMessage;
var msgUri = msgHdr.folder.getUriForMsg(msgHdr);
console.log(msgHdr.folder.URI);
console.log(msgHdr.messageId);
console.log(msgUri);
})();
Code: Select all
(function () {
// show folderUri of archive folder
var folder = gFolderDisplay.displayedFolder;
var archiveFolder = folder.rootFolder.
getFolderWithFlags(Components.interfaces.nsMsgFolderFlags.Archive);
console.log(archiveFolder.URI);
})();
Code: Select all
(function () {
// show msgUri using messageId and folderUri
var messageId = "123456789@example.org";
var folderUri = "imap://abracadabra%40gmail.com@imap.googlemail.com/[Gmail]/All Mail";
var folder = MailUtils.getExistingFolder(folderUri);
var msgHdr = folder.msgDatabase.getMsgHdrForMessageID(messageId);
var msgUri = msgHdr.folder.getUriForMsg(msgHdr);
console.log(msgUri);
})();
ThunderKdB search results
http://github.com/cleidigh/ThunderKdB/s ... lename:.js
http://github.com/cleidigh/ThunderKdB/s ... lename:.js
-
- Posts: 196
- Joined: September 23rd, 2018, 11:07 am
Re: Archive a message and then get its URI
Thank you for all the ideas. I am trying to find a solution to the problem.
In one of my attempts, I stumped at the following problem. The archiving of the message is asynchronous. Is there any way to block the code and wait for the oncomplete function to execute before continuing the execution? I tried to set a variable "end" to true when executing oncomplete and test its value with a loop, but it seems there is no sleep method that I could execute between sleeps (a busy loop with no sleep freezes TB, as expected).
In one of my attempts, I stumped at the following problem. The archiving of the message is asynchronous. Is there any way to block the code and wait for the oncomplete function to execute before continuing the execution? I tried to set a variable "end" to true when executing oncomplete and test its value with a loop, but it seems there is no sleep method that I could execute between sleeps (a busy loop with no sleep freezes TB, as expected).
-
- Posts: 6432
- Joined: February 3rd, 2009, 6:29 pm
Re: Archive a message and then get its URI
The above code works for me with a selected message in the Inbox folder.
After running the code, I checked the messageId of the selected message in the All Mail folder.
Are you asking how to force an asynchronous call to behave synchronously?
Asynchronous JavaScript
http://developer.mozilla.org/docs/Learn ... ynchronous
Code: Select all
(function () {
var msgHdr = gFolderDisplay.selectedMessage;
var msgUri = msgHdr.folder.getUriForMsg(msgHdr);
var messageId = msgHdr.messageId;
var archiveFolder = msgHdr.folder.rootFolder.
getFolderWithFlags(Components.interfaces.nsMsgFolderFlags.Archive);
console.log(msgUri);
console.log(messageId);
console.log(archiveFolder.URI);
var archiver = new MessageArchiver();
archiver.folderDisplay = gFolderDisplay;
archiver.msgWindow = msgWindow;
archiver.oncomplete = function () {
var archiveMsgHdr = archiveFolder.msgDatabase.getMsgHdrForMessageID(messageId);
var archiveMsgUri = archiveMsgHdr.folder.getUriForMsg(archiveMsgHdr);
archiveFolder.msgDatabase = null; // don't leak
console.log(archiveMsgUri);
setTimeout(function () {
gFolderTreeView.selectFolder(archiveFolder);
gFolderDisplay.selectMessage(archiveMsgHdr);
}, 2000);
};
archiver.archiveMessages(gFolderDisplay.selectedMessages);
})();
Code: Select all
gFolderDisplay.selectedMessage.messageId;
Asynchronous JavaScript
http://developer.mozilla.org/docs/Learn ... ynchronous
-
- Posts: 196
- Joined: September 23rd, 2018, 11:07 am
Re: Archive a message and then get its URI
Thank you very much for this code! This seems very useful and promising.
However, with most messages I get an error executing that code:
Exception: TypeError: archiveFolder is null
In other words, the execution of the line to initialize the variable archiveFolder seems to return null. However, there is an archive folder, as I can click on the "Archive" button and the message goes to my archive folder (in this case, Archives -> ARCHIVED - Local Folders).
Regarding the other question, yes I was querying about how to make an asynchronous call synchronous. I looked a the URL that you provided and I concluded that the trick was to use await. However, I tried with:
await archiver.archiveMessages(gFolderDisplay.selectedMessages);
but this leads to an error:
Exception: SyntaxError: await is only valid in async functions and async generators
Thanks a lot for any suggestion.
However, with most messages I get an error executing that code:
Exception: TypeError: archiveFolder is null
In other words, the execution of the line to initialize the variable archiveFolder seems to return null. However, there is an archive folder, as I can click on the "Archive" button and the message goes to my archive folder (in this case, Archives -> ARCHIVED - Local Folders).
Regarding the other question, yes I was querying about how to make an asynchronous call synchronous. I looked a the URL that you provided and I concluded that the trick was to use await. However, I tried with:
await archiver.archiveMessages(gFolderDisplay.selectedMessages);
but this leads to an error:
Exception: SyntaxError: await is only valid in async functions and async generators
Thanks a lot for any suggestion.
-
- Posts: 6432
- Joined: February 3rd, 2009, 6:29 pm
Re: Archive a message and then get its URI
Try this:user2018 wrote:Local Folders
Code: Select all
(function () {
var accountManager = Components.classes["@mozilla.org/messenger/account-manager;1"].
getService(Components.interfaces.nsIMsgAccountManager);
var archiveFolder = accountManager.localFoldersServer.rootFolder.
getFolderWithFlags(Components.interfaces.nsMsgFolderFlags.Archive);
console.log(archiveFolder.URI);
})();
-
- Posts: 196
- Joined: September 23rd, 2018, 11:07 am
Re: Archive a message and then get its URI
Thank you very much. This avoids the previous error but a new one is shown in the console:
TypeError: archiveMsgHdr is null
I see that probably the problem is that the archived folder retrieved is "mailbox://nobody@Local%20Folders/ARCHIVED" (this is the text shown in the console, but it should be "mailbox-message://nobody@Local%20Folders/ARCHIVED/2020/2020-02".
Any further ideas?
I still also have the problem of how to make the main code wait until the archiving of the message has completed (end of the execution of archiver.oncomplete).
TypeError: archiveMsgHdr is null
I see that probably the problem is that the archived folder retrieved is "mailbox://nobody@Local%20Folders/ARCHIVED" (this is the text shown in the console, but it should be "mailbox-message://nobody@Local%20Folders/ARCHIVED/2020/2020-02".
Any further ideas?
I still also have the problem of how to make the main code wait until the archiving of the message has completed (end of the execution of archiver.oncomplete).
-
- Posts: 6432
- Joined: February 3rd, 2009, 6:29 pm
Re: Archive a message and then get its URI
If the msgHdr is null, then I guess the message isn't in the folder.
If the nsMsgFolderFlags.Archive flag doesn't work, then use the folder url.
I'm only a hobbyist. Ask someone else about asynchronous programming. It's too hard for me to explain.
If the nsMsgFolderFlags.Archive flag doesn't work, then use the folder url.
Code: Select all
(function () {
var archiveFolderUri = "mailbox://nobody@Local%20Folders/Archives/123/Whatever";
var archiveFolder = MailUtils.getExistingFolder(archiveFolderUri);
console.log(archiveFolder.URI);
})();