1 /*
2  * Copyright 2008-2019 by Emeric Vernat
3  *
4  *     This file is part of Java Melody.
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *     http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  */

18 package net.bull.javamelody;
19
20 import java.util.ArrayList;
21 import java.util.List;
22
23 import org.springframework.beans.factory.config.BeanPostProcessor;
24 import org.springframework.core.PriorityOrdered;
25 import org.springframework.http.client.ClientHttpRequestInterceptor;
26 import org.springframework.web.client.RestTemplate;
27
28 import net.bull.javamelody.internal.common.LOG;
29
30 /**
31  * Post-processor Spring pour un éventuel {@link RestTemplate} défini dans le fichier xml Spring.
32  * @author Emeric Vernat
33  */

34 public class SpringRestTemplateBeanPostProcessor implements BeanPostProcessor, PriorityOrdered {
35     private static final boolean REST_TEMPLATE_INTERCEPTOR_AVAILABLE = isRestTemplateInterceptorAvailable();
36
37     // l'interface PriorityOrdered place la priorité assez haute dans le contexte Spring
38     // quelle que soit la valeur de order
39     private int order = LOWEST_PRECEDENCE;
40
41     /** {@inheritDoc} */
42     @Override
43     public int getOrder() {
44         return order;
45     }
46
47     /**
48      * Définit la priorité dans le contexte Spring.
49      * @param order int
50      */

51     public void setOrder(int order) {
52         this.order = order;
53     }
54
55     /** {@inheritDoc} */
56     @Override
57     public Object postProcessBeforeInitialization(Object bean, String beanName) {
58         return bean;
59     }
60
61     /** {@inheritDoc} */
62     @Override
63     public Object postProcessAfterInitialization(Object bean, String beanName) {
64         // RestTemplate et getInterceptors() existent depuis spring-web 3.1.0.RELEASE
65         if (REST_TEMPLATE_INTERCEPTOR_AVAILABLE && bean instanceof RestTemplate) {
66             final RestTemplate restTemplate = (RestTemplate) bean;
67             final List<ClientHttpRequestInterceptor> interceptors = new ArrayList<>(
68                     restTemplate.getInterceptors());
69             for (final ClientHttpRequestInterceptor interceptor : interceptors) {
70                 if (interceptor instanceof SpringRestTemplateInterceptor) {
71                     return bean;
72                 }
73             }
74             interceptors.add(SpringRestTemplateInterceptor.SINGLETON);
75             restTemplate.setInterceptors(interceptors);
76             LOG.debug("rest template interceptor initialized");
77         }
78
79         return bean;
80     }
81
82     private static boolean isRestTemplateInterceptorAvailable() {
83         try {
84             final Class<?> clazz = Class.forName("org.springframework.web.client.RestTemplate");
85             clazz.getMethod("getInterceptors");
86             return true;
87         } catch (final ClassNotFoundException | SecurityException | NoSuchMethodException e) {
88             return false;
89         }
90     }
91 }
92