Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion src/FileCache/FileCache.cs
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,11 @@ public enum PayloadMode
/// <summary>
/// Treat the paylad as raw bytes. A byte[] and readable streams are supported on add.
/// </summary>
RawBytes
RawBytes,
/// <summary>
/// Treat the payload as a crypto serializable object.
/// </summary>
CryptoSerializable,
}

/// <summary>
Expand Down
70 changes: 70 additions & 0 deletions src/FileCache/FileCacheManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
using System.Reflection;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Binary;
using System.Security.Cryptography;
using System.Text;
using System.Threading;

Expand All @@ -21,6 +22,7 @@ public abstract class FileCacheManager
public string CacheSubFolder { get; set; }
public string PolicySubFolder { get; set; }
public SerializationBinder Binder { get; set; }
public string CryptoKey { get; set; }

/// <summary>
/// Used to determine how long the FileCache will wait for a file to become
Expand Down Expand Up @@ -151,6 +153,9 @@ public virtual FileCachePayload ReadFile(FileCache.PayloadMode mode, string key,
case FileCache.PayloadMode.RawBytes:
payload.Payload = LoadRawPayloadData(cachePath);
break;
case FileCache.PayloadMode.CryptoSerializable:
payload.Payload = DeserializeCrypto(cachePath);
break;
default:
throw new ArgumentOutOfRangeException(nameof(mode), mode, null);
}
Expand Down Expand Up @@ -222,6 +227,54 @@ protected virtual object Deserialize(string fileName, SerializationBinder object
}
return data;
}
protected virtual object DeserializeCrypto(string fileName, SerializationBinder objectBinder = null)
{
object data = null;
if (File.Exists(fileName))
{
AesCryptoServiceProvider aes = new AesCryptoServiceProvider();
MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider();
SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider();
byte[] aeskey = sha256.ComputeHash(Encoding.UTF8.GetBytes(CryptoKey));
byte[] aesiv = md5.ComputeHash(Encoding.UTF8.GetBytes(CryptoKey));
aes.Key = aeskey;
aes.IV = aesiv;

using (FileStream stream = GetStream(fileName, FileMode.Open, FileAccess.Read, FileShare.Read))
{
using (Stream cryptoStream = new CryptoStream(stream, aes.CreateDecryptor(), CryptoStreamMode.Read))
{
BinaryFormatter formatter = new BinaryFormatter();

//AC: From http://spazzarama.com//2009/06/25/binary-deserialize-unable-to-find-assembly/
// Needed to deserialize custom objects
if (objectBinder != null)
{
//take supplied binder over default binder
formatter.Binder = objectBinder;
}
else if (Binder != null)
{
formatter.Binder = Binder;
}
try
{
data = formatter.Deserialize(cryptoStream);
}
catch (SerializationException)
{
data = null;
}
finally
{
cryptoStream.Close();
stream.Close();
}
}
}
}
return data;
}

/// <summary>
/// This function serves to centralize file writes within this class
Expand Down Expand Up @@ -276,6 +329,23 @@ public virtual long WriteFile(FileCache.PayloadMode mode, string key, FileCacheP
case FileCache.PayloadMode.Filename:
File.Copy((string)data.Payload, cachedItemPath, true);
break;
case FileCache.PayloadMode.CryptoSerializable:
AesCryptoServiceProvider aes = new AesCryptoServiceProvider();
MD5CryptoServiceProvider md5 = new MD5CryptoServiceProvider();
SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider();
byte[] aeskey = sha256.ComputeHash(Encoding.UTF8.GetBytes(CryptoKey));
byte[] aesiv = md5.ComputeHash(Encoding.UTF8.GetBytes(CryptoKey));
aes.Key = aeskey;
aes.IV = aesiv;
using (FileStream stream = GetStream(cachedItemPath, FileMode.Create, FileAccess.Write, FileShare.None))
{
using (CryptoStream cryptoStream = new CryptoStream(stream, aes.CreateEncryptor(), CryptoStreamMode.Write))
{
BinaryFormatter formatter = new BinaryFormatter();
formatter.Serialize(cryptoStream, data.Payload);
}
}
break;
}

//adjust cache size (while we have the file to ourselves)
Expand Down