1
+ /*
2
+ * Copyright 2002-2022 the original author or authors.
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * https://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+
17
+ package org .springframework .core .io .support ;
18
+
19
+ import java .util .List ;
20
+ import java .util .Map ;
21
+ import java .util .function .Consumer ;
22
+
23
+ import org .apache .commons .logging .Log ;
24
+ import org .apache .commons .logging .LogFactory ;
25
+
26
+ import org .springframework .aot .hint .MemberCategory ;
27
+ import org .springframework .aot .hint .RuntimeHints ;
28
+ import org .springframework .aot .hint .RuntimeHintsRegistrar ;
29
+ import org .springframework .aot .hint .TypeHint ;
30
+ import org .springframework .core .log .LogMessage ;
31
+ import org .springframework .lang .Nullable ;
32
+ import org .springframework .util .ClassUtils ;
33
+
34
+ /**
35
+ * {@link RuntimeHintsRegistrar} to register hints for {@code spring.factories}.
36
+ *
37
+ * @author Brian Clozel
38
+ * @author Phillip Webb
39
+ * @since 6.0
40
+ * @see SpringFactoriesLoader
41
+ */
42
+ class SpringFactoriesLoaderRuntimeHintsRegistrar implements RuntimeHintsRegistrar {
43
+
44
+ private static List <String > RESOURCE_LOCATIONS = List
45
+ .of (SpringFactoriesLoader .FACTORIES_RESOURCE_LOCATION );
46
+
47
+ private static final Consumer <TypeHint .Builder > HINT = builder -> builder
48
+ .withMembers (MemberCategory .INVOKE_DECLARED_CONSTRUCTORS );
49
+
50
+ private final Log logger = LogFactory .getLog (SpringFactoriesLoaderRuntimeHintsRegistrar .class );
51
+
52
+
53
+ @ Override
54
+ public void registerHints (RuntimeHints hints , ClassLoader classLoader ) {
55
+ for (String resourceLocation : RESOURCE_LOCATIONS ) {
56
+ registerHints (hints , classLoader , resourceLocation );
57
+ }
58
+ }
59
+
60
+ private void registerHints (RuntimeHints hints , ClassLoader classLoader ,
61
+ String resourceLocation ) {
62
+ hints .resources ().registerPattern (resourceLocation );
63
+ Map <String , List <String >> factories = SpringFactoriesLoader
64
+ .loadFactoriesResource (classLoader , resourceLocation );
65
+ factories .forEach ((factoryClassName , implementationClassNames ) ->
66
+ registerHints (hints , classLoader , factoryClassName , implementationClassNames ));
67
+ }
68
+
69
+ private void registerHints (RuntimeHints hints , ClassLoader classLoader ,
70
+ String factoryClassName , List <String > implementationClassNames ) {
71
+ Class <?> factoryClass = resolveClassName (classLoader , factoryClassName );
72
+ if (factoryClass == null ) {
73
+ logger .trace (LogMessage .format ("Skipping factories for [%s]" , factoryClassName ));
74
+ return ;
75
+ }
76
+ logger .trace (LogMessage .format ("Processing factories for [%s]" , factoryClassName ));
77
+ hints .reflection ().registerType (factoryClass , HINT );
78
+ for (String implementationClassName : implementationClassNames ) {
79
+ Class <?> implementationType = resolveClassName (classLoader , implementationClassName );
80
+ logger .trace (LogMessage .format ("%s factory type [%s] and implementation [%s]" ,
81
+ (implementationType != null ) ? "Processing" : "Skipping" , factoryClassName , implementationClassName ));
82
+ if (implementationType != null ) {
83
+ hints .reflection ().registerType (implementationType , HINT );
84
+ }
85
+ }
86
+ }
87
+
88
+ @ Nullable
89
+ private Class <?> resolveClassName (ClassLoader classLoader , String factoryClassName ) {
90
+ try {
91
+ return ClassUtils .resolveClassName (factoryClassName , classLoader );
92
+ }
93
+ catch (Exception ex ) {
94
+ return null ;
95
+ }
96
+ }
97
+
98
+ }
0 commit comments