Я бачив декілька пропозицій, як, наприклад, щоб каталог зображень був символічним посиланням, що вказує на каталог поза веб-контейнером, але чи буде такий підхід працювати як у Windows, так і * nix?
Якщо ви дотримуєтесь правил шляху до файлової системи * nix (тобто ви використовуєте виключно передні косої риски, як у /path/to/files), то вона також буде працювати і в Windows, без необхідності поспішати з потворними File.separatorрядками. Однак він буде сканований лише на тому ж робочому диску, що і звідки викликана ця команда. Отже, якщо Tomcat, наприклад, встановлений на, C:тоді це /path/to/filesнасправді вказувати б C:\path\to\files.
Якщо всі файли знаходяться за межами веб-сторінки, і ви хочете, щоб Tomcat працював з DefaultServletними, то все, що вам потрібно зробити в Tomcat, - це додати наступний елемент контексту до /conf/server.xmlвнутрішнього <Host>тегу:
<Context docBase="/path/to/files" path="/files" />
Таким чином , вони будуть доступні через http://example.com/files/.... Приклад конфігурації GlassFish / Payara можна знайти тут, а приклад конфігурації WildFly - тут .
Якщо ви хочете , щоб мати контроль над читанням / запис файлів самостійно, то вам необхідно створити Servletдля цього , яке в основному тільки отримує InputStreamз файлу в ароматі, наприклад , FileInputStreamі записує його в OutputStreamз HttpServletResponse.
У відповіді слід встановити Content-Typeзаголовок, щоб клієнт знав, яку програму пов’язати із наданим файлом. І вам слід встановити Content-Lengthзаголовок, щоб клієнт міг обчислити хід завантаження, інакше це буде невідомо. І вам слід встановити Content-Dispositionзаголовок, attachmentякщо ви хочете діалогове вікно " Зберегти як" , інакше клієнт намагатиметься відобразити його в рядку. Нарешті просто запишіть вміст файлу у вихідний потік відповіді.
Ось основний приклад такого сервлета:
@WebServlet("/files/*")
public class FileServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException
{
String filename = URLDecoder.decode(request.getPathInfo().substring(1), "UTF-8");
File file = new File("/path/to/files", filename);
response.setHeader("Content-Type", getServletContext().getMimeType(filename));
response.setHeader("Content-Length", String.valueOf(file.length()));
response.setHeader("Content-Disposition", "inline; filename=\"" + file.getName() + "\"");
Files.copy(file.toPath(), response.getOutputStream());
}
}
url-patternНаприклад /files/*, якщо їх відобразити на, наприклад , ви можете зателефонувати за ним http://example.com/files/image.png. Таким чином, ви можете мати більше контролю над запитами, ніж над цим DefaultServlet, наприклад, наданням зображення за замовчуванням (тобто if (!file.exists()) file = new File("/path/to/files", "404.gif")тощо). Також використовувати request.getPathInfo()перевагу вище, request.getParameter()оскільки це більш зручно для SEO, інакше IE не вибере правильне ім’я файлу під час Save As .
Ви можете використовувати ту саму логіку для обслуговування файлів із бази даних. Просто замініть new FileInputStream()на ResultSet#getInputStream().
Сподіваюся, це допомагає.
Дивитися також: