Spring MVC ファイルをアップロードする
Spring MVCで画像ファイルをアップロードするプログラムを書いてみました。
Apache上で動くHTMLから画像ファイルをポストして、それをサーバ側で受け取って、特定のディレクトリに格納します。
目次
ディレクトリ構成
ディレクトリ構成はこんな感じです。pom.xml
STSで作ったSpring web mavenプロジェクトのデフォルトのpom.xmlに少し追加しています。コメントに「追加したもの」と書いています。
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>org.springframework.samples.service.service</groupId> <artifactId>shiori</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>war</packaging> <properties> <!-- Generic properties --> <java.version>1.6</java.version> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> <!-- Web --> <jsp.version>2.2</jsp.version> <jstl.version>1.2</jstl.version> <servlet.version>2.5</servlet.version> <!-- Spring --> <spring-framework.version>3.2.3.RELEASE</spring-framework.version> <!-- Hibernate / JPA --> <hibernate.version>4.2.1.Final</hibernate.version> <!-- Logging --> <logback.version>1.0.13</logback.version> <slf4j.version>1.7.5</slf4j.version> <!-- Test --> <junit.version>4.11</junit.version> </properties> <dependencies> <!-- Spring MVC --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-webmvc</artifactId> <version>${spring-framework.version}</version> </dependency> <!-- Other Web dependencies --> <dependency> <groupId>javax.servlet</groupId> <artifactId>jstl</artifactId> <version>${jstl.version}</version> </dependency> <dependency> <groupId>javax.servlet</groupId> <artifactId>servlet-api</artifactId> <version>${servlet.version}</version> <scope>provided</scope> </dependency> <dependency> <groupId>javax.servlet.jsp</groupId> <artifactId>jsp-api</artifactId> <version>${jsp.version}</version> <scope>provided</scope> </dependency> <!-- Spring and Transactions --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-tx</artifactId> <version>${spring-framework.version}</version> </dependency> <!-- Logging with SLF4J & LogBack --> <dependency> <groupId>org.slf4j</groupId> <artifactId>slf4j-api</artifactId> <version>${slf4j.version}</version> <scope>compile</scope> </dependency> <dependency> <groupId>ch.qos.logback</groupId> <artifactId>logback-classic</artifactId> <version>${logback.version}</version> <scope>runtime</scope> </dependency> <!-- Hibernate --> <dependency> <groupId>org.hibernate</groupId> <artifactId>hibernate-entitymanager</artifactId> <version>${hibernate.version}</version> </dependency> <!-- Test Artifacts --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-test</artifactId> <version>${spring-framework.version}</version> <scope>test</scope> </dependency> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>${junit.version}</version> <scope>test</scope> </dependency> <!-- デフォルトから追加したもの --> <dependency> <groupId>javax.servlet</groupId> <artifactId>servlet-api</artifactId> <version>2.5</version> </dependency> <dependency> <groupId>commons-io</groupId> <artifactId>commons-io</artifactId> <version>2.4</version> </dependency> <dependency> <groupId>commons-fileupload</groupId> <artifactId>commons-fileupload</artifactId> <version>1.3.1</version> </dependency> <dependency> <groupId>javax.validation</groupId> <artifactId>validation-api</artifactId> <version>1.0.0.GA</version> </dependency> <dependency> <groupId>org.hibernate</groupId> <artifactId>hibernate-validator</artifactId> <version>4.3.1.Final</version> </dependency> <dependency> <groupId>org.hibernate</groupId> <artifactId>hibernate-validator-annotation-processor</artifactId> <version>4.1.0.Final</version> </dependency> <!-- Jackson JSON Mapper --> <dependency> <groupId>org.codehaus.jackson</groupId> <artifactId>jackson-mapper-asl</artifactId> <version>1.9.10</version> </dependency> </dependencies> </project>
web.xml
<?xml version="1.0" encoding="ISO-8859-1"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" id="WebApp_ID" version="2.5"> <display-name>shiori</display-name> <!-- - Location of the XML file that defines the root application context. - Applied by ContextLoaderListener. --> <context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:spring/application-config.xml</param-value> </context-param> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <!-- - Servlet that dispatches request to registered handlers (Controller implementations). --> <servlet> <servlet-name>dispatcherServlet</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <init-param> <param-name>contextConfigLocation</param-name> <param-value>/WEB-INF/mvc-config.xml</param-value> </init-param> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>dispatcherServlet</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping> </web-app>
ImageController.java
コントローラーは以下のとおりです。ここでPOSTリクエストでアップロードされたファイルを受け取って、ディレクトリに格納しています。
デフォルトのままだと、Spring MVCのVIEWが開かれてしまうので、このリクエストを受けたらJSONを返すようにしました。
JacksonをMavenに書く必要があります。
これについて詳しくは、ページの一番下にリンクを貼ったサイトを見てください。
package shiori.controller; import java.io.File; import java.io.IOException; import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.ResponseBody; import org.springframework.web.multipart.MultipartFile; import shiori.domain.Image; @Controller public class ImageController { @Autowired ServletContext context; @RequestMapping(value = "img_save", method=RequestMethod.POST) public @ResponseBody Image saveProduct(HttpServletRequest request, @RequestParam("file") MultipartFile file) throws IllegalStateException, IOException { Image image = new Image(); if (file.getSize() > 0) { image.setName(file.getOriginalFilename()); image.setSize(file.getSize()); File imageFile = new File(context.getRealPath("/") + "/images",image.getName()); if (!imageFile.exists()) { File imageDir = new File(context.getRealPath("/") + "/images"); imageDir.mkdir(); } file.transferTo(imageFile); } return image; } }
Image.java
モデルの部分です。package shiori.domain; import java.io.Serializable; import java.util.List; import org.springframework.web.multipart.MultipartFile; public class Image implements Serializable { private static final long serialVersionUID = 7302826202936253750L; private String name; private long size; private List<MultipartFile> images; private List<String> imageUrls; public String getName() { return name; } public void setName(String name) { this.name = name; } public List<MultipartFile> getImages() { return images; } public void setImages(List<MultipartFile> images) { this.images = images; } public List<String> getImageUrls() { return imageUrls; } public void setImageUrls(List<String> imageUrls) { this.imageUrls = imageUrls; } public long getSize() { return size; } public void setSize(long size) { this.size = size; } }
リクエストを投げるHTML
Apacheで動いているものです。Spring MVCのViewでは無いですが、基本的には同じように使えます。
<!doctype html> <html> <head> <meata charset="utf-8"> <title>file upload</title> </head> <body> <form action="http://localhost:8080/shiori/img_save" method="post" enctype="multipart/form-data"> <input type="file" name="file"> <button type="submit">submit</button> </form> </body> </html>
submitすると、JSONが返ってきます。
Spring MVCでレスポンスをJSONで返すのはこのサイトを参考にしました。
Spring MVCのレスポンスをJSONで返す
- 作者: Paul Deck
- 出版社/メーカー: Brainy Software
- 発売日: 2013/10/18
- メディア: Kindle版
- この商品を含むブログを見る