Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/spring-mvc/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Spring 如何使用客户端上载多部分表单数据_Spring_Spring Mvc - Fatal编程技术网

Spring 如何使用客户端上载多部分表单数据

Spring 如何使用客户端上载多部分表单数据,spring,spring-mvc,Spring,Spring Mvc,我正在尝试将多部分表单数据从web客户端上传到SpringMVC控制器。我在“Spring”实现中搜索以下curl命令: curl -v -X POST -F "logo=@walmart.jpg" -F "id=12345" -F "name=Walmart" http://localhost:8080/api/cardprovider/logo 请注意:我不是通过html表单上传表单,这不是我想要实现的 现在我的问题是: 您会使用ApacheCommonsHttpClient来实现这一点

我正在尝试将多部分表单数据从web客户端上传到SpringMVC控制器。我在“Spring”实现中搜索以下curl命令:

curl -v -X POST -F "logo=@walmart.jpg" -F "id=12345" -F "name=Walmart" http://localhost:8080/api/cardprovider/logo
请注意:我不是通过html表单上传表单,这不是我想要实现的

现在我的问题是:

  • 您会使用ApacheCommonsHttpClient来实现这一点吗 ?
  • 还是有一个“春天”式的魔法图书馆 帮我做这个
我花了好几天时间使用Spring库搜索解决方案,但是Spring手册中的所有示例都涉及html表单上传,或者非常简单,只有基本文本

Spring对我来说是相当新的,但是里面有这么多很棒的库,如果Spring的人没有想到一些东西可以让上传多部分数据变得更容易(看起来好像是从表单发送的),我会感到惊讶

上面的curl命令正在使用以下服务器端代码成功运行:

控制器:

@Controller
@RequestMapping("/api/cardprovider/logo")
public class CardproviderLogoResourceController {

  @Resource(name = "cardproviderLogoService")
  private CardproviderLogoService cardproviderLogoService;

  /**
   * Used to upload a binary logo of a Cardprovider through a Multipart request. The  id is provided as form element.
   * <p/>
   * Example to upload a file using curl:
   * curl -v -X POST -F "image=@star.jpg" -F "id=12345" -F "name=Walmart" http://localhost:8080/api/cardprovider/logo
   * <p/>
   *
   * @param logo the Multipart request
   * @param id    the Cardprovider id
   * @param name  the Cardprovider name
   */
  @RequestMapping(value = "", method = RequestMethod.POST)
  @ResponseStatus(HttpStatus.NO_CONTENT)
  public void storeCardproviderLogo(@RequestParam(value = "logo", required = false) MultipartFile logo,
                                  @RequestParam(value = "name") String name,
                                  @RequestParam(value = "id") String id) throws IOException {

    cardproviderLogoService.storeLogo(logo, id, name);
  }
}
@RequestMapping(value = "/add", method = RequestMethod.POST)
public String addCardprovider(
        @ModelAttribute("cardproviderAttribute") Cardprovider cardprovider,
        Model model) {

    // Prepare acceptable media type
    List<MediaType> acceptableMediaTypes = new ArrayList<MediaType>();
    acceptableMediaTypes.add(MediaType.APPLICATION_XML);

    // Prepare header
    HttpHeaders headers = new HttpHeaders();
    headers.setAccept(acceptableMediaTypes);
    // Pass the new person and header
    HttpEntity<Cardprovider> entity = new HttpEntity<Cardprovider>(
            cardprovider, headers);

    // Send the request as POST
    try {
        // Save Cardprovider details
        ResponseEntity<Cardprovider> response = restTemplate.exchange(
                "http://localhost:8080/api/cardprovider", HttpMethod.POST,
                entity, Cardprovider.class);

        // Save Cardprovider logo
        String tempDir = System.getProperty("java.io.tmpdir");
        File file = new File(tempDir + "/" + cardprovider.getLogo().getOriginalFilename());
        cardprovider.getLogo().transferTo(file);

        MultiValueMap<String, Object> parts = new LinkedMultiValueMap<String, Object>();
        parts.add("id", response.getBody().getId());
        parts.add("name", response.getBody().getName());
        parts.add("logo", new FileSystemResource(file));

        restTemplate.postForLocation("http://localhost:8080/api/cardprovider/logo", parts);

    } catch (Exception e) {
        e.printStackTrace();
    }

    // This will redirect to /web/cardprovider/getall
    return "redirect:/web/cardprovider/getall";
}
@控制器
@请求映射(“/api/cardprovider/logo”)
公共类CardproviderLogoResourceController{
@资源(name=“cardproviderLogoService”)
私人卡提供商LogoService卡提供商LogoService;
/**
*用于通过多部分请求上载Cardprovider的二进制徽标。id作为表单元素提供。
*

*使用curl上载文件的示例: *curl-v-X POST-F“image=@star.jpg”-F“id=12345”-F“name=Walmart”http://localhost:8080/api/cardprovider/logo *

* *@param logo支持多部分请求 *@param id-Cardprovider id *@param name Cardprovider名称 */ @RequestMapping(value=”“,method=RequestMethod.POST) @ResponseStatus(HttpStatus.无内容) public void storeCardproviderLogo(@RequestParam(value=“logo”,required=false)多部分文件徽标, @RequestParam(value=“name”)字符串名称, @RequestParam(value=“id”)字符串id)引发IOException{ cardproviderLogoService.storeLogo(徽标、id、名称); } }

下面是我的服务类,它将多部分请求存储在GridFS数据库中:

服务:

@Service
public class CardproviderLogoService {

  @Autowired
  GridFsOperations gridOperation;

  /**
   * Create the logo in MongoDB GridFS with the data returned from the Multipart
   * <p/>
   *
   * @param logo the MultipartFile content
   * @param id      the Cardprovider id
   * @param name    the Cardprovider name
   * @return true if the image can be saved in the database, else false
   */
  public Boolean storeLogo(MultipartFile logo, String id, String name) {
    Boolean save_state = false;

    BasicDBObject metadata = new BasicDBObject();
    metadata.put("cardproviderId", id);
    metadata.put("cardproviderName", name);
    metadata.put("contentType", logo.getContentType());
    metadata.put("fileName", createLogoFilename(name, logo.getOriginalFilename()));
    metadata.put("originalFilename", logo.getOriginalFilename());
    metadata.put("dirShortcut", "cardproviderLogo");
    metadata.put("filePath", "/resources/images/cardproviders/logos/");

    try {
        gridOperation.store(logo.getInputStream(),
                metadata.getString("fileName").toLowerCase().replace(" ", "-"),
                metadata);
        save_state = true;
    } catch (Exception ex) {
        Logger.getLogger(CardproviderLogoService.class.getName())
                .log(Level.SEVERE, "Storage of Logo failed!", ex);
    }

    return save_state;
}

/**
 * Creates the new filename before storing the file in MongoDB GridFS. The filename is created by taking the
 * name of the Cardprovider, lowercase the name and replace the whitespaces with dashes. At last the file
 * extension is added that was provided by the original filename.
 * <p/>
 *
 * @param name the Cardprovider name
 * @param originalFilename the original filename
 * @return the new filename as String
 */
private String createLogoFilename(String name, String originalFilename) {
    String cpName = name.toLowerCase().replace(" ", "-");

    String extension = "";
    int i = originalFilename.lastIndexOf('.');
    if (i > 0 && i < originalFilename.length() - 1) {
        extension = originalFilename.substring(i + 1).toLowerCase();
    }
    return cpName + "." + extension;
  }
}
@服务
公共类CardproviderLogoService{
@自动连线
GridFS操作gridOperation;
/**
*使用多部分返回的数据在MongoDB GridFS中创建徽标
*

* *@param logo显示多部分文件内容 *@param id-Cardprovider id *@param name Cardprovider名称 *@如果图像可以保存在数据库中,则返回true,否则返回false */ 公共布尔存储徽标(多部分文件徽标、字符串id、字符串名称){ 布尔值save_state=false; BasicDBObject元数据=新建BasicDBObject(); metadata.put(“cardproviderId”,id); metadata.put(“cardproviderName”,name); put(“contentType”,logo.getContentType()); put(“fileName”,createLogoFilename(name,logo.getOriginalFilename()); put(“originalFilename”,logo.getOriginalFilename()); metadata.put(“dirShortcut”、“cardproviderLogo”); metadata.put(“文件路径”,“/resources/images/cardproviders/logo/”; 试一试{ gridOperation.store(logo.getInputStream(), metadata.getString(“文件名”).toLowerCase().replace(“,“-”), 元数据); save_state=true; }捕获(例外情况除外){ Logger.getLogger(CardproviderLogoService.class.getName()) .log(Level.SEVERE,“徽标存储失败!”,例如); } 返回保存状态; } /** *在将文件存储到MongoDB GridFS之前创建新文件名 *Cardprovider的名称,将名称小写,并将空格替换为破折号。最后,文件 *添加了由原始文件名提供的扩展名。 *

* *@param name Cardprovider名称 *@param originalFilename原始文件名 *@以字符串形式返回新文件名 */ 私有字符串createLogoFilename(字符串名称、字符串原始文件名){ 字符串cpName=name.toLowerCase().replace(“,“-”); 字符串扩展名=”; int i=原始文件名.lastIndexOf('.'); 如果(i>0&&i

谢谢你的帮助和亲切的问候, 克里斯

解决方案

我可以用下面的方法解决这个问题。我有一个HtmlController,它接受表单输入并建立到RestController的连接以传输文件

以下是HtmlController的方法:

@Controller
@RequestMapping("/api/cardprovider/logo")
public class CardproviderLogoResourceController {

  @Resource(name = "cardproviderLogoService")
  private CardproviderLogoService cardproviderLogoService;

  /**
   * Used to upload a binary logo of a Cardprovider through a Multipart request. The  id is provided as form element.
   * <p/>
   * Example to upload a file using curl:
   * curl -v -X POST -F "image=@star.jpg" -F "id=12345" -F "name=Walmart" http://localhost:8080/api/cardprovider/logo
   * <p/>
   *
   * @param logo the Multipart request
   * @param id    the Cardprovider id
   * @param name  the Cardprovider name
   */
  @RequestMapping(value = "", method = RequestMethod.POST)
  @ResponseStatus(HttpStatus.NO_CONTENT)
  public void storeCardproviderLogo(@RequestParam(value = "logo", required = false) MultipartFile logo,
                                  @RequestParam(value = "name") String name,
                                  @RequestParam(value = "id") String id) throws IOException {

    cardproviderLogoService.storeLogo(logo, id, name);
  }
}
@RequestMapping(value = "/add", method = RequestMethod.POST)
public String addCardprovider(
        @ModelAttribute("cardproviderAttribute") Cardprovider cardprovider,
        Model model) {

    // Prepare acceptable media type
    List<MediaType> acceptableMediaTypes = new ArrayList<MediaType>();
    acceptableMediaTypes.add(MediaType.APPLICATION_XML);

    // Prepare header
    HttpHeaders headers = new HttpHeaders();
    headers.setAccept(acceptableMediaTypes);
    // Pass the new person and header
    HttpEntity<Cardprovider> entity = new HttpEntity<Cardprovider>(
            cardprovider, headers);

    // Send the request as POST
    try {
        // Save Cardprovider details
        ResponseEntity<Cardprovider> response = restTemplate.exchange(
                "http://localhost:8080/api/cardprovider", HttpMethod.POST,
                entity, Cardprovider.class);

        // Save Cardprovider logo
        String tempDir = System.getProperty("java.io.tmpdir");
        File file = new File(tempDir + "/" + cardprovider.getLogo().getOriginalFilename());
        cardprovider.getLogo().transferTo(file);

        MultiValueMap<String, Object> parts = new LinkedMultiValueMap<String, Object>();
        parts.add("id", response.getBody().getId());
        parts.add("name", response.getBody().getName());
        parts.add("logo", new FileSystemResource(file));

        restTemplate.postForLocation("http://localhost:8080/api/cardprovider/logo", parts);

    } catch (Exception e) {
        e.printStackTrace();
    }

    // This will redirect to /web/cardprovider/getall
    return "redirect:/web/cardprovider/getall";
}
@RequestMapping(value=“/add”,method=RequestMethod.POST)
公共字符串addCardprovider(
@ModelAttribute(“cardproviderAttribute”)Cardprovider Cardprovider,
(模型){
//准备可接受的介质类型
List acceptableMediaTypes=new ArrayList();
acceptableMediaTypes.add(MediaType.APPLICATION\uXML);
//准备收割台
HttpHeaders=新的HttpHeaders();
headers.setAccept(acceptableMediaTypes);
//传递新的人员和标题
HttpEntity=新的HttpEntity(
卡片提供者,标题);
//以邮寄方式发送请求
试一试{
//保存Cardprovider详细信息
ResponseEntity response=restemplate.exchange(
"http://localhost:8080/api/cardprovider“,HttpMethod.POST,
实体,Cardprovider.class);
//保存Cardprovider徽标
字符串tempDir=System.getProperty(“java.io.tmpdir”);
File File=新文件(tempDir+“/”+cardprovider.getLogo().getOriginalFilename());
cardprovider.getLogo().transferTo(文件);
MultiValueMap parts=新链接的MultiValueMap();
parts.add(“id”,response.getBody().getId());
parts.add(“name”,response.getBody().getName());
帕