Skip to content

Commit 9445cdc

Browse files
committed
Polishing.
Apply consistent formatting. Extract superinterface for rendering. Refine tests. See #3961 Original pull request: #3962
1 parent 2704a58 commit 9445cdc

File tree

2 files changed

+128
-64
lines changed

2 files changed

+128
-64
lines changed

spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/JpqlQueryBuilder.java

Lines changed: 69 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,7 @@ public Select select(Selection selection) {
142142
Selection postProcess(Selection selection) {
143143
return distinct ? new DistinctSelection(selection) : selection;
144144
}
145+
145146
};
146147
}
147148

@@ -299,6 +300,7 @@ public static WhereStep where(Origin source, PropertyPath path) {
299300
public static WhereStep where(Expression rhs) {
300301

301302
return new WhereStep() {
303+
302304
@Override
303305
public Predicate between(Expression lower, Expression upper) {
304306
return new BetweenPredicate(rhs, lower, upper);
@@ -393,6 +395,7 @@ public Predicate eq(Expression value) {
393395
public Predicate neq(Expression value) {
394396
return new OperatorPredicate(rhs, "!=", value);
395397
}
398+
396399
};
397400
}
398401

@@ -506,7 +509,9 @@ default Select select(JpqlQueryBuilder.PathExpression path) {
506509
}
507510

508511
public interface Selection {
512+
509513
String render(RenderContext context);
514+
510515
}
511516

512517
/**
@@ -525,6 +530,7 @@ public String render(RenderContext context) {
525530
public String toString() {
526531
return render(RenderContext.EMPTY);
527532
}
533+
528534
}
529535

530536
static PathAndOrigin path(Origin origin, String path) {
@@ -538,29 +544,28 @@ static PathAndOrigin path(Origin origin, String path) {
538544
throw new RuntimeException(e);
539545
}
540546
}
547+
541548
if (origin instanceof Join join) {
542549

543550
Origin parent = join.source;
544551
List<String> segments = new ArrayList<>();
545552
segments.add(join.path);
546553
while (!(parent instanceof Entity)) {
547-
if (parent instanceof Join pj) {
548-
parent = pj.source;
549-
segments.add(pj.path);
554+
if (parent instanceof Join parentJoin) {
555+
parent = parentJoin.source;
556+
segments.add(parentJoin.path);
550557
} else {
551558
parent = null;
552559
}
553560
}
554561

555-
if (parent instanceof Entity) {
556-
Collections.reverse(segments);
557-
segments.add(path);
558-
PathAndOrigin path1 = path(parent, StringUtils.collectionToDelimitedString(segments, "."));
559-
return new PathAndOrigin(path1.path().getLeafProperty(), origin, false);
560-
}
562+
Collections.reverse(segments);
563+
segments.add(path);
564+
PathAndOrigin joinedPath = path(parent, StringUtils.collectionToDelimitedString(segments, "."));
565+
return new PathAndOrigin(joinedPath.path().getLeafProperty(), origin, false);
561566
}
562-
throw new IllegalStateException(" oh no ");
563567

568+
throw new IllegalStateException("🙈 Unsupported origin type: " + origin);
564569
}
565570

566571
/**
@@ -579,6 +584,7 @@ public String render(RenderContext context) {
579584
public String toString() {
580585
return render(RenderContext.EMPTY);
581586
}
587+
582588
}
583589

584590
/**
@@ -598,6 +604,7 @@ public String render(RenderContext context) {
598604
public String toString() {
599605
return render(RenderContext.EMPTY);
600606
}
607+
601608
}
602609

603610
/**
@@ -618,6 +625,7 @@ public String render(RenderContext context) {
618625
public String toString() {
619626
return render(RenderContext.EMPTY);
620627
}
628+
621629
}
622630

623631
/**
@@ -652,21 +660,29 @@ public String render(RenderContext context) {
652660
public String toString() {
653661
return render(RenderContext.EMPTY);
654662
}
663+
655664
}
656665

657666
/**
658-
* {@code WHERE} predicate.
667+
* Interface specifying a predicate or expression that can be rendered to {@code String}.
659668
*/
660-
public interface Predicate {
669+
public interface Renderable {
661670

662671
/**
663-
* Render the predicate given {@link RenderContext}.
672+
* Render the predicate or expression given {@link RenderContext}.
664673
*
665674
* @param context
666675
* @return
667676
*/
668677
String render(RenderContext context);
669678

679+
}
680+
681+
/**
682+
* {@code WHERE} predicate.
683+
*/
684+
public interface Predicate extends Renderable {
685+
670686
/**
671687
* {@code OR}-concatenate this predicate with {@code other}.
672688
*
@@ -701,21 +717,21 @@ default Predicate and(Predicate other) { // don't like the structuring of this a
701717
default Predicate nest() {
702718
return new NestedPredicate(this);
703719
}
720+
704721
}
705722

706723
/**
707724
* Interface specifying an expression that can be rendered to {@code String}.
708725
*/
709-
public interface Expression {
726+
public interface Expression extends Renderable {
710727

711728
/**
712-
* Render the expression given {@link RenderContext}.
729+
* Create an {@link AliasedExpression} with the given {@code alias}. If the expression is already aliased, the
730+
* previous alias is discarded and replaced with the new one.
713731
*
714-
* @param context
732+
* @param alias
715733
* @return
716734
*/
717-
String render(RenderContext context);
718-
719735
default AliasedExpression as(String alias) {
720736

721737
if (this instanceof DefaultAliasedExpression de) {
@@ -724,6 +740,7 @@ default AliasedExpression as(String alias) {
724740

725741
return new DefaultAliasedExpression(this, alias);
726742
}
743+
727744
}
728745

729746
/**
@@ -756,6 +773,7 @@ public String getAlias() {
756773
public String toString() {
757774
return render(RenderContext.EMPTY);
758775
}
776+
759777
}
760778

761779
/**
@@ -768,6 +786,7 @@ public interface PathExpression extends Expression {
768786
* @return the associated {@link PropertyPath}.
769787
*/
770788
PropertyPath getPropertyPath();
789+
771790
}
772791

773792
/**
@@ -865,6 +884,7 @@ String render() {
865884

866885
return result.toString();
867886
}
887+
868888
}
869889

870890
/**
@@ -889,6 +909,7 @@ public AbstractJpqlQuery where(Predicate predicate) {
889909
public String toString() {
890910
return render();
891911
}
912+
892913
}
893914

894915
record OrderExpression(Expression sortExpression, @org.springframework.lang.Nullable Sort.Direction direction,
@@ -915,6 +936,7 @@ public String render(RenderContext context) {
915936

916937
return builder.toString();
917938
}
939+
918940
}
919941

920942
/**
@@ -966,6 +988,7 @@ public String prefixWithAlias(Origin source, String fragment) {
966988
public boolean isConstructorContext() {
967989
return false;
968990
}
991+
969992
}
970993

971994
static class ConstructorContext extends RenderContext {
@@ -978,6 +1001,7 @@ static class ConstructorContext extends RenderContext {
9781001
public boolean isConstructorContext() {
9791002
return true;
9801003
}
1004+
9811005
}
9821006

9831007
/**
@@ -992,6 +1016,7 @@ public interface Origin {
9921016
* @return the simple name of the origin (e.g. {@link Class#getSimpleName()})
9931017
*/
9941018
String getName();
1019+
9951020
}
9961021

9971022
/**
@@ -1001,6 +1026,7 @@ public interface Origin {
10011026
public interface Bindable {
10021027

10031028
boolean isRoot();
1029+
10041030
}
10051031

10061032
/**
@@ -1283,6 +1309,7 @@ default Predicate like(String value, String escape) {
12831309
* @return
12841310
*/
12851311
Predicate neq(Expression value);
1312+
12861313
}
12871314

12881315
record LiteralExpression(String expression) implements Expression {
@@ -1296,6 +1323,7 @@ public String render(RenderContext context) {
12961323
public String toString() {
12971324
return render(RenderContext.EMPTY);
12981325
}
1326+
12991327
}
13001328

13011329
record StringLiteralExpression(String literal) implements Expression {
@@ -1313,6 +1341,7 @@ public String raw() {
13131341
public String toString() {
13141342
return render(RenderContext.EMPTY);
13151343
}
1344+
13161345
}
13171346

13181347
record ParameterExpression(ParameterPlaceholder parameter) implements Expression {
@@ -1326,6 +1355,7 @@ public String render(RenderContext context) {
13261355
public String toString() {
13271356
return render(RenderContext.EMPTY);
13281357
}
1358+
13291359
}
13301360

13311361
record FunctionExpression(String function, List<Expression> arguments) implements Expression {
@@ -1351,6 +1381,7 @@ public String render(RenderContext context) {
13511381
public String toString() {
13521382
return render(RenderContext.EMPTY);
13531383
}
1384+
13541385
}
13551386

13561387
record OperatorPredicate(Expression path, String operator, Expression predicate) implements Predicate {
@@ -1364,6 +1395,7 @@ public String render(RenderContext context) {
13641395
public String toString() {
13651396
return render(RenderContext.EMPTY);
13661397
}
1398+
13671399
}
13681400

13691401
record MemberOfPredicate(Expression path, String operator, Expression predicate) implements Predicate {
@@ -1377,6 +1409,7 @@ public String render(RenderContext context) {
13771409
public String toString() {
13781410
return render(RenderContext.EMPTY);
13791411
}
1412+
13801413
}
13811414

13821415
record LhsPredicate(Expression path, String predicate) implements Predicate {
@@ -1390,6 +1423,7 @@ public String render(RenderContext context) {
13901423
public String toString() {
13911424
return render(RenderContext.EMPTY);
13921425
}
1426+
13931427
}
13941428

13951429
record BetweenPredicate(Expression path, Expression lower, Expression upper) implements Predicate {
@@ -1403,6 +1437,7 @@ public String render(RenderContext context) {
14031437
public String toString() {
14041438
return render(RenderContext.EMPTY);
14051439
}
1440+
14061441
}
14071442

14081443
record LikePredicate(Expression left, String operator, Expression right, String escape) implements Predicate {
@@ -1416,27 +1451,29 @@ public String render(RenderContext context) {
14161451
public String toString() {
14171452
return render(RenderContext.EMPTY);
14181453
}
1454+
14191455
}
14201456

14211457
record InPredicate(Expression path, String operator, Expression predicate) implements Predicate {
14221458

14231459
@Override
14241460
public String render(RenderContext context) {
14251461

1426-
String predicateStr = predicate.render(context);
1427-
1428-
// Avoid double parentheses if predicate string already starts and ends with parentheses
1429-
if (predicateStr.startsWith("(") && predicateStr.endsWith(")")) {
1430-
return "%s %s %s".formatted(path.render(context), operator, predicateStr);
1431-
}
1432-
1433-
return "%s %s (%s)".formatted(path.render(context), operator, predicateStr);
1462+
Expression predicate = this.predicate;
1463+
String rendered = predicate.render(context);
1464+
1465+
return (hasParenthesis(rendered) ? "%s %s %s" : "%s %s (%s)").formatted(path.render(context), operator, rendered);
14341466
}
14351467

14361468
@Override
14371469
public String toString() {
14381470
return render(RenderContext.EMPTY);
14391471
}
1472+
1473+
private static boolean hasParenthesis(String str) {
1474+
return str.startsWith("(") && str.endsWith(")");
1475+
}
1476+
14401477
}
14411478

14421479
record AndPredicate(Predicate left, Predicate right) implements Predicate {
@@ -1450,6 +1487,7 @@ public String render(RenderContext context) {
14501487
public String toString() {
14511488
return render(RenderContext.EMPTY);
14521489
}
1490+
14531491
}
14541492

14551493
record OrPredicate(Predicate left, Predicate right) implements Predicate {
@@ -1463,6 +1501,7 @@ public String render(RenderContext context) {
14631501
public String toString() {
14641502
return render(RenderContext.EMPTY);
14651503
}
1504+
14661505
}
14671506

14681507
record NestedPredicate(Predicate delegate) implements Predicate {
@@ -1476,6 +1515,7 @@ public String render(RenderContext context) {
14761515
public String toString() {
14771516
return render(RenderContext.EMPTY);
14781517
}
1518+
14791519
}
14801520

14811521
/**
@@ -1507,6 +1547,7 @@ public String render(RenderContext context) {
15071547
public String getAlias() {
15081548
return path().getSegment();
15091549
}
1550+
15101551
}
15111552

15121553
/**
@@ -1541,5 +1582,7 @@ public static ParameterPlaceholder named(String name) {
15411582
Assert.hasText(name, "Placeholder name must not be empty");
15421583
return new ParameterPlaceholder(":%s".formatted(name));
15431584
}
1585+
15441586
}
1587+
15451588
}

0 commit comments

Comments
 (0)