os/persistentdata/persistentstorage/centralrepository/cenrepnotifierhandler/src/cenrepnotifyhandler.cpp
First public contribution.
1 // Copyright (c) 2004-2009 Nokia Corporation and/or its subsidiary(-ies).
2 // All rights reserved.
3 // This component and the accompanying materials are made available
4 // under the terms of "Eclipse Public License v1.0"
5 // which accompanies this distribution, and is available
6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
8 // Initial Contributors:
9 // Nokia Corporation - initial contribution.
21 #include <centralrepository.h>
22 #include "cenrepnotifyhandler.h"
24 // ============================ MEMBER FUNCTIONS ===============================
27 * Constructor used for single key listening.
29 * @param aCallback Reference to a callback instance.
30 * @param aSession Reference to an existing repository session.
31 * @param aKeyType Type of the key identified by aId parameter.
32 * @param aId Id of the key that change notifications are needed for.
35 CCenRepNotifyHandler::CCenRepNotifyHandler(
36 MCenRepNotifyHandlerCallback& aCallback,
37 CRepository& aSession,
38 TCenRepKeyType aKeyType,
40 : CActive(EPriorityStandard), iSession(aSession),
41 iCallback(aCallback), iKeyType(aKeyType), iId(aId), iWholeRepository(EFalse)
43 CActiveScheduler::Add(this);
47 * Constructor used for whole repository listening.
49 * @param aCallback Reference to a callback instance.
50 * @param aSession Reference to an existing repository session.
53 CCenRepNotifyHandler::CCenRepNotifyHandler(
54 MCenRepNotifyHandlerCallback& aCallback,
55 CRepository& aSession)
56 : CActive(EPriorityStandard), iSession(aSession), iCallback(aCallback),
57 iKeyType(EIntKey), iId(0), iWholeRepository(ETrue)
59 CActiveScheduler::Add(this);
63 * This is a two-phase constructor method that is used to
64 * create a new instance for listening to the changes in a single key.
66 * @param aCallback Reference to a callback instance.
67 * @param aSession Reference to an existing repository session.
68 * Do not close this session until all CCenRepNotifyHandler
69 * instances referring to it have been deleted.
70 * @param aKeyType Type of the key identified by aId parameter.
71 * @param aId Id of the key that change notifications are needed for.
72 * @return A pointer to a new instance of the CCenRepNotifyHandler class.
74 * @leave KErrArgument if invalid key type is passed as a parameter.
77 EXPORT_C CCenRepNotifyHandler* CCenRepNotifyHandler::NewL(
78 MCenRepNotifyHandlerCallback& aCallback,
79 CRepository& aSession,
80 TCenRepKeyType aKeyType,
83 CCenRepNotifyHandler* newInstance = NewLC(aCallback, aSession, aKeyType, aId);
89 * This is a two-phase constructor method that is used to create a new
90 * instance for listening to the changes in all keys in the repository.
92 * Type specific callback methods of MCenRepNotifyHandlerCallback will not
93 * be used when notifying about changes in this case,
94 * only HandleNotifyGeneric() is used.
96 * @param aCallback Reference to a callback instance.
97 * @param aSession Reference to an existing repository session.
98 * Do not close this session until all CCenRepNotifyHandler
99 * instances referring to it have been deleted.
100 * @return A pointer to a new instance of the CCenRepNotifyHandler class.
103 EXPORT_C CCenRepNotifyHandler* CCenRepNotifyHandler::NewL(
104 MCenRepNotifyHandlerCallback& aCallback,
105 CRepository& aSession)
107 CCenRepNotifyHandler* newInstance = NewLC(aCallback, aSession);
113 * This is a two-phase constructor method that is used to create a new
114 * instance for listening to the changes in a single key.
115 * Leaves the constructed instance to cleanup stack.
117 * @param aCallback Reference to a callback instance.
118 * @param aSession Reference to an existing repository session.
119 * Do not close this session until all CCenRepNotifyHandler
120 * instances referring to it have been deleted.
121 * @param aKeyType Type of the key identified by aId parameter.
122 * @param aId Id of the key that change notifications are needed for.
123 * @return A pointer to a new instance of the CCenRepNotifyHandler class.
125 * @leave KErrArgument if invalid key type is passed as a parameter.
128 EXPORT_C CCenRepNotifyHandler* CCenRepNotifyHandler::NewLC(
129 MCenRepNotifyHandlerCallback& aCallback,
130 CRepository& aSession,
131 TCenRepKeyType aKeyType,
134 if ( aKeyType != EIntKey &&
135 aKeyType != ERealKey &&
136 aKeyType != EStringKey &&
137 aKeyType != EBinaryKey )
139 User::Leave( KErrArgument );
142 CCenRepNotifyHandler* newInstance = new (ELeave) CCenRepNotifyHandler( aCallback, aSession,
144 CleanupStack::PushL( newInstance );
149 * This is a two-phase constructor method that is used to create a new
150 * instance for listening to the changes in all keys in the repository.
151 * Leaves the constructed instance to cleanup stack.
153 * Type specific callback methods of MCenRepNotifyHandlerCallback will
154 * not be used when notifying about changes in this case,
155 * only HandleNotifyGeneric() is used.
157 * @param aCallback Reference to a callback instance.
158 * @param aSession Reference to an existing repository session.
159 * Do not close this session until all CCenRepNotifyHandler
160 * instances referring to it have been deleted.
161 * @return A pointer to a new instance of the CCenRepNotifyHandler class.
164 EXPORT_C CCenRepNotifyHandler* CCenRepNotifyHandler::NewLC(
165 MCenRepNotifyHandlerCallback& aCallback,
166 CRepository& aSession)
168 CCenRepNotifyHandler* newInstance = new (ELeave) CCenRepNotifyHandler(aCallback, aSession);
169 CleanupStack::PushL( newInstance );
175 EXPORT_C CCenRepNotifyHandler::~CCenRepNotifyHandler()
181 * When this method is called, the CCenRepNotifyHandler starts
182 * listening for notifications. If it is already listening, nothing happens.
184 * For single setting handler when there is already an existing notification
185 * on the same setting and session,the HandleNotifyError will be trigerred with
186 * KErrAlreadyExists error
187 * @leave KErrNotFound if setting does not exist
188 * KErrPermissionDenied if client does not have the necessary capability
189 * plus other system-wide error codes.
190 * For whole settings handler, the HandleNotifyError will be trigerred with the
192 * @capability Dependent Capability required depends on platform security of keyspace.
194 EXPORT_C void CCenRepNotifyHandler::StartListeningL()
200 User::LeaveIfError(OrderNotification());
206 * When this method is called, the CCenRepNotifyHandler stops
207 * listening for notifications. If it is already stopped, nothing happens.
210 EXPORT_C void CCenRepNotifyHandler::StopListening()
221 void CCenRepNotifyHandler::RunL()
223 // Check that notification was for correct ID or it was caused by
224 // a repository wide reset (KInvalidNotificationId).
225 TUint32 status = static_cast<TUint32>(iStatus.Int());
226 if( !iWholeRepository && status != iId &&
227 status != NCentralRepositoryConstants::KInvalidNotificationId )
230 RDebug::Print(_L("CCenRepNotifyHandler::RunL(): Received notif about unknown key: %d"),
232 RDebug::Print(_L("CCenRepNotifyHandler::RunL(): Notification not renewed."));
234 // We are not listening to key notified for us. Do not reorder notification
235 // as there is clearly some problems in central repository.
236 iCallback.HandleNotifyError(status, KErrArgument, this);
240 if (iWholeRepository && iStatus.Int() == KErrPermissionDenied)
243 RArray<TUint32> allKeyList;
244 //check every single settings that we have read permission
245 TRAPD(err,iSession.FindL(0x00000000,0x00000000,allKeyList));
248 TInt arrayCount=allKeyList.Count();
249 for (TInt i=0;i<arrayCount;i++)
252 err=iSession.GetMeta(allKeyList[i],dummyMeta);
253 //potential error at this stage likely to include only
254 //KErrPermissionDenied plus other resource allocation
255 //error such as KErrNoMemory
258 TInt errorkey=allKeyList[i];
260 iCallback.HandleNotifyError(errorkey, err, this);
267 iCallback.HandleNotifyError( NCentralRepositoryConstants::KUnspecifiedKey , err, this );
272 // Reorder notification
273 TInt err = OrderNotification();
275 // Handle notification
276 if ( err == KErrNone )
279 if ( iWholeRepository )
281 iCallback.HandleNotifyGeneric(status);
290 err=iSession.Get(iId, newValue);
293 iCallback.HandleNotifyInt(iId, newValue);
300 err=iSession.Get(iId, newValue);
303 iCallback.HandleNotifyReal(iId, newValue);
309 TBuf16<NCentralRepositoryConstants::KMaxUnicodeStringLength> newValue;
310 err=iSession.Get(iId, newValue);
313 iCallback.HandleNotifyString(iId, newValue);
319 TBuf8<NCentralRepositoryConstants::KMaxBinaryLength> newValue;
320 err=iSession.Get(iId, newValue);
323 iCallback.HandleNotifyBinary(iId, newValue);
332 iCallback.HandleNotifyError(iId,err,this);
338 iCallback.HandleNotifyError(status, err, this);
344 * @param aError the error returned
347 TInt CCenRepNotifyHandler::RunError(TInt aError)
349 if ( iWholeRepository )
351 iCallback.HandleNotifyError(NCentralRepositoryConstants::KInvalidNotificationId,
356 iCallback.HandleNotifyError(iId, aError, this);
365 void CCenRepNotifyHandler::DoCancel()
367 if ( iWholeRepository )
369 iSession.NotifyCancelAll();
373 iSession.NotifyCancel(iId);
379 * @return error code from CenRep
381 TInt CCenRepNotifyHandler::OrderNotification()
383 if ( iWholeRepository )
385 // order notification for all keys in repository
386 return iSession.NotifyRequest(0x00000000, 0x00000000, iStatus);
390 return iSession.NotifyRequest(iId, iStatus);
394 // -----------------------------------------------------------------------------
395 // MCenRepNotifyHandlerCallback::HandleNotifyXXX
396 // Default implementations for callback interface.
397 // In debug build these methods print trace.
398 // In release build they do nothing.
400 // These methods are documented in cenrepnotifierhandler.h. Don't redocument
402 // -----------------------------------------------------------------------------
405 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyInt(TUint32 aId, TInt aNewValue)
407 RDebug::Print(_L("MCenRepNotifyHandlerCallback: Integer key %d changed, new value: %d"),
411 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyReal(TUint32 aId, TReal aNewValue)
413 RDebug::Print(_L("MCenRepNotifyHandlerCallback: Real key %d changed, new value: %e"),
417 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyString(TUint32 aId,
418 const TDesC16& aNewValue)
420 RDebug::Print(_L("MCenRepNotifyHandlerCallback: String key %d changed, new value: %S"),
424 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyBinary(TUint32 aId,
425 const TDesC8& aNewValue)
427 RDebug::Print(_L("MCenRepNotifyHandlerCallback: Binary key %d changed, new value: %s"),
428 aId, aNewValue.Ptr());
431 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyGeneric(TUint32 aId)
433 if ( aId == NCentralRepositoryConstants::KInvalidNotificationId )
435 RDebug::Print(_L("MCenRepNotifyHandlerCallback: "));
436 RDebug::Print(_L("Repository wide reset caused generic notification"));
440 RDebug::Print(_L("MCenRepNotifyHandlerCallback: Generic key %d changed"), aId);
444 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyError(TUint32 aId, TInt aError,
445 CCenRepNotifyHandler* aHandler)
447 RDebug::Print(_L("MCenRepNotifyHandlerCallback %d notifies error for id: %d, error: %d"),
448 aHandler, aId, aError);
453 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyInt(TUint32 /*aId*/, TInt /*aNewValue*/)
457 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyReal(TUint32 /*aId*/, TReal /*aNewValue*/)
461 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyString(TUint32 /*aId*/,
462 const TDesC16& /*aNewValue*/)
466 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyBinary(TUint32 /*aId*/,
467 const TDesC8& /*aNewValue*/)
471 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyGeneric(TUint32 /*aId*/)
475 EXPORT_C void MCenRepNotifyHandlerCallback::HandleNotifyError(TUint32 /*aId*/, TInt /*aError*/,
476 CCenRepNotifyHandler* /*aHandler*/)