2015-05-26 4 views
17

Я уже успешно показываю доступные файлы, но мне нужно знать, как я могу передать этот файл в браузер для загрузки пользователем, не обязательно сохраняя его на сервереКак загрузить файл в браузер из Azure Blob Storage

Вот как я получаю список файлов

var azureConnectionString = CloudConfigurationManager.GetSetting("AzureBackupStorageConnectString"); 
var containerName = ConfigurationManager.AppSettings["FmAzureBackupStorageContainer"]; 
if (azureConnectionString == null || containerName == null) 
    return null; 

CloudStorageAccount backupStorageAccount = CloudStorageAccount.Parse(azureConnectionString); 
var backupBlobClient = backupStorageAccount.CreateCloudBlobClient(); 
var container = backupBlobClient.GetContainerReference(containerName); 
var blobs = container.ListBlobs(useFlatBlobListing: true); 
var downloads = blobs.Select(blob => blob.Uri.Segments.Last()).ToList(); 

ответ

36

В то время как содержимое блоба может передаваться через веб-сервер, а вместе с конечным пользователем через браузер это решение загружает веб-сервер, как процессор, так и сетевой адаптер.

Альтернативный подход заключается в том, чтобы предоставить конечному пользователю uri желаемому загружаемому блоку, который они могут щелкнуть в html-контенте. например https://myaccount.blob.core.windows.net/mycontainer/myblob.ext.

Проблема с этим заключается в том, что содержимое является конфиденциальным, так как uri, такой как указанный выше, не будет работать, если не использовать публичные капли. Для этого вы можете создать подпись общего доступа (или серверную политику), которая затем приведет к хешированию, добавленному в uri. Этот новый uri будет действителен в течение заданного периода времени (например, 10 минут).

Вот небольшой пример создания SAS для сгустка:

var sasConstraints = new SharedAccessBlobPolicy(); 
sasConstraints.SharedAccessStartTime = DateTime.UtcNow.AddMinutes(-5); 
sasConstraints.SharedAccessExpiryTime = DateTime.UtcNow.AddMinutes(10); 
sasConstraints.Permissions = SharedAccessBlobPermissions.Read; 

var sasBlobToken = blob.GetSharedAccessSignature(sasConstraints); 

return blob.Uri + sasBlobToken; 

Обратите внимание, что время начала устанавливается равным несколько минут в прошлом. Это касается дрифта часов. Вот full tutorial Я схватил/модифицировал этот образец кода.

Используя прямой доступ к blob, вы полностью обойдете экземпляр экземпляра виртуальной машины/веб-сайта или уменьшите нагрузку на сервер, а ваш конечный пользователь вытащить содержимое блоба непосредственно из хранилища blob. Вы все еще можете использовать свое веб-приложение, чтобы иметь дело с разрешением, решая, какой контент для доставки и т. Д. Но ... это позволяет вам напрямую ссылаться на ресурсы blob, а не передавать их через ваш веб-сервер.

+0

Подробнее о шаблоне ключа Valet: https://msdn.microsoft.com/en-us/library/dn568102.aspx –

+0

Я должен принять аналогичный подход при получении ошибки для загрузки файла только с его URI. Спасибо за головы Дэвида. – Kris

7

После того как пользователь нажмет на файл-сервер отвечает с этим

var blob = container.GetBlobReferenceFromServer(option); 

var memStream = new MemoryStream(); 
blob.DownloadToStream(memStream); 

Response.ContentType = blob.Properties.ContentType; 
Response.AddHeader("Content-Disposition", "Attachment;filename=" + option); 
Response.AddHeader("Content-Length", blob.Properties.Length.ToString()); 
Response.BinaryWrite(memStream.ToArray()); 

Огромное спасибо Dhananjay Kumar для этого решения

+2

Итак, вы понимаете, что все содержимое blob будет проходить через ваш сервер, верно? То есть, содержимое blob будет перемещаться из хранилища blob в экземпляр виртуальной машины/веб-сайта или веб-роли, а затем через вашего пользователя, через IIS/OWIN/и т. Д.? –

+0

что вы посоветуете? Я не могу предоставить своим конечным пользователям доступ ко всему хранилищу, поэтому исследователь Azure не будет работать. – stackoverfloweth

+3

Я отправил альтернативный ответ. –

Смежные вопросы