--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/commsfwtools/preparedefaultcommsdatabase/src/MetaDatabaseVisitorRecordSet.cpp Thu Dec 17 09:22:25 2009 +0200
@@ -0,0 +1,349 @@
+// Copyright (c) 2004-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:
+// NB - no mapping necessary at the table level
+//
+//
+
+/**
+ @file MetaDatabaseVisitorRecordSet.cpp
+ @internalComponent
+*/
+
+
+#include "CommsDatInternalDefs.h"
+#include "CommsDatTypesV1_1.h"
+#include "MetaDatabaseVisitor.h"
+#include "CommsDat.h"
+#include "Commsdat_Log.h"
+
+
+using namespace CommsDat;
+
+using namespace Meta;
+
+
+
+CommsDat::TMDBRecordSetVisitor::TMDBRecordSetVisitor(RPointerArray<CMDBRecordBase>* aData)
+: TMDBVisitorBase(0), iTarget(aData)
+/**
+ * Constructor
+ */
+ {
+ }
+
+CommsDat::TMDBRecordSetVisitor* CommsDat::TMDBRecordSetVisitor::NewL(const TAny* aMem, const TAny* aData)
+/**
+ * Instantiates a RecordSet Visitor of a particular type.
+ * Used for attribute registration (in the data v-table).
+ */
+ {
+ return static_cast<CommsDat::TMDBRecordSetVisitor*>( ::new ((TUint8*)aMem) CommsDat::TMDBRecordSetVisitor( (RPointerArray<CMDBRecordBase>*)(aData) ) );
+ }
+
+
+TInt CommsDat::TMDBRecordSetVisitor::Changed() const
+/*
+this composite class always returns changed so iterator will look for changed members.
+*/
+ {
+ return 1;
+ }
+
+
+TInt CommsDat::TMDBRecordSetVisitor::LoadL(CMDBSessionImpl* aSession, TMDBElementId aRecordId, TMDBAttributeFlags aAttributeFlags)
+/*
+Assumes type and record id set by caller
+
+@internalComponent
+*/
+ {
+
+ RArray<TUint32> ids;
+ CleanupClosePushL(ids);
+
+ // find out record ids from storage server
+ TUint32 mask = KCDMaskShowType | aSession->GetReadAttributeMask() | KCDUtilityFlag;
+ // TUint32 mask = KCDMaskShowType | (~aAttributeFlags & KCDMaskShowAttributes) | KCDUtilityFlag;
+ TUint32 id = (ElementId() & (KCDMaskShowRecordType | aSession->GetReadAttributeMask())) | KCDMaskShowFieldType | (aAttributeFlags & aSession->GetReadAttributeMask()) ; // look for nodes
+
+ TInt err = aSession->StorageL()->FindL( id, mask, ids );
+
+ if ( err != KErrNone && err != KErrNotFound )
+ {
+ CleanupStack::PopAndDestroy(&ids);
+ User::Leave(err);
+ }
+
+ if (ids.Count() == 0)
+ {
+ err = KErrNotFound;
+ }
+
+ else
+ {
+ err = LoadL(aSession, aRecordId, aAttributeFlags, ids);
+ }
+
+ CleanupStack::PopAndDestroy(&ids);
+ return err;
+ }
+
+
+TInt CommsDat::TMDBRecordSetVisitor::LoadL(CMDBSessionImpl* aSession, TMDBElementId /*aRecordId*/, TMDBAttributeFlags /*aAttributeFlags*/, RArray<TUint32>& aIds)
+/*
+Load all records of this type
+When re-loading a record set, all data will be overwritten with the current data from the database
+// KErrNotFound
+// KErrPermissionDenied
+
+@internalComponent
+*/
+ {
+ if (!iTarget)
+ {
+ User::Leave(KErrNotReady);
+ }
+
+ // just a check. Should not be empty
+ if ( aIds.Count() == 0)
+ {
+ return KErrNotFound;
+ }
+
+ TInt i(0);
+
+ TUint32 idMask = KCDMaskShowType | KCDMaskShowRecordId | KCDMaskShowAttributes;
+
+ //TUint32 idMask = KCDMaskShowType | KCDMaskShowRecordId | (~aAttributeFlags & KCDMaskShowAttributes);
+
+ if ( iTarget->Count() == 0 )
+ {
+ for ( i = 0; i < aIds.Count(); i++ )
+ {
+ // Don't want to show the column id here or any attributes that shouldn't be visible
+ TUint32 id = aIds[i] & idMask;
+ if ( id != 0 &&
+ (id & KCDMaskShowRecordId) != KCDMaskShowRecordId )
+ {
+ // create each record and load it
+ CMDBRecordBase* record = CCDRecordBase::RecordFactoryL(id & ~KCDMaskShowFieldType);
+ CleanupStack::PushL(record);
+ record->LoadL(aSession->iOwner);
+ iTarget->AppendL(record);
+ CleanupStack::Pop(record);
+ }
+ }
+ }
+ else
+ {
+ if ((*iTarget)[0])
+ {
+ (*iTarget)[0]->SetElementId(aIds[0] & idMask);
+ }
+
+ for (i = 0; i < iTarget->Count(); i++)
+ {
+ if( (*iTarget)[i] )
+ {
+ // Check each Target record is included in the list of found ids
+ TInt loc = aIds.Find((*iTarget)[i]->ElementId());
+
+ if ( loc >= 0 )
+ {
+ // refresh any record that is in the aIds list
+ (*iTarget)[i]->LoadL(aSession->iOwner);
+ aIds.Remove(loc);
+ }
+
+ if ( loc < 0 )
+ {
+ // remove any record that is not in the aIds list
+ // __FLOG_STATIC2(KLogComponent, KCDErrLog, _L("MMetaDBVisitor::LoadL(). deleting record %08x after err %d"), (*iTarget)[i].ElementId(), err);
+
+ delete (*iTarget)[i];
+ iTarget->Remove(i);
+ --i;
+ }
+ }
+ else
+ {
+ // target record already null so just remove it
+ iTarget->Remove(i); // record already null so remove it.
+ --i;
+ }
+ }
+
+
+ // add any remaining new records left in the approved aIds list to the target container
+ for (i = 0; i < aIds.Count(); i++)
+ {
+ CMDBRecordBase* newRecord = CCDRecordBase::RecordFactoryL(aIds[i] & idMask);
+ CleanupStack::PushL(newRecord);
+ newRecord->LoadL(aSession->iOwner);
+ iTarget->AppendL(newRecord);
+ CleanupStack::Pop(newRecord);
+ }
+ }
+
+ if(iTarget->Count()==0)
+ {
+ //We did not leave with KErrNotFound till now beacuse of hidden records
+ //We now have to leave with KErrNotFound as we have no records at all to give back
+ User::Leave(KErrNotFound);
+ }
+ return KErrNone;
+ }
+
+
+
+TInt CommsDat::TMDBRecordSetVisitor::FindL(CMDBSessionImpl* aSession, RArray<TUint32>& aMatchingIds)
+/*
+Load all requested fields that match any instantiated values
+
+// KErrNotFound
+/
+@internalComponent
+*/
+ {
+ // Finding must be done at this level - can't hand off work to records
+
+ TInt retval = KErrNone;
+
+ if ( iTarget->Count() == 0 )
+ {
+ return KErrNotFound;
+ }
+
+ RArray<TUint32> candidates;
+ CleanupClosePushL(candidates);
+
+ // Try to find one or more matches in depth-first search
+ // assumption is that depth will be v short
+
+ // Act on the first record's data table, not your own.
+ DoFindL(*aSession, *((*iTarget)[0]), retval, candidates, aMatchingIds);
+
+ if ( ! aMatchingIds.Count())
+ {
+ retval = KErrNotFound;
+ }
+
+ CleanupStack::PopAndDestroy(&candidates);
+
+ return retval;
+ }
+
+
+
+void CommsDat::TMDBRecordSetVisitor::DoFindL(CMDBSessionImpl& aSession, CMDBElement& aElement, TInt& aErr, RArray<TUint32>& aCandidates, RArray<TUint32>& aMatches)
+ {
+ SVDataTableEntry const* entry = NULL;
+ TMDBVisitorBase* metaDBVisitor = NULL;
+ TAny* mem[KMMetaDBVisitorMaxSize];
+
+ TMetaVTableIterator attribIter(&aElement);
+
+ while ( aErr == KErrNone && (entry = attribIter++) != NULL )
+ {
+ metaDBVisitor = static_cast<TMDBVisitorBase*>(entry->iMetaNewL(mem,aElement.GetAttribPtr(entry->iOffset))); // target
+
+ if (metaDBVisitor)
+ {
+ metaDBVisitor->SetOwner(&aElement);
+
+ if ( metaDBVisitor->Changed() )
+ {
+ aErr = metaDBVisitor->FindL(&aSession, aCandidates);
+
+ if (aErr == KErrNone )
+ {
+ aErr = aSession.FindMatchL(aCandidates, aMatches, KCDMaskShowFieldType);
+ }
+ }
+ }
+ }
+ }
+
+
+
+TInt CommsDat::TMDBRecordSetVisitor::RefreshL(CMDBSessionImpl* aSession)
+/*
+Update existing records
+Do not add new records
+Destroy deleted records only if they have not been changed at all.- but log the error
+// KErrNotFound
+// KErrPermissionDenied
+
+@internalComponent
+*/
+ {
+ for (TInt i = 0; i < iTarget->Count(); i++)
+ {
+ if((*iTarget)[i])
+ {
+ (*iTarget)[i]->RefreshL(aSession->iOwner);
+ }
+ }
+
+ return KErrNone;
+ }
+
+
+
+
+TInt CommsDat::TMDBRecordSetVisitor::StoreL(CMDBSessionImpl* aSession, TMDBElementId /*aRecordId*/, TMDBAttributeFlags /*aAttributeFlags*/)
+/*
+Create new records in the repository
+Will Leave on failure with the following specific errors (and KErrNoMemory etc)
+Stores always done in a batch and will
+// KErrPermissionDenied
+// KErrAlreadyExists
+
+@internalComponent
+*/
+ {
+ for (TInt i = 0; i < iTarget->Count(); i++)
+ {
+ if((*iTarget)[i])
+ {
+ (*iTarget)[i]->StoreL(aSession->iOwner);
+ }
+ }
+
+ return KErrNone;
+ }
+
+
+
+TInt CommsDat::TMDBRecordSetVisitor::ModifyL(CMDBSessionImpl* aSession, TMDBAttributeFlags /*aAttributeFlags*/)
+/*
+Modify all changed fields in the store
+May return
+ KErrPermissionDenied
+ KErrNotFound
+*/
+ {
+ for (TInt i = 0; i < iTarget->Count(); i++)
+ {
+ if((*iTarget)[i])
+ {
+ (*iTarget)[i]->ModifyL(aSession->iOwner);
+ }
+ }
+
+ return KErrNone;
+ }
+
+
+//EOF