Skip to content

Commit dcda1de

Browse files
committed
feat: enums
1 parent c2ee36f commit dcda1de

File tree

83 files changed

+2235
-458
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

83 files changed

+2235
-458
lines changed

codegen/internal/generator/model.go

Lines changed: 70 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,8 @@ type schemaModel struct {
8888
Fields []schemaField
8989
Imports []string
9090
HasRequired bool
91+
IsEnum bool
92+
EnumValues []enumValueModel
9193
}
9294

9395
// schemaField stores metadata for a field within a schemaModel.
@@ -98,6 +100,12 @@ type schemaField struct {
98100
Required bool
99101
}
100102

103+
// enumValueModel captures a single enum constant and its wire value.
104+
type enumValueModel struct {
105+
Name string
106+
WireValue string
107+
}
108+
101109
const (
102110
parameterInPath = "path"
103111
parameterInQuery = "query"
@@ -507,8 +515,24 @@ func buildSchemas(doc *v3.Document, params Params, resolver *typeResolver) []sch
507515
if ref == nil {
508516
continue
509517
}
510-
fields, imports, hasRequired := buildSchemaFields(name, ref, resolver)
511518
description := schemaDescription(ref)
519+
if enumValues, ok := enumValuesForSchema(schemaFromProxy(ref)); ok {
520+
imports := sortedImports(map[string]struct{}{
521+
"com.fasterxml.jackson.annotation.JsonCreator": {},
522+
"com.fasterxml.jackson.annotation.JsonValue": {},
523+
})
524+
result = append(result, schemaModel{
525+
Name: name,
526+
ClassName: pascalCase(name, ""),
527+
Package: params.modelPackage(),
528+
DescriptionLines: splitComment(description),
529+
Imports: imports,
530+
IsEnum: true,
531+
EnumValues: enumValues,
532+
})
533+
continue
534+
}
535+
fields, imports, hasRequired := buildSchemaFields(name, ref, resolver)
512536
if hasRequired {
513537
imports = uniqueStrings(append(imports, "java.util.Objects"))
514538
}
@@ -587,6 +611,51 @@ func buildSchemaFields(name string, ref *base.SchemaProxy, resolver *typeResolve
587611
return fields, sortedImports(imports), hasRequired
588612
}
589613

614+
// enumValuesForSchema extracts enum values for string schemas.
615+
func enumValuesForSchema(schema *base.Schema) ([]enumValueModel, bool) {
616+
if schema == nil || len(schema.Enum) == 0 {
617+
return nil, false
618+
}
619+
if len(schema.Type) > 0 && !schemaHasType(schema, "string") {
620+
return nil, false
621+
}
622+
if len(schema.Type) == 0 && !schemaHasType(schema, "string") {
623+
for _, node := range schema.Enum {
624+
if node == nil || node.Tag != "!!str" {
625+
return nil, false
626+
}
627+
}
628+
}
629+
630+
values := make([]enumValueModel, 0, len(schema.Enum))
631+
usedNames := map[string]int{}
632+
for _, node := range schema.Enum {
633+
if node == nil {
634+
continue
635+
}
636+
raw := node.Value
637+
if raw == "" {
638+
var decoded string
639+
if err := node.Decode(&decoded); err == nil {
640+
raw = decoded
641+
}
642+
}
643+
name := enumConstantName(raw)
644+
if count := usedNames[name]; count > 0 {
645+
name = fmt.Sprintf("%s_%d", name, count+1)
646+
}
647+
usedNames[name] = usedNames[name] + 1
648+
values = append(values, enumValueModel{
649+
Name: name,
650+
WireValue: raw,
651+
})
652+
}
653+
if len(values) == 0 {
654+
return nil, false
655+
}
656+
return values, true
657+
}
658+
590659
// collectProperties gathers direct and allOf properties into a unified map.
591660
func collectProperties(schema *base.Schema) map[string]*base.SchemaProxy {
592661
props := map[string]*base.SchemaProxy{}

codegen/internal/generator/naming.go

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,29 @@ func camelCase(input string, fallback string) string {
5252
return name
5353
}
5454

55+
// enumConstantName converts an enum value into a valid Java enum constant name.
56+
func enumConstantName(value string) string {
57+
trimmed := strings.TrimSpace(value)
58+
if trimmed == "" {
59+
return "EMPTY"
60+
}
61+
words := tokenize(trimmed)
62+
if len(words) == 0 {
63+
return "VALUE"
64+
}
65+
for i, word := range words {
66+
words[i] = strings.ToUpper(word)
67+
}
68+
name := strings.Join(words, "_")
69+
if name == "" {
70+
name = "VALUE"
71+
}
72+
if len(name) > 0 && unicode.IsDigit([]rune(name)[0]) {
73+
name = "VALUE_" + name
74+
}
75+
return name
76+
}
77+
5578
// asyncClientClassName returns the asynchronous variant of a generated client.
5679
func asyncClientClassName(name string) string {
5780
if strings.HasSuffix(name, "Client") {

codegen/internal/generator/render.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -370,6 +370,8 @@ func prepareModelTemplateData(schema schemaModel) map[string]any {
370370
"DescriptionLines": schema.DescriptionLines,
371371
"Fields": schema.Fields,
372372
"HasRequired": schema.HasRequired,
373+
"IsEnum": schema.IsEnum,
374+
"EnumValues": schema.EnumValues,
373375
}
374376
}
375377

codegen/internal/generator/templates/model.tmpl

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,41 @@ package {{ .Package }};
1111
{{- end }}
1212
*/
1313
{{- end }}
14+
{{- if .IsEnum }}
15+
public enum {{ .ClassName }} {
16+
{{- range $index, $value := .EnumValues }}{{ if $index }},
17+
{{ end }} {{ $value.Name }}({{ quote $value.WireValue }}){{ end }};
18+
19+
private final String value;
20+
21+
{{ .ClassName }}(String value) {
22+
this.value = value;
23+
}
24+
25+
@JsonValue
26+
public String getValue() {
27+
return value;
28+
}
29+
30+
@Override
31+
public String toString() {
32+
return value;
33+
}
34+
35+
@JsonCreator
36+
public static {{ .ClassName }} fromValue(String value) {
37+
if (value == null) {
38+
return null;
39+
}
40+
for ({{ .ClassName }} entry : values()) {
41+
if (entry.value.equals(value)) {
42+
return entry;
43+
}
44+
}
45+
throw new IllegalArgumentException("Unknown {{ .ClassName }} value: " + value);
46+
}
47+
}
48+
{{- else }}
1449
public record {{ .ClassName }}(
1550
{{- if .Fields }}
1651
{{- range $index, $field := .Fields }}{{ if $index }},
@@ -94,3 +129,4 @@ public record {{ .ClassName }}(
94129
}
95130
}
96131
}
132+
{{- end }}

codegen/internal/generator/types.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -90,6 +90,14 @@ func (r *typeResolver) javaType(ref *base.SchemaProxy, context ...string) javaTy
9090
if schema == nil {
9191
return r.genericMap()
9292
}
93+
if enumValues, ok := enumValuesForSchema(schema); ok && len(enumValues) > 0 {
94+
name := r.registerInlineSchema(schema, context)
95+
fqn := r.params.modelPackage() + "." + name
96+
return javaType{
97+
Name: fqn,
98+
TypeRefExpr: fmt.Sprintf("new TypeReference<%s>() {}", fqn),
99+
}
100+
}
93101
switch {
94102
case schemaHasType(schema, "string"):
95103
return r.stringType(schema)
@@ -319,6 +327,24 @@ func (r *typeResolver) inlineSchemaModels(params Params) []schemaModel {
319327
if info.processed {
320328
continue
321329
}
330+
if enumValues, ok := enumValuesForSchema(info.schema); ok {
331+
imports := sortedImports(map[string]struct{}{
332+
"com.fasterxml.jackson.annotation.JsonCreator": {},
333+
"com.fasterxml.jackson.annotation.JsonValue": {},
334+
})
335+
models = append(models, schemaModel{
336+
Name: info.className,
337+
ClassName: info.className,
338+
Package: params.modelPackage(),
339+
DescriptionLines: splitComment(info.description),
340+
Imports: imports,
341+
IsEnum: true,
342+
EnumValues: enumValues,
343+
})
344+
info.processed = true
345+
added = true
346+
continue
347+
}
322348
fields, imports, hasRequired := buildSchemaFields(info.className, base.CreateSchemaProxy(info.schema), r)
323349
if hasRequired {
324350
imports = uniqueStrings(append(imports, "java.util.Objects"))

src/main/java/com/sumup/sdk/clients/MerchantAsyncClient.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -246,7 +246,7 @@ public static final class GetAccountQueryParams {
246246
* only personal and merchant profile information will be returned.
247247
* @return This GetAccountQueryParams instance.
248248
*/
249-
public GetAccountQueryParams include(java.util.List<String> value) {
249+
public GetAccountQueryParams include(java.util.List<com.sumup.sdk.models.IncludeItem> value) {
250250
this.values.put("include[]", Objects.requireNonNull(value, "include"));
251251
return this;
252252
}

src/main/java/com/sumup/sdk/clients/MerchantClient.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -236,7 +236,7 @@ public static final class GetAccountQueryParams {
236236
* only personal and merchant profile information will be returned.
237237
* @return This GetAccountQueryParams instance.
238238
*/
239-
public GetAccountQueryParams include(java.util.List<String> value) {
239+
public GetAccountQueryParams include(java.util.List<com.sumup.sdk.models.IncludeItem> value) {
240240
this.values.put("include[]", Objects.requireNonNull(value, "include"));
241241
return this;
242242
}

src/main/java/com/sumup/sdk/clients/PayoutsAsyncClient.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -210,7 +210,7 @@ public static final class ListPayoutsQueryParams {
210210
* @param value Query parameter value.
211211
* @return This ListPayoutsQueryParams instance.
212212
*/
213-
public ListPayoutsQueryParams format(String value) {
213+
public ListPayoutsQueryParams format(com.sumup.sdk.models.Format2 value) {
214214
this.values.put("format", Objects.requireNonNull(value, "format"));
215215
return this;
216216
}
@@ -232,7 +232,7 @@ public ListPayoutsQueryParams limit(Long value) {
232232
* @param value Query parameter value.
233233
* @return This ListPayoutsQueryParams instance.
234234
*/
235-
public ListPayoutsQueryParams order(String value) {
235+
public ListPayoutsQueryParams order(com.sumup.sdk.models.Order2 value) {
236236
this.values.put("order", Objects.requireNonNull(value, "order"));
237237
return this;
238238
}
@@ -257,7 +257,7 @@ public static final class ListPayoutsV1QueryParams {
257257
* @param value Query parameter value.
258258
* @return This ListPayoutsV1QueryParams instance.
259259
*/
260-
public ListPayoutsV1QueryParams format(String value) {
260+
public ListPayoutsV1QueryParams format(com.sumup.sdk.models.Format value) {
261261
this.values.put("format", Objects.requireNonNull(value, "format"));
262262
return this;
263263
}
@@ -279,7 +279,7 @@ public ListPayoutsV1QueryParams limit(Long value) {
279279
* @param value Query parameter value.
280280
* @return This ListPayoutsV1QueryParams instance.
281281
*/
282-
public ListPayoutsV1QueryParams order(String value) {
282+
public ListPayoutsV1QueryParams order(com.sumup.sdk.models.Order2 value) {
283283
this.values.put("order", Objects.requireNonNull(value, "order"));
284284
return this;
285285
}

src/main/java/com/sumup/sdk/clients/PayoutsClient.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,7 @@ public static final class ListPayoutsQueryParams {
209209
* @param value Query parameter value.
210210
* @return This ListPayoutsQueryParams instance.
211211
*/
212-
public ListPayoutsQueryParams format(String value) {
212+
public ListPayoutsQueryParams format(com.sumup.sdk.models.Format2 value) {
213213
this.values.put("format", Objects.requireNonNull(value, "format"));
214214
return this;
215215
}
@@ -231,7 +231,7 @@ public ListPayoutsQueryParams limit(Long value) {
231231
* @param value Query parameter value.
232232
* @return This ListPayoutsQueryParams instance.
233233
*/
234-
public ListPayoutsQueryParams order(String value) {
234+
public ListPayoutsQueryParams order(com.sumup.sdk.models.Order2 value) {
235235
this.values.put("order", Objects.requireNonNull(value, "order"));
236236
return this;
237237
}
@@ -256,7 +256,7 @@ public static final class ListPayoutsV1QueryParams {
256256
* @param value Query parameter value.
257257
* @return This ListPayoutsV1QueryParams instance.
258258
*/
259-
public ListPayoutsV1QueryParams format(String value) {
259+
public ListPayoutsV1QueryParams format(com.sumup.sdk.models.Format value) {
260260
this.values.put("format", Objects.requireNonNull(value, "format"));
261261
return this;
262262
}
@@ -278,7 +278,7 @@ public ListPayoutsV1QueryParams limit(Long value) {
278278
* @param value Query parameter value.
279279
* @return This ListPayoutsV1QueryParams instance.
280280
*/
281-
public ListPayoutsV1QueryParams order(String value) {
281+
public ListPayoutsV1QueryParams order(com.sumup.sdk.models.Order2 value) {
282282
this.values.put("order", Objects.requireNonNull(value, "order"));
283283
return this;
284284
}

src/main/java/com/sumup/sdk/clients/TransactionsAsyncClient.java

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -586,7 +586,7 @@ public ListTransactionsQueryParams oldestTime(java.time.OffsetDateTime value) {
586586
* @param value Specifies the order in which the returned results are displayed.
587587
* @return This ListTransactionsQueryParams instance.
588588
*/
589-
public ListTransactionsQueryParams order(String value) {
589+
public ListTransactionsQueryParams order(com.sumup.sdk.models.Order2 value) {
590590
this.values.put("order", Objects.requireNonNull(value, "order"));
591591
return this;
592592
}
@@ -611,7 +611,8 @@ public ListTransactionsQueryParams paymentTypes(
611611
* transactions.
612612
* @return This ListTransactionsQueryParams instance.
613613
*/
614-
public ListTransactionsQueryParams statuses(java.util.List<String> value) {
614+
public ListTransactionsQueryParams statuses(
615+
java.util.List<com.sumup.sdk.models.StatusesItem2> value) {
615616
this.values.put("statuses", Objects.requireNonNull(value, "statuses"));
616617
return this;
617618
}
@@ -633,7 +634,8 @@ public ListTransactionsQueryParams transactionCode(String value) {
633634
* @param value Filters the returned results by the specified list of transaction types.
634635
* @return This ListTransactionsQueryParams instance.
635636
*/
636-
public ListTransactionsQueryParams types(java.util.List<String> value) {
637+
public ListTransactionsQueryParams types(
638+
java.util.List<com.sumup.sdk.models.TypesItem2> value) {
637639
this.values.put("types", Objects.requireNonNull(value, "types"));
638640
return this;
639641
}
@@ -746,7 +748,7 @@ public ListTransactionsV21QueryParams oldestTime(java.time.OffsetDateTime value)
746748
* @param value Specifies the order in which the returned results are displayed.
747749
* @return This ListTransactionsV21QueryParams instance.
748750
*/
749-
public ListTransactionsV21QueryParams order(String value) {
751+
public ListTransactionsV21QueryParams order(com.sumup.sdk.models.Order value) {
750752
this.values.put("order", Objects.requireNonNull(value, "order"));
751753
return this;
752754
}
@@ -771,7 +773,8 @@ public ListTransactionsV21QueryParams paymentTypes(
771773
* transactions.
772774
* @return This ListTransactionsV21QueryParams instance.
773775
*/
774-
public ListTransactionsV21QueryParams statuses(java.util.List<String> value) {
776+
public ListTransactionsV21QueryParams statuses(
777+
java.util.List<com.sumup.sdk.models.StatusesItem> value) {
775778
this.values.put("statuses", Objects.requireNonNull(value, "statuses"));
776779
return this;
777780
}
@@ -793,7 +796,8 @@ public ListTransactionsV21QueryParams transactionCode(String value) {
793796
* @param value Filters the returned results by the specified list of transaction types.
794797
* @return This ListTransactionsV21QueryParams instance.
795798
*/
796-
public ListTransactionsV21QueryParams types(java.util.List<String> value) {
799+
public ListTransactionsV21QueryParams types(
800+
java.util.List<com.sumup.sdk.models.TypesItem> value) {
797801
this.values.put("types", Objects.requireNonNull(value, "types"));
798802
return this;
799803
}

0 commit comments

Comments
 (0)