Support RFC 6855 / RFC 5738 (UTF8)

This commit is contained in:
djmaze 2021-11-22 21:01:30 +01:00
parent c9a497eb9d
commit 299ec7faf8
25 changed files with 249 additions and 505 deletions

View file

@ -299,8 +299,8 @@ class AppUser extends AbstractApp {
}
]);
} else if (oMoveFolder) {
this.messagesMoveHelper(sFromFolderFullNameRaw, oMoveFolder.fullNameRaw, aUidForRemove);
MessageUserStore.removeMessagesFromList(sFromFolderFullNameRaw, aUidForRemove, oMoveFolder.fullNameRaw);
this.messagesMoveHelper(sFromFolderFullNameRaw, oMoveFolder.fullName, aUidForRemove);
MessageUserStore.removeMessagesFromList(sFromFolderFullNameRaw, aUidForRemove, oMoveFolder.fullName);
}
}
@ -317,12 +317,12 @@ class AppUser extends AbstractApp {
if (oFromFolder && oToFolder) {
if (undefined === bCopy ? false : !!bCopy) {
this.messagesCopyHelper(oFromFolder.fullNameRaw, oToFolder.fullNameRaw, aUidForMove);
this.messagesCopyHelper(oFromFolder.fullName, oToFolder.fullName, aUidForMove);
} else {
this.messagesMoveHelper(oFromFolder.fullNameRaw, oToFolder.fullNameRaw, aUidForMove);
this.messagesMoveHelper(oFromFolder.fullName, oToFolder.fullName, aUidForMove);
}
MessageUserStore.removeMessagesFromList(oFromFolder.fullNameRaw, aUidForMove, oToFolder.fullNameRaw, bCopy);
MessageUserStore.removeMessagesFromList(oFromFolder.fullName, aUidForMove, oToFolder.fullName, bCopy);
return true;
}
}
@ -487,12 +487,12 @@ class AppUser extends AbstractApp {
folderFromCache.messageCountUnread(result.MessageUnseenCount);
if (unreadCountChange) {
MessageFlagsCache.clearFolder(folderFromCache.fullNameRaw);
MessageFlagsCache.clearFolder(folderFromCache.fullName);
}
if (result.Flags.length) {
result.Flags.forEach(flags =>
MessageFlagsCache.storeByFolderAndUid(folderFromCache.fullNameRaw, flags.Uid.toString(), [
MessageFlagsCache.storeByFolderAndUid(folderFromCache.fullName, flags.Uid.toString(), [
!!flags.IsUnseen,
!!flags.IsFlagged,
!!flags.IsAnswered,
@ -505,15 +505,15 @@ class AppUser extends AbstractApp {
}
MessageUserStore.initUidNextAndNewMessages(
folderFromCache.fullNameRaw,
folderFromCache.fullName,
result.UidNext,
result.NewMessages
);
if (!hash || unreadCountChange || result.Hash !== hash) {
if (folderFromCache.fullNameRaw === FolderUserStore.currentFolderFullNameRaw()) {
if (folderFromCache.fullName === FolderUserStore.currentFolderFullNameRaw()) {
this.reloadMessageList();
} else if (getFolderInboxName() === folderFromCache.fullNameRaw) {
} else if (getFolderInboxName() === folderFromCache.fullName) {
Remote.messageList(null, {Folder: getFolderInboxName()}, true);
}
}
@ -551,17 +551,17 @@ class AppUser extends AbstractApp {
folder.messageCountUnread(item.MessageUnseenCount);
if (unreadCountChange) {
MessageFlagsCache.clearFolder(folder.fullNameRaw);
MessageFlagsCache.clearFolder(folder.fullName);
}
if (!hash || item.Hash !== hash) {
if (folder.fullNameRaw === FolderUserStore.currentFolderFullNameRaw()) {
if (folder.fullName === FolderUserStore.currentFolderFullNameRaw()) {
this.reloadMessageList();
}
} else if (unreadCountChange
&& folder.fullNameRaw === FolderUserStore.currentFolderFullNameRaw()
&& folder.fullName === FolderUserStore.currentFolderFullNameRaw()
&& MessageUserStore.list.length) {
this.folderInformation(folder.fullNameRaw, MessageUserStore.list());
this.folderInformation(folder.fullName, MessageUserStore.list());
}
}
});

View file

@ -200,14 +200,14 @@ folderListOptionsBuilder = (
folders.forEach(oItem => {
if (showUnsubscribed || oItem.hasSubscriptions() || !oItem.exists) {
aResult.push({
id: oItem.fullNameRaw,
id: oItem.fullName,
name:
sDeepPrefix.repeat(oItem.deep) +
fRenameCallback(oItem),
system: false,
disabled: !bNoSelectSelectable && (
!oItem.selectable() ||
aDisabled.includes(oItem.fullNameRaw) ||
aDisabled.includes(oItem.fullName) ||
fDisableCallback(oItem))
});
}

View file

@ -145,7 +145,7 @@ ko.bindingHandlers.dropmessages = {
if ('messages' === getDragAction(e) && ['move','copy'].includes(e.dataTransfer.effectAllowed)) {
let data = dragData.data;
if (folder && data && data.folder && isArray(data.uids)) {
rl.app.moveMessagesToFolder(data.folder, data.uids, folder.fullNameRaw, data.copy && e.ctrlKey);
rl.app.moveMessagesToFolder(data.folder, data.uids, folder.fullName, data.copy && e.ctrlKey);
}
}
});

View file

@ -69,7 +69,7 @@ export class FolderCollectionModel extends AbstractCollectionModel
}
return super.reviveFromJson(object, oFolder => {
let oCacheFolder = Cache.getFolderFromCacheList(oFolder.FullNameRaw);
let oCacheFolder = Cache.getFolderFromCacheList(oFolder.FullName);
if (oCacheFolder) {
oFolder.SubFolders = FolderCollectionModel.reviveFromJson(oFolder.SubFolders);
@ -79,14 +79,14 @@ export class FolderCollectionModel extends AbstractCollectionModel
if (!oCacheFolder)
return null;
if (1 == SystemFolders.indexOf(oFolder.FullNameRaw)) {
if (1 == SystemFolders.indexOf(oFolder.FullName)) {
oCacheFolder.type(FolderType.Inbox);
Cache.setFolderInboxName(oFolder.FullNameRaw);
Cache.setFolderInboxName(oFolder.FullName);
}
Cache.setFolder(oCacheFolder.fullNameHash, oFolder.FullNameRaw, oCacheFolder);
Cache.setFolder(oCacheFolder.fullNameHash, oFolder.FullName, oCacheFolder);
}
let type = SystemFolders.indexOf(oFolder.FullNameRaw);
let type = SystemFolders.indexOf(oFolder.FullName);
if (1 < type) {
oCacheFolder.type(type);
}
@ -97,7 +97,7 @@ export class FolderCollectionModel extends AbstractCollectionModel
if (oFolder.Extended) {
if (oFolder.Extended.Hash) {
Cache.setFolderHash(oCacheFolder.fullNameRaw, oFolder.Extended.Hash);
Cache.setFolderHash(oCacheFolder.fullName, oFolder.Extended.Hash);
}
if (null != oFolder.Extended.MessageCount) {
@ -196,7 +196,6 @@ export class FolderModel extends AbstractModel {
super();
this.fullName = '';
this.fullNameRaw = '';
this.fullNameHash = '';
this.delimiter = '';
this.namespace = '';
@ -244,7 +243,7 @@ export class FolderModel extends AbstractModel {
static reviveFromJson(json) {
const folder = super.reviveFromJson(json);
if (folder) {
folder.deep = json.FullNameRaw.split(folder.delimiter).length - 1;
folder.deep = json.FullName.split(folder.delimiter).length - 1;
let type = (folder.metadata[FolderMetadataKeys.KolabFolderType]
|| folder.metadata[FolderMetadataKeys.KolabFolderTypeShared]

View file

@ -19,10 +19,19 @@ import { AbstractFetchRemote } from 'Remote/AbstractFetch';
import { FolderCollectionModel } from 'Model/FolderCollection';
const urlSafeJSON = data => btoa(JSON.stringify(data))
// unescape(encodeURIComponent()) makes the UTF-16 DOMString to an UTF-8 string
const urlSafeJSON = data => btoa(unescape(encodeURIComponent(JSON.stringify(data))))
.replace(/\+/g, '-')
.replace(/\//g, '_')
.replace(/=+$/, '');
/* Withous deprecated 'unescape':
const urlSafeJSON = data => btoa(encodeURIComponent(JSON.stringify(data)).replace(
/%([0-9A-F]{2})/g, (match, p1) => String.fromCharCode('0x' + p1)
))
.replace(/\+/g, '-')
.replace(/\//g, '_')
.replace(/=+$/, '');
*/
class RemoteUserFetch extends AbstractFetchRemote {

View file

@ -73,11 +73,11 @@ export class FoldersUserSettings /*extends AbstractViewSettings*/ {
Local.set(ClientSideKeyName.FoldersLashHash, '');
rl.app.foldersPromisesActionHelper(
Remote.folderRename(folder.fullNameRaw, nameToEdit),
Remote.folderRename(folder.fullName, nameToEdit),
Notification.CantRenameFolder
);
removeFolderFromCacheList(folder.fullNameRaw);
removeFolderFromCacheList(folder.fullName);
folder.name(nameToEdit);
}
@ -120,11 +120,11 @@ export class FoldersUserSettings /*extends AbstractViewSettings*/ {
// rl.app.foldersPromisesActionHelper
Remote.abort('Folders')
.folderDelete(folderToRemove.fullNameRaw)
.folderDelete(folderToRemove.fullName)
.then(
() => {
folderToRemove.selectable(false)
removeFolderFromCacheList(folderToRemove.fullNameRaw);
removeFolderFromCacheList(folderToRemove.fullName);
FolderUserStore.folderList(FolderUserStore.folderList.filter(folder => folder !== folderToRemove));
},
error => {
@ -143,20 +143,20 @@ export class FoldersUserSettings /*extends AbstractViewSettings*/ {
toggleFolderKolabType(folder, event) {
let type = event.target.value;
// TODO: append '.default' ?
Remote.folderSetMetadata(null, folder.fullNameRaw, FolderMetadataKeys.KolabFolderType, type);
Remote.folderSetMetadata(null, folder.fullName, FolderMetadataKeys.KolabFolderType, type);
folder.kolabType(type);
}
toggleFolderSubscription(folder) {
let subscribe = !folder.subscribed();
Local.set(ClientSideKeyName.FoldersLashHash, '');
Remote.folderSetSubscribe(null, folder.fullNameRaw, subscribe);
Remote.folderSetSubscribe(null, folder.fullName, subscribe);
folder.subscribed(subscribe);
}
toggleFolderCheckable(folder) {
let checkable = !folder.checkable();
Remote.folderSetCheckable(null, folder.fullNameRaw, checkable);
Remote.folderSetCheckable(null, folder.fullName, checkable);
folder.checkable(checkable);
}
}

View file

@ -58,7 +58,7 @@ export const FolderUserStore = new class {
draftFolderNotEnabled: () => !self.draftFolder() || UNUSED_OPTION_VALUE === self.draftFolder(),
currentFolderFullNameRaw: () => (self.currentFolder() ? self.currentFolder().fullNameRaw : ''),
currentFolderFullNameRaw: () => (self.currentFolder() ? self.currentFolder().fullName : ''),
currentFolderFullName: () => (self.currentFolder() ? self.currentFolder().fullName : ''),
currentFolderFullNameHash: () => (self.currentFolder() ? self.currentFolder().fullNameHash : ''),
@ -136,7 +136,7 @@ export const FolderUserStore = new class {
timeout > folder.expires &&
(folder.isSystemFolder() || (folder.subscribed() && (folder.checkable() || !bDisplaySpecSetting)))
) {
timeouts.push([folder.expires, folder.fullNameRaw]);
timeouts.push([folder.expires, folder.fullName]);
}
if (folder && folder.subFolders.length) {

View file

@ -308,7 +308,7 @@ export const MessageUserStore = new class {
}
if (toFolder) {
if (trashFolder === toFolder.fullNameRaw || spamFolder === toFolder.fullNameRaw) {
if (trashFolder === toFolder.fullName || spamFolder === toFolder.fullName) {
unseenCount = 0;
}
@ -661,13 +661,13 @@ export const MessageUserStore = new class {
if (null != collection.MessageUnseenCount) {
if (pInt(folder.messageCountUnread()) !== pInt(collection.MessageUnseenCount)) {
unreadCountChange = true;
MessageFlagsCache.clearFolder(folder.fullNameRaw);
MessageFlagsCache.clearFolder(folder.fullName);
}
folder.messageCountUnread(collection.MessageUnseenCount);
}
this.initUidNextAndNewMessages(folder.fullNameRaw, collection.UidNext, collection.NewMessages);
this.initUidNextAndNewMessages(folder.fullName, collection.UidNext, collection.NewMessages);
}
this.listCount(iCount);
@ -688,7 +688,7 @@ export const MessageUserStore = new class {
clearNewMessageCache();
if (folder && (cached || unreadCountChange || SettingsUserStore.useThreads())) {
rl.app.folderInformation(folder.fullNameRaw, collection);
rl.app.folderInformation(folder.fullName, collection);
}
} else {
this.listCount(0);

View file

@ -52,7 +52,7 @@ class FolderClearPopupView extends AbstractViewPopup {
folderToClear.messageCountAll(0);
folderToClear.messageCountUnread(0);
setFolderHash(folderToClear.fullNameRaw, '');
setFolderHash(folderToClear.fullName, '');
Remote.folderClear(iError => {
this.clearingProcess(false);
@ -62,7 +62,7 @@ class FolderClearPopupView extends AbstractViewPopup {
rl.app.reloadMessageList(true);
this.cancelCommand();
}
}, folderToClear.fullNameRaw);
}, folderToClear.fullName);
}
}

View file

@ -30,7 +30,7 @@ class FolderCreatePopupView extends AbstractViewPopup {
oItem =>
oItem ? (oItem.isSystemFolder() ? oItem.name() + ' ' + oItem.manageFolderSystemName() : oItem.name()) : '',
FolderUserStore.namespace
? item => FolderUserStore.namespace !== item.fullNameRaw.substr(0, FolderUserStore.namespace.length)
? item => FolderUserStore.namespace !== item.fullName.substr(0, FolderUserStore.namespace.length)
: null,
true
)

View file

@ -88,7 +88,7 @@ export class MailFolderList extends AbstractViewLeft {
rl.app.moveMessagesToFolder(
FolderUserStore.currentFolderFullNameRaw(),
MessageUserStore.listCheckedOrSelectedUidsWithSubMails(),
folder.fullNameRaw,
folder.fullName,
event.ctrlKey
);
} else {
@ -96,8 +96,8 @@ export class MailFolderList extends AbstractViewLeft {
MessageUserStore.message(null);
}
if (folder.fullNameRaw === FolderUserStore.currentFolderFullNameRaw()) {
setFolderHash(folder.fullNameRaw, '');
if (folder.fullName === FolderUserStore.currentFolderFullNameRaw()) {
setFolderHash(folder.fullName, '');
}
rl.route.setHash(

View file

@ -1374,239 +1374,16 @@ END;
public static function Utf7ModifiedToUtf8(string $sStr) : string
{
$aArray = array(-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
-1,-1,-1,-1,-1,-1,-1,-1,-1,62, 63,-1,-1,-1,52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-1,-1,-1,-1,0,1,2,3,4,5,6,7,8,9,
10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1,-1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,
41,42,43,44,45,46,47,48,49,50,51,-1,-1,-1,-1,-1);
$sResult = '';
$bError = false;
$iLen = \strlen($sStr);
for ($iIndex = 0; $iLen > 0; $iIndex++, $iLen--)
{
$sChar = $sStr[$iIndex];
if ($sChar == '&')
{
$iIndex++;
$iLen--;
$sChar = isset($sStr[$iIndex]) ? $sStr[$iIndex] : null;
if ($sChar === null)
{
break;
}
if ($iLen && $sChar == '-')
{
$sResult .= '&';
continue;
}
$iCh = 0;
$iK = 10;
for (; $iLen > 0; $iIndex++, $iLen--)
{
$sChar = $sStr[$iIndex];
$iB = $aArray[\ord($sChar)];
if ((\ord($sChar) & 0x80) || $iB == -1)
{
break;
}
if ($iK > 0)
{
$iCh |= $iB << $iK;
$iK -= 6;
}
else
{
$iCh |= $iB >> (-$iK);
if ($iCh < 0x80)
{
if (0x20 <= $iCh && $iCh < 0x7f)
{
return $bError;
}
$sResult .= \chr($iCh);
}
else if ($iCh < 0x800)
{
$sResult .= \chr(0xc0 | ($iCh >> 6));
$sResult .= \chr(0x80 | ($iCh & 0x3f));
}
else
{
$sResult .= \chr(0xe0 | ($iCh >> 12));
$sResult .= \chr(0x80 | (($iCh >> 6) & 0x3f));
$sResult .= \chr(0x80 | ($iCh & 0x3f));
}
$iCh = ($iB << (16 + $iK)) & 0xffff;
$iK += 10;
}
}
if (($iCh || $iK < 6) ||
(!$iLen || $sChar != '-') ||
($iLen > 2 && '&' === $sStr[$iIndex+1] && '-' !== $sStr[$iIndex+2]))
{
return $bError;
}
}
else if (\ord($sChar) < 0x20 || \ord($sChar) >= 0x7f)
{
return $bError;
}
else
{
$sResult .= $sChar;
}
}
return $sResult;
return \is_callable('imap_mutf7_to_utf8')
? \imap_mutf7_to_utf8($sStr)
: \mb_convert_encoding($sStr, 'UTF-8', 'UTF7-IMAP');
}
public static function Utf8ToUtf7Modified(string $sStr) : string
{
$sArray = array('A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S',
'T','U','V','W','X','Y','Z', 'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o',
'p','q','r','s','t','u','v','w','x','y','z', '0','1','2','3','4','5','6','7','8','9','+',',');
$sLen = \strlen($sStr);
$bIsB = false;
$iIndex = $iN = 0;
$sReturn = '';
$bError = false;
$iCh = $iB = $iK = 0;
while ($sLen)
{
$iC = \ord($sStr[$iIndex]);
if ($iC < 0x80)
{
$iCh = $iC;
$iN = 0;
}
else if ($iC < 0xc2)
{
return $bError;
}
else if ($iC < 0xe0)
{
$iCh = $iC & 0x1f;
$iN = 1;
}
else if ($iC < 0xf0)
{
$iCh = $iC & 0x0f;
$iN = 2;
}
else if ($iC < 0xf8)
{
$iCh = $iC & 0x07;
$iN = 3;
}
else if ($iC < 0xfc)
{
$iCh = $iC & 0x03;
$iN = 4;
}
else if ($iC < 0xfe)
{
$iCh = $iC & 0x01;
$iN = 5;
}
else
{
return $bError;
}
$iIndex++;
$sLen--;
if ($iN > $sLen)
{
return $bError;
}
for ($iJ = 0; $iJ < $iN; $iJ++)
{
$iO = \ord($sStr[$iIndex+$iJ]);
if (($iO & 0xc0) != 0x80)
{
return $bError;
}
$iCh = ($iCh << 6) | ($iO & 0x3f);
}
if ($iN > 1 && !($iCh >> ($iN * 5 + 1)))
{
return $bError;
}
$iIndex += $iN;
$sLen -= $iN;
if ($iCh < 0x20 || $iCh >= 0x7f)
{
if (!$bIsB)
{
$sReturn .= '&';
$bIsB = true;
$iB = 0;
$iK = 10;
}
if ($iCh & ~0xffff)
{
$iCh = 0xfffe;
}
$sReturn .= $sArray[($iB | $iCh >> $iK)];
$iK -= 6;
for (; $iK >= 0; $iK -= 6)
{
$sReturn .= $sArray[(($iCh >> $iK) & 0x3f)];
}
$iB = ($iCh << (-$iK)) & 0x3f;
$iK += 16;
}
else
{
if ($bIsB)
{
if ($iK > 10)
{
$sReturn .= $sArray[$iB];
}
$sReturn .= '-';
$bIsB = false;
}
$sReturn .= \chr($iCh);
if ('&' === \chr($iCh))
{
$sReturn .= '-';
}
}
}
if ($bIsB)
{
if ($iK > 10)
{
$sReturn .= $sArray[$iB];
}
$sReturn .= '-';
}
return $sReturn;
return \is_callable('imap_utf8_to_mutf7')
? \imap_utf8_to_mutf7($sStr)
: \mb_convert_encoding($sStr, 'UTF7-IMAP', 'UTF-8');
}
public static function FunctionExistsAndEnabled($mFunctionNameOrNames) : bool

View file

@ -45,7 +45,7 @@ trait Metadata
for ($i = 0; $i < $c; $i += 2) {
$aMetadata[$oResponse->ResponseList[3][$i]] = $oResponse->ResponseList[3][$i+1];
}
$aReturn[$oResponse->ResponseList[2]] = $aMetadata;
$aReturn[$this->toUTF8($oResponse->ResponseList[2])] = $aMetadata;
}
}
} catch (\Throwable $e) {
@ -75,7 +75,7 @@ trait Metadata
}
}
$arguments[] = $this->EscapeString($sFolderName);
$arguments[] = $this->EscapeFolderName($sFolderName);
$arguments[] = '(' . \implode(' ', \array_map([$this, 'EscapeString'], $aEntries)) . ')';
@ -118,7 +118,7 @@ trait Metadata
throw new \MailSo\Base\Exceptions\InvalidArgumentException("Wrong argument for SETMETADATA command");
}
$arguments = [$this->EscapeString($sFolderName)];
$arguments = [$this->EscapeFolderName($sFolderName)];
\array_walk($aEntries, function(&$v, $k){
$v = $this->EscapeString($k) . ' ' . $this->EscapeString($v);

View file

@ -29,7 +29,7 @@ trait Quota
public function Quota(string $sRootName = '') : ?array
{
return $this->IsSupported('QUOTA')
? $this->SendRequestGetResponse("GETQUOTA {$this->EscapeString($sRootName)}")->getQuotaResult()
? $this->getQuotaResult($this->SendRequestGetResponse("GETQUOTA {$this->EscapeFolderName($sRootName)}"))
: null;
}
@ -42,7 +42,45 @@ trait Quota
public function QuotaRoot(string $sFolderName = 'INBOX') : ?array
{
return $this->IsSupported('QUOTA')
? $this->SendRequestGetResponse("GETQUOTAROOT {$this->EscapeString($sFolderName)}")->getQuotaResult()
? $this->getQuotaResult($this->SendRequestGetResponse("GETQUOTAROOT {$this->EscapeFolderName($sFolderName)}"))
: null;
}
private function getQuotaResult(\MailSo\Imap\ResponseCollection $oResponseCollection) : array
{
$aReturn = array(0, 0);
foreach ($oResponseCollection as $oResponse) {
if (Enumerations\ResponseType::UNTAGGED === $oResponse->ResponseType
&& 'QUOTA' === $oResponse->StatusOrIndex
&& \is_array($oResponse->ResponseList)
&& isset($oResponse->ResponseList[3])
&& \is_array($oResponse->ResponseList[3])
&& 2 < \count($oResponse->ResponseList[3])
&& 'STORAGE' === \strtoupper($oResponse->ResponseList[3][0])
&& \is_numeric($oResponse->ResponseList[3][1])
&& \is_numeric($oResponse->ResponseList[3][2])
)
{
$aReturn = array(
(int) $oResponse->ResponseList[3][1],
(int) $oResponse->ResponseList[3][2],
0,
0
);
if (5 < \count($oResponse->ResponseList[3])
&& 'MESSAGE' === \strtoupper($oResponse->ResponseList[3][3])
&& \is_numeric($oResponse->ResponseList[3][4])
&& \is_numeric($oResponse->ResponseList[3][5])
)
{
$aReturn[2] = (int) $oResponse->ResponseList[3][4];
$aReturn[3] = (int) $oResponse->ResponseList[3][5];
}
}
}
return $aReturn;
}
}

View file

@ -23,12 +23,7 @@ class Folder
/**
* @var string
*/
private $sNameRaw;
/**
* @var string
*/
private $sFullNameRaw;
private $sFullName;
/**
* @var string
@ -48,15 +43,20 @@ class Folder
/**
* @throws \MailSo\Base\Exceptions\InvalidArgumentException
*/
function __construct(string $sFullNameRaw, string $sDelimiter = null, array $aFlags = array())
function __construct(string $sFullName, string $sDelimiter = null, array $aFlags = array())
{
if (!\strlen($sFullNameRaw)) {
if (!\strlen($sFullName)) {
throw new \MailSo\Base\Exceptions\InvalidArgumentException;
}
$this->sFullNameRaw = $sFullNameRaw;
$this->sFullName = $sFullName;
$this->setDelimiter($sDelimiter);
$this->setFlags($aFlags);
/*
if (\in_array('\\noutf8', $this->aFlagsLowerCase)) {
}
if (\in_array('\\utf8only', $this->aFlagsLowerCase)) {
}
*/
}
public function setFlags(array $aFlags) : void
@ -67,22 +67,21 @@ class Folder
public function setDelimiter(?string $sDelimiter) : void
{
$this->sDelimiter = $sDelimiter;
if ($sDelimiter) {
$aNames = \explode($this->sDelimiter, $this->sFullNameRaw);
$this->sNameRaw = \end($aNames);
} else {
$this->sNameRaw = $this->sFullNameRaw;
}
public function Name() : string
{
$sNameRaw = $this->sFullName;
if ($this->sDelimiter) {
$aNames = \explode($this->sDelimiter, $sNameRaw);
return \end($aNames);
}
return $sNameRaw;
}
public function NameRaw() : string
public function FullName() : string
{
return $this->sNameRaw;
}
public function FullNameRaw() : string
{
return $this->sFullNameRaw;
return $this->sFullName;
}
public function Delimiter() : ?string
@ -102,7 +101,7 @@ class Folder
public function IsInbox() : bool
{
return 'INBOX' === \strtoupper($this->sFullNameRaw) || \in_array('\\inbox', $this->aFlagsLowerCase);
return 'INBOX' === \strtoupper($this->sFullName) || \in_array('\\inbox', $this->aFlagsLowerCase);
}
/**

View file

@ -66,6 +66,11 @@ class ImapClient extends \MailSo\Net\NetClient
*/
public $__FORCE_SELECT_ON_EXAMINE__ = false;
/**
* @var bool
*/
private $UTF8 = false;
function __construct()
{
\ini_set('xdebug.max_nesting_level', 500);
@ -248,11 +253,12 @@ class ImapClient extends \MailSo\Net\NetClient
if ($this->IsSupported('IMAP4rev2')) {
$this->SendRequestGetResponse('ENABLE', array('IMAP4rev1'));
}
// TODO: RFC 6855
if ($this->IsSupported('UTF8=ONLY')) {
*/
// RFC 6855 || RFC 5738
$this->UTF8 = $this->IsSupported('UTF8=ONLY') || $this->IsSupported('UTF8=ACCEPT');
if ($this->UTF8) {
$this->SendRequestGetResponse('ENABLE', array('UTF8=ACCEPT'));
}
*/
}
catch (Exceptions\NegativeResponseException $oException)
{
@ -377,7 +383,7 @@ class ImapClient extends \MailSo\Net\NetClient
public function FolderCreate(string $sFolderName) : self
{
$this->SendRequestGetResponse('CREATE',
array($this->EscapeString($sFolderName)));
array($this->EscapeFolderName($sFolderName)));
return $this;
}
@ -391,7 +397,7 @@ class ImapClient extends \MailSo\Net\NetClient
// Uncomment will work issue #124 ?
// $this->selectOrExamineFolder($sFolderName, true);
$this->SendRequestGetResponse('DELETE',
array($this->EscapeString($sFolderName)));
array($this->EscapeFolderName($sFolderName)));
// $this->FolderCheck();
// $this->FolderUnSelect();
return $this;
@ -405,7 +411,7 @@ class ImapClient extends \MailSo\Net\NetClient
public function FolderSubscribe(string $sFolderName) : self
{
$this->SendRequestGetResponse('SUBSCRIBE',
array($this->EscapeString($sFolderName)));
array($this->EscapeFolderName($sFolderName)));
return $this;
}
@ -417,7 +423,7 @@ class ImapClient extends \MailSo\Net\NetClient
public function FolderUnSubscribe(string $sFolderName) : self
{
$this->SendRequestGetResponse('UNSUBSCRIBE',
array($this->EscapeString($sFolderName)));
array($this->EscapeFolderName($sFolderName)));
return $this;
}
@ -429,8 +435,8 @@ class ImapClient extends \MailSo\Net\NetClient
public function FolderRename(string $sOldFolderName, string $sNewFolderName) : self
{
$this->SendRequestGetResponse('RENAME', array(
$this->EscapeString($sOldFolderName),
$this->EscapeString($sNewFolderName)));
$this->EscapeFolderName($sOldFolderName),
$this->EscapeFolderName($sNewFolderName)));
return $this;
}
@ -465,8 +471,14 @@ class ImapClient extends \MailSo\Net\NetClient
$bReselect = true;
$this->FolderUnSelect();
}
$aResult = $this->SendRequestGetResponse('STATUS', array($this->EscapeString($sFolderName), $aStatusItems))
->getStatusFolderInformationResult();
$oResponseCollection = $this->SendRequestGetResponse('STATUS', array($this->EscapeFolderName($sFolderName), $aStatusItems));
$oInfo = new FolderInformation($sFolderName, false);
foreach ($oResponseCollection as $oResponse) {
$oInfo->setStatusFromResponse($oResponse);
}
$aResult = $oInfo->getStatusItems();
if ($bReselect) {
$this->selectOrExamineFolder($sFolderName, $bWritable, false);
}
@ -502,7 +514,7 @@ class ImapClient extends \MailSo\Net\NetClient
}
}
$aParameters[] = $this->EscapeString($sParentFolderName);
$aParameters[] = $this->EscapeFolderName($sParentFolderName);
$aParameters[] = $this->EscapeString(\strlen(\trim($sListPattern)) ? $sListPattern : '*');
// RFC 5819
@ -529,7 +541,11 @@ class ImapClient extends \MailSo\Net\NetClient
$aReturnParams[] = 'STATUS';
$aReturnParams[] = $aL;
}
/*
if ($this->UTF8) {
$aReturnParams[] = 'UTF8'; // 'UTF8ONLY';
}
*/
if ($aReturnParams) {
$aParameters[] = 'RETURN';
$aParameters[] = $aReturnParams;
@ -540,7 +556,7 @@ class ImapClient extends \MailSo\Net\NetClient
if ($bPassthru) {
$this->streamResponse();
} else {
$aReturn = $this->getResponse()->getFoldersResult($sCmd);
$aReturn = $this->getResponse()->getFoldersResult($sCmd, $this);
}
// RFC 5464
@ -549,15 +565,15 @@ class ImapClient extends \MailSo\Net\NetClient
$aMetadata = $this->getAllMetadata();
if ($aMetadata) {
foreach ($aReturn as $oFolder) {
if (isset($aMetadata[$oFolder->FullNameRaw()])) {
$oFolder->SetAllMetadata($aMetadata[$oFolder->FullNameRaw()]);
if (isset($aMetadata[$oFolder->FullName()])) {
$oFolder->SetAllMetadata($aMetadata[$oFolder->FullName()]);
}
}
} else {
foreach ($aReturn as $oFolder) {
try {
$oFolder->SetAllMetadata(
$this->getMetadata($oFolder->FullNameRaw(), ['/shared', '/private'], ['DEPTH'=>'infinity'])
$this->getMetadata($oFolder->FullName(), ['/shared', '/private'], ['DEPTH'=>'infinity'])
);
} catch (\Throwable $e) {
// Ignore error
@ -602,7 +618,7 @@ class ImapClient extends \MailSo\Net\NetClient
*/
public function FolderHierarchyDelimiter(string $sFolderName = '') : ?string
{
$oResponse = $this->SendRequestGetResponse('LIST', ['""', $this->EscapeString($sFolderName)]);
$oResponse = $this->SendRequestGetResponse('LIST', ['""', $this->EscapeFolderName($sFolderName)]);
return ('LIST' === $oResponse[0]->ResponseList[1]) ? $oResponse[0]->ResponseList[3] : null;
}
@ -628,18 +644,57 @@ class ImapClient extends \MailSo\Net\NetClient
throw new \MailSo\Base\Exceptions\InvalidArgumentException;
}
$aParams = array($this->EscapeString($sFolderName));
$aSelectParams = array();
/*
if ($this->IsSupported('CONDSTORE')) {
$aParams[] = ['CONDSTORE'];
$aSelectParams[] = 'CONDSTORE';
}
if ($this->UTF8) {
$aSelectParams[] = 'UTF8';
}
*/
$aParams = array(
$this->EscapeFolderName($sFolderName)
);
if ($aSelectParams) {
$aParams[] = $aSelectParams;
}
/**
* IMAP4rev2 SELECT/EXAMINE are now required to return an untagged LIST response.
*/
$this->oCurrentFolderInfo = $this->SendRequestGetResponse($bIsWritable ? 'SELECT' : 'EXAMINE',
$aParams)
->getCurrentFolderInformation($sFolderName, $bIsWritable);
$oResponseCollection = $this->SendRequestGetResponse($bIsWritable ? 'SELECT' : 'EXAMINE', $aParams);
$oResult = new FolderInformation($sFolderName, $bIsWritable);
foreach ($oResponseCollection as $oResponse) {
if (Enumerations\ResponseType::UNTAGGED === $oResponse->ResponseType) {
if (!$oResult->setStatusFromResponse($oResponse)) {
// OK untagged responses
if (\is_array($oResponse->OptionalResponse)) {
$key = $oResponse->OptionalResponse[0];
if (\count($oResponse->OptionalResponse) > 1) {
if ('PERMANENTFLAGS' === $key && \is_array($oResponse->OptionalResponse[1])) {
$oResult->PermanentFlags = $oResponse->OptionalResponse[1];
}
} else if ('READ-ONLY' === $key) {
// $oResult->IsWritable = false;
} else if ('READ-WRITE' === $key) {
// $oResult->IsWritable = true;
} else if ('NOMODSEQ' === $key) {
// https://datatracker.ietf.org/doc/html/rfc4551#section-3.1.2
}
}
// untagged responses
else if (\count($oResponse->ResponseList) > 2
&& 'FLAGS' === $oResponse->ResponseList[1]
&& \is_array($oResponse->ResponseList[2])) {
$oResult->Flags = $oResponse->ResponseList[2];
}
}
}
}
$this->oCurrentFolderInfo = $oResult;
return $this;
}
@ -885,7 +940,7 @@ class ImapClient extends \MailSo\Net\NetClient
}
$this->SendRequestGetResponse($bIndexIsUid ? 'UID COPY' : 'COPY',
array($sIndexRange, $this->EscapeString($sToFolder)));
array($sIndexRange, $this->EscapeFolderName($sToFolder)));
return $this;
}
@ -911,7 +966,7 @@ class ImapClient extends \MailSo\Net\NetClient
}
$this->SendRequestGetResponse($bIndexIsUid ? 'UID MOVE' : 'MOVE',
array($sIndexRange, $this->EscapeString($sToFolder)));
array($sIndexRange, $this->EscapeFolderName($sToFolder)));
return $this;
}
@ -972,7 +1027,7 @@ class ImapClient extends \MailSo\Net\NetClient
*/
public function MessageAppendStream(string $sFolderName, $rMessageAppendStream, int $iStreamSize, array $aAppendFlags = null, int &$iUid = null, int $iDateTime = 0) : self
{
$aData = array($this->EscapeString($sFolderName), $aAppendFlags);
$aData = array($this->EscapeFolderName($sFolderName), $aAppendFlags);
if (0 < $iDateTime)
{
$aData[] = $this->EscapeString(\gmdate('d-M-Y H:i:s', $iDateTime).' +0000');
@ -1239,4 +1294,14 @@ class ImapClient extends \MailSo\Net\NetClient
return 'UNKNOWN';
}
public function EscapeFolderName(string $sFolderName) : string
{
return $this->EscapeString($this->UTF8 ? $sFolderName : \MailSo\Base\Utils::Utf8ToUtf7Modified($sFolderName));
}
public function toUTF8(string $sText) : string
{
return $this->UTF8 ? $sText : \MailSo\Base\Utils::Utf7ModifiedToUtf8($sText);
}
}

View file

@ -20,42 +20,32 @@ class NamespaceResult
/**
* @var string
*/
private $sPersonal;
private $sPersonal = '';
/**
* @var string
*/
private $sPersonalDelimiter;
private $sPersonalDelimiter = '';
/**
* @var string
*/
private $sOtherUser;
private $sOtherUser = '';
/**
* @var string
*/
private $sOtherUserDelimiter;
private $sOtherUserDelimiter = '';
/**
* @var string
*/
private $sShared;
private $sShared = '';
/**
* @var string
*/
private $sSharedDelimiter;
function __construct()
{
$this->sPersonal = '';
$this->sPersonalDelimiter = '';
$this->sOtherUser = '';
$this->sOtherUserDelimiter = '';
$this->sShared = '';
$this->sSharedDelimiter = '';
}
private $sSharedDelimiter = '';
public function InitByImapResponse(\MailSo\Imap\Response $oImapResponse) : self
{
@ -103,8 +93,4 @@ class NamespaceResult
return $this->sPersonal;
}
public function GetPersonalNamespaceDelimiter() : string
{
return $this->sPersonalDelimiter;
}
}

View file

@ -88,7 +88,7 @@ class ResponseCollection extends \MailSo\Base\Collection
return $aReturn;
}
public function getFoldersResult(string $sStatus) : array
public function getFoldersResult(string $sStatus, ImapClient $oImapClient) : array
{
$aReturn = array();
@ -99,7 +99,7 @@ class ResponseCollection extends \MailSo\Base\Collection
continue;
}
if ('STATUS' === $oResponse->StatusOrIndex && isset($oResponse->ResponseList[2])) {
$sFullNameRaw = $oResponse->ResponseList[2];
$sFullNameRaw = $oImapClient->toUTF8($oResponse->ResponseList[2]);
if (!isset($aReturn[$sFullNameRaw])) {
$aReturn[$sFullNameRaw] = new Folder($sFullNameRaw);
}
@ -108,14 +108,14 @@ class ResponseCollection extends \MailSo\Base\Collection
else if ($sStatus === $oResponse->StatusOrIndex && 5 == \count($oResponse->ResponseList)) {
try
{
$sFullNameRaw = $oResponse->ResponseList[4];
$sFullNameRaw = $oImapClient->toUTF8($oResponse->ResponseList[4]);
/**
* $oResponse->ResponseList[0] = *
* $oResponse->ResponseList[1] = LIST (all) | LSUB (subscribed)
* $oResponse->ResponseList[2] = Flags
* $oResponse->ResponseList[3] = Delimiter
* $oResponse->ResponseList[4] = FullNameRaw
* $oResponse->ResponseList[4] = FullName
*/
if (!isset($aReturn[$sFullNameRaw])) {
$oFolder = new Folder($sFullNameRaw,
@ -220,45 +220,6 @@ class ResponseCollection extends \MailSo\Base\Collection
return $aReturn;
}
/**
* Called by selectOrExamineFolder
*/
public function getCurrentFolderInformation(string $sFolderName, bool $bIsWritable) : FolderInformation
{
$oResult = new FolderInformation($sFolderName, $bIsWritable);
foreach ($this as $oResponse) {
if (Enumerations\ResponseType::UNTAGGED === $oResponse->ResponseType) {
if (!$oResult->setStatusFromResponse($oResponse)) {
// OK untagged responses
if (\is_array($oResponse->OptionalResponse)) {
$key = $oResponse->OptionalResponse[0];
if (\count($oResponse->OptionalResponse) > 1) {
if ('PERMANENTFLAGS' === $key && \is_array($oResponse->OptionalResponse[1])) {
$oResult->PermanentFlags = $oResponse->OptionalResponse[1];
}
} else if ('READ-ONLY' === $key) {
// $oResult->IsWritable = false;
} else if ('READ-WRITE' === $key) {
// $oResult->IsWritable = true;
} else if ('NOMODSEQ' === $key) {
// https://datatracker.ietf.org/doc/html/rfc4551#section-3.1.2
}
}
// untagged responses
else if (\count($oResponse->ResponseList) > 2) {
if ('FLAGS' === $oResponse->ResponseList[1] && \is_array($oResponse->ResponseList[2]))
{
$oResult->Flags = $oResponse->ResponseList[2];
}
}
}
}
}
return $oResult;
}
public function getNamespaceResult() : NamespaceResult
{
foreach ($this as $oResponse) {
@ -273,43 +234,6 @@ class ResponseCollection extends \MailSo\Base\Collection
throw new Exceptions\ResponseException;
}
public function getQuotaResult() : array
{
$aReturn = array(0, 0);
foreach ($this as $oResponse) {
if (Enumerations\ResponseType::UNTAGGED === $oResponse->ResponseType
&& 'QUOTA' === $oResponse->StatusOrIndex
&& \is_array($oResponse->ResponseList)
&& isset($oResponse->ResponseList[3])
&& \is_array($oResponse->ResponseList[3])
&& 2 < \count($oResponse->ResponseList[3])
&& 'STORAGE' === \strtoupper($oResponse->ResponseList[3][0])
&& \is_numeric($oResponse->ResponseList[3][1])
&& \is_numeric($oResponse->ResponseList[3][2])
)
{
$aReturn = array(
(int) $oResponse->ResponseList[3][1],
(int) $oResponse->ResponseList[3][2],
0,
0
);
if (5 < \count($oResponse->ResponseList[3])
&& 'MESSAGE' === \strtoupper($oResponse->ResponseList[3][3])
&& \is_numeric($oResponse->ResponseList[3][4])
&& \is_numeric($oResponse->ResponseList[3][5])
)
{
$aReturn[2] = (int) $oResponse->ResponseList[3][4];
$aReturn[3] = (int) $oResponse->ResponseList[3][5];
}
}
}
return $aReturn;
}
public function getSimpleESearchOrESortResult(string $sRequestTag, bool $bReturnUid) : array
{
$aResult = array();
@ -340,15 +264,6 @@ class ResponseCollection extends \MailSo\Base\Collection
return $aResult;
}
public function getStatusFolderInformationResult() : array
{
$oInfo = new FolderInformation('', false);
foreach ($this as $oResponse) {
$oInfo->setStatusFromResponse($oResponse);
}
return $oInfo->getStatusItems();
}
/**
* @param mixed $mValue
*

View file

@ -3,7 +3,7 @@
/*
* This file is part of MailSo.
*
* (c) 2014 Usenko Timur
* (c) 2021 DJMaze
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.

View file

@ -112,10 +112,10 @@ trait Status
* EXAMINE https://datatracker.ietf.org/doc/html/rfc3501#section-6.3.2
* STATUS https://datatracker.ietf.org/doc/html/rfc3501#section-6.3.10
*
* getCurrentFolderInformation
* selectOrExamineFolder
* ResponseList[2] => EXISTS | RECENT
* OptionalResponse[0] => UNSEEN
* getStatusFolderInformationResult
* FolderStatus
* OptionalResponse[0] => HIGHESTMODSEQ
* ResponseList[1] => STATUS
* getFoldersResult LIST-EXTENDED

View file

@ -20,16 +20,6 @@ use MailSo\Imap\Enumerations\MetadataKeys;
*/
class Folder implements \JsonSerializable
{
/**
* @var string
*/
private $sParentFullNameRaw;
/**
* @var int
*/
private $iNestingLevel;
/**
* @var bool
*/
@ -48,7 +38,7 @@ class Folder implements \JsonSerializable
/**
* @var \MailSo\Mail\FolderCollection
*/
private $oSubFolders;
private $oSubFolders = null;
/**
* @throws \MailSo\Base\Exceptions\InvalidArgumentException
@ -56,18 +46,6 @@ class Folder implements \JsonSerializable
function __construct(\MailSo\Imap\Folder $oImapFolder, bool $bSubscribed = true, bool $bExists = true)
{
$this->oImapFolder = $oImapFolder;
$this->oSubFolders = null;
$aNames = \explode($this->oImapFolder->Delimiter(), $this->oImapFolder->FullNameRaw());
$this->iNestingLevel = \count($aNames);
$this->sParentFullNameRaw = '';
if (1 < $this->iNestingLevel)
{
\array_pop($aNames);
$this->sParentFullNameRaw = \implode($this->oImapFolder->Delimiter(), $aNames);
}
$this->bSubscribed = $bSubscribed || \in_array('\\subscribed', $oImapFolder->FlagsLowerCase());
$this->bExists = $bExists;
}
@ -84,16 +62,12 @@ class Folder implements \JsonSerializable
public function Name() : string
{
return \MailSo\Base\Utils::ConvertEncoding($this->NameRaw(),
\MailSo\Base\Enumerations\Charset::UTF_7_IMAP,
\MailSo\Base\Enumerations\Charset::UTF_8);
return $this->oImapFolder->Name();
}
public function FullName() : string
{
return \MailSo\Base\Utils::ConvertEncoding($this->FullNameRaw(),
\MailSo\Base\Enumerations\Charset::UTF_7_IMAP,
\MailSo\Base\Enumerations\Charset::UTF_8);
return $this->oImapFolder->FullName();
}
public function NameRaw() : string
@ -101,23 +75,6 @@ class Folder implements \JsonSerializable
return $this->oImapFolder->NameRaw();
}
public function FullNameRaw() : string
{
return $this->oImapFolder->FullNameRaw();
}
public function ParentFullName() : string
{
return \MailSo\Base\Utils::ConvertEncoding($this->sParentFullNameRaw,
\MailSo\Base\Enumerations\Charset::UTF_7_IMAP,
\MailSo\Base\Enumerations\Charset::UTF_8);
}
public function ParentFullNameRaw() : string
{
return $this->sParentFullNameRaw;
}
public function Delimiter() : string
{
return $this->oImapFolder->Delimiter();
@ -188,7 +145,7 @@ class Folder implements \JsonSerializable
switch (true)
{
case \in_array('\\inbox', $aFlags) || 'INBOX' === \strtoupper($this->FullNameRaw()):
case \in_array('\\inbox', $aFlags) || 'INBOX' === \strtoupper($this->FullName()):
return FolderType::INBOX;
case \in_array('\\sent', $aFlags):
@ -221,7 +178,7 @@ class Folder implements \JsonSerializable
return FolderType::ALL;
// TODO
// case 'Templates' === $this->FullNameRaw():
// case 'Templates' === $this->FullName():
// return FolderType::TEMPLATES;
}
@ -287,7 +244,7 @@ class Folder implements \JsonSerializable
'MessageUnseenCount' => (int) $aStatus['UNSEEN'],
'UidNext' => (int) $aStatus['UIDNEXT'],
// 'Hash' => $this->MailClient()->GenerateFolderHash(
// $this->FullNameRaw(), $aStatus['MESSAGES'], $aStatus['UIDNEXT'],
// $this->FullName(), $aStatus['MESSAGES'], $aStatus['UIDNEXT'],
// empty($aStatus['HIGHESTMODSEQ']) ? 0 : $aStatus['HIGHESTMODSEQ'])
);
}
@ -296,7 +253,6 @@ class Folder implements \JsonSerializable
'@Object' => 'Object/Folder',
'Name' => $this->Name(),
'FullName' => $this->FullName(),
'FullNameRaw' => $this->FullNameRaw(),
'Delimiter' => (string) $this->Delimiter(),
// 'HasVisibleSubFolders' => $this->HasVisibleSubFolders(),
'Subscribed' => $this->bSubscribed,

View file

@ -57,7 +57,7 @@ class FolderCollection extends \MailSo\Base\Collection
$mResult = null;
foreach ($this as $oFolder)
{
if ($oFolder->FullNameRaw() === $sFullNameRaw)
if ($oFolder->FullName() === $sFullNameRaw)
{
$mResult = $oFolder;
break;
@ -119,7 +119,7 @@ class FolderCollection extends \MailSo\Base\Collection
{
foreach ($this as $oItemFolder)
{
if (0 === \strpos($oMailFolder->FullNameRaw(), $oItemFolder->FullNameRaw().$oItemFolder->Delimiter()))
if (0 === \strpos($oMailFolder->FullName(), $oItemFolder->FullName().$oItemFolder->Delimiter()))
{
$oItemFolder->SubFolders(true)->AddWithPositionSearch($oMailFolder);
return;

View file

@ -1219,7 +1219,7 @@ class MailClient
$aImapSubscribedFoldersHelper = array();
foreach ($aSubscribedFolders as /* @var $oImapFolder \MailSo\Imap\Folder */ $oImapFolder)
{
$aImapSubscribedFoldersHelper[] = $oImapFolder->FullNameRaw();
$aImapSubscribedFoldersHelper[] = $oImapFolder->FullName();
}
}
catch (\Throwable $oException)
@ -1253,13 +1253,13 @@ class MailClient
foreach ($aFolders as /* @var $oImapFolder \MailSo\Imap\Folder */ $oImapFolder)
{
$oMailFolder = new Folder($oImapFolder,
($bUseListSubscribeStatus && (null === $aImapSubscribedFoldersHelper || \in_array($oImapFolder->FullNameRaw(), $aImapSubscribedFoldersHelper)))
($bUseListSubscribeStatus && (null === $aImapSubscribedFoldersHelper || \in_array($oImapFolder->FullName(), $aImapSubscribedFoldersHelper)))
|| $oImapFolder->IsInbox()
);
if ($oImapFolder->IsInbox()) {
$sINBOX = $oMailFolder->FullNameRaw();
$sINBOX = $oMailFolder->FullName();
}
$aSortedByLenImapFolders[$oMailFolder->FullNameRaw()] = $oMailFolder;
$aSortedByLenImapFolders[$oMailFolder->FullName()] = $oMailFolder;
}
// Add NonExistent folders
@ -1267,7 +1267,7 @@ class MailClient
foreach ($aSortedByLenImapFolders as /* @var $oMailFolder Folder */ $oMailFolder)
{
$sDelimiter = $oMailFolder->Delimiter();
$aFolderExplode = \explode($sDelimiter, $oMailFolder->FullNameRaw());
$aFolderExplode = \explode($sDelimiter, $oMailFolder->FullName());
if (1 < \count($aFolderExplode))
{
@ -1418,7 +1418,7 @@ class MailClient
$aSubscribeFolders = $this->oImapClient->FolderSubscribeList($sPrevFolderFullNameRaw, '*');
foreach ($aSubscribeFolders as /* @var $oFolder \MailSo\Imap\Folder */ $oFolder)
{
$this->oImapClient->FolderUnSubscribe($oFolder->FullNameRaw());
$this->oImapClient->FolderUnSubscribe($oFolder->FullName());
}
}
@ -1442,7 +1442,7 @@ class MailClient
foreach ($aSubscribeFolders as /* @var $oFolder \MailSo\Imap\Folder */ $oFolder)
{
$sFolderFullNameRawForResubscrine = $oFolder->FullNameRaw();
$sFolderFullNameRawForResubscrine = $oFolder->FullName();
if (0 === \strpos($sFolderFullNameRawForResubscrine, $sPrevFolderFullNameRaw))
{
$sNewFolderFullNameRawForResubscrine = $sNewFolderFullNameRaw.

View file

@ -460,7 +460,7 @@ trait Folders
{
foreach ($oFolders as $oFolder)
{
$aResult[] = $oFolder->FullNameRaw()."|".
$aResult[] = $oFolder->FullName()."|".
implode("|", $oFolder->FlagsLowerCase()).($oFolder->IsSubscribed() ? '1' : '0');
$oSub = $oFolder->SubFolders();
@ -492,7 +492,7 @@ trait Folders
FolderType::ARCHIVE
)))
{
$aResult[$iFolderType] = $oFolder->FullNameRaw();
$aResult[$iFolderType] = $oFolder->FullName();
}
}
@ -524,7 +524,7 @@ trait Folders
FolderType::ARCHIVE
)))
{
$aResult[$iFolderType] = $oFolder->FullNameRaw();
$aResult[$iFolderType] = $oFolder->FullName();
}
}
}

View file

@ -373,7 +373,7 @@ trait Response
'MessageUnseenCount' => (int) $aStatus['UNSEEN'],
'UidNext' => (int) $aStatus['UIDNEXT'],
'Hash' => $this->MailClient()->GenerateFolderHash(
$mResponse->FullNameRaw(), $aStatus['MESSAGES'], $aStatus['UIDNEXT'],
$mResponse->FullName(), $aStatus['MESSAGES'], $aStatus['UIDNEXT'],
empty($aStatus['HIGHESTMODSEQ']) ? 0 : $aStatus['HIGHESTMODSEQ'])
);
}
@ -394,8 +394,8 @@ trait Response
return \array_merge(
$mResponse->jsonSerialize(),
array(
'FullNameHash' => $this->hashFolderFullName($mResponse->FullNameRaw(), $mResponse->FullName()),
'Checkable' => \in_array($mResponse->FullNameRaw(), $this->aCheckableFolder),
'FullNameHash' => $this->hashFolderFullName($mResponse->FullName(), $mResponse->FullName()),
'Checkable' => \in_array($mResponse->FullName(), $this->aCheckableFolder),
'Extended' => $aExtended,
'SubFolders' => $this->responseObject($mResponse->SubFolders(), $sParent, $aParameters)
)