我有一个提供文件的控制器(图像,pdf等等):
@Controller
public class FileController {
@ResponseBody
@RequestMapping("/{filename}")
public Object download(@PathVariable String filename) throws Exception {
returns MyFile.findFile(filename);
}
}
如果我请求带有以下Accept标头的文件,我会收到406:
Request URL: http://localhost:8080/files/thmb_AA039258_204255d0.png Request Method:GET Status Code:406 Not Acceptable Request Headers Accept:*/*
如果我使用以下Accept标头请求相同的文件,我会得到200:
URL: http://localhost:8080/files/thmb_AA039258_204255d0.png Request Method: GET Status Code:200 OK Request Headers Accept: application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5
这是我在spring-mvc上下文中唯一的视图解析器:
<bean class="org.springframework.web.servlet.view.UrlBasedViewResolver" id="tilesViewResolver">
<property name="viewClass" value="org.springframework.web.servlet.view.tiles2.TilesView"/>
</bean>
是否有配置spring mvc忽略Accept标头?我已经看到使用ContentNegotiatingViewResolver执行此操作的示例,但仅用于处理xml和json。
答案 0 :(得分:4)
所以这是我最终得到它的代码:
@Controller
public class FileController {
@ResponseBody
@RequestMapping("/{filename}")
public void download(@PathVariable String filename, ServletResponse response) throws Exception {
MyFile file = MyFile.find(filename);
response.setContentType(file.getContentType());
response.getOutputStream().write(file.getBytes());
}
}
答案 1 :(得分:0)
当你使用ResponseBody注释时,我认为这是它看待Accept标头并试图做一些映射或其他什么的交易的一部分。如果您无法弄清楚如何使用该注释来发送响应,还有很多其他方法可以发送响应。
答案 2 :(得分:0)
我用它来锁定JSON响应类型:
@Configuration
@EnableWebMvc
public class ApplicationConfiguration extends WebMvcConfigurerAdapter {
public void configureContentNegotiation(ContentNegotiationConfigurer configurer) {
configurer.favorPathExtension(false);
configurer.ignoreAcceptHeader(true);
configurer.defaultContentType(MediaType.APPLICATION_JSON);
}
}
favorPathExtension(false)
是必需的,因为Spring默认情况下(至少在4.1.5中)支持基于路径的内容协商(即如果URL以“.xml”结尾,它将尝试返回XML等)