Merge branch '1.2.x'
This commit is contained in:
@@ -57,7 +57,7 @@ public class MetricRegistryMetricReader implements MetricReader, MetricRegistryL
|
||||
|
||||
private static Log logger = LogFactory.getLog(MetricRegistryMetricReader.class);
|
||||
|
||||
private static final Map<Class<?>, Set<String>> NUMBER_KEYS = new ConcurrentHashMap<Class<?>, Set<String>>();
|
||||
private static final Map<Class<?>, Set<String>> numberKeys = new ConcurrentHashMap<Class<?>, Set<String>>();
|
||||
|
||||
private final Object monitor = new Object();
|
||||
|
||||
@@ -129,17 +129,16 @@ public class MetricRegistryMetricReader implements MetricReader, MetricRegistryL
|
||||
|
||||
@Override
|
||||
public void onGaugeAdded(String name, Gauge<?> gauge) {
|
||||
if (gauge.getValue() instanceof Number) {
|
||||
this.names.put(name, name);
|
||||
synchronized (this.monitor) {
|
||||
this.reverse.add(name, name);
|
||||
if (!(gauge.getValue() instanceof Number)) {
|
||||
if (logger.isDebugEnabled()) {
|
||||
logger.debug("Ignoring gauge '" + name + "' (" + gauge
|
||||
+ ") as its value is not a Number");
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (logger.isDebugEnabled()) {
|
||||
logger.debug("Ignoring gauge '" + name + "' (" + gauge
|
||||
+ ") as its value is not a Number");
|
||||
this.names.put(name, name);
|
||||
synchronized (this.monitor) {
|
||||
this.reverse.add(name, name);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -225,11 +224,9 @@ public class MetricRegistryMetricReader implements MetricReader, MetricRegistryL
|
||||
|
||||
private void remove(String name) {
|
||||
List<String> keys;
|
||||
|
||||
synchronized (this.monitor) {
|
||||
keys = this.reverse.remove(name);
|
||||
}
|
||||
|
||||
if (keys != null) {
|
||||
for (String key : keys) {
|
||||
this.names.remove(name + "." + key);
|
||||
@@ -238,7 +235,7 @@ public class MetricRegistryMetricReader implements MetricReader, MetricRegistryL
|
||||
}
|
||||
|
||||
private static Set<String> getNumberKeys(Object metric) {
|
||||
Set<String> result = NUMBER_KEYS.get(metric.getClass());
|
||||
Set<String> result = numberKeys.get(metric.getClass());
|
||||
if (result == null) {
|
||||
result = new HashSet<String>();
|
||||
}
|
||||
@@ -249,7 +246,7 @@ public class MetricRegistryMetricReader implements MetricReader, MetricRegistryL
|
||||
result.add(descriptor.getName());
|
||||
}
|
||||
}
|
||||
NUMBER_KEYS.put(metric.getClass(), result);
|
||||
numberKeys.put(metric.getClass(), result);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ import static org.hamcrest.Matchers.nullValue;
|
||||
import static org.junit.Assert.assertThat;
|
||||
|
||||
/**
|
||||
* Tests for {@link MetricRegistryMetricReader}
|
||||
* Tests for {@link MetricRegistryMetricReader}.
|
||||
*
|
||||
* @author Andy Wilkinson
|
||||
*/
|
||||
@@ -73,4 +73,5 @@ public class MetricRegistryMetricReaderTests {
|
||||
this.metricRegistry.remove("test");
|
||||
assertThat(this.metricReader.findOne("test"), is(nullValue()));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2012-2014 the original author or authors.
|
||||
* Copyright 2012-2015 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.
|
||||
@@ -63,8 +63,8 @@ class DataSourceInitializer implements ApplicationListener<DataSourceInitialized
|
||||
logger.debug("Initialization disabled (not running DDL scripts)");
|
||||
return;
|
||||
}
|
||||
if (applicationContext.getBeanNamesForType(DataSource.class, false, false).length > 0) {
|
||||
this.dataSource = applicationContext.getBean(DataSource.class);
|
||||
if (this.applicationContext.getBeanNamesForType(DataSource.class, false, false).length > 0) {
|
||||
this.dataSource = this.applicationContext.getBean(DataSource.class);
|
||||
}
|
||||
if (this.dataSource == null) {
|
||||
logger.debug("No DataSource found so not initializing");
|
||||
|
||||
@@ -22,12 +22,14 @@ import java.util.Set;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
|
||||
import org.springframework.beans.factory.SmartInitializingSingleton;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.security.SecurityProperties.User;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ApplicationListener;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Primary;
|
||||
@@ -70,55 +72,33 @@ public class AuthenticationManagerConfiguration {
|
||||
|
||||
@Bean
|
||||
@Primary
|
||||
public AuthenticationManager authenticationManager(AuthenticationConfiguration auth)
|
||||
throws Exception {
|
||||
return auth.getAuthenticationManager();
|
||||
public AuthenticationManager authenticationManager(
|
||||
AuthenticationConfiguration configuration) throws Exception {
|
||||
return configuration.getAuthenticationManager();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public static BootDefaultingAuthenticationConfigurerAdapter bootDefaultingAuthenticationConfigurerAdapter(
|
||||
SecurityProperties security, List<SecurityPrerequisite> dependencies) {
|
||||
return new BootDefaultingAuthenticationConfigurerAdapter(security);
|
||||
}
|
||||
|
||||
@Component
|
||||
protected static class AuthenticationManagerConfigurationListener implements
|
||||
SmartInitializingSingleton {
|
||||
|
||||
@Autowired
|
||||
private AuthenticationEventPublisher authenticationEventPublisher;
|
||||
|
||||
@Autowired
|
||||
private ApplicationContext context;
|
||||
|
||||
@Override
|
||||
public void afterSingletonsInstantiated() {
|
||||
if (this.context.getBeanNamesForType(AuthenticationManager.class).length == 0) {
|
||||
return;
|
||||
}
|
||||
AuthenticationManager manager = this.context
|
||||
.getBean(AuthenticationManager.class);
|
||||
if (manager instanceof ProviderManager) {
|
||||
((ProviderManager) manager)
|
||||
.setAuthenticationEventPublisher(this.authenticationEventPublisher);
|
||||
}
|
||||
}
|
||||
|
||||
public static SpringBootAuthenticationConfigurerAdapter springBootAuthenticationConfigurerAdapter(
|
||||
SecurityProperties securityProperties, List<SecurityPrerequisite> dependencies) {
|
||||
return new SpringBootAuthenticationConfigurerAdapter(securityProperties);
|
||||
}
|
||||
|
||||
/**
|
||||
* We must add {@link BootDefaultingAuthenticationConfigurerAdapter} in the init phase
|
||||
* of the last {@link GlobalAuthenticationConfigurerAdapter}. The reason is that the
|
||||
* typical flow is something like:
|
||||
* {@link GlobalAuthenticationConfigurerAdapter} to apply
|
||||
* {@link DefaultInMemoryUserDetailsManagerConfigurer}. We must apply
|
||||
* {@link DefaultInMemoryUserDetailsManagerConfigurer} in the init phase of the last
|
||||
* {@link GlobalAuthenticationConfigurerAdapter}. The reason is that the typical flow
|
||||
* is something like:
|
||||
*
|
||||
* <ul>
|
||||
* <li>A
|
||||
* {@link GlobalAuthenticationConfigurerAdapter#init(AuthenticationManagerBuilder)}
|
||||
* exists that adds a {@link SecurityConfigurer} to the
|
||||
* {@link AuthenticationManagerBuilder}</li>
|
||||
* {@link AuthenticationManagerBuilder}.</li>
|
||||
* <li>
|
||||
* {@link AuthenticationManagerConfiguration#init(AuthenticationManagerBuilder)} adds
|
||||
* BootDefaultingAuthenticationConfigurerAdapter so it is after the
|
||||
* {@link SecurityConfigurer} in the first step</li>
|
||||
* {@link SpringBootAuthenticationConfigurerAdapter} so it is after the
|
||||
* {@link SecurityConfigurer} in the first step.</li>
|
||||
* <li>We then can default an {@link AuthenticationProvider} if necessary. Note we can
|
||||
* only invoke the
|
||||
* {@link AuthenticationManagerBuilder#authenticationProvider(AuthenticationProvider)}
|
||||
@@ -128,70 +108,106 @@ public class AuthenticationManagerConfiguration {
|
||||
* </ul>
|
||||
*/
|
||||
@Order(Ordered.LOWEST_PRECEDENCE - 100)
|
||||
private static class BootDefaultingAuthenticationConfigurerAdapter extends
|
||||
private static class SpringBootAuthenticationConfigurerAdapter extends
|
||||
GlobalAuthenticationConfigurerAdapter {
|
||||
private final SecurityProperties security;
|
||||
|
||||
private final SecurityProperties securityProperties;
|
||||
|
||||
@Autowired
|
||||
public BootDefaultingAuthenticationConfigurerAdapter(SecurityProperties security) {
|
||||
this.security = security;
|
||||
public SpringBootAuthenticationConfigurerAdapter(
|
||||
SecurityProperties securityProperties) {
|
||||
this.securityProperties = securityProperties;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void init(AuthenticationManagerBuilder auth) throws Exception {
|
||||
auth.apply(new DefaultingInMemoryUserDetailsManagerConfigurer(this.security));
|
||||
}
|
||||
|
||||
/**
|
||||
* This is necessary to delay adding the default user.
|
||||
*
|
||||
* <ul>
|
||||
* <li>A GlobalAuthenticationConfigurerAdapter will initialize the
|
||||
* AuthenticationManagerBuilder with a Configurer which will be after any
|
||||
* GlobalAuthenticationConfigurerAdapter</li>
|
||||
* <li>BootDefaultingAuthenticationConfigurerAdapter will be invoked after all
|
||||
* GlobalAuthenticationConfigurerAdapter, but before the Configurers that were
|
||||
* added by other GlobalAuthenticationConfigurerAdapter instances</li>
|
||||
* <li>BootDefaultingAuthenticationConfigurerAdapter will add
|
||||
* DefaultingInMemoryUserDetailsManagerConfigurer after all Configurer instances</li>
|
||||
* <li>All init methods will be invoked</li>
|
||||
* <li>All configure methods will be invoked which is where the
|
||||
* AuthenticationProvider instances are setup</li>
|
||||
* <li>If no AuthenticationProviders were provided,
|
||||
* DefaultingInMemoryUserDetailsManagerConfigurer will default the value</li>
|
||||
* </ul>
|
||||
*
|
||||
* @author Rob Winch
|
||||
*/
|
||||
private static class DefaultingInMemoryUserDetailsManagerConfigurer extends
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder> {
|
||||
private final SecurityProperties security;
|
||||
|
||||
public DefaultingInMemoryUserDetailsManagerConfigurer(
|
||||
SecurityProperties security) {
|
||||
this.security = security;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
if (auth.isConfigured()) {
|
||||
return;
|
||||
}
|
||||
|
||||
User user = this.security.getUser();
|
||||
if (user.isDefaultPassword()) {
|
||||
logger.info("\n\nUsing default security password: "
|
||||
+ user.getPassword() + "\n");
|
||||
}
|
||||
|
||||
Set<String> roles = new LinkedHashSet<String>(user.getRole());
|
||||
withUser(user.getName()).password(user.getPassword()).roles(
|
||||
roles.toArray(new String[roles.size()]));
|
||||
|
||||
super.configure(auth);
|
||||
}
|
||||
|
||||
auth.apply(new DefaultInMemoryUserDetailsManagerConfigurer(
|
||||
this.securityProperties));
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@link InMemoryUserDetailsManagerConfigurer} to add user details from
|
||||
* {@link SecurityProperties}. This is necessary to delay adding the default user.
|
||||
*
|
||||
* <ul>
|
||||
* <li>A {@link GlobalAuthenticationConfigurerAdapter} will initialize the
|
||||
* {@link AuthenticationManagerBuilder} with a Configurer which will be after any
|
||||
* {@link GlobalAuthenticationConfigurerAdapter}.</li>
|
||||
* <li>{@link SpringBootAuthenticationConfigurerAdapter} will be invoked after all
|
||||
* {@link GlobalAuthenticationConfigurerAdapter}, but before the Configurers that were
|
||||
* added by other {@link GlobalAuthenticationConfigurerAdapter} instances.</li>
|
||||
* <li>A {@link SpringBootAuthenticationConfigurerAdapter} will add
|
||||
* {@link DefaultInMemoryUserDetailsManagerConfigurer} after all Configurer instances.
|
||||
* </li>
|
||||
* <li>All init methods will be invoked.</li>
|
||||
* <li>All configure methods will be invoked which is where the
|
||||
* {@link AuthenticationProvider} instances are setup.</li>
|
||||
* <li>If no AuthenticationProviders were provided,
|
||||
* {@link DefaultInMemoryUserDetailsManagerConfigurer} will default the value.</li>
|
||||
* </ul>
|
||||
*/
|
||||
private static class DefaultInMemoryUserDetailsManagerConfigurer extends
|
||||
InMemoryUserDetailsManagerConfigurer<AuthenticationManagerBuilder> {
|
||||
|
||||
private final SecurityProperties securityProperties;
|
||||
|
||||
public DefaultInMemoryUserDetailsManagerConfigurer(
|
||||
SecurityProperties securityProperties) {
|
||||
this.securityProperties = securityProperties;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void configure(AuthenticationManagerBuilder auth) throws Exception {
|
||||
if (auth.isConfigured()) {
|
||||
return;
|
||||
}
|
||||
User user = this.securityProperties.getUser();
|
||||
if (user.isDefaultPassword()) {
|
||||
logger.info("\n\nUsing default security password: " + user.getPassword()
|
||||
+ "\n");
|
||||
}
|
||||
Set<String> roles = new LinkedHashSet<String>(user.getRole());
|
||||
withUser(user.getName()).password(user.getPassword()).roles(
|
||||
roles.toArray(new String[roles.size()]));
|
||||
super.configure(auth);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* {@link ApplicationListener} to autowire the {@link AuthenticationEventPublisher}
|
||||
* into the {@link AuthenticationManager}.
|
||||
*/
|
||||
@Component
|
||||
protected static class AuthenticationManagerConfigurationListener implements
|
||||
SmartInitializingSingleton {
|
||||
|
||||
@Autowired
|
||||
private AuthenticationEventPublisher eventPublisher;
|
||||
|
||||
@Autowired
|
||||
private ApplicationContext context;
|
||||
|
||||
@Override
|
||||
public void afterSingletonsInstantiated() {
|
||||
try {
|
||||
configureAuthenticationManager(this.context
|
||||
.getBean(AuthenticationManager.class));
|
||||
}
|
||||
catch (NoSuchBeanDefinitionException ex) {
|
||||
// Ignore
|
||||
}
|
||||
}
|
||||
|
||||
private void configureAuthenticationManager(AuthenticationManager manager) {
|
||||
if (manager instanceof ProviderManager) {
|
||||
((ProviderManager) manager)
|
||||
.setAuthenticationEventPublisher(this.eventPublisher);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -141,29 +141,35 @@ public class UndertowEmbeddedServletContainer implements EmbeddedServletContaine
|
||||
}
|
||||
|
||||
private Port getPortFromChannel(Object channel) {
|
||||
Object tcpServer;
|
||||
String protocol;
|
||||
Object tcpServer = channel;
|
||||
String protocol = "http";
|
||||
Field sslContext = ReflectionUtils.findField(channel.getClass(), "sslContext");
|
||||
if (sslContext != null) {
|
||||
Field tcpServerField = ReflectionUtils.findField(channel.getClass(),
|
||||
"tcpServer");
|
||||
ReflectionUtils.makeAccessible(tcpServerField);
|
||||
tcpServer = ReflectionUtils.getField(tcpServerField, channel);
|
||||
tcpServer = getTcpServer(channel);
|
||||
protocol = "https";
|
||||
}
|
||||
else {
|
||||
tcpServer = channel;
|
||||
protocol = "http";
|
||||
}
|
||||
Field socketField = ReflectionUtils.findField(tcpServer.getClass(), "socket");
|
||||
if (socketField != null) {
|
||||
ReflectionUtils.makeAccessible(socketField);
|
||||
return new Port(((ServerSocket) ReflectionUtils.getField(socketField,
|
||||
tcpServer)).getLocalPort(), protocol);
|
||||
ServerSocket socket = getSocket(tcpServer);
|
||||
if (socket != null) {
|
||||
return new Port(socket.getLocalPort(), protocol);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private Object getTcpServer(Object channel) {
|
||||
Field field = ReflectionUtils.findField(channel.getClass(), "tcpServer");
|
||||
ReflectionUtils.makeAccessible(field);
|
||||
return ReflectionUtils.getField(field, channel);
|
||||
}
|
||||
|
||||
private ServerSocket getSocket(Object tcpServer) {
|
||||
Field socketField = ReflectionUtils.findField(tcpServer.getClass(), "socket");
|
||||
if (socketField == null) {
|
||||
return null;
|
||||
}
|
||||
ReflectionUtils.makeAccessible(socketField);
|
||||
return (ServerSocket) ReflectionUtils.getField(socketField, tcpServer);
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void stop() throws EmbeddedServletContainerException {
|
||||
if (this.started) {
|
||||
@@ -178,24 +184,32 @@ public class UndertowEmbeddedServletContainer implements EmbeddedServletContaine
|
||||
if (ports.isEmpty()) {
|
||||
return 0;
|
||||
}
|
||||
return ports.get(0).portNumber;
|
||||
return ports.get(0).getNumber();
|
||||
}
|
||||
|
||||
/**
|
||||
* An active undertow port.
|
||||
*/
|
||||
private static class Port {
|
||||
|
||||
private final int portNumber;
|
||||
private final int number;
|
||||
|
||||
private final String protocol;
|
||||
|
||||
private Port(int portNumber, String protocol) {
|
||||
this.portNumber = portNumber;
|
||||
private Port(int number, String protocol) {
|
||||
this.number = number;
|
||||
this.protocol = protocol;
|
||||
}
|
||||
|
||||
public int getNumber() {
|
||||
return this.number;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return this.portNumber + " (" + this.protocol + ")";
|
||||
return this.number + " (" + this.protocol + ")";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user