use latest parent
[yosql.git] / yosql-models / yosql-models-configuration / src / main / java / wtf / metio / yosql / models / configuration / SqlParameter.java
blob4377b1dc04dfa47a855b8d0b88e56e5f735a7248
1 /*
2 * This file is part of yosql. It is subject to the license terms in the LICENSE file found in the top-level
3 * directory of this distribution and at https://creativecommons.org/publicdomain/zero/1.0/. No part of yosql,
4 * including this file, may be copied, modified, propagated, or distributed except according to the terms contained
5 * in the LICENSE file.
6 */
7 package wtf.metio.yosql.models.configuration;
9 import com.fasterxml.jackson.annotation.JsonIgnore;
10 import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
11 import com.fasterxml.jackson.databind.annotation.JsonSerialize;
12 import com.squareup.javapoet.TypeName;
13 import org.immutables.value.Value;
14 import wtf.metio.javapoet.TypeGuesser;
15 import wtf.metio.yosql.internals.jdk.Buckets;
17 import java.util.List;
18 import java.util.Optional;
19 import java.util.stream.Collectors;
20 import java.util.stream.Stream;
22 /**
23 * Represents a single input parameter of a SQL statement.
25 @Value.Immutable
26 @JsonSerialize(
27 as = ImmutableSqlParameter.class
29 @JsonDeserialize(
30 as = ImmutableSqlParameter.class
32 public interface SqlParameter {
34 //region builders
36 static ImmutableSqlParameter.Builder builder() {
37 return ImmutableSqlParameter.builder();
40 static ImmutableSqlParameter copyOf(final SqlParameter parameter) {
41 return ImmutableSqlParameter.copyOf(parameter);
44 //endregion
46 //region utils
48 /**
49 * Deeply merges two parameter lists using the name of the parameter as identifying key.
51 * @param first The first list of parameters.
52 * @param second The second list of parameters.
53 * @return The merged list of parameters.
55 static List<SqlParameter> mergeParameters(
56 final List<SqlParameter> first,
57 final List<SqlParameter> second) {
58 if (first == null || first.isEmpty()) {
59 return second;
61 return Stream.concat(copyAttributes(first, second), copyAttributes(second, first))
62 .filter(Buckets.distinctByKey(SqlParameter::name))
63 .collect(Collectors.toList());
66 private static Stream<ImmutableSqlParameter> copyAttributes(final List<SqlParameter> first, final List<SqlParameter> second) {
67 return first.stream()
68 .map(param -> second.stream()
69 .filter(other -> param.name().equals(other.name()))
70 .findFirst()
71 .map(other -> SqlParameter.copyOf(param)
72 .withType(param.type().or(other::type))
73 .withIndices(param.indices().or(other::indices))
74 .withVariant(param.variant().or(other::variant))
75 .withSqlType(param.sqlType().or(other::sqlType))
76 .withScale(param.scale().or(other::scale)))
77 .orElseGet(() -> SqlParameter.copyOf(param)));
80 //endregion
82 /**
83 * @return The name of the parameter.
85 Optional<String> name();
87 /**
88 * @return The fully-qualified type name.
90 Optional<String> type();
92 /**
93 * @return The indices in the SQL statement that match this parameter.
95 @JsonIgnore
96 Optional<int[]> indices();
98 /**
99 * @return The variant of this parameter.
101 Optional<SqlParameterVariant> variant();
104 * @return The JDBC type of this parameter.
106 Optional<Integer> sqlType();
109 * @return The scale of this parameter in case its sqlType is numeric/decimal.
111 Optional<Integer> scale();
113 //region lazy
116 * @return The parsed type name of this parameter.
118 @Value.Lazy
119 default Optional<TypeName> typeName() {
120 return type().map(TypeGuesser::guessTypeName);
124 * @return <code>true</code> in case this statement has indices, <code>false</code> otherwise.
126 @Value.Lazy
127 default boolean hasIndices() {
128 return indices().map(values -> values.length > 0).orElse(Boolean.FALSE);
131 //endregion