publicclassADALTokenCache : TokenCache
{
privateApplicationDbContextdb = newApplicationDbContext();
privatestringuserId;
privateUserTokenCacheCache;
publicADALTokenCache(stringsignedInUserId)
{
// associate the cache to the current user of the web app
userId = signedInUserId;
this.AfterAccess = AfterAccessNotification;
this.BeforeAccess = BeforeAccessNotification;
this.BeforeWrite = BeforeWriteNotification;
// look up the entry in the database
Cache = db.UserTokenCacheList.FirstOrDefault(c => c.webUserUniqueId == userId);
// place the entry in memorythis.Deserialize((Cache == null) ? null : MachineKey.Unprotect(Cache.cacheBits,"ADALCache"));
}
// clean up the databasepublicoverridevoidClear()
{
base.Clear();
varcacheEntry = db.UserTokenCacheList.FirstOrDefault(c => c.webUserUniqueId == userId);
db.UserTokenCacheList.Remove(cacheEntry);
db.SaveChanges();
}
// Notification raised before ADAL accesses the cache.// This is your chance to update the in-memory copy from the DB, if the in-memory version is stalevoidBeforeAccessNotification(TokenCacheNotificationArgsargs)
{
if (Cache == null)
{
// first time access
Cache = db.UserTokenCacheList.FirstOrDefault(c => c.webUserUniqueId == userId);
}
else
{
// retrieve last write from the DBvarstatus = from e in db.UserTokenCacheList
where (e.webUserUniqueId == userId)
selectnew
{
LastWrite = e.LastWrite
};
// if the in-memory copy is older than the persistent copyif (status.First().LastWrite > Cache.LastWrite)
{
// read fromfrom storage, update in-memory copy
Cache = db.UserTokenCacheList.FirstOrDefault(c => c.webUserUniqueId == userId);
}
}
this.Deserialize((Cache == null) ? null : MachineKey.Unprotect(Cache.cacheBits, "ADALCache"));
}
// Notification raised after ADAL accessed the cache.// If the HasStateChanged flag is set, ADAL changed the content of the cachevoidAfterAccessNotification(TokenCacheNotificationArgsargs)
{
// if state changedif (this.HasStateChanged)
{
if (Cache == null)
{
Cache = newUserTokenCache
{
webUserUniqueId = userId
};
}
Cache.cacheBits = MachineKey.Protect(this.Serialize(), "ADALCache");
Cache.LastWrite = DateTime.Now;
// update the DB and the lastwrite
db.Entry(Cache).State = Cache.UserTokenCacheId == 0 ? EntityState.Added : EntityState.Modified;
db.SaveChanges();
this.HasStateChanged = false;
}
}
voidBeforeWriteNotification(TokenCacheNotificationArgsargs)
{
// if you want to ensure that no concurrent write take place, use this notification to place a lock on the entry
}
publicoverridevoidDeleteItem(TokenCacheItemitem)
{
base.DeleteItem(item);
}
}