diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/App.config b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/App.config
new file mode 100644
index 000000000..f6da346b3
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/App.config
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/BlobGettingStarted.csproj b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/BlobGettingStarted.csproj
new file mode 100644
index 000000000..dcb4b211b
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/BlobGettingStarted.csproj
@@ -0,0 +1,140 @@
+
+
+
+
+ Debug
+ AnyCPU
+ {6DFB68F9-ECAC-4105-95A7-0A51B840A691}
+ Exe
+ Properties
+ BlobGettingStarted
+ BlobGettingStarted
+ v4.5
+ 512
+
+
+ AnyCPU
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ AnyCPU
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+ ..\packages\Hyak.Common.1.0.2\lib\net45\Hyak.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.NetFramework.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Core.0.9.1-preview\lib\net40\Microsoft.Azure.KeyVault.Core.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Extensions.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Edm.5.6.2\lib\net40\Microsoft.Data.Edm.dll
+ True
+
+
+ ..\packages\Microsoft.Data.OData.5.6.2\lib\net40\Microsoft.Data.OData.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Services.Client.5.6.2\lib\net40\Microsoft.Data.Services.Client.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.Desktop.dll
+ True
+
+
+ ..\packages\Microsoft.WindowsAzure.ConfigurationManager.1.8.0.0\lib\net35-full\Microsoft.WindowsAzure.Configuration.dll
+ True
+
+
+ ..\packages\WindowsAzure.Storage.4.4.0-preview\lib\net40\Microsoft.WindowsAzure.Storage.dll
+ True
+
+
+ ..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll
+ True
+
+
+
+
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Primitives.dll
+ True
+
+
+
+ ..\packages\System.Spatial.5.6.2\lib\net40\System.Spatial.dll
+ True
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/LocalResolver.cs b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/LocalResolver.cs
new file mode 100644
index 000000000..2d3a03b3e
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/LocalResolver.cs
@@ -0,0 +1,42 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace BlobGettingStarted
+{
+ using Microsoft.Azure.KeyVault.Core;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
+
+ public class LocalResolver : IKeyResolver
+ {
+ private Dictionary keys = new Dictionary();
+
+ public void Add(IKey key)
+ {
+ keys[key.Kid] = key;
+ }
+
+ public async Task ResolveKeyAsync(string kid, CancellationToken token)
+ {
+ IKey result;
+
+ keys.TryGetValue(kid, out result);
+
+ return await Task.FromResult(result);
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Program.cs b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Program.cs
new file mode 100644
index 000000000..98cb46acc
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Program.cs
@@ -0,0 +1,122 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace BlobGettingStarted
+{
+ using Microsoft.Azure.KeyVault;
+ using Microsoft.Azure.KeyVault.Core;
+ using Microsoft.WindowsAzure;
+ using Microsoft.WindowsAzure.Storage;
+ using Microsoft.WindowsAzure.Storage.Blob;
+ using System;
+ using System.IO;
+ using System.Security.Cryptography;
+
+ ///
+ /// Demonstrates how to use encryption with the Azure Blob service.
+ ///
+ public class Program
+ {
+ const string DemoContainer = "democontainer";
+
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Blob encryption sample");
+
+ // Retrieve storage account information from connection string
+ // How to create a storage connection string - http://msdn.microsoft.com/en-us/library/azure/ee758697.aspx
+ CloudStorageAccount storageAccount = CreateStorageAccountFromConnectionString(CloudConfigurationManager.GetSetting("StorageConnectionString"));
+ CloudBlobClient client = storageAccount.CreateCloudBlobClient();
+ CloudBlobContainer container = client.GetContainerReference(DemoContainer + Guid.NewGuid().ToString("N"));
+
+ try
+ {
+ container.Create();
+ int size = 5 * 1024 * 1024;
+ byte[] buffer = new byte[size];
+
+ Random rand = new Random();
+ rand.NextBytes(buffer);
+
+ CloudBlockBlob blob = container.GetBlockBlobReference("blockblob");
+
+ // Create the IKey used for encryption.
+ RsaKey key = new RsaKey("private:key1");
+
+ // Create the encryption policy to be used for upload.
+ BlobEncryptionPolicy uploadPolicy = new BlobEncryptionPolicy(key, null);
+
+ // Set the encryption policy on the request options.
+ BlobRequestOptions uploadOptions = new BlobRequestOptions() { EncryptionPolicy = uploadPolicy };
+
+ Console.WriteLine("Uploading the encrypted blob.");
+
+ // Upload the encrypted contents to the blob.
+ using (MemoryStream stream = new MemoryStream(buffer))
+ {
+ blob.UploadFromStream(stream, size, null, uploadOptions, null);
+ }
+
+ // Download the encrypted blob.
+ // For downloads, a resolver can be set up that will help pick the key based on the key id.
+ LocalResolver resolver = new LocalResolver();
+ resolver.Add(key);
+
+ BlobEncryptionPolicy downloadPolicy = new BlobEncryptionPolicy(null, resolver);
+
+ // Set the decryption policy on the request options.
+ BlobRequestOptions downloadOptions = new BlobRequestOptions() { EncryptionPolicy = downloadPolicy };
+
+ Console.WriteLine("Downloading the encrypted blob.");
+
+ // Download and decrypt the encrypted contents from the blob.
+ using (MemoryStream outputStream = new MemoryStream())
+ {
+ blob.DownloadToStream(outputStream, null, downloadOptions, null);
+ }
+
+ Console.WriteLine("Press enter key to exit");
+ Console.ReadLine();
+ }
+ finally
+ {
+ container.DeleteIfExists();
+ }
+ }
+
+ private static CloudStorageAccount CreateStorageAccountFromConnectionString(string storageConnectionString)
+ {
+ CloudStorageAccount storageAccount;
+ try
+ {
+ storageAccount = CloudStorageAccount.Parse(storageConnectionString);
+ }
+ catch (FormatException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+ catch (ArgumentException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+
+ return storageAccount;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Properties/AssemblyInfo.cs b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Properties/AssemblyInfo.cs
new file mode 100644
index 000000000..0d4b4b6d0
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("BlobGettingStarted")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("BlobGettingStarted")]
+[assembly: AssemblyCopyright("Copyright © 2015")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("66d06292-516c-41b4-9041-aa94b8115119")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/packages.config b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/packages.config
new file mode 100644
index 000000000..2133f779f
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/BlobGettingStarted/packages.config
@@ -0,0 +1,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/GettingStartedSamples.sln b/Samples/GettingStarted/EncryptionSamples/GettingStartedSamples.sln
new file mode 100644
index 000000000..91d872789
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/GettingStartedSamples.sln
@@ -0,0 +1,46 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio 2013
+VisualStudioVersion = 12.0.31101.0
+MinimumVisualStudioVersion = 10.0.40219.1
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "QueueGettingStarted", "QueueGettingStarted\QueueGettingStarted.csproj", "{96209F76-E19B-426E-8C02-6CE26B6187C9}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TableGettingStartedUsingResolver", "TableGettingStarted\TableGettingStartedUsingResolver.csproj", "{449D75A7-140A-495A-B35A-9B056095F571}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "BlobGettingStarted", "BlobGettingStarted\BlobGettingStarted.csproj", "{6DFB68F9-ECAC-4105-95A7-0A51B840A691}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "KVGettingStarted", "KVGettingStarted\KVGettingStarted.csproj", "{AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}"
+EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TableGettingStartedUsingAttributes", "TableGettingStartedUsingAttributes\TableGettingStartedUsingAttributes.csproj", "{804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}"
+EndProject
+Global
+ GlobalSection(SolutionConfigurationPlatforms) = preSolution
+ Debug|Any CPU = Debug|Any CPU
+ Release|Any CPU = Release|Any CPU
+ EndGlobalSection
+ GlobalSection(ProjectConfigurationPlatforms) = postSolution
+ {96209F76-E19B-426E-8C02-6CE26B6187C9}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {96209F76-E19B-426E-8C02-6CE26B6187C9}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {96209F76-E19B-426E-8C02-6CE26B6187C9}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {96209F76-E19B-426E-8C02-6CE26B6187C9}.Release|Any CPU.Build.0 = Release|Any CPU
+ {449D75A7-140A-495A-B35A-9B056095F571}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {449D75A7-140A-495A-B35A-9B056095F571}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {449D75A7-140A-495A-B35A-9B056095F571}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {449D75A7-140A-495A-B35A-9B056095F571}.Release|Any CPU.Build.0 = Release|Any CPU
+ {6DFB68F9-ECAC-4105-95A7-0A51B840A691}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {6DFB68F9-ECAC-4105-95A7-0A51B840A691}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {6DFB68F9-ECAC-4105-95A7-0A51B840A691}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {6DFB68F9-ECAC-4105-95A7-0A51B840A691}.Release|Any CPU.Build.0 = Release|Any CPU
+ {AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}.Release|Any CPU.Build.0 = Release|Any CPU
+ {804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}.Release|Any CPU.Build.0 = Release|Any CPU
+ EndGlobalSection
+ GlobalSection(SolutionProperties) = preSolution
+ HideSolutionNode = FALSE
+ EndGlobalSection
+EndGlobal
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/App.config b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/App.config
new file mode 100644
index 000000000..dedb150a2
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/App.config
@@ -0,0 +1,15 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/KVGettingStarted.csproj b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/KVGettingStarted.csproj
new file mode 100644
index 000000000..fe4b7d00f
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/KVGettingStarted.csproj
@@ -0,0 +1,148 @@
+
+
+
+
+ Debug
+ AnyCPU
+ {AB26C6E1-1375-45FD-BF32-4FAE7FFF078A}
+ Exe
+ Properties
+ KVGettingStarted
+ KVGettingStarted
+ v4.5
+ 512
+
+
+ AnyCPU
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ AnyCPU
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+ ..\packages\Hyak.Common.1.0.2\lib\net45\Hyak.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.NetFramework.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Core.0.9.1-preview\lib\net40\Microsoft.Azure.KeyVault.Core.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Extensions.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Edm.5.6.2\lib\net40\Microsoft.Data.Edm.dll
+ True
+
+
+ ..\packages\Microsoft.Data.OData.5.6.2\lib\net40\Microsoft.Data.OData.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Services.Client.5.6.2\lib\net40\Microsoft.Data.Services.Client.dll
+ True
+
+
+ ..\packages\Microsoft.IdentityModel.Clients.ActiveDirectory.2.16.204221202\lib\net45\Microsoft.IdentityModel.Clients.ActiveDirectory.dll
+ True
+
+
+ ..\packages\Microsoft.IdentityModel.Clients.ActiveDirectory.2.16.204221202\lib\net45\Microsoft.IdentityModel.Clients.ActiveDirectory.WindowsForms.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.Desktop.dll
+ True
+
+
+ ..\packages\Microsoft.WindowsAzure.ConfigurationManager.1.8.0.0\lib\net35-full\Microsoft.WindowsAzure.Configuration.dll
+ True
+
+
+ ..\packages\WindowsAzure.Storage.4.4.0-preview\lib\net40\Microsoft.WindowsAzure.Storage.dll
+ True
+
+
+ ..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll
+ True
+
+
+
+
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Primitives.dll
+ True
+
+
+
+ ..\packages\System.Spatial.5.6.2\lib\net40\System.Spatial.dll
+ True
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/LocalResolver.cs b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/LocalResolver.cs
new file mode 100644
index 000000000..27c34063b
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/LocalResolver.cs
@@ -0,0 +1,42 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace KVGettingStarted
+{
+ using Microsoft.Azure.KeyVault.Core;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
+
+ public class LocalResolver : IKeyResolver
+ {
+ private Dictionary keys = new Dictionary();
+
+ public void Add(IKey key)
+ {
+ keys[key.Kid] = key;
+ }
+
+ public async Task ResolveKeyAsync(string kid, CancellationToken token)
+ {
+ IKey result;
+
+ keys.TryGetValue(kid, out result);
+
+ return await Task.FromResult(result);
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Program.cs b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Program.cs
new file mode 100644
index 000000000..cb8ca10bd
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Program.cs
@@ -0,0 +1,189 @@
+using Microsoft.Azure.KeyVault;
+using Microsoft.Azure.KeyVault.Core;
+using Microsoft.IdentityModel.Clients.ActiveDirectory;
+using Microsoft.WindowsAzure;
+using Microsoft.WindowsAzure.Storage;
+using Microsoft.WindowsAzure.Storage.Blob;
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Text;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace KVGettingStarted
+{
+ ///
+ /// Demonstrates how to use encryption along with Azure Key Vault integration for the Azure Blob service.
+ ///
+ public class Program
+ {
+ const string DemoContainer = "democontainer";
+
+ static async Task GetAccessToken(string authority, string resource, string scope)
+ {
+ ClientCredential credential = new ClientCredential(CloudConfigurationManager.GetSetting("KVClientId"), CloudConfigurationManager.GetSetting("KVClientKey"));
+
+ AuthenticationContext ctx = new AuthenticationContext(new Uri(authority).AbsoluteUri, false);
+ AuthenticationResult result = await ctx.AcquireTokenAsync(resource, credential);
+
+ return result.AccessToken;
+ }
+
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Blob encryption with Key Vault integration");
+
+ // Retrieve storage account information from connection string
+ // How to create a storage connection string - http://msdn.microsoft.com/en-us/library/azure/ee758697.aspx
+ CloudStorageAccount storageAccount = CreateStorageAccountFromConnectionString(CloudConfigurationManager.GetSetting("StorageConnectionString"));
+ CloudBlobClient client = storageAccount.CreateCloudBlobClient();
+ CloudBlobContainer container = client.GetContainerReference(DemoContainer + Guid.NewGuid().ToString("N"));
+
+ // Get reference to a Cloud Key Vault and key resolver.
+ KeyVaultClient cloudVault = new KeyVaultClient(GetAccessToken);
+ KeyVaultKeyResolver cloudResolver = new KeyVaultKeyResolver(GetAccessToken);
+
+ // Get reference to a local key and key resolver.
+ RsaKey rsaKey = new RsaKey("rsakey");
+ LocalResolver resolver = new LocalResolver();
+ resolver.Add(rsaKey);
+
+ // If there are multiple key sources like Azure Key Vault and local KMS, set up an aggregate resolver as follows.
+ // This helps users to define a plugin model for all the different key providers they support.
+ AggregateKeyResolver aggregateResolver = new AggregateKeyResolver()
+ .Add(resolver)
+ .Add(cloudResolver);
+
+ // Set up a caching resolver so the secrets can be cached on the client. This is the recommended usage pattern since the throttling
+ // targets for Storage and Key Vault services are orders of magnitude different.
+ CachingKeyResolver cachingResolver = new CachingKeyResolver(2, aggregateResolver);
+
+ // Establish a symmetric KEK stored as a Secret in the cloud key vault
+ string vaultUri = CloudConfigurationManager.GetSetting("VaultUri");
+
+ try
+ {
+ cloudVault.DeleteSecretAsync(vaultUri, "secret").GetAwaiter().GetResult();
+ }
+ catch (KeyVaultClientException ex)
+ {
+ if (ex.Status != System.Net.HttpStatusCode.NotFound)
+ throw;
+ }
+
+ // Create a symmetric 256bit symmetric key and convert it to Base64
+ SymmetricKey symmetricKey = new SymmetricKey("secret", SymmetricKey.KeySize256);
+ string symmetricBytes = Convert.ToBase64String(symmetricKey.Key);
+
+ // Store the Base64 of the key in the key vault. This is shown inline for simplicity but
+ // the recommended approach is to create this key offline and upload it to key vault and
+ // then use secrets base identifier as a parameter to resolve the current version of the
+ // secret for encryption. Note that the content-type of the secret must
+ // be application/octet-stream or the KeyVaultKeyResolver will refuse to load it as a key.
+ Secret cloudSecret = cloudVault.SetSecretAsync(vaultUri, "secret", symmetricBytes, null, "application/octet-stream").GetAwaiter().GetResult();
+ IKey cloudKey = cachingResolver.ResolveKeyAsync(cloudSecret.SecretIdentifier.BaseIdentifier, CancellationToken.None).GetAwaiter().GetResult();
+
+ try
+ {
+ container.Create();
+ int size = 5 * 1024 * 1024;
+ byte[] buffer = new byte[size];
+
+ Random rand = new Random();
+ rand.NextBytes(buffer);
+
+ // Upload first blob using the secret stored in Azure Key Vault.
+ CloudBlockBlob blob = container.GetBlockBlobReference("blockblob1");
+
+ // Create the encryption policy using the secret stored in Azure Key Vault to be used for upload.
+ BlobEncryptionPolicy uploadPolicy = new BlobEncryptionPolicy(cloudKey, null);
+
+ // Set the encryption policy on the request options.
+ BlobRequestOptions uploadOptions = new BlobRequestOptions() { EncryptionPolicy = uploadPolicy };
+
+ Console.WriteLine("Uploading the 1st encrypted blob.");
+
+ // Upload the encrypted contents to the blob.
+ using (MemoryStream stream = new MemoryStream(buffer))
+ {
+ blob.UploadFromStream(stream, size, null, uploadOptions, null);
+ }
+
+ // Download the encrypted blob.
+ BlobEncryptionPolicy downloadPolicy = new BlobEncryptionPolicy(null, cachingResolver);
+
+ // Set the decryption policy on the request options.
+ BlobRequestOptions downloadOptions = new BlobRequestOptions() { EncryptionPolicy = downloadPolicy };
+
+ Console.WriteLine("Downloading the 1st encrypted blob.");
+
+ // Download and decrypt the encrypted contents from the blob.
+ using (MemoryStream outputStream = new MemoryStream())
+ {
+ blob.DownloadToStream(outputStream, null, downloadOptions, null);
+ }
+
+ // Upload second blob using the local key.
+ blob = container.GetBlockBlobReference("blockblob2");
+
+ // Create the encryption policy using the local key.
+ uploadPolicy = new BlobEncryptionPolicy(rsaKey, null);
+
+ // Set the encryption policy on the request options.
+ uploadOptions = new BlobRequestOptions() { EncryptionPolicy = uploadPolicy };
+
+ Console.WriteLine("Uploading the 2nd encrypted blob.");
+
+ // Upload the encrypted contents to the blob.
+ using (MemoryStream stream = new MemoryStream(buffer))
+ {
+ blob.UploadFromStream(stream, size, null, uploadOptions, null);
+ }
+
+ // Download the encrypted blob. The same policy and options created before can be used because the aggregate resolver contains both
+ // resolvers and will pick the right one based on the key id stored in blob metadata on the service.
+ Console.WriteLine("Downloading the 2nd encrypted blob.");
+
+ // Download and decrypt the encrypted contents from the blob.
+ using (MemoryStream outputStream = new MemoryStream())
+ {
+ blob.DownloadToStream(outputStream, null, downloadOptions, null);
+ }
+
+ Console.WriteLine("Press enter key to exit");
+ Console.ReadLine();
+ }
+ finally
+ {
+ container.DeleteIfExists();
+ }
+ }
+
+ private static CloudStorageAccount CreateStorageAccountFromConnectionString(string storageConnectionString)
+ {
+ CloudStorageAccount storageAccount;
+ try
+ {
+ storageAccount = CloudStorageAccount.Parse(storageConnectionString);
+ }
+ catch (FormatException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+ catch (ArgumentException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+
+ return storageAccount;
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Properties/AssemblyInfo.cs b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Properties/AssemblyInfo.cs
new file mode 100644
index 000000000..91b9d360d
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("KVGettingStarted")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("KVGettingStarted")]
+[assembly: AssemblyCopyright("Copyright © 2015")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("137f7827-64e9-4893-932a-3bb9a29909f3")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/packages.config b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/packages.config
new file mode 100644
index 000000000..618d3ced1
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/KVGettingStarted/packages.config
@@ -0,0 +1,21 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/App.config b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/App.config
new file mode 100644
index 000000000..083ba01a6
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/App.config
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/LocalResolver.cs b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/LocalResolver.cs
new file mode 100644
index 000000000..97f86dc30
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/LocalResolver.cs
@@ -0,0 +1,42 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace QueueGettingStarted
+{
+ using Microsoft.Azure.KeyVault.Core;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
+
+ public class LocalResolver : IKeyResolver
+ {
+ private Dictionary keys = new Dictionary();
+
+ public void Add(IKey key)
+ {
+ keys[key.Kid] = key;
+ }
+
+ public async Task ResolveKeyAsync(string kid, CancellationToken token)
+ {
+ IKey result;
+
+ keys.TryGetValue(kid, out result);
+
+ return await Task.FromResult(result);
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Program.cs b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Program.cs
new file mode 100644
index 000000000..e42cf55c3
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Program.cs
@@ -0,0 +1,117 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace QueueGettingStarted
+{
+ using Microsoft.Azure.KeyVault;
+ using Microsoft.WindowsAzure;
+ using Microsoft.WindowsAzure.Storage;
+ using Microsoft.WindowsAzure.Storage.Core;
+ using Microsoft.WindowsAzure.Storage.Queue;
+ using System;
+ using System.IO;
+ using System.Security.Cryptography;
+
+ ///
+ /// Demonstrates how to use encryption with the Azure Queue service.
+ ///
+ public class Program
+ {
+ const string DemoQueue = "demoqueue";
+
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Queue encryption sample");
+
+ // Retrieve storage account information from connection string
+ // How to create a storage connection string - http://msdn.microsoft.com/en-us/library/azure/ee758697.aspx
+ CloudStorageAccount storageAccount = CreateStorageAccountFromConnectionString(CloudConfigurationManager.GetSetting("StorageConnectionString"));
+ CloudQueueClient client = storageAccount.CreateCloudQueueClient();
+ CloudQueue queue = client.GetQueueReference(DemoQueue + Guid.NewGuid().ToString("N"));
+
+ try
+ {
+ queue.Create();
+
+ // Create the IKey used for encryption.
+ RsaKey key = new RsaKey("private:key1");
+
+ // Create the encryption policy to be used for insert and update.
+ QueueEncryptionPolicy insertPolicy = new QueueEncryptionPolicy(key, null);
+
+ // Set the encryption policy on the request options.
+ QueueRequestOptions insertOptions = new QueueRequestOptions() { EncryptionPolicy = insertPolicy };
+
+ string messageStr = Guid.NewGuid().ToString();
+ CloudQueueMessage message = new CloudQueueMessage(messageStr);
+
+ // Add message
+ Console.WriteLine("Inserting the encrypted message.");
+ queue.AddMessage(message, null, null, insertOptions, null);
+
+ // For retrieves, a resolver can be set up that will help pick the key based on the key id.
+ LocalResolver resolver = new LocalResolver();
+ resolver.Add(key);
+
+ QueueEncryptionPolicy retrPolicy = new QueueEncryptionPolicy(null, resolver);
+ QueueRequestOptions retrieveOptions = new QueueRequestOptions() { EncryptionPolicy = retrPolicy };
+
+ // Retrieve message
+ Console.WriteLine("Retrieving the encrypted message.");
+ CloudQueueMessage retrMessage = queue.GetMessage(null, retrieveOptions, null);
+
+ // Update message
+ Console.WriteLine("Updating the encrypted message.");
+ string updatedMessage = Guid.NewGuid().ToString("N");
+ retrMessage.SetMessageContent(updatedMessage);
+ queue.UpdateMessage(retrMessage, TimeSpan.FromSeconds(0), MessageUpdateFields.Content | MessageUpdateFields.Visibility, insertOptions, null);
+
+ // Retrieve updated message
+ Console.WriteLine("Retrieving the updated encrypted message.");
+ retrMessage = queue.GetMessage(null, retrieveOptions, null);
+
+ Console.WriteLine("Press enter key to exit");
+ Console.ReadLine();
+ }
+ finally
+ {
+ queue.DeleteIfExists();
+ }
+ }
+
+ private static CloudStorageAccount CreateStorageAccountFromConnectionString(string storageConnectionString)
+ {
+ CloudStorageAccount storageAccount;
+ try
+ {
+ storageAccount = CloudStorageAccount.Parse(storageConnectionString);
+ }
+ catch (FormatException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+ catch (ArgumentException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+
+ return storageAccount;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Properties/AssemblyInfo.cs b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Properties/AssemblyInfo.cs
new file mode 100644
index 000000000..ce5ce7026
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("QueueGettingStarted")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("QueueGettingStarted")]
+[assembly: AssemblyCopyright("Copyright © 2015")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("88aebdfe-c738-41aa-9c66-6e52c0ac5e83")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/QueueGettingStarted.csproj b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/QueueGettingStarted.csproj
new file mode 100644
index 000000000..c2696fc4a
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/QueueGettingStarted.csproj
@@ -0,0 +1,140 @@
+
+
+
+
+ Debug
+ AnyCPU
+ {96209F76-E19B-426E-8C02-6CE26B6187C9}
+ Exe
+ Properties
+ QueueGettingStarted
+ QueueGettingStarted
+ v4.5
+ 512
+
+
+ AnyCPU
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ AnyCPU
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+ ..\packages\Hyak.Common.1.0.2\lib\net45\Hyak.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.NetFramework.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Core.0.9.1-preview\lib\net40\Microsoft.Azure.KeyVault.Core.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Extensions.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Edm.5.6.2\lib\net40\Microsoft.Data.Edm.dll
+ True
+
+
+ ..\packages\Microsoft.Data.OData.5.6.2\lib\net40\Microsoft.Data.OData.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Services.Client.5.6.2\lib\net40\Microsoft.Data.Services.Client.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.Desktop.dll
+ True
+
+
+ ..\packages\Microsoft.WindowsAzure.ConfigurationManager.1.8.0.0\lib\net35-full\Microsoft.WindowsAzure.Configuration.dll
+ True
+
+
+ ..\packages\WindowsAzure.Storage.4.4.0-preview\lib\net40\Microsoft.WindowsAzure.Storage.dll
+ True
+
+
+ ..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll
+ True
+
+
+
+
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Primitives.dll
+ True
+
+
+
+ ..\packages\System.Spatial.5.6.2\lib\net40\System.Spatial.dll
+ True
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/packages.config b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/packages.config
new file mode 100644
index 000000000..2133f779f
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/QueueGettingStarted/packages.config
@@ -0,0 +1,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/App.config b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/App.config
new file mode 100644
index 000000000..083ba01a6
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/App.config
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/LocalResolver.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/LocalResolver.cs
new file mode 100644
index 000000000..616a553e0
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/LocalResolver.cs
@@ -0,0 +1,42 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace TableGettingStartedUsingResolver
+{
+ using Microsoft.Azure.KeyVault.Core;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
+
+ public class LocalResolver : IKeyResolver
+ {
+ private Dictionary keys = new Dictionary();
+
+ public void Add(IKey key)
+ {
+ keys[key.Kid] = key;
+ }
+
+ public async Task ResolveKeyAsync(string kid, CancellationToken token)
+ {
+ IKey result;
+
+ keys.TryGetValue(kid, out result);
+
+ return await Task.FromResult(result);
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Program.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Program.cs
new file mode 100644
index 000000000..b07afb969
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Program.cs
@@ -0,0 +1,125 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace TableGettingStartedUsingResolver
+{
+ using Microsoft.Azure.KeyVault;
+ using Microsoft.WindowsAzure;
+ using Microsoft.WindowsAzure.Storage;
+ using Microsoft.WindowsAzure.Storage.Core;
+ using Microsoft.WindowsAzure.Storage.Table;
+ using System;
+ using System.IO;
+ using System.Security.Cryptography;
+
+ ///
+ /// Demonstrates how to use encryption with the Azure Table service.
+ ///
+ public class Program
+ {
+ const string DemoTable = "demotable";
+
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Table encryption sample");
+
+ // Retrieve storage account information from connection string
+ // How to create a storage connection string - http://msdn.microsoft.com/en-us/library/azure/ee758697.aspx
+ CloudStorageAccount storageAccount = CreateStorageAccountFromConnectionString(CloudConfigurationManager.GetSetting("StorageConnectionString"));
+ CloudTableClient client = storageAccount.CreateCloudTableClient();
+ CloudTable table = client.GetTableReference(DemoTable + Guid.NewGuid().ToString("N"));
+
+ try
+ {
+ table.Create();
+
+ // Create the IKey used for encryption.
+ RsaKey key = new RsaKey("private:key1");
+
+ DynamicTableEntity ent = new DynamicTableEntity() { PartitionKey = Guid.NewGuid().ToString(), RowKey = DateTime.Now.Ticks.ToString() };
+ ent.Properties.Add("EncryptedProp1", new EntityProperty(string.Empty));
+ ent.Properties.Add("EncryptedProp2", new EntityProperty("bar"));
+ ent.Properties.Add("NotEncryptedProp", new EntityProperty(1234));
+
+ // This is used to indicate whether a property should be encrypted or not given the partition key, row key,
+ // and the property name.
+ Func encryptionResolver = (pk, rk, propName) =>
+ {
+ if (propName.StartsWith("EncryptedProp"))
+ {
+ return true;
+ }
+
+ return false;
+ };
+
+ TableRequestOptions insertOptions = new TableRequestOptions()
+ {
+ EncryptionPolicy = new TableEncryptionPolicy(key, null),
+
+ EncryptionResolver = encryptionResolver
+ };
+
+ // Insert Entity
+ Console.WriteLine("Inserting the encrypted entity.");
+ table.Execute(TableOperation.Insert(ent), insertOptions, null);
+
+ // For retrieves, a resolver can be set up that will help pick the key based on the key id.
+ LocalResolver resolver = new LocalResolver();
+ resolver.Add(key);
+
+ TableRequestOptions retrieveOptions = new TableRequestOptions()
+ {
+ EncryptionPolicy = new TableEncryptionPolicy(null, resolver)
+ };
+
+ // Retrieve Entity
+ Console.WriteLine("Retrieving the encrypted entity.");
+ TableOperation operation = TableOperation.Retrieve(ent.PartitionKey, ent.RowKey);
+ TableResult result = table.Execute(operation, retrieveOptions, null);
+
+ Console.WriteLine("Press enter key to exit");
+ Console.ReadLine();
+ }
+ finally
+ {
+ table.DeleteIfExists();
+ }
+ }
+
+ private static CloudStorageAccount CreateStorageAccountFromConnectionString(string storageConnectionString)
+ {
+ CloudStorageAccount storageAccount;
+ try
+ {
+ storageAccount = CloudStorageAccount.Parse(storageConnectionString);
+ }
+ catch (FormatException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+ catch (ArgumentException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+
+ return storageAccount;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Properties/AssemblyInfo.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Properties/AssemblyInfo.cs
new file mode 100644
index 000000000..ede1e7b02
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("TableGettingStarted")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("TableGettingStarted")]
+[assembly: AssemblyCopyright("Copyright © 2015")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("abd0736d-ec22-437b-a2ad-a6235558513c")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/TableGettingStartedUsingResolver.csproj b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/TableGettingStartedUsingResolver.csproj
new file mode 100644
index 000000000..74183bf48
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/TableGettingStartedUsingResolver.csproj
@@ -0,0 +1,142 @@
+
+
+
+
+ Debug
+ AnyCPU
+ {449D75A7-140A-495A-B35A-9B056095F571}
+ Exe
+ Properties
+ TableGettingStarted
+ TableGettingStarted
+ v4.5
+ 512
+
+
+ AnyCPU
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ AnyCPU
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+ ..\packages\Hyak.Common.1.0.2\lib\net45\Hyak.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.NetFramework.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Core.0.9.1-preview\lib\net40\Microsoft.Azure.KeyVault.Core.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Extensions.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Edm.5.6.2\lib\net40\Microsoft.Data.Edm.dll
+ True
+
+
+ ..\packages\Microsoft.Data.OData.5.6.2\lib\net40\Microsoft.Data.OData.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Services.Client.5.6.2\lib\net40\Microsoft.Data.Services.Client.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.Desktop.dll
+ True
+
+
+ ..\packages\Microsoft.WindowsAzure.ConfigurationManager.1.8.0.0\lib\net35-full\Microsoft.WindowsAzure.Configuration.dll
+ True
+
+
+ ..\packages\WindowsAzure.Storage.4.4.0-preview\lib\net40\Microsoft.WindowsAzure.Storage.dll
+ True
+
+
+ ..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll
+ True
+
+
+
+
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Primitives.dll
+ True
+
+
+
+ ..\packages\System.Spatial.5.6.2\lib\net40\System.Spatial.dll
+ True
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Designer
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/packages.config b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/packages.config
new file mode 100644
index 000000000..2133f779f
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStarted/packages.config
@@ -0,0 +1,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/App.config b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/App.config
new file mode 100644
index 000000000..083ba01a6
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/App.config
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/EncryptedEntity.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/EncryptedEntity.cs
new file mode 100644
index 000000000..83d8ca46b
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/EncryptedEntity.cs
@@ -0,0 +1,52 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace TableGettingStartedUsingAttributes
+{
+ using Microsoft.WindowsAzure.Storage.Table;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading.Tasks;
+
+ public class EncryptedEntity : TableEntity
+ {
+ public EncryptedEntity()
+ {
+ }
+
+ public EncryptedEntity(string pk, string rk)
+ : base(pk, rk)
+ {
+ }
+
+ public void Populate()
+ {
+ this.EncryptedProperty1 = string.Empty;
+ this.EncryptedProperty2 = "foo";
+ this.NotEncryptedProperty = "b";
+ this.NotEncryptedIntProperty = 1234;
+ }
+
+ [EncryptProperty]
+ public string EncryptedProperty1 { get; set; }
+
+ [EncryptProperty]
+ public string EncryptedProperty2 { get; set; }
+
+ public string NotEncryptedProperty { get; set; }
+
+ public int NotEncryptedIntProperty { get; set; }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/LocalResolver.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/LocalResolver.cs
new file mode 100644
index 000000000..a24c6e309
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/LocalResolver.cs
@@ -0,0 +1,42 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace TableGettingStartedUsingAttributes
+{
+ using Microsoft.Azure.KeyVault.Core;
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
+
+ public class LocalResolver : IKeyResolver
+ {
+ private Dictionary keys = new Dictionary();
+
+ public void Add(IKey key)
+ {
+ keys[key.Kid] = key;
+ }
+
+ public async Task ResolveKeyAsync(string kid, CancellationToken token)
+ {
+ IKey result;
+
+ keys.TryGetValue(kid, out result);
+
+ return await Task.FromResult(result);
+ }
+ }
+}
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Program.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Program.cs
new file mode 100644
index 000000000..f2b1750b2
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Program.cs
@@ -0,0 +1,109 @@
+//----------------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation. All rights reserved.
+//
+// THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
+// EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
+// OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
+//----------------------------------------------------------------------------------
+// The example companies, organizations, products, domain names,
+// e-mail addresses, logos, people, places, and events depicted
+// herein are fictitious. No association with any real company,
+// organization, product, domain name, email address, logo, person,
+// places, or events is intended or should be inferred.
+//----------------------------------------------------------------------------------
+namespace TableGettingStartedUsingAttributes
+{
+ using Microsoft.Azure.KeyVault;
+ using Microsoft.WindowsAzure;
+ using Microsoft.WindowsAzure.Storage;
+ using Microsoft.WindowsAzure.Storage.Core;
+ using Microsoft.WindowsAzure.Storage.Table;
+ using System;
+ using System.IO;
+ using System.Security.Cryptography;
+
+ ///
+ /// Demonstrates how to use encryption with the Azure Table service.
+ ///
+ public class Program
+ {
+ const string DemoTable = "demotable";
+
+ static void Main(string[] args)
+ {
+ Console.WriteLine("Table encryption sample");
+
+ // Retrieve storage account information from connection string
+ // How to create a storage connection string - http://msdn.microsoft.com/en-us/library/azure/ee758697.aspx
+ CloudStorageAccount storageAccount = CreateStorageAccountFromConnectionString(CloudConfigurationManager.GetSetting("StorageConnectionString"));
+ CloudTableClient client = storageAccount.CreateCloudTableClient();
+ CloudTable table = client.GetTableReference(DemoTable + Guid.NewGuid().ToString("N"));
+
+ try
+ {
+ table.Create();
+
+ // Create the IKey used for encryption.
+ RsaKey key = new RsaKey("private:key1");
+
+ EncryptedEntity ent = new EncryptedEntity() { PartitionKey = Guid.NewGuid().ToString(), RowKey = DateTime.Now.Ticks.ToString() };
+ ent.Populate();
+
+ TableRequestOptions insertOptions = new TableRequestOptions()
+ {
+ EncryptionPolicy = new TableEncryptionPolicy(key, null)
+ };
+
+ // Insert Entity
+ Console.WriteLine("Inserting the encrypted entity.");
+ table.Execute(TableOperation.Insert(ent), insertOptions, null);
+
+ // For retrieves, a resolver can be set up that will help pick the key based on the key id.
+ LocalResolver resolver = new LocalResolver();
+ resolver.Add(key);
+
+ TableRequestOptions retrieveOptions = new TableRequestOptions()
+ {
+ EncryptionPolicy = new TableEncryptionPolicy(null, resolver)
+ };
+
+ // Retrieve Entity
+ Console.WriteLine("Retrieving the encrypted entity.");
+ TableOperation operation = TableOperation.Retrieve(ent.PartitionKey, ent.RowKey);
+ TableResult result = table.Execute(operation, retrieveOptions, null);
+
+ Console.WriteLine("Press enter key to exit");
+ Console.ReadLine();
+ }
+ finally
+ {
+ table.DeleteIfExists();
+ }
+ }
+
+ private static CloudStorageAccount CreateStorageAccountFromConnectionString(string storageConnectionString)
+ {
+ CloudStorageAccount storageAccount;
+ try
+ {
+ storageAccount = CloudStorageAccount.Parse(storageConnectionString);
+ }
+ catch (FormatException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+ catch (ArgumentException)
+ {
+ Console.WriteLine("Invalid storage account information provided. Please confirm the AccountName and AccountKey are valid in the app.config file - then restart the sample.");
+ Console.WriteLine("Press any key to exit");
+ Console.ReadLine();
+ throw;
+ }
+
+ return storageAccount;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Properties/AssemblyInfo.cs b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Properties/AssemblyInfo.cs
new file mode 100644
index 000000000..109886864
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/Properties/AssemblyInfo.cs
@@ -0,0 +1,36 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about an assembly is controlled through the following
+// set of attributes. Change these attribute values to modify the information
+// associated with an assembly.
+[assembly: AssemblyTitle("TableGettingStartedUsingAttributes")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("TableGettingStartedUsingAttributes")]
+[assembly: AssemblyCopyright("Copyright © 2015")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// Setting ComVisible to false makes the types in this assembly not visible
+// to COM components. If you need to access a type in this assembly from
+// COM, set the ComVisible attribute to true on that type.
+[assembly: ComVisible(false)]
+
+// The following GUID is for the ID of the typelib if this project is exposed to COM
+[assembly: Guid("bbaa3e35-34d7-40f9-90db-7f3484022527")]
+
+// Version information for an assembly consists of the following four values:
+//
+// Major Version
+// Minor Version
+// Build Number
+// Revision
+//
+// You can specify all the values or you can default the Build and Revision Numbers
+// by using the '*' as shown below:
+// [assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
+[assembly: AssemblyFileVersion("1.0.0.0")]
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/TableGettingStartedUsingAttributes.csproj b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/TableGettingStartedUsingAttributes.csproj
new file mode 100644
index 000000000..fb8fd4070
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/TableGettingStartedUsingAttributes.csproj
@@ -0,0 +1,141 @@
+
+
+
+
+ Debug
+ AnyCPU
+ {804DF8D6-CCCC-4408-8B2E-2FF09CC3B266}
+ Exe
+ Properties
+ TableGettingStartedUsingAttributes
+ TableGettingStartedUsingAttributes
+ v4.5
+ 512
+
+
+ AnyCPU
+ true
+ full
+ false
+ bin\Debug\
+ DEBUG;TRACE
+ prompt
+ 4
+
+
+ AnyCPU
+ pdbonly
+ true
+ bin\Release\
+ TRACE
+ prompt
+ 4
+
+
+
+ ..\packages\Hyak.Common.1.0.2\lib\net45\Hyak.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.Common.2.0.4\lib\net45\Microsoft.Azure.Common.NetFramework.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Core.0.9.1-preview\lib\net40\Microsoft.Azure.KeyVault.Core.dll
+ True
+
+
+ ..\packages\Microsoft.Azure.KeyVault.Extensions.0.9.1-preview\lib\net45\Microsoft.Azure.KeyVault.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Edm.5.6.2\lib\net40\Microsoft.Data.Edm.dll
+ True
+
+
+ ..\packages\Microsoft.Data.OData.5.6.2\lib\net40\Microsoft.Data.OData.dll
+ True
+
+
+ ..\packages\Microsoft.Data.Services.Client.5.6.2\lib\net40\Microsoft.Data.Services.Client.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Bcl.Async.1.0.168\lib\net40\Microsoft.Threading.Tasks.Extensions.Desktop.dll
+ True
+
+
+ ..\packages\Microsoft.WindowsAzure.ConfigurationManager.1.8.0.0\lib\net35-full\Microsoft.WindowsAzure.Configuration.dll
+ True
+
+
+ ..\packages\WindowsAzure.Storage.4.4.0-preview\lib\net40\Microsoft.WindowsAzure.Storage.dll
+ True
+
+
+ ..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll
+ True
+
+
+
+
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Extensions.dll
+ True
+
+
+ ..\packages\Microsoft.Net.Http.2.2.22\lib\net45\System.Net.Http.Primitives.dll
+ True
+
+
+
+ ..\packages\System.Spatial.5.6.2\lib\net40\System.Spatial.dll
+ True
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/packages.config b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/packages.config
new file mode 100644
index 000000000..2133f779f
--- /dev/null
+++ b/Samples/GettingStarted/EncryptionSamples/TableGettingStartedUsingAttributes/packages.config
@@ -0,0 +1,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file