mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-01-27 07:34:20 +00:00
bug 120485:Can't delete folders on IMAP server cascadely
r=bienvenu sr=mscott Check in for Henry Jia's(henry.jia@sun.com) fix
This commit is contained in:
parent
43746f29aa
commit
4e2b201681
@ -2038,7 +2038,8 @@ void nsImapProtocol::ProcessSelectedStateURL()
|
||||
}
|
||||
|
||||
}
|
||||
DeleteSubFolders(mailboxName);
|
||||
PRBool deleteSelf = PR_FALSE;
|
||||
DeleteSubFolders(mailboxName, deleteSelf); // don't delete self
|
||||
}
|
||||
break;
|
||||
case nsIImapUrl::nsImapAppendDraftFromFile:
|
||||
@ -5474,13 +5475,15 @@ PRBool nsImapProtocol::RenameHierarchyByHand(const char *oldParentMailboxName,
|
||||
return renameSucceeded;
|
||||
}
|
||||
|
||||
PRBool nsImapProtocol::DeleteSubFolders(const char* selectedMailbox)
|
||||
PRBool nsImapProtocol::DeleteSubFolders(const char* selectedMailbox, PRBool &aDeleteSelf)
|
||||
{
|
||||
PRBool deleteSucceeded = PR_TRUE;
|
||||
m_deletableChildren = new nsVoidArray();
|
||||
|
||||
if (m_deletableChildren)
|
||||
{
|
||||
PRBool folderDeleted = PR_FALSE;
|
||||
|
||||
m_hierarchyNameState = kDeleteSubFoldersInProgress;
|
||||
nsCString pattern(selectedMailbox);
|
||||
char onlineDirSeparator = kOnlineHierarchySeparatorUnknown;
|
||||
@ -5500,7 +5503,29 @@ PRBool nsImapProtocol::DeleteSubFolders(const char* selectedMailbox)
|
||||
// ** jt - why? I don't understand this.
|
||||
PRInt32 numberToDelete = m_deletableChildren->Count();
|
||||
PRInt32 outerIndex, innerIndex;
|
||||
|
||||
|
||||
// intelligently decide if myself(either plain format or following the dir-separator)
|
||||
// is in the sub-folder list
|
||||
PRBool folderInSubfolderList = PR_FALSE; // For Performance
|
||||
char *selectedMailboxDir = nsnull;
|
||||
{
|
||||
PRInt32 length = strlen(selectedMailbox);
|
||||
selectedMailboxDir = (char *)PR_MALLOC(length+2);
|
||||
if( selectedMailboxDir ) // only do the intelligent test if there is enough memory
|
||||
{
|
||||
strcpy(selectedMailboxDir, selectedMailbox);
|
||||
selectedMailboxDir[length] = onlineDirSeparator;
|
||||
selectedMailboxDir[length+1] = '\0';
|
||||
PRInt32 i;
|
||||
for( i=0; i<numberToDelete && !folderInSubfolderList; i++ )
|
||||
{
|
||||
char *currentName = (char *) m_deletableChildren->ElementAt(i);
|
||||
if( !strcmp(currentName, selectedMailbox) || !strcmp(currentName, selectedMailboxDir) )
|
||||
folderInSubfolderList = PR_TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
deleteSucceeded = GetServerStateParser().LastCommandSuccessful();
|
||||
for (outerIndex = 0;
|
||||
(outerIndex < numberToDelete) && deleteSucceeded;
|
||||
@ -5514,8 +5539,7 @@ PRBool nsImapProtocol::DeleteSubFolders(const char* selectedMailbox)
|
||||
{
|
||||
char *currentName =
|
||||
(char *) m_deletableChildren->ElementAt(innerIndex);
|
||||
if (!longestName ||
|
||||
PL_strlen(longestName) < PL_strlen(currentName))
|
||||
if (!longestName || strlen(longestName) < strlen(currentName))
|
||||
{
|
||||
longestName = currentName;
|
||||
longestIndex = innerIndex;
|
||||
@ -5543,23 +5567,57 @@ PRBool nsImapProtocol::DeleteSubFolders(const char* selectedMailbox)
|
||||
// string passed to the list command. Be defensive and make sure
|
||||
// we only delete children of the trash
|
||||
if (longestName &&
|
||||
PL_strcmp(selectedMailbox, longestName) &&
|
||||
!PL_strncmp(selectedMailbox, longestName,
|
||||
PL_strlen(selectedMailbox)))
|
||||
strcmp(selectedMailbox, longestName) &&
|
||||
!strncmp(selectedMailbox, longestName, strlen(selectedMailbox)))
|
||||
{
|
||||
nsCOMPtr<nsIImapIncomingServer> imapServer =
|
||||
do_QueryReferent(m_server);
|
||||
if (imapServer)
|
||||
imapServer->ResetConnection(longestName);
|
||||
PRBool deleted =
|
||||
DeleteMailboxRespectingSubscriptions(longestName);
|
||||
if (deleted)
|
||||
FolderDeleted(longestName);
|
||||
deleteSucceeded = deleted;
|
||||
if( selectedMailboxDir && !strcmp(selectedMailboxDir, longestName) ) // just myself
|
||||
{
|
||||
if( aDeleteSelf )
|
||||
{
|
||||
PRBool deleted = DeleteMailboxRespectingSubscriptions(longestName);
|
||||
if (deleted)
|
||||
FolderDeleted(longestName);
|
||||
folderDeleted = deleted;
|
||||
deleteSucceeded = deleted;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
nsCOMPtr<nsIImapIncomingServer> imapServer = do_QueryReferent(m_server);
|
||||
if (imapServer)
|
||||
imapServer->ResetConnection(longestName);
|
||||
PRBool deleted = PR_FALSE;
|
||||
if( folderInSubfolderList ) // for performance
|
||||
{
|
||||
nsVoidArray* pDeletableChildren = m_deletableChildren;
|
||||
m_deletableChildren = nsnull;
|
||||
PRBool folderDeleted = PR_TRUE;
|
||||
deleted = DeleteSubFolders(longestName, folderDeleted);
|
||||
// longestName may have subfolder list including itself
|
||||
if( !folderDeleted )
|
||||
{
|
||||
if (deleted)
|
||||
deleted = DeleteMailboxRespectingSubscriptions(longestName);
|
||||
if (deleted)
|
||||
FolderDeleted(longestName);
|
||||
}
|
||||
m_deletableChildren = pDeletableChildren;
|
||||
}
|
||||
else
|
||||
{
|
||||
deleted = DeleteMailboxRespectingSubscriptions(longestName);
|
||||
if (deleted)
|
||||
FolderDeleted(longestName);
|
||||
}
|
||||
deleteSucceeded = deleted;
|
||||
}
|
||||
}
|
||||
PR_FREEIF(longestName);
|
||||
}
|
||||
|
||||
|
||||
aDeleteSelf = folderDeleted; // feedback if myself is deleted
|
||||
PR_Free(selectedMailboxDir);
|
||||
|
||||
delete m_deletableChildren;
|
||||
m_deletableChildren = nsnull;
|
||||
}
|
||||
@ -5612,11 +5670,16 @@ void nsImapProtocol::FolderRenamed(const char *oldName,
|
||||
|
||||
void nsImapProtocol::OnDeleteFolder(const char * sourceMailbox)
|
||||
{
|
||||
PRBool deleted = DeleteSubFolders(sourceMailbox);
|
||||
if (deleted)
|
||||
deleted = DeleteMailboxRespectingSubscriptions(sourceMailbox);
|
||||
if (deleted)
|
||||
FolderDeleted(sourceMailbox);
|
||||
// intelligently delete the folder
|
||||
PRBool folderDeleted = PR_TRUE;
|
||||
PRBool deleted = DeleteSubFolders(sourceMailbox, folderDeleted);
|
||||
if( !folderDeleted )
|
||||
{
|
||||
if (deleted)
|
||||
deleted = DeleteMailboxRespectingSubscriptions(sourceMailbox);
|
||||
if (deleted)
|
||||
FolderDeleted(sourceMailbox);
|
||||
}
|
||||
}
|
||||
|
||||
void nsImapProtocol::OnRenameFolder(const char * sourceMailbox)
|
||||
|
@ -520,7 +520,10 @@ private:
|
||||
void List(const char *mailboxPattern, PRBool addDirectoryIfNecessary);
|
||||
void Subscribe(const char *mailboxName);
|
||||
void Unsubscribe(const char *mailboxName);
|
||||
PRBool DeleteSubFolders(const char* mailboxName);
|
||||
// Some imap servers include the mailboxName following the dir-separator in the list of
|
||||
// subfolders of the mailboxName. In fact, they are the same. So we should decide if
|
||||
// we should delete such subfolder and provide feedback if the delete operation succeed.
|
||||
PRBool DeleteSubFolders(const char* aMailboxName, PRBool & aDeleteSelf);
|
||||
PRBool RenameHierarchyByHand(const char *oldParentMailboxName,
|
||||
const char *newParentMailboxName);
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user