From 0aaa6528dcb07ef76049cf74a4d6aecb4ee6c610 Mon Sep 17 00:00:00 2001 From: Arjen Poutsma Date: Tue, 14 Mar 2017 14:56:01 +0100 Subject: [PATCH] Remove JAF references This commit updates the main code base to conform to the dropped JAF dependency in MediaTypeFactory. Specifically, it - Removes JAF detection (JAF_PRESENT constants) - Deprecated useJaf properties, with no direct replacement. - Updated docs to remove JAF references, in favor of MediaTypeFactory. Issue: SPR-14908 --- .../ResourceHttpMessageConverter.java | 17 +++------- .../ResourceRegionHttpMessageConverter.java | 31 ++++++++++--------- .../web/accept/ContentNegotiationManager.java | 7 ++--- .../ContentNegotiationManagerFactoryBean.java | 29 +++++------------ ...thExtensionContentNegotiationStrategy.java | 31 +++++-------------- ...thExtensionContentNegotiationStrategy.java | 8 +++-- .../PathExtensionContentTypeResolver.java | 30 +++++------------- .../RequestedContentTypeResolverBuilder.java | 30 +++++------------- .../ContentNegotiationConfigurer.java | 20 +++++------- 9 files changed, 67 insertions(+), 136 deletions(-) diff --git a/spring-web/src/main/java/org/springframework/http/converter/ResourceHttpMessageConverter.java b/spring-web/src/main/java/org/springframework/http/converter/ResourceHttpMessageConverter.java index 180bf3f199..9c5c1245f3 100644 --- a/spring-web/src/main/java/org/springframework/http/converter/ResourceHttpMessageConverter.java +++ b/spring-web/src/main/java/org/springframework/http/converter/ResourceHttpMessageConverter.java @@ -27,16 +27,14 @@ import org.springframework.http.HttpInputMessage; import org.springframework.http.HttpOutputMessage; import org.springframework.http.MediaType; import org.springframework.http.MediaTypeFactory; -import org.springframework.util.ClassUtils; import org.springframework.util.StreamUtils; /** * Implementation of {@link HttpMessageConverter} that can read/write {@link Resource Resources} * and supports byte range requests. * - *

By default, this converter can read all media types. The Java Activation Framework (JAF) - - * if available - is used to determine the {@code Content-Type} of written resources. - * If JAF is not available, {@code application/octet-stream} is used. + *

By default, this converter can read all media types. The {@link MediaTypeFactory} is used + * to determine the {@code Content-Type} of written resources. * * @author Arjen Poutsma * @author Juergen Hoeller @@ -45,9 +43,6 @@ import org.springframework.util.StreamUtils; */ public class ResourceHttpMessageConverter extends AbstractHttpMessageConverter { - private static final boolean jafPresent = ClassUtils.isPresent( - "javax.activation.FileTypeMap", ResourceHttpMessageConverter.class.getClassLoader()); - private final boolean supportsReadStreaming; @@ -107,12 +102,8 @@ public class ResourceHttpMessageConverter extends AbstractHttpMessageConverter { - private static final boolean jafPresent = ClassUtils.isPresent( - "javax.activation.FileTypeMap", ResourceHttpMessageConverter.class.getClassLoader()); - public ResourceRegionHttpMessageConverter() { super(MediaType.ALL); } @@ -80,18 +77,24 @@ public class ResourceRegionHttpMessageConverter extends AbstractGenericHttpMessa @Override @SuppressWarnings("unchecked") protected MediaType getDefaultContentType(Object object) { - if (jafPresent) { - if(object instanceof ResourceRegion) { - return MediaTypeFactory.getMediaType(((ResourceRegion) object).getResource()); - } - else { - Collection regions = (Collection) object; - if(regions.size() > 0) { - return MediaTypeFactory.getMediaType(regions.iterator().next().getResource()); - } + Resource resource = null; + if (object instanceof ResourceRegion) { + resource = ((ResourceRegion) object).getResource(); + } + else { + Collection regions = (Collection) object; + if (regions.size() > 0) { + resource = regions.iterator().next().getResource(); } } - return MediaType.APPLICATION_OCTET_STREAM; + MediaType result = null; + if (resource != null) { + result = MediaTypeFactory.getMediaType(resource); + } + if (result == null) { + return MediaType.APPLICATION_OCTET_STREAM; + } + return result; } @Override diff --git a/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManager.java b/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManager.java index 2fd4e43de7..7a3763d5e8 100644 --- a/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManager.java +++ b/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManager.java @@ -143,10 +143,9 @@ public class ContentNegotiationManager implements ContentNegotiationStrategy, Me *

At startup this method returns extensions explicitly registered with * either {@link PathExtensionContentNegotiationStrategy} or * {@link ParameterContentNegotiationStrategy}. At runtime if there is a - * "path extension" strategy and its - * {@link PathExtensionContentNegotiationStrategy#setUseJaf(boolean) - * useJaf} property is set to "true", the list of extensions may - * increase as file extensions are resolved via JAF and cached. + * "path extension" strategy, the list of extensions may + * increase as file extensions are resolved via + * {@link org.springframework.http.MediaTypeFactory} and cached. */ @Override public List getAllFileExtensions() { diff --git a/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManagerFactoryBean.java b/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManagerFactoryBean.java index 45858803c5..5bc8a65966 100644 --- a/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManagerFactoryBean.java +++ b/spring-web/src/main/java/org/springframework/web/accept/ContentNegotiationManagerFactoryBean.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2016 the original author or authors. + * Copyright 2002-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -28,6 +28,7 @@ import javax.servlet.ServletContext; import org.springframework.beans.factory.FactoryBean; import org.springframework.beans.factory.InitializingBean; import org.springframework.http.MediaType; +import org.springframework.http.MediaTypeFactory; import org.springframework.util.Assert; import org.springframework.util.CollectionUtils; import org.springframework.web.context.ServletContextAware; @@ -81,8 +82,7 @@ import org.springframework.web.context.ServletContextAware; * "application/json". * *

The path extension strategy will also use {@link ServletContext#getMimeType} - * and the Java Activation framework (JAF), if available, to resolve a path - * extension to a MediaType. You may {@link #setUseJaf suppress} the use of JAF. + * and {@link MediaTypeFactory} to resolve a path extension to a MediaType. * * @author Rossen Stoyanchev * @since 3.2 @@ -100,8 +100,6 @@ public class ContentNegotiationManagerFactoryBean private boolean ignoreUnknownPathExtensions = true; - private Boolean useJaf; - private String parameterName = "format"; private ContentNegotiationStrategy defaultNegotiationStrategy; @@ -130,8 +128,8 @@ public class ContentNegotiationManagerFactoryBean * (see Spring Framework reference documentation for more details on RFD * attack protection). *

The path extension strategy will also try to use - * {@link ServletContext#getMimeType} and JAF (if present) to resolve path - * extensions. To change this behavior see the {@link #useJaf} property. + * {@link ServletContext#getMimeType} and + * {@link org.springframework.http.MediaTypeFactory} to resolve path extensions. * @param mediaTypes media type mappings * @see #addMediaType(String, MediaType) * @see #addMediaTypes(Map) @@ -177,18 +175,10 @@ public class ContentNegotiationManagerFactoryBean } /** - * When {@link #setFavorPathExtension favorPathExtension} is set, this - * property determines whether to allow use of JAF (Java Activation Framework) - * to resolve a path extension to a specific MediaType. - *

By default this is not set in which case - * {@code PathExtensionContentNegotiationStrategy} will use JAF if available. + * @deprecated as 5.0, in favor of {@link MediaTypeFactory}, which has no JAF dependency. */ + @Deprecated public void setUseJaf(boolean useJaf) { - this.useJaf = useJaf; - } - - private boolean isUseJafTurnedOff() { - return (this.useJaf != null && !this.useJaf); } /** @@ -254,7 +244,7 @@ public class ContentNegotiationManagerFactoryBean if (this.favorPathExtension) { PathExtensionContentNegotiationStrategy strategy; - if (this.servletContext != null && !isUseJafTurnedOff()) { + if (this.servletContext != null) { strategy = new ServletPathExtensionContentNegotiationStrategy( this.servletContext, this.mediaTypes); } @@ -262,9 +252,6 @@ public class ContentNegotiationManagerFactoryBean strategy = new PathExtensionContentNegotiationStrategy(this.mediaTypes); } strategy.setIgnoreUnknownExtensions(this.ignoreUnknownPathExtensions); - if (this.useJaf != null) { - strategy.setUseJaf(this.useJaf); - } strategies.add(strategy); } diff --git a/spring-web/src/main/java/org/springframework/web/accept/PathExtensionContentNegotiationStrategy.java b/spring-web/src/main/java/org/springframework/web/accept/PathExtensionContentNegotiationStrategy.java index 438027a37d..d26704c655 100644 --- a/spring-web/src/main/java/org/springframework/web/accept/PathExtensionContentNegotiationStrategy.java +++ b/spring-web/src/main/java/org/springframework/web/accept/PathExtensionContentNegotiationStrategy.java @@ -27,7 +27,6 @@ import org.springframework.core.io.Resource; import org.springframework.http.MediaType; import org.springframework.http.MediaTypeFactory; import org.springframework.util.Assert; -import org.springframework.util.ClassUtils; import org.springframework.util.StringUtils; import org.springframework.web.HttpMediaTypeNotAcceptableException; import org.springframework.web.context.request.NativeWebRequest; @@ -39,26 +38,18 @@ import org.springframework.web.util.UrlPathHelper; * request path to a key to be used to look up a media type. * *

If the file extension is not found in the explicit registrations provided - * to the constructor, the Java Activation Framework (JAF) is used as a fallback + * to the constructor, the {@link MediaTypeFactory} is used as a fallback * mechanism. * - *

The presence of the JAF is detected and enabled automatically but the - * {@link #setUseJaf(boolean)} property may be set to false. - * * @author Rossen Stoyanchev * @since 3.2 */ public class PathExtensionContentNegotiationStrategy extends AbstractMappingContentNegotiationStrategy { - private static final boolean JAF_PRESENT = ClassUtils.isPresent("javax.activation.FileTypeMap", - PathExtensionContentNegotiationStrategy.class.getClassLoader()); - private static final Log logger = LogFactory.getLog(PathExtensionContentNegotiationStrategy.class); private UrlPathHelper urlPathHelper = new UrlPathHelper(); - private boolean useJaf = true; - private boolean ignoreUnknownExtensions = true; @@ -89,11 +80,10 @@ public class PathExtensionContentNegotiationStrategy extends AbstractMappingCont } /** - * Whether to use the Java Activation Framework to look up file extensions. - *

By default this is set to "true" but depends on JAF being present. + * @deprecated as 5.0, in favor of {@link MediaTypeFactory}, which has no JAF dependency. */ + @Deprecated public void setUseJaf(boolean useJaf) { - this.useJaf = useJaf; } /** @@ -122,11 +112,9 @@ public class PathExtensionContentNegotiationStrategy extends AbstractMappingCont protected MediaType handleNoMatch(NativeWebRequest webRequest, String extension) throws HttpMediaTypeNotAcceptableException { - if (this.useJaf && JAF_PRESENT) { - MediaType mediaType = MediaTypeFactory.getMediaType("file." + extension); - if (mediaType != null && !MediaType.APPLICATION_OCTET_STREAM.equals(mediaType)) { - return mediaType; - } + MediaType mediaType = MediaTypeFactory.getMediaType("file." + extension); + if (mediaType != null) { + return mediaType; } if (this.ignoreUnknownExtensions) { return null; @@ -138,7 +126,7 @@ public class PathExtensionContentNegotiationStrategy extends AbstractMappingCont * A public method exposing the knowledge of the path extension strategy to * resolve file extensions to a {@link MediaType} in this case for a given * {@link Resource}. The method first looks up any explicitly registered - * file extensions first and then falls back on JAF if available. + * file extensions first and then falls back on {@link MediaTypeFactory} if available. * @param resource the resource to look up * @return the MediaType for the extension, or {@code null} if none found * @since 4.3 @@ -151,12 +139,9 @@ public class PathExtensionContentNegotiationStrategy extends AbstractMappingCont if (extension != null) { mediaType = lookupMediaType(extension); } - if (mediaType == null && JAF_PRESENT) { + if (mediaType == null) { mediaType = MediaTypeFactory.getMediaType(filename); } - if (MediaType.APPLICATION_OCTET_STREAM.equals(mediaType)) { - mediaType = null; - } return mediaType; } diff --git a/spring-web/src/main/java/org/springframework/web/accept/ServletPathExtensionContentNegotiationStrategy.java b/spring-web/src/main/java/org/springframework/web/accept/ServletPathExtensionContentNegotiationStrategy.java index 10d80b2bee..05a27a66ae 100644 --- a/spring-web/src/main/java/org/springframework/web/accept/ServletPathExtensionContentNegotiationStrategy.java +++ b/spring-web/src/main/java/org/springframework/web/accept/ServletPathExtensionContentNegotiationStrategy.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2016 the original author or authors. + * Copyright 2002-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -52,7 +52,8 @@ public class ServletPathExtensionContentNegotiationStrategy extends PathExtensio /** * Create an instance without any mappings to start with. Mappings may be * added later when extensions are resolved through - * {@link ServletContext#getMimeType(String)} or via JAF. + * {@link ServletContext#getMimeType(String)} or via + * {@link org.springframework.http.MediaTypeFactory}. */ public ServletPathExtensionContentNegotiationStrategy(ServletContext context) { this(context, null); @@ -61,7 +62,8 @@ public class ServletPathExtensionContentNegotiationStrategy extends PathExtensio /** * Resolve file extension via {@link ServletContext#getMimeType(String)} - * and also delegate to base class for a potential JAF lookup. + * and also delegate to base class for a potential + * {@link org.springframework.http.MediaTypeFactory} lookup. */ @Override protected MediaType handleNoMatch(NativeWebRequest webRequest, String extension) diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/accept/PathExtensionContentTypeResolver.java b/spring-webflux/src/main/java/org/springframework/web/reactive/accept/PathExtensionContentTypeResolver.java index 5a2d17a639..d32bdde74f 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/accept/PathExtensionContentTypeResolver.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/accept/PathExtensionContentTypeResolver.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2016 the original author or authors. + * Copyright 2002-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -33,17 +33,14 @@ import org.springframework.web.util.UriUtils; * the request path and uses that as the media type lookup key. * *

If the file extension is not found in the explicit registrations provided - * to the constructor, the Java Activation Framework (JAF) is used as a fallback - * mechanism. The presence of the JAF is detected and enabled automatically but - * the {@link #setUseJaf(boolean)} property may be set to false. + * to the constructor, the {@link MediaTypeFactory} is used as a fallback + * mechanism. * * @author Rossen Stoyanchev * @since 5.0 */ public class PathExtensionContentTypeResolver extends AbstractMappingContentTypeResolver { - private boolean useJaf = true; - private boolean ignoreUnknownExtensions = true; @@ -63,14 +60,6 @@ public class PathExtensionContentTypeResolver extends AbstractMappingContentType } - /** - * Whether to use the Java Activation Framework to look up file extensions. - *

By default this is set to "true" but depends on JAF being present. - */ - public void setUseJaf(boolean useJaf) { - this.useJaf = useJaf; - } - /** * Whether to ignore requests with unknown file extension. Setting this to * {@code false} results in {@code HttpMediaTypeNotAcceptableException}. @@ -90,11 +79,9 @@ public class PathExtensionContentTypeResolver extends AbstractMappingContentType @Override protected MediaType handleNoMatch(String key) throws NotAcceptableStatusException { - if (this.useJaf) { - MediaType mediaType = MediaTypeFactory.getMediaType("file." + key); - if (mediaType != null && !MediaType.APPLICATION_OCTET_STREAM.equals(mediaType)) { - return mediaType; - } + MediaType mediaType = MediaTypeFactory.getMediaType("file." + key); + if (mediaType != null) { + return mediaType; } if (!this.ignoreUnknownExtensions) { throw new NotAcceptableStatusException(getAllMediaTypes()); @@ -105,7 +92,7 @@ public class PathExtensionContentTypeResolver extends AbstractMappingContentType /** * A public method exposing the knowledge of the path extension resolver to * determine the media type for a given {@link Resource}. First it checks - * the explicitly registered mappings and then falls back on JAF. + * the explicitly registered mappings and then falls back on {@link MediaTypeFactory}. * @param resource the resource * @return the MediaType for the extension, or {@code null} if none determined */ @@ -120,9 +107,6 @@ public class PathExtensionContentTypeResolver extends AbstractMappingContentType if (mediaType == null) { mediaType = MediaTypeFactory.getMediaType(filename); } - if (MediaType.APPLICATION_OCTET_STREAM.equals(mediaType)) { - mediaType = null; - } return mediaType; } diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/accept/RequestedContentTypeResolverBuilder.java b/spring-webflux/src/main/java/org/springframework/web/reactive/accept/RequestedContentTypeResolverBuilder.java index 67cf5e774d..101b864e17 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/accept/RequestedContentTypeResolverBuilder.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/accept/RequestedContentTypeResolverBuilder.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2016 the original author or authors. + * Copyright 2002-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -74,9 +74,9 @@ import org.springframework.util.CollectionUtils; * {@link #mediaTypes(Map)}. This will be used to resolve path extensions or a * parameter value such as "json" to a media type such as "application/json". * - *

The path extension strategy will also use the Java Activation framework - * (JAF), if available, to resolve a path extension to a MediaType. You may - * {@link #useJaf suppress} the use of JAF. + *

The path extension strategy will also use + * {@link org.springframework.http.MediaTypeFactory} to resolve a path extension + * to a MediaType. * * @author Rossen Stoyanchev * @since 5.0 @@ -93,8 +93,6 @@ public class RequestedContentTypeResolverBuilder { private boolean ignoreUnknownPathExtensions = true; - private Boolean useJaf; - private String parameterName = "format"; private RequestedContentTypeResolver contentTypeResolver; @@ -119,8 +117,9 @@ public class RequestedContentTypeResolverBuilder { * whitelisted for the purpose of Reflected File Download attack detection * (see Spring Framework reference documentation for more details on RFD * attack protection). - *

The path extension strategy will also try to use JAF (if present) to - * resolve path extensions. To change this behavior see {@link #useJaf}. + *

The path extension strategy will also use the + * {@link org.springframework.http.MediaTypeFactory} to resolve path + * extensions. * @param mediaTypes media type mappings */ public RequestedContentTypeResolverBuilder mediaTypes(Map mediaTypes) { @@ -153,18 +152,6 @@ public class RequestedContentTypeResolverBuilder { return this; } - /** - * When {@link #favorPathExtension favorPathExtension} is set, this - * property determines whether to allow use of JAF (Java Activation Framework) - * to resolve a path extension to a specific MediaType. - *

By default this is not set in which case - * {@code PathExtensionContentNegotiationStrategy} will use JAF if available. - */ - public RequestedContentTypeResolverBuilder useJaf(boolean useJaf) { - this.useJaf = useJaf; - return this; - } - /** * Whether a request parameter ("format" by default) should be used to * determine the requested media type. For this option to work you must @@ -224,9 +211,6 @@ public class RequestedContentTypeResolverBuilder { if (this.favorPathExtension) { PathExtensionContentTypeResolver resolver = new PathExtensionContentTypeResolver(this.mediaTypes); resolver.setIgnoreUnknownExtensions(this.ignoreUnknownPathExtensions); - if (this.useJaf != null) { - resolver.setUseJaf(this.useJaf); - } resolvers.add(resolver); } diff --git a/spring-webmvc/src/main/java/org/springframework/web/servlet/config/annotation/ContentNegotiationConfigurer.java b/spring-webmvc/src/main/java/org/springframework/web/servlet/config/annotation/ContentNegotiationConfigurer.java index 68d0f053fd..27f22f766a 100644 --- a/spring-webmvc/src/main/java/org/springframework/web/servlet/config/annotation/ContentNegotiationConfigurer.java +++ b/spring-webmvc/src/main/java/org/springframework/web/servlet/config/annotation/ContentNegotiationConfigurer.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2016 the original author or authors. + * Copyright 2002-2017 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -20,6 +20,7 @@ import java.util.Map; import javax.servlet.ServletContext; import org.springframework.http.MediaType; +import org.springframework.http.MediaTypeFactory; import org.springframework.web.accept.ContentNegotiationManager; import org.springframework.web.accept.ContentNegotiationManagerFactoryBean; import org.springframework.web.accept.ContentNegotiationStrategy; @@ -76,9 +77,8 @@ import org.springframework.web.accept.PathExtensionContentNegotiationStrategy; * type such as "application/json". * *

The path extension strategy will also use {@link ServletContext#getMimeType} - * and the Java Activation framework (JAF), if available, to resolve a path - * extension to a MediaType. You may however {@link #useJaf suppress} the use - * of JAF. + * and the {@link MediaTypeFactory} to resolve a path + * extension to a MediaType. * * @author Rossen Stoyanchev * @since 3.2 @@ -119,8 +119,8 @@ public class ContentNegotiationConfigurer { * (see Spring Framework reference documentation for more details on RFD * attack protection). *

The path extension strategy will also try to use - * {@link ServletContext#getMimeType} and JAF (if present) to resolve path - * extensions. To change this behavior see the {@link #useJaf} property. + * {@link ServletContext#getMimeType} and {@link MediaTypeFactory} to resolve path + * extensions. * @param extension the key to look up * @param mediaType the media type * @see #mediaTypes(Map) @@ -166,14 +166,10 @@ public class ContentNegotiationConfigurer { } /** - * When {@link #favorPathExtension} is set, this property determines whether - * to allow use of JAF (Java Activation Framework) to resolve a path - * extension to a specific MediaType. - *

By default this is not set in which case - * {@code PathExtensionContentNegotiationStrategy} will use JAF if available. + * @deprecated as 5.0, in favor of {@link MediaTypeFactory}, which has no JAF dependency. */ + @Deprecated public ContentNegotiationConfigurer useJaf(boolean useJaf) { - this.factory.setUseJaf(useJaf); return this; } -- GitLab