18
18
import static org .springframework .data .mongodb .repository .aot .MongoCodeBlocks .*;
19
19
import static org .springframework .data .mongodb .repository .aot .QueryBlocks .*;
20
20
21
+ import java .io .IOException ;
21
22
import java .lang .reflect .Method ;
23
+ import java .util .Properties ;
22
24
23
25
import org .apache .commons .logging .Log ;
24
26
import org .apache .commons .logging .LogFactory ;
25
27
import org .jspecify .annotations .Nullable ;
26
28
27
29
import org .springframework .core .annotation .AnnotatedElementUtils ;
30
+ import org .springframework .core .io .support .PathMatchingResourcePatternResolver ;
28
31
import org .springframework .data .mongodb .core .MongoOperations ;
29
32
import org .springframework .data .mongodb .core .aggregation .AggregationUpdate ;
30
33
import org .springframework .data .mongodb .core .convert .MongoCustomConversions ;
31
34
import org .springframework .data .mongodb .core .mapping .MongoMappingContext ;
32
35
import org .springframework .data .mongodb .repository .Query ;
33
36
import org .springframework .data .mongodb .repository .Update ;
34
37
import org .springframework .data .mongodb .repository .VectorSearch ;
38
+ import org .springframework .data .mongodb .repository .config .MongoRepositoryConfigurationExtension ;
35
39
import org .springframework .data .mongodb .repository .query .MongoQueryMethod ;
36
40
import org .springframework .data .repository .aot .generate .AotRepositoryClassBuilder ;
37
41
import org .springframework .data .repository .aot .generate .AotRepositoryConstructorBuilder ;
38
42
import org .springframework .data .repository .aot .generate .MethodContributor ;
39
43
import org .springframework .data .repository .aot .generate .QueryMetadata ;
40
44
import org .springframework .data .repository .aot .generate .RepositoryContributor ;
41
45
import org .springframework .data .repository .config .AotRepositoryContext ;
46
+ import org .springframework .data .repository .config .PropertiesBasedNamedQueriesFactoryBean ;
47
+ import org .springframework .data .repository .config .RepositoryConfigurationSource ;
48
+ import org .springframework .data .repository .core .NamedQueries ;
42
49
import org .springframework .data .repository .core .RepositoryInformation ;
50
+ import org .springframework .data .repository .core .support .PropertiesBasedNamedQueries ;
43
51
import org .springframework .data .repository .core .support .RepositoryFactoryBeanSupport ;
44
52
import org .springframework .data .repository .query .QueryMethod ;
45
53
import org .springframework .data .repository .query .parser .PartTree ;
@@ -61,11 +69,18 @@ public class MongoRepositoryContributor extends RepositoryContributor {
61
69
62
70
private final AotQueryCreator queryCreator ;
63
71
private final MongoMappingContext mappingContext ;
72
+ private final NamedQueries namedQueries ;
64
73
65
74
public MongoRepositoryContributor (AotRepositoryContext repositoryContext ) {
66
75
67
76
super (repositoryContext );
68
77
78
+ ClassLoader classLoader = repositoryContext .getBeanFactory () != null ? repositoryContext .getClassLoader () : null ;
79
+ if (classLoader == null ) {
80
+ classLoader = getClass ().getClassLoader ();
81
+ }
82
+ namedQueries = getNamedQueries (repositoryContext .getConfigurationSource (), classLoader );
83
+
69
84
// avoid Java Time (JSR-310) Type introspection
70
85
MongoCustomConversions mongoCustomConversions = MongoCustomConversions
71
86
.create (MongoCustomConversions .MongoConverterConfigurationAdapter ::useNativeDriverJavaTimeCodecs );
@@ -78,6 +93,32 @@ public MongoRepositoryContributor(AotRepositoryContext repositoryContext) {
78
93
this .queryCreator = new AotQueryCreator (this .mappingContext );
79
94
}
80
95
96
+ private NamedQueries getNamedQueries (@ Nullable RepositoryConfigurationSource configSource , ClassLoader classLoader ) {
97
+
98
+ String location = configSource != null ? configSource .getNamedQueryLocation ().orElse (null ) : null ;
99
+
100
+ if (location == null ) {
101
+ location = new MongoRepositoryConfigurationExtension ().getDefaultNamedQueryLocation ();
102
+ }
103
+
104
+ if (StringUtils .hasText (location )) {
105
+
106
+ try {
107
+
108
+ PathMatchingResourcePatternResolver resolver = new PathMatchingResourcePatternResolver (classLoader );
109
+
110
+ PropertiesBasedNamedQueriesFactoryBean factoryBean = new PropertiesBasedNamedQueriesFactoryBean ();
111
+ factoryBean .setLocations (resolver .getResources (location ));
112
+ factoryBean .afterPropertiesSet ();
113
+ return factoryBean .getObject ();
114
+ } catch (IOException e ) {
115
+ throw new RuntimeException (e );
116
+ }
117
+ }
118
+
119
+ return new PropertiesBasedNamedQueries (new Properties ());
120
+ }
121
+
81
122
@ Override
82
123
protected void customizeClass (AotRepositoryClassBuilder classBuilder ) {
83
124
classBuilder .customize (builder -> builder .superclass (TypeName .get (MongoAotRepositoryFragmentSupport .class )));
@@ -189,6 +230,10 @@ private QueryInteraction createStringQuery(RepositoryInformation repositoryInfor
189
230
if (queryMethod .hasAnnotatedQuery () && queryAnnotation != null ) {
190
231
query = new QueryInteraction (new AotStringQuery (queryMethod .getAnnotatedQuery ()), queryAnnotation .count (),
191
232
queryAnnotation .delete (), queryAnnotation .exists ());
233
+ } else if (namedQueries .hasQuery (queryMethod .getNamedQueryName ())) {
234
+ query = new QueryInteraction (new AotStringQuery (namedQueries .getQuery (queryMethod .getNamedQueryName ())),
235
+ queryAnnotation != null && queryAnnotation .count (), queryAnnotation != null && queryAnnotation .delete (),
236
+ queryAnnotation != null && queryAnnotation .exists ());
192
237
} else {
193
238
194
239
PartTree partTree = new PartTree (queryMethod .getName (), repositoryInformation .getDomainType ());
0 commit comments