Отправка файлов (C#)

Скотт Митчелл

Загрузить PDF-файл

Узнайте, как разрешить пользователям отправлять двоичные файлы (например, Word или PDF-документы) на веб-сайт, где они могут храниться в файловой системе сервера или базе данных.

Введение

Все учебники, которые мы рассмотрели до сих пор, работали исключительно с текстовыми данными. Однако во многих приложениях есть модели данных, которые захватывают как текстовые, так и двоичные данные. Веб-сайт знакомств может позволить пользователям загрузить фотографию для связи с их профилем. Веб-сайт по подбору персонала может позволить пользователям отправлять свое резюме в виде документа Microsoft Word или PDF.

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

Примечание

Двоичные данные, которые являются частью модели данных приложения, иногда называют большим двоичным объектом( аббревиатурой большого двоичного объекта OBject). В этих руководствах я решил использовать термин двоичные данные, хотя термин BLOB является синонимом.

Шаг 1. Создание веб-страниц для работы с двоичными данными

Прежде чем приступить к изучению проблем, связанных с добавлением поддержки двоичных данных, давайте сначала уделим время созданию страниц ASP.NET в проекте веб-сайта, которые потребуются для работы с этим руководством и следующими тремя. Начните с добавления новой папки с именем BinaryData. Затем добавьте в нее следующие страницы ASP.NET, обязательно свяжите каждую страницу со страницей Site.master master:

  • Default.aspx
  • FileUpload.aspx
  • DisplayOrDownloadData.aspx
  • UploadInDetailsView.aspx
  • UpdatingAndDeleting.aspx

Добавление страниц ASP.NET для руководства по двоичному Data-Related

Рис. 1. Добавление страниц ASP.NET для руководства по двоичному Data-Related

Как и в других папках, Default.aspx в папке BinaryData будет отображаться список учебников в своем разделе. Помните, что SectionLevelTutorialListing.ascx пользовательский элемент управления предоставляет эту функцию. Поэтому добавьте этот пользовательский элемент управления в , Default.aspx перетащив его из Обозреватель решений в режим конструктора страницы.

Добавьте пользовательский элемент управления SectionLevelTutorialListing.ascx в Default.aspx

Рис. 2. Добавление пользовательского SectionLevelTutorialListing.ascx элемента управления в Default.aspx (щелкните для просмотра полноразмерного изображения)

Наконец, добавьте эти страницы в качестве записей в Web.sitemap файл. В частности, добавьте следующую разметку после расширения GridView <siteMapNode>:

<siteMapNode 
    title="Working with Binary Data" 
    url="~/BinaryData/Default.aspx" 
    description="Extend the data model to include collecting binary data.">
    
    <siteMapNode 
        title="Uploading Files" 
        url="~/BinaryData/FileUpload.aspx" 
        description="Examine the different ways to store binary data on the 
                     web server and see how to accept uploaded files from users 
                     with the FileUpload control." />
    <siteMapNode 
        title="Display or Download Binary Data" 
        url="~/BinaryData/DisplayOrDownloadData.aspx" 
        description="Let users view or download the captured binary data." />
    <siteMapNode 
        title="Adding New Binary Data" 
        url="~/BinaryData/UploadInDetailsView.aspx" 
        description="Learn how to augment the inserting interface to 
                     include a FileUpload control." />
    <siteMapNode 
        title="Updating and Deleting Existing Binary Data" 
        url="~/BinaryData/UpdatingAndDeleting.aspx" 
        description="Learn how to update and delete existing binary data." />
</siteMapNode>

После обновления Web.sitemapпросмотрите веб-сайт учебников в браузере. Меню слева теперь содержит элементы для учебников По работе с двоичными данными.

Карта сайта теперь включает записи для учебников по работе с двоичными данными

Рис. 3. Схема сайта теперь включает записи для учебников по работе с двоичными данными

Шаг 2. Выбор места хранения двоичных данных

Двоичные данные, связанные с моделью данных приложения, могут храниться в одном из двух мест: в файловой системе веб-сервера со ссылкой на файл, хранящийся в базе данных; или непосредственно в самой базе данных (см. рис. 4). Каждый подход имеет свой собственный набор плюсов и недостатков и заслуживает более подробного обсуждения.

Двоичные данные могут храниться в файловой системе или непосредственно в базе данных

Рис. 4. Двоичные данные могут храниться в файловой системе или непосредственно в базе данных (щелкните для просмотра полноразмерного изображения)

Представьте, что мы хотим расширить базу данных Northwind, чтобы связать рисунок с каждым продуктом. Один из вариантов — сохранить эти файлы изображений в файловой системе веб-сервера и записать путь в таблицу Products . При таком подходе мы добавим ImagePath столбец в таблицу Products типа varchar(200), возможно. Когда пользователь отправляет изображение для Chai, это изображение может храниться в файловой системе веб-сервера по адресу ~/Images/Tea.jpg, где ~ представляет физический путь приложения. То есть, если веб-сайт имеет корень по физическому пути C:\Websites\Northwind\, ~/Images/Tea.jpg будет эквивалентно C:\Websites\Northwind\Images\Tea.jpg. После отправки файла изображения мы обновим запись Chai в Products таблице таким образом, чтобы столбец ImagePath ссылался на путь к новому образу. Мы могли бы использовать ~/Images/Tea.jpg или, Tea.jpg если бы решили, что все образы продуктов будут помещены в папку приложения Images .

Main преимущества хранения двоичных данных в файловой системе:

  • Простота реализации , как мы увидим вскоре, хранение и извлечение двоичных данных, хранящихся непосредственно в базе данных, требует немного больше кода, чем при работе с данными через файловую систему. Кроме того, чтобы пользователь просматривал или скачивать двоичные данные, ей необходимо предоставить URL-адрес для них. Если данные находятся в файловой системе веб-сервера, URL-адрес прост. Однако если данные хранятся в базе данных, необходимо создать веб-страницу, которая будет извлекать и возвращать данные из базы данных.
  • Более широкий доступ к двоичным данным , которые могут потребоваться для других служб или приложений, которые не могут извлечь данные из базы данных. Например, изображения, связанные с каждым продуктом, также должны быть доступны пользователям через FTP, и в этом случае мы хотим сохранить двоичные данные в файловой системе.
  • Производительность , если двоичные данные хранятся в файловой системе, спрос и перегрузка сети между сервером базы данных и веб-сервером будет меньше, чем при хранении двоичных данных непосредственно в базе данных.

Недостаток main хранения двоичных данных в файловой системе заключается в том, что данные отделяют от базы данных. При удалении записи из Products таблицы связанный файл в файловой системе веб-сервера не удаляется автоматически. Необходимо написать дополнительный код, чтобы удалить файл, иначе файловая система будет перегружена неиспользуемых потерянными файлами. Кроме того, при резервном копировании базы данных необходимо также создать резервные копии связанных двоичных данных в файловой системе. Перемещение базы данных на другой сайт или сервер создает аналогичные проблемы.

Кроме того, двоичные данные можно хранить непосредственно в базе данных Microsoft SQL Server 2005 путем создания столбца типа varbinary. Как и в случае с другими типами данных переменной длины, можно указать максимальную длину двоичных данных, которые могут храниться в этом столбце. Например, чтобы зарезервировать не более 5000 байт, используйте varbinary(5000); varbinary(MAX) позволяет использовать максимальный размер хранилища около 2 ГБ.

Преимуществом main хранения двоичных данных непосредственно в базе данных является тесная взаимосвязь между двоичными данными и записью базы данных. Это значительно упрощает задачи администрирования базы данных, такие как резервное копирование или перемещение базы данных на другой сайт или сервер. Кроме того, при удалении записи автоматически удаляются соответствующие двоичные данные. Хранение двоичных данных в базе данных также дает более тонкие преимущества. Дополнительные сведения см. в статье Хранение двоичных файлов непосредственно в базе данных с помощью ASP.NET 2.0 .

Примечание

В Microsoft SQL Server 2000 и более ранних версиях varbinary тип данных имел максимальное ограничение в 8000 байт. Для хранения двоичных данных image размером до 2 ГБ необходимо использовать тип данных. Однако image с добавлением MAX в SQL Server 2005 году тип данных стал устаревшим. Он по-прежнему поддерживается для обратной совместимости, но корпорация Майкрософт объявила, что image тип данных будет удален в будущей версии SQL Server.

При работе с более старой моделью данных может отображаться image тип данных. Таблица базы данных Categories Northwind содержит Picture столбец, который можно использовать для хранения двоичных данных файла изображения для категории. Так как база данных Northwind имеет свои корни в Microsoft Access и более ранних версиях SQL Server, этот столбец имеет тип image.

В этом и следующих трех руководствах мы будем использовать оба подхода. В Categories таблице уже есть Picture столбец для хранения двоичного содержимого изображения для категории. Мы добавим дополнительный столбец , BrochurePathчтобы сохранить путь к PDF-файлу в файловой системе веб-сервера, который можно использовать для предоставления качественного обзора категории.

Шаг 3. Добавление столбца вBrochurePathтаблицуCategories

В настоящее время таблица "Категории" содержит только четыре столбца: CategoryID, CategoryName, Descriptionи Picture. В дополнение к этим полям необходимо добавить новое, которое будет указывать на брошюру категории (если таковой существует). Чтобы добавить этот столбец, перейдите на сервер Обозреватель, перейдите в раздел Таблицы, щелкните таблицу правой Categories кнопкой мыши и выберите Команду Открыть определение таблицы (см. рис. 5). Если Обозреватель сервера не отображается, откройте его, выбрав параметр Сервер Обозреватель в меню Вид или нажав клавиши CTRL+ALT+S.

Добавьте новый varchar(200) столбец в таблицу Categories с именем BrochurePath и разрешает NULL s, а затем щелкните значок Сохранить (или нажмите клавиши CTRL+S).

Добавление столбца BrochurePath в таблицу категорий

Рис. 5. Добавление BrochurePath столбца в таблицу Categories (щелкните для просмотра полноразмерного изображения)

Шаг 4. Обновление архитектуры для использования столбцовPictureиBrochurePath

Объект CategoriesDataTable в уровне доступа к данным (DAL) в настоящее время определяет четыре DataColumn объекта: CategoryID, CategoryName, Descriptionи NumberOfProducts. Когда мы изначально разрабатывали эту таблицу DataTable в учебнике Создание уровня доступа к данным , CategoriesDataTable в ней были только первые три столбца. NumberOfProducts Столбец был добавлен в учебнике Master/Detail Using a Bulleted List of Master Records with a Details DataList .

Как описано в разделе Создание уровня доступа к данным, данные в типизированном наборе данных составляют бизнес-объекты. TableAdapters отвечают за обмен данными с базой данных и заполнение бизнес-объектов результатами запроса. заполняется CategoriesDataTable с помощью CategoriesTableAdapter, который имеет три метода извлечения данных:

  • GetCategories()выполняет запрос main TableAdapter и возвращает CategoryIDполя , CategoryNameи Description для всех записей в Categories таблице. Запрос main используется автоматически созданными Insert методами и Update .
  • GetCategoryByCategoryID(categoryID)CategoryIDвозвращает поля , CategoryNameи Description категории, для которой CategoryID равно categoryID.
  • GetCategoriesAndNumberOfProducts() — возвращает CategoryIDполя , CategoryNameи Description для всех записей в Categories таблице. Также использует вложенный запрос для возврата количества продуктов, связанных с каждой категорией.

Обратите внимание, что ни один из этих запросов не возвращает Categories таблицы Picture или BrochurePath столбцы, а CategoriesDataTable не предоставляет DataColumn для этих полей . Для работы со свойствами Picture и BrochurePath необходимо сначала добавить их в CategoriesDataTable , а затем обновить CategoriesTableAdapter класс , чтобы вернуть эти столбцы.

PictureДобавление иBrochurePath``DataColumn

Начните с добавления этих двух столбцов в CategoriesDataTable. Щелкните правой CategoriesDataTable кнопкой мыши заголовок , выберите Добавить в контекстном меню, а затем выберите параметр Столбец. При этом в DataTable будет создан новый DataColumn объект с именем Column1. Переименуйте этот столбец в Picture. В окно свойств присвойте свойству DataColumn s DataType значение System.Byte[] (это не параметр в раскрывающемся списке; его необходимо ввести).

Создание именованного рисунка DataColumn с типом DataType System.Byte[]

Рис. 6. Создание именованного DataTypePictureSystem.Byte[] объекта DataColumn с именем ( щелкните для просмотра полноразмерного изображения)

Добавьте еще один DataColumn элемент в dataTable, назвав его BrochurePath значением по умолчанию DataType (System.String).

Возврат значенийPictureиBrochurePathиз объекта TableAdapter

После добавления этих двух DataColumn элементов в CategoriesDataTableмы готовы к обновлению CategoriesTableAdapter. Мы могли бы возвращать оба значения столбца в запросе main TableAdapter, но это будет возвращать двоичные данные при каждом GetCategories() вызове метода. Вместо этого обновите запрос main TableAdapter, чтобы вернуть BrochurePath и создать дополнительный метод извлечения данных, который возвращает столбец определенной Picture категории.

Чтобы обновить запрос main TableAdapter, щелкните правой кнопкой мыши CategoriesTableAdapter заголовок s и выберите параметр Настроить в контекстном меню. Откроется мастер настройки адаптера таблиц, который мы видели в нескольких предыдущих руководствах. Обновите запрос, чтобы вернуть BrochurePath и нажмите кнопку Готово.

Обновите список столбцов в инструкции SELECT, чтобы он также возвращал Буклет Путь

Рис. 7. Обновление списка столбцов в операторе SELECT для возврата BrochurePath (щелкните для просмотра полноразмерного изображения)

При использовании нерегламентированных инструкций SQL для TableAdapter обновление списка столбцов в main запрос обновляет список столбцов SELECT для всех методов запроса в TableAdapter. Это означает, GetCategoryByCategoryID(categoryID) что метод был обновлен для возврата столбца BrochurePath , что может быть то, что мы и планировали. Однако он также обновил список столбцов в методе GetCategoriesAndNumberOfProducts() , удалив вложенный запрос, возвращающий количество продуктов для каждой категории. Поэтому необходимо обновить запрос этого метода SELECT . Щелкните метод правой GetCategoriesAndNumberOfProducts() кнопкой мыши, выберите Настроить и отменить изменения SELECT запрос к исходному значению:

SELECT CategoryID, CategoryName, Description, 
       (SELECT COUNT(*) 
            FROM Products p 
            WHERE p.CategoryID = c.CategoryID) 
       as NumberOfProducts
FROM Categories c

Затем создайте новый метод TableAdapter, который возвращает значение столбца определенной Picture категории. Щелкните правой CategoriesTableAdapter кнопкой мыши заголовок и выберите параметр Добавить запрос, чтобы запустить мастер настройки запросов TableAdapter. На первом шаге этого мастера мы запрашиваем данные с помощью нерегламентированной инструкции SQL, новой хранимой процедуры или существующей. Выберите Использовать инструкции SQL и нажмите кнопку Далее. Так как мы будем возвращать строку, выберите параметр SELECT, который возвращает строки из второго шага.

Выберите параметр Use SQL statements (Использовать инструкции SQL).

Рис. 8. Выбор параметра Использовать инструкции SQL (щелкните для просмотра полноразмерного изображения)

Так как запрос вернет запись из таблицы категорий, выберите SELECT, который возвращает строки.

Рис. 9. Так как запрос вернет запись из таблицы категорий, выберите SELECT, который возвращает строки (щелкните, чтобы просмотреть полноразмерное изображение)

На третьем шаге введите следующий SQL-запрос и нажмите кнопку Далее:

SELECT     CategoryID, CategoryName, Description, BrochurePath, Picture
FROM       Categories
WHERE      CategoryID = @CategoryID

Последним шагом является выбор имени для нового метода. Используйте FillCategoryWithBinaryDataByCategoryID и GetCategoryWithBinaryDataByCategoryID для шаблонов Fill a DataTable и Return a DataTable соответственно. Чтобы завершить работу мастера, нажмите кнопку Готово.

Выбор имен для методов TableAdapter

Рис. 10. Выбор имен для методов TableAdapter (щелкните, чтобы просмотреть полноразмерное изображение)

Примечание

После завершения работы мастера настройки запросов адаптера таблиц может появилось диалоговое окно с сообщением о том, что новый текст команды возвращает данные со схемой, отличной от схемы запроса main. Короче говоря, мастер отмечает, что запрос GetCategories() main TableAdapter возвращает схему, отличную от созданной. Но это то, что мы хотим, так что вы можете игнорировать это сообщение.

Кроме того, помните, что если вы используете нерегламентированные инструкции SQL и используете мастер для изменения запроса main TableAdapter позже, он изменит GetCategoryWithBinaryDataByCategoryID список столбцов инструкции методаSELECT, чтобы включить только те столбцы из запроса main (то есть он удалит Picture столбец из запроса). Вам придется вручную обновить список столбцов, чтобы вернуть Picture столбец, аналогично тому, как мы делали с методом GetCategoriesAndNumberOfProducts() ранее на этом шаге.

После добавления двух DataColumn объектов CategoriesDataTableGetCategoryWithBinaryDataByCategoryID в и метода CategoriesTableAdapterв , эти классы в Designer Typed DataSet должны выглядеть, как на снимке экрана на рисунке 11.

Набор данных Designer включает новые столбцы и метод

Рис. 11. Designer DataSet включает новые столбцы и метод

Обновление уровня бизнес-логики (BLL)

После обновления DAL остается только расширить уровень бизнес-логики (BLL), чтобы включить метод для нового CategoriesTableAdapter метода. Добавьте в класс CategoriesBLL следующий метод:

[System.ComponentModel.DataObjectMethodAttribute
    (System.ComponentModel.DataObjectMethodType.Select, false)] 
public Northwind.CategoriesDataTable 
    GetCategoryWithBinaryDataByCategoryID(int categoryID)
{
    return Adapter.GetCategoryWithBinaryDataByCategoryID(categoryID);
}

Шаг 5. Отправка файла из клиента на веб-сервер

При сборе двоичных данных эти данные часто предоставляются конечным пользователем. Чтобы получить эти сведения, пользователь должен иметь возможность отправить файл со своего компьютера на веб-сервер. Отправленные данные необходимо интегрировать с моделью данных, что может означать сохранение файла в файловой системе веб-сервера и добавление пути к файлу в базе данных или запись двоичного содержимого непосредственно в базу данных. На этом шаге мы рассмотрим, как разрешить пользователю отправлять файлы со своего компьютера на сервер. В следующем руководстве мы рассмотрим интеграцию отправленного файла с моделью данных.

ASP.NET 2.0 новый веб-элемент управления FileUpload предоставляет пользователям механизм отправки файла с компьютера на веб-сервер. Элемент управления FileUpload отрисовывается в виде <input> элемента, атрибуту которого type задано значение file, которое в браузерах отображается в виде текстового поля с кнопкой Обзор. При нажатии кнопки Обзор откроется диалоговое окно, из которого пользователь может выбрать файл. При обратной отправке формы содержимое выбранного файла отправляется вместе с обратной отправкой. На стороне сервера сведения о отправленном файле доступны через свойства элемента управления FileUpload.

Чтобы продемонстрировать отправку файлов, откройте FileUpload.aspx страницу в BinaryData папке, перетащите элемент управления FileUpload с панели элементов на Designer и присвойте свойству элемента управления ID значение UploadTest. Затем добавьте веб-элемент управления Кнопка, задав для его ID свойств UploadButton и Text значения и отправить выбранный файл соответственно. Наконец, поместите элемент управления Label Web под button, очистите его Text свойство и задайте для него ID значение UploadDetails.

Добавление элемента управления FileUpload на страницу ASP.NET

Рис. 12. Добавление элемента управления FileUpload на страницу ASP.NET (щелкните для просмотра полноразмерного изображения)

На рисунке 13 показана эта страница при просмотре в браузере. Обратите внимание, что при нажатии кнопки Обзор открывается диалоговое окно выбора файла, позволяющее пользователю выбрать файл со своего компьютера. После выбора файла нажатие кнопки Отправить выбранный файл вызывает обратную передачу, которая отправляет двоичное содержимое выбранного файла на веб-сервер.

Пользователь может выбрать файл для отправки со своего компьютера на сервер

Рис. 13. Пользователь может выбрать файл для отправки со своего компьютера на сервер (щелкните для просмотра полноразмерного изображения)

При обратной передаче отправленный файл может быть сохранен в файловой системе или с его двоичными данными можно работать непосредственно через Stream. В этом примере создадим папку и сохраним в ней ~/Brochures отправленный файл. Начните с добавления Brochures папки на сайт в качестве вложенной папки корневого каталога. Затем создайте обработчик событий для UploadButton события s Click и добавьте следующий код:

protected void UploadButton_Click(object sender, EventArgs e)
{
    if (UploadTest.HasFile == false)
    {
        // No file uploaded!
        UploadDetails.Text = "Please first select a file to upload...";            
    }
    else
    {
        // Display the uploaded file's details
        UploadDetails.Text = string.Format(
                @"Uploaded file: {0}<br />
                  File size (in bytes): {1:N0}<br />
                  Content-type: {2}", 
                  UploadTest.FileName, 
                  UploadTest.FileBytes.Length,
                  UploadTest.PostedFile.ContentType);
        // Save the file
        string filePath = 
            Server.MapPath("~/Brochures/" + UploadTest.FileName);
        UploadTest.SaveAs(filePath);
    }
}

Элемент управления FileUpload предоставляет различные свойства для работы с отправленными данными. Например, свойство указывает, HasFile был ли файл отправлен пользователем, а FileBytes свойство предоставляет доступ к отправленным двоичным данным в виде массива байтов. Обработчик Click событий начинается с того, что файл был отправлен. Если файл отправлен, в поле Метка отображается имя отправленного файла, его размер в байтах и тип содержимого.

Примечание

Чтобы убедиться, что пользователь отправляет файл, можно проверка HasFile свойство и отобразить предупреждение, если оно имеет falseзначение , или вместо него можно использовать элемент управления RequiredFieldValidator.

FileUpload SaveAs(filePath) сохраняет отправленный файл в указанный filePath. FilePath должен быть физическим путем (C:\Websites\Brochures\SomeFile.pdf), а не виртуальнымпутем (/Brochures/SomeFile.pdf). МетодServer.MapPath(virtPath) принимает виртуальный путь и возвращает соответствующий ему физический путь. Здесь виртуальный путь — ~/Brochures/fileName, где fileName — имя отправленного файла. Дополнительные сведения о виртуальных и физических путях и использовании Server.MapPathсм. в разделе Метод Server.MapPath .

Завершив работу обработчика Click событий, проверьте страницу в браузере. Нажмите кнопку Обзор, выберите файл с жесткого диска, а затем нажмите кнопку Отправить выбранный файл. Обратная передача отправляет содержимое выбранного файла на веб-сервер, который затем отображает сведения о файле перед сохранением его в папку ~/Brochures . После отправки файла вернитесь в Visual Studio и нажмите кнопку Обновить в Обозреватель решений. Вы должны увидеть файл, который вы только что отправили в папку ~/Буклеты!

Файл EvolutionValley.jpg отправлен на веб-сервер

Рис. 14. Файл EvolutionValley.jpg был отправлен на веб-сервер (щелкните, чтобы просмотреть полноразмерное изображение)

EvolutionValley.jpg сохранено в папке ~/Буклеты

Рис. 15. EvolutionValley.jpg Был сохранен в папке ~/Brochures

Тонкости сохранения отправленных файлов в файловой системе

При сохранении файлов в файловой системе веб-сервера необходимо учитывать несколько тонкостей. Во-первых, это проблема безопасности. Чтобы сохранить файл в файловой системе, контекст безопасности, в котором выполняется страница ASP.NET, должен иметь разрешения на запись. Веб-сервер разработки ASP.NET выполняется в контексте текущей учетной записи пользователя. Если в качестве веб-сервера вы используете службы MICROSOFT IIS, контекст безопасности зависит от версии IIS и ее конфигурации.

Другая проблема сохранения файлов в файловой системе связана с именованием файлов. В настоящее время наша страница сохраняет все отправленные файлы в ~/Brochures каталог, используя то же имя, что и файл на клиентском компьютере. Если пользователь A отправляет брошюру с именем Brochure.pdf, файл будет сохранен как ~/Brochure/Brochure.pdf. Но что делать, если через некоторое время пользователь Б загрузит другой файл брошюры с тем же именем файла (Brochure.pdf)? С помощью кода, который у нас есть, файл пользователя A будет перезаписан отправкой пользователя B.

Существует ряд методов разрешения конфликтов имен файлов. Один из вариантов — запретить отправку файла, если он уже существует с тем же именем. При таком подходе, когда пользователь Б пытается отправить файл с именем Brochure.pdf, система не сохраняет файл и вместо этого отображает сообщение, информирующее пользователя Б переименовать файл и повторить попытку. Другой подход заключается в сохранении файла с использованием уникального имени файла, которое может быть глобальным уникальным идентификатором (GUID) или значением из соответствующих столбцов первичного ключа записи базы данных (при условии, что отправка связана с определенной строкой в модели данных). В следующем руководстве мы рассмотрим эти параметры более подробно.

Проблемы, связанные с очень большими объемами двоичных данных

В этих руководствах предполагается, что объем двоичных данных невелик. Работа с очень большими объемами двоичных файлов данных, размер которых составляет несколько мегабайт или больше, ставит перед собой новые задачи, выходящие за рамки область этих учебников. Например, по умолчанию ASP.NET отклоняет отправки размером более 4 МБ, хотя это можно настроить с помощью <httpRuntime> элемента в Web.config. СЛУЖБЫ IIS также накладывают ограничения на размер отправляемых файлов. Кроме того, время, затраченное на отправку больших файлов, может превышать 110 секунд по умолчанию, ASP.NET будет ожидать запроса. При работе с большими файлами также возникают проблемы с памятью и производительностью.

Элемент управления FileUpload нецелесообразно для отправки больших файлов. По мере публикации содержимого файла на сервере конечный пользователь должен терпеливо ждать, не подтверждая, что отправка выполняется. Это не столько проблема при работе с файлами меньшего размера, которые могут быть отправлены в течение нескольких секунд, но может быть проблемой при работе с более крупными файлами, которые могут занять несколько минут. Существуют различные сторонние элементы управления отправкой файлов, которые лучше подходят для обработки больших объемов отправки, и многие из этих поставщиков предоставляют индикаторы хода выполнения и диспетчеры отправки ActiveX, которые обеспечивают гораздо более удобный пользовательский интерфейс.

Если приложению требуется обработка больших файлов, необходимо тщательно изучить проблемы и найти подходящие решения для конкретных потребностей.

Сводка

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

Счастливого программирования!

Дополнительные материалы

Дополнительные сведения о темах, рассмотренных в этом руководстве, см. в следующих ресурсах:

Об авторе

Скотт Митчелл( Scott Mitchell), автор семи книг ASP/ASP.NET и основатель 4GuysFromRolla.com, работает с веб-технологиями Майкрософт с 1998 года. Скотт работает независимым консультантом, тренером и писателем. Его последняя книга Sams Teach Yourself ASP.NET 2.0 в 24 часах. Он может быть доступен в mitchell@4GuysFromRolla.com. или через его блог, который можно найти по адресу http://ScottOnWriting.NET.

Особая благодарность

Эта серия учебников была рассмотрена многими полезными рецензентами. Ведущими рецензентами этого руководства были Тетера Мерфи и Бернадетт Ли. Хотите просмотреть предстоящие статьи MSDN? Если да, опустите мне строку на mitchell@4GuysFromRolla.com.