@@ -46,7 +46,7 @@ public class GraphLookupOperation implements InheritsFieldsAggregationOperation
4646 private static final Set <Class <?>> ALLOWED_START_TYPES = new HashSet <Class <?>>(
4747 Arrays .<Class <?>> asList (AggregationExpression .class , String .class , Field .class , Document .class ));
4848
49- private final String from ;
49+ private final Object from ;
5050 private final List <Object > startWith ;
5151 private final Field connectFrom ;
5252 private final Field connectTo ;
@@ -55,7 +55,7 @@ public class GraphLookupOperation implements InheritsFieldsAggregationOperation
5555 private final @ Nullable Field depthField ;
5656 private final @ Nullable CriteriaDefinition restrictSearchWithMatch ;
5757
58- private GraphLookupOperation (String from , List <Object > startWith , Field connectFrom , Field connectTo , Field as ,
58+ private GraphLookupOperation (Object from , List <Object > startWith , Field connectFrom , Field connectTo , Field as ,
5959 @ Nullable Long maxDepth , @ Nullable Field depthField , @ Nullable CriteriaDefinition restrictSearchWithMatch ) {
6060
6161 this .from = from ;
@@ -82,7 +82,7 @@ public Document toDocument(AggregationOperationContext context) {
8282
8383 Document graphLookup = new Document ();
8484
85- graphLookup .put ("from" , from );
85+ graphLookup .put ("from" , getCollectionName ( context ) );
8686
8787 List <Object > mappedStartWith = new ArrayList <>(startWith .size ());
8888
@@ -99,7 +99,7 @@ public Document toDocument(AggregationOperationContext context) {
9999
100100 graphLookup .put ("startWith" , mappedStartWith .size () == 1 ? mappedStartWith .iterator ().next () : mappedStartWith );
101101
102- graphLookup .put ("connectFromField" , connectFrom . getTarget ( ));
102+ graphLookup .put ("connectFromField" , getForeignFieldName ( context ));
103103 graphLookup .put ("connectToField" , connectTo .getTarget ());
104104 graphLookup .put ("as" , as .getName ());
105105
@@ -118,6 +118,16 @@ public Document toDocument(AggregationOperationContext context) {
118118 return new Document (getOperator (), graphLookup );
119119 }
120120
121+ String getCollectionName (AggregationOperationContext context ) {
122+ return from instanceof Class <?> type ? context .getCollection (type ) : from .toString ();
123+ }
124+
125+ String getForeignFieldName (AggregationOperationContext context ) {
126+
127+ return from instanceof Class <?> type ? context .getMappedFieldName (type , connectFrom .getTarget ())
128+ : connectFrom .getTarget ();
129+ }
130+
121131 @ Override
122132 public String getOperator () {
123133 return "$graphLookup" ;
@@ -128,7 +138,7 @@ public ExposedFields getFields() {
128138
129139 List <ExposedField > fields = new ArrayList <>(2 );
130140 fields .add (new ExposedField (as , true ));
131- if (depthField != null ) {
141+ if (depthField != null ) {
132142 fields .add (new ExposedField (depthField , true ));
133143 }
134144 return ExposedFields .from (fields .toArray (new ExposedField [0 ]));
@@ -146,6 +156,17 @@ public interface FromBuilder {
146156 * @return never {@literal null}.
147157 */
148158 StartWithBuilder from (String collectionName );
159+
160+ /**
161+ * Use the given type to determine name of the foreign collection and map
162+ * {@link ConnectFromBuilder#connectFrom(String)} against it to consider eventually present
163+ * {@link org.springframework.data.mongodb.core.mapping.Field} annotations.
164+ *
165+ * @param type must not be {@literal null}.
166+ * @return never {@literal null}.
167+ * @since 4.2
168+ */
169+ StartWithBuilder from (Class <?> type );
149170 }
150171
151172 /**
@@ -218,7 +239,7 @@ public interface ConnectToBuilder {
218239 static final class GraphLookupOperationFromBuilder
219240 implements FromBuilder , StartWithBuilder , ConnectFromBuilder , ConnectToBuilder {
220241
221- private @ Nullable String from ;
242+ private @ Nullable Object from ;
222243 private @ Nullable List <? extends Object > startWith ;
223244 private @ Nullable String connectFrom ;
224245
@@ -231,6 +252,14 @@ public StartWithBuilder from(String collectionName) {
231252 return this ;
232253 }
233254
255+ @ Override
256+ public StartWithBuilder from (Class <?> type ) {
257+
258+ Assert .notNull (type , "Type must not be null" );
259+ this .from = type ;
260+ return this ;
261+ }
262+
234263 @ Override
235264 public ConnectFromBuilder startWith (String ... fieldReferences ) {
236265
@@ -321,15 +350,15 @@ public GraphLookupOperationBuilder connectTo(String fieldName) {
321350 */
322351 public static final class GraphLookupOperationBuilder {
323352
324- private final String from ;
353+ private final Object from ;
325354 private final List <Object > startWith ;
326355 private final Field connectFrom ;
327356 private final Field connectTo ;
328357 private @ Nullable Long maxDepth ;
329358 private @ Nullable Field depthField ;
330359 private @ Nullable CriteriaDefinition restrictSearchWithMatch ;
331360
332- protected GraphLookupOperationBuilder (String from , List <? extends Object > startWith , String connectFrom ,
361+ protected GraphLookupOperationBuilder (Object from , List <? extends Object > startWith , String connectFrom ,
333362 String connectTo ) {
334363
335364 this .from = from ;
0 commit comments