diff -r 000000000000 -r 8e480a14352b messagingfw/wappushfw/SISLPushMsgUtils/src/SISLPushMsgUtils.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/messagingfw/wappushfw/SISLPushMsgUtils/src/SISLPushMsgUtils.cpp Mon Jan 18 20:36:02 2010 +0200 @@ -0,0 +1,632 @@ +// Copyright (c) 2000-2009 Nokia Corporation and/or its subsidiary(-ies). +// All rights reserved. +// This component and the accompanying materials are made available +// under the terms of "Eclipse Public License v1.0" +// which accompanies this distribution, and is available +// at the URL "http://www.eclipse.org/legal/epl-v10.html". +// +// Initial Contributors: +// Nokia Corporation - initial contribution. +// +// Contributors: +// +// Description: +// + +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + + +/** +Allocates and constructs a new SISL Push Message Utility object. + +@return +New SISL Push Message Utility object. +*/ +EXPORT_C CSISLPushMsgUtils* CSISLPushMsgUtils::NewL() + { + CSISLPushMsgUtils* self = new (ELeave) CSISLPushMsgUtils(); + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(); + return self; + } + + +/** +Constructor. +*/ +CSISLPushMsgUtils::CSISLPushMsgUtils() : CWapPushMsgUtils() + { + } + + +/** +Constructor. Creates CMsvSession and CMsvEntry. +*/ +void CSISLPushMsgUtils::ConstructL() + { + CWapPushMsgUtils::ConstructL(); + } + + +/** +Destructor. +*/ +EXPORT_C CSISLPushMsgUtils::~CSISLPushMsgUtils() + { + } + + +/** +Locates a selection of SI entries with the specified ID. + +Assumes that all SI entries are saved as children of the Push Service Message Folder. +If the id of the Push Message Folder happens to be Null, it gets the Id of the folder. + +The return value CMsvEntrySelection is on the Cleanup Stack. + +@param aSiId +Id of SI message to locate + +@return +Id of the message entries if it exists, or KMsvNullIndexEntryId if it doesn't. +*/ +EXPORT_C CMsvEntrySelection* CSISLPushMsgUtils::FindSiIdLC(const TDesC& aSiId) + { + CMsvEntrySelection* matching = new (ELeave) CMsvEntrySelection; + CleanupStack::PushL(matching); + + CSIPushMsgEntry* siEntry = CSIPushMsgEntry::NewL(); + CleanupStack::PushL(siEntry); + + if (iPushFolderId == KMsvNullIndexEntryId) + GetPushMsgFolderIdL(iPushFolderId); + iMsvEntry->SetEntryL(iPushFolderId); + + CMsvEntrySelection* children; + children = GetChildrenWithMtmLC(KUidMtmWapPush);//leave children on CleanupStack + + TInt numEntries= children->Count(); + TMsvEntry currentEntry; + + // loop until we find a match or reach the end of the SI entries + for (TInt count=0; countSetEntryL(children->At(count)); + currentEntry = iMsvEntry->Entry(); + // Hard coded check for the Message Push Type + if (currentEntry.iBioType == KUidWapPushMsgSI.iUid) //It's an SI message! + { + siEntry->SetEntry(currentEntry); + siEntry->RetrieveL(*iMsvSession, currentEntry.Id()); + if (aSiId.CompareF( siEntry->Id()) ==0)// Found a match + matching->AppendL( currentEntry.Id()); // get the Id to return + } + } + CleanupStack::PopAndDestroy(2); // children, siEntry + + return matching; //Still on CleanupStack + } + + +/** +Finds any entry with the specified Url and Push Message Type Uid. + +The function assumes that the entries are stored under the Push Message Folder Entry. + +@param aUrl +URL to find + +@param aPushType +Push Message type to filter entries. + +@return +Message entry for the specified Url and message type, +or KMsvNullIndexEntryId if a match is not found. + +@leave KErrNotFound Could not locate a SISL Push message with the specified URL and push type. +@leave CSISLPushMsgUtils::GetPushMsgFolderIdL +@leave CMsvEntry::SetEntryL +@leave CMsvEntry::HasStoreL +@leave CMsvEntry::ReadStoreL +@leave CMsvStore::IsPresentL +@leave CMsvEntry::EntryId +@leave CMsvStore::RetrieveL +*/ +EXPORT_C TMsvId CSISLPushMsgUtils::FindUrlL(const TDesC& aUrl, TUid aPushType) + { + //Finds all of the entries with the Push Mtm type, + //and then checks if each that has the correct Push Message Type, until either a match is + //found or there are no more entries. + + TMsvId pushID = KMsvNullIndexEntryId; + + if (iPushFolderId == KMsvNullIndexEntryId) + GetPushMsgFolderIdL(iPushFolderId); + iMsvEntry->SetEntryL(iPushFolderId); + + CMsvEntrySelection* children; + children = GetChildrenWithMtmLC(KUidMtmWapPush);//leave children on CleanupStack + + TInt numEntries= children->Count(); + TMsvEntry currentEntry; + + // loop until we find a match or reach the end of the SI entries + for (TInt count=0; countSetEntryL(children->At(count)); + currentEntry = iMsvEntry->Entry(); + if (currentEntry.iBioType == aPushType.iUid && iMsvEntry->HasStoreL()) + //It's the right type of message! + { + CPushMsgEntryBase* pushEntry = GetPushMsgEntryL(aPushType); + if (pushEntry) + { + TPtrC url; + if (aPushType == KUidWapPushMsgSI) + { + url.Set(static_cast(pushEntry)->Url()); + } + else + { + url.Set(static_cast(pushEntry)->Url()); + } + CleanupStack::PushL(pushEntry); + pushEntry->RetrieveL(*iMsvSession, currentEntry.Id()); + if (aUrl.CompareF(url) == 0) + pushID = currentEntry.Id(); + CleanupStack::PopAndDestroy(pushEntry); + } + } + } + CleanupStack::PopAndDestroy(); // children + return pushID; + } + + +/** +Gets the action value for the specified message. + +@param aId +Message entry of interest. + +@return +Action level for the message, or KErrNotFound if action level not found. +*/ +EXPORT_C TInt CSISLPushMsgUtils::GetActionL(TMsvId aId) + { + //Creates an instance of the correct message entry type which is used to + //get the action value. This ensures that the decoding routine of the + //PushEntry class is used, maintaining encapsulation. + + TInt action = KErrNotFound; // -1 to indicate we haven't found the action level + TMsvEntry myEntry; + iMsvEntry->SetEntryL(aId); + myEntry = iMsvEntry->Entry(); + + if (myEntry.iBioType == KUidWapPushMsgSI.iUid) + { + CSIPushMsgEntry* siMsg = CSIPushMsgEntry::NewL(); + siMsg->SetEntry(myEntry); + action = siMsg->Action(); + delete siMsg; + } + else if (myEntry.iBioType == KUidWapPushMsgSL.iUid) + { + CSLPushMsgEntry* slMsg = CSLPushMsgEntry::NewL(); + slMsg->SetEntry(myEntry); + action = slMsg->Action(); + delete slMsg; + } + return action; + } + + +/** +Gets SI or SL Push Message (CSIPushMsgEntry or CSLPushMsgEntry) object from the message +store for the specified message type. + +@param aPushType +Push Message type. + +@return +SI or SL Push Message object for the specified message type. + +@leave CMsvEntry::HasStoreL +@leave CMsvEntry::ReadStoreL +@leave CMsvStore::IsPresentL +@leave CMsvEntry::EntryId +@leave CMsvStore::RetrieveL +*/ +CPushMsgEntryBase* CSISLPushMsgUtils::GetPushMsgEntryL(const TUid aPushType) + { + TBool streamExists=EFalse; + + if (iMsvEntry->HasStoreL()) + { + CMsvStore* store = iMsvEntry->ReadStoreL(); + CleanupStack::PushL(store); + if (store->IsPresentL(aPushType) ) + streamExists = ETrue; + CleanupStack::PopAndDestroy(store); + } + + if (!streamExists) + return NULL; + + CPushMsgEntryBase* pushMsg = NULL; + if (aPushType == KUidWapPushMsgSI) + { + pushMsg = CSIPushMsgEntry::NewL(); + } + else if (aPushType == KUidWapPushMsgSL) + { + pushMsg = CSLPushMsgEntry::NewL(); + } + + CleanupStack::PushL(pushMsg); + pushMsg->RetrieveL(Session(), iMsvEntry->EntryId()); + CleanupStack::Pop(pushMsg); + + return pushMsg; + } + + +/** +Gets the expiry date for the message with the specified Id. + +The function assumes that the Id passed as a parameter is for an SI message, +and cannot currently handle any other type of message. + +@param aId +Id of message to find expiry date. + +@return +Expiry date/time of SI message. +*/ +EXPORT_C const TTime CSISLPushMsgUtils::GetExpiryL(TMsvId aId) + { + TInt64 nullTime = 0; + TTime siExpires = nullTime; + + iMsvEntry->SetEntryL(aId); + + // Ensures we only have an SI Msg - otherwise cannot get an expiry date + __ASSERT_ALWAYS(iMsvEntry->Entry().iBioType == KUidWapPushMsgSI.iUid, + User::Panic(KSISLPushMsgUtilsPanicTitle,ESISLPushMsgUtilsNotSiMsg)); + + CSIPushMsgEntry* siEntry = CSIPushMsgEntry::NewL(); + CleanupStack::PushL(siEntry); + siEntry->RetrieveL(*iMsvSession, aId); + siExpires = siEntry->Expires(); + CleanupStack::PopAndDestroy(siEntry); + return siExpires; + } + + +/** +Finds the message of a specified Push type with the highest action level. + +@param aPushType +Uid for the type of WAP Push Message + +@return +Id of the message entry with the highest action + +@leave KErrNotSupported +If aPushType is not a SI or SL push message type. +@leave CMsvEntry::SetEntryL +@leave CSIPushMsgEntry::NewL +@leave CMsvEntry::ChildrenWithMtmL +@leave CArrayFixFlat::AppendL +*/ +EXPORT_C TMsvId CSISLPushMsgUtils::GetHighestActionL(TUid aPushType) + { + //Action only applies to the SI and SL messages - both stored under the Service Entry + CMsvEntrySelection* sel; + + if (iPushFolderId ==KMsvNullIndexEntryId) + GetPushMsgFolderIdL(iPushFolderId); + iMsvEntry->SetEntryL(iPushFolderId); + + sel=GetChildrenWithMtmLC(KUidMtmWapPush); + + CPushMsgEntryBase* pushMsg=NULL; + + if (aPushType == KUidWapPushMsgSI) + pushMsg = CSIPushMsgEntry::NewL(); + else if(aPushType == KUidWapPushMsgSL) + pushMsg = CSLPushMsgEntry::NewL(); + else + User::Leave(KErrNotSupported); + + CleanupStack::PushL(pushMsg); + + TMsvId maxId =KMsvNullIndexEntryId ; + TInt maxAction=-1; + TInt currentAction=-1; + TInt entries = sel->Count(); + + for (TInt count = 0; count < entries; count++) + { + iMsvEntry->SetEntryL(sel->At(count)); + pushMsg->SetEntry(iMsvEntry->Entry()); + if (iMsvEntry->Entry().iBioType == aPushType.iUid) + { + if (aPushType == KUidWapPushMsgSI ) + currentAction = STATIC_CAST(CSIPushMsgEntry*, pushMsg) ->Action(); + else if ((aPushType == KUidWapPushMsgSL)) + currentAction = STATIC_CAST(CSLPushMsgEntry*, pushMsg) ->Action(); + else continue; + + if (currentAction>maxAction) // Found a new highest action - store the details + { + maxAction = currentAction; + maxId = sel->At(count); + } + currentAction = -1; + } + } + CleanupStack::PopAndDestroy(2); //sel, pushMsg + return maxId; + } + + +/** +Gets the earliest expiry date of all the SI Messages that are not flagged for deletion. + +@return +Id of the message with the earliest expiry date +*/ +EXPORT_C TMsvId CSISLPushMsgUtils::GetNextExpiryL() + { + //Function searches through the SI Messages and keeps hold of the earliest expiry up + //to that point. Because the function just compares each message with the preceding + //ones it is possible for it to return a date before the current date and time. + //This just means that the message has expired but has not been either removed from + //the system or flagged for deletion. + + CMsvEntrySelection* sel; + + if (iPushFolderId ==KMsvNullIndexEntryId) + GetPushMsgFolderIdL(iPushFolderId); + iMsvEntry->SetEntryL(iPushFolderId); + + sel=GetChildrenWithMtmLC(KUidMtmWapPush); + + TInt count = sel->Count(); + // Ensure that we start with Max time, everything ought to be less than this + TTime earliestTime = Time::MaxTTime(); + TMsvId siExpiring = KMsvNullIndexEntryId; + + CSIPushMsgEntry* siEntry = CSIPushMsgEntry::NewL(); + CleanupStack::PushL(siEntry); + + for (TInt current = 0; current< count;current++) + { + + iMsvEntry->SetEntryL(sel->At(current)); + if (iMsvEntry->Entry().iBioType == KUidWapPushMsgSI.iUid) + { + + siEntry->RetrieveL(*iMsvSession, iMsvEntry->Entry().Id()); + + // Ignore null expiry times and entries flagged for deletion + if ( (siEntry->Expires() == Time::NullTTime() ) + || (siEntry->Status() == CPushMsgEntryBase::EPushMsgStatusDeleted) ) + continue; + else if ( (siEntry->Expires() < earliestTime )) + { + earliestTime = siEntry->Expires().Int64(); + siExpiring = iMsvEntry->Entry().Id(); + } + } + + } + CleanupStack::PopAndDestroy(); //siEntry + CleanupStack::PopAndDestroy(); // sel + return siExpiring; + } + + +/** +Gets the Id of the Push Message Folder under which all Push Messages are stored. + +If the folder does not exist, it is created. + +@param aFolderId +On return, Id of the Push Message Folder. +@leave CMsvEntry::ChildrenWithTypeL +@leave CMsvEntry::SetEntryL +@leave CArrayFixFlat::AppendL +*/ +EXPORT_C void CSISLPushMsgUtils::GetPushMsgFolderIdL(TMsvId& aFolderId) + { + //Returns the Service IDs of MTM aMtm + if (iPushFolderId != KMsvNullIndexEntryId) + { + aFolderId = iPushFolderId; + return; + } + + aFolderId = KMsvNullIndexEntryId; + + iMsvEntry->SetEntryL(KMsvLocalServiceIndexEntryId); + + //Get the children on the Root Index Entry + CMsvEntrySelection* selection = iMsvEntry->ChildrenWithTypeL(KUidMsvFolderEntry); + CleanupStack::PushL(selection); + + CMsvEntrySelection* pushFolders = new (ELeave) CMsvEntrySelection; + CleanupStack::PushL(pushFolders); + + TInt count = selection->Count(); + + //Find an entry for MTM aMtm + for (TInt curChild = 0; curChild < count; curChild++) + { + iMsvEntry->SetEntryL(selection->At(curChild)); + + if (iMsvEntry->Entry().iMtm == KUidMtmWapPush) + { + pushFolders->AppendL( iMsvEntry->Entry().Id()); + } + } + iMsvEntry->SetEntryL(KMsvRootIndexEntryId);//Point our entry to something safe + + if (pushFolders->Count() >0) + aFolderId = pushFolders->At(0); // grab the first, should only be one! + else if (pushFolders->Count() ==0) + { + aFolderId = CreatePushMsgFolderL(); + } + + if (aFolderId!= KMsvNullIndexEntryId && (&iPushFolderId != &aFolderId) ) //service Id & not self assignment + iPushFolderId = aFolderId; // Keep this - may save effort in forthcoming fn calls + CleanupStack::PopAndDestroy(2); //selection + } + + +/** +Gets the date field from the message with the specified Id. + +Creation Date is stored in iMsgDate for SI messages, whilst the field holds the date +and time of transmission for SL messages. This function is called by GetCreationDate +and GetTransmissionDate + +@param aId +Id of the message entry with the required date field. + +@param aPushType +Uid for the type of WAP Push Message + +@return +Value of the date field. +@leave CMsvEntry::SetEntryL +@leave CMsvEntry::HasStoreL +@leave CMsvEntry::ReadStoreL +@leave CMsvStore::IsPresentL +@leave CMsvEntry::EntryId +@leave CMsvStore::RetrieveL +*/ +TTime CSISLPushMsgUtils::GetDateL(TMsvId aId, const TUid aPushType) + { + TTime date = Time::NullTTime(); + + iMsvEntry->SetEntryL(aId); + + CPushMsgEntryBase* pushEntry = GetPushMsgEntryL(aPushType); + + if (aPushType == KUidWapPushMsgSI) + { + date = STATIC_CAST(CSIPushMsgEntry*, pushEntry) ->Created(); + } + else if (aPushType == KUidWapPushMsgSL) + { + date = STATIC_CAST(CSLPushMsgEntry*, pushEntry) ->TimeSent(); + } + delete pushEntry; + return date; + } + + +/** +Creates a new Push Service folder under the local service. + +Called when GetPushMsgFolderL fails to find a folder entry. + +@return +Id of the newly created folder entry +*/ +TMsvId CSISLPushMsgUtils::CreatePushMsgFolderL() + { + TMsvId id = 0; + TMsvEntry entry; + entry.iServiceId = KMsvLocalServiceIndexEntryId; + entry.iMtm = KUidMtmWapPush; + entry.iType = KUidMsvFolderEntry; + entry.SetReadOnly(ETrue); + entry.SetVisible(EFalse); + entry.iDetails.Set(KPushFolderDescription); + + iMsvEntry->SetEntryL(KMsvLocalServiceIndexEntryId); + iMsvEntry->CreateL(entry); + id = entry.Id(); + return id; + } + + +/** +Sets the status of the specified Push message to be deleted. + +Any messages marked as deleted in the Push Message Folder under the Local Service will be +deleted by the UI later. Sets the value of the first 4 bits of the TMsvEntry field +iMtmData1 to EPushMsgStatusDeleted. + +@param aId +Id of the entry to be set to Deleted +*/ +EXPORT_C void CSISLPushMsgUtils::DeleteEntryL(TMsvId aId) + { + iMsvEntry->SetEntryL(aId); + + TMsvEntry entry = iMsvEntry->Entry(); + entry.SetMtmData1( (entry.MtmData1() & (~KPushMaskOnlyStatus)) + + CPushMsgEntryBase::EPushMsgStatusDeleted ); + iMsvEntry->ChangeL(entry); + } + +/** +Deletes the specified Push Message. + +This function deletes the item immediately. + +@param aId +Id of the entry to be Deleted +*/ +EXPORT_C void CSISLPushMsgUtils::DeleteEntryNowL(TMsvId aId) + { + iMsvEntry->DeleteL(aId); + } + +/** +Gets all the children of the current message context which have the specified Mtm Uid. + +Assumes that the calling function has set the iMsvEntry member to the correct context, prior +to the function call. + +@param aMtm +Mtm Uid to filter children with + +@return +Pointer to an array of TMsvId's for entries which match the Mtm Uid +@leave CMsvEntry::ChildrenWithMtmL +*/ +CMsvEntrySelection* CSISLPushMsgUtils::GetChildrenWithMtmLC(TUid aMtm) + { + CMsvEntrySelection* children; + children = iMsvEntry->ChildrenWithMtmL(aMtm); + CleanupStack::PushL(children); + return children; + } + + +#ifndef EKA2 +GLDEF_C TInt E32Dll(TDllReason/* aReason*/) + { + return (KErrNone); + } +#endif + +