Skip to content

Commit 3388954

Browse files
committed
Isolating as method on utils; refactor ObjectMapperFactoryProvider to lazy init mapper
Signed-off-by: Ricardo Zanini <ricardozanini@gmail.com>
1 parent 281101d commit 3388954

4 files changed

Lines changed: 113 additions & 57 deletions

File tree

‎experimental/model/src/main/java/io/serverlessworkflow/impl/model/func/JavaModelCollection.java‎

Lines changed: 12 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -15,16 +15,14 @@
1515
*/
1616
package io.serverlessworkflow.impl.model.func;
1717

18+
import io.serverlessworkflow.impl.CollectionConversionUtils;
1819
import io.serverlessworkflow.impl.WorkflowModel;
1920
import io.serverlessworkflow.impl.WorkflowModelCollection;
20-
import java.lang.reflect.Array;
2121
import java.util.ArrayList;
2222
import java.util.Collection;
23-
import java.util.HashSet;
2423
import java.util.Iterator;
2524
import java.util.List;
2625
import java.util.Optional;
27-
import java.util.Set;
2826

2927
public class JavaModelCollection implements Collection<WorkflowModel>, WorkflowModelCollection {
3028

@@ -82,14 +80,22 @@ public Iterator<WorkflowModel> iterator() {
8280
return new ModelIterator(object.iterator());
8381
}
8482

83+
private List<WorkflowModel> toModelList() {
84+
List<WorkflowModel> models = new ArrayList<>(object.size());
85+
for (Object obj : object)
86+
models.add(obj instanceof WorkflowModel value ? value : nextItem(obj));
87+
88+
return models;
89+
}
90+
8591
@Override
8692
public Object[] toArray() {
87-
throw new UnsupportedOperationException("toArray is not supported yet");
93+
return toModelList().toArray();
8894
}
8995

9096
@Override
9197
public <T> T[] toArray(T[] a) {
92-
throw new UnsupportedOperationException("toArray is not supported yet");
98+
return toModelList().toArray(a);
9399
}
94100

95101
@Override
@@ -142,29 +148,11 @@ public Class<?> objectClass() {
142148
}
143149

144150
@Override
145-
@SuppressWarnings({"rawtypes", "unchecked"})
146151
public <T> Optional<T> as(Class<T> clazz) {
147152
if (object == null) return Optional.empty();
148153

149154
if (clazz.isInstance(object)) return Optional.of(clazz.cast(object));
150155

151-
if (clazz.isAssignableFrom(List.class)) return Optional.of(clazz.cast(new ArrayList<>(object)));
152-
else if (clazz.isAssignableFrom(Set.class))
153-
return Optional.of(clazz.cast(new HashSet<>(object)));
154-
155-
if (clazz.isArray()) {
156-
Class<?> componentType = clazz.getComponentType();
157-
if (!componentType.isPrimitive()) {
158-
Object[] typedArray = (Object[]) Array.newInstance(componentType, 0);
159-
return Optional.of(clazz.cast(object.toArray(typedArray)));
160-
}
161-
162-
Object primitiveArray = Array.newInstance(componentType, object.size());
163-
int i = 0;
164-
for (Object item : object) Array.set(primitiveArray, i++, item);
165-
return Optional.of(clazz.cast(primitiveArray));
166-
}
167-
168-
return Optional.empty();
156+
return CollectionConversionUtils.as(object, clazz);
169157
}
170158
}
Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
/*
2+
* Copyright 2020-Present The Serverless Workflow Specification Authors
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
package io.serverlessworkflow.impl;
17+
18+
import java.lang.reflect.Array;
19+
import java.util.ArrayList;
20+
import java.util.Collection;
21+
import java.util.HashSet;
22+
import java.util.List;
23+
import java.util.Optional;
24+
import java.util.Set;
25+
import java.util.function.BiFunction;
26+
27+
public final class CollectionConversionUtils {
28+
private CollectionConversionUtils() {}
29+
30+
/**
31+
* Safely converts a base Collection into the requested List, Set, or Array type.
32+
*
33+
* @param elements The base collection of elements.
34+
* @param clazz The target class to convert to.
35+
* @param primitiveConverter Strategy for converting items to primitives if an array is requested.
36+
*/
37+
public static <T> Optional<T> as(
38+
Collection<?> elements,
39+
Class<T> clazz,
40+
BiFunction<Object, Class<?>, Object> primitiveConverter) {
41+
if (clazz.isAssignableFrom(List.class))
42+
return Optional.of(clazz.cast(new ArrayList<>(elements)));
43+
else if (clazz.isAssignableFrom(Set.class))
44+
return Optional.of(clazz.cast(new HashSet<>(elements)));
45+
46+
if (clazz.isArray()) {
47+
Class<?> componentType = clazz.getComponentType();
48+
49+
if (!componentType.isPrimitive()) {
50+
Object[] typedArray = (Object[]) Array.newInstance(componentType, 0);
51+
return Optional.of(clazz.cast(elements.toArray(typedArray)));
52+
}
53+
54+
Object primitiveArray = Array.newInstance(componentType, elements.size());
55+
56+
int i = 0;
57+
for (Object item : elements)
58+
Array.set(primitiveArray, i++, primitiveConverter.apply(item, componentType));
59+
60+
return Optional.of(clazz.cast(primitiveArray));
61+
}
62+
63+
return Optional.empty();
64+
}
65+
66+
/**
67+
* @see #as(Collection, Class, BiFunction)
68+
*/
69+
public static <T> Optional<T> as(Collection<?> elements, Class<T> clazz) {
70+
return as(elements, clazz, (item, type) -> item);
71+
}
72+
}

‎impl/json-utils/src/main/java/io/serverlessworkflow/impl/jackson/ObjectMapperFactoryProvider.java‎

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,6 @@ public class ObjectMapperFactoryProvider implements Supplier<ObjectMapperFactory
2626

2727
private static ObjectMapperFactoryProvider instance = new ObjectMapperFactoryProvider();
2828

29-
private static final ObjectMapper DEFAULT_MAPPER =
30-
new ObjectMapper()
31-
.findAndRegisterModules()
32-
.registerModule(JsonFormat.getCloudEventJacksonModule());
33-
3429
public static ObjectMapperFactoryProvider instance() {
3530
return instance;
3631
}
@@ -49,10 +44,28 @@ public ObjectMapperFactory get() {
4944
synchronized (this) {
5045
if (objectMapperFactory == null) {
5146
objectMapperFactory =
52-
loadFirst(ObjectMapperFactory.class).orElseGet(() -> () -> DEFAULT_MAPPER);
47+
loadFirst(ObjectMapperFactory.class).orElseGet(DefaultObjectMapperFactory::new);
5348
}
5449
}
5550
}
5651
return objectMapperFactory;
5752
}
53+
54+
/** Internal default private factory lazy initialized. */
55+
private static class DefaultObjectMapperFactory implements ObjectMapperFactory {
56+
57+
private final ObjectMapper mapper;
58+
59+
DefaultObjectMapperFactory() {
60+
this.mapper =
61+
new ObjectMapper()
62+
.findAndRegisterModules()
63+
.registerModule(JsonFormat.getCloudEventJacksonModule());
64+
}
65+
66+
@Override
67+
public ObjectMapper get() {
68+
return mapper;
69+
}
70+
}
5871
}

‎impl/model/src/main/java/io/serverlessworkflow/impl/model/jackson/JacksonModelCollection.java‎

Lines changed: 10 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -17,17 +17,15 @@
1717

1818
import com.fasterxml.jackson.databind.JsonNode;
1919
import com.fasterxml.jackson.databind.node.ArrayNode;
20+
import io.serverlessworkflow.impl.CollectionConversionUtils;
2021
import io.serverlessworkflow.impl.WorkflowModel;
2122
import io.serverlessworkflow.impl.WorkflowModelCollection;
2223
import io.serverlessworkflow.impl.jackson.JsonUtils;
23-
import java.lang.reflect.Array;
2424
import java.util.ArrayList;
2525
import java.util.Collection;
26-
import java.util.HashSet;
2726
import java.util.Iterator;
2827
import java.util.List;
2928
import java.util.Optional;
30-
import java.util.Set;
3129

3230
public class JacksonModelCollection implements WorkflowModelCollection {
3331

@@ -46,33 +44,12 @@ public <T> Optional<T> as(Class<T> clazz) {
4644
if (node == null) return Optional.empty();
4745

4846
if (clazz.isInstance(node)) return Optional.of(clazz.cast(node));
49-
5047
if (clazz.isInstance(this)) return Optional.of(clazz.cast(this));
5148

5249
List<JsonNode> elements = new ArrayList<>(node.size());
5350
node.forEach(elements::add);
5451

55-
if (clazz.isAssignableFrom(List.class)) return Optional.of(clazz.cast(elements));
56-
else if (clazz.isAssignableFrom(Set.class))
57-
return Optional.of(clazz.cast(new HashSet<>(elements)));
58-
59-
if (clazz.isArray()) {
60-
Class<?> componentType = clazz.getComponentType();
61-
62-
if (!componentType.isPrimitive()) {
63-
Object[] typedArray = (Object[]) Array.newInstance(componentType, 0);
64-
return Optional.of(clazz.cast(elements.toArray(typedArray)));
65-
}
66-
67-
Object primitiveArray = Array.newInstance(componentType, elements.size());
68-
int i = 0;
69-
for (Object item : elements)
70-
Array.set(primitiveArray, i++, JsonUtils.convertValue(item, componentType));
71-
72-
return Optional.of(clazz.cast(primitiveArray));
73-
}
74-
75-
return Optional.empty();
52+
return CollectionConversionUtils.as(elements, clazz, JsonUtils::convertValue);
7653
}
7754

7855
@Override
@@ -115,14 +92,20 @@ public WorkflowModel next() {
11592
}
11693
}
11794

95+
private List<WorkflowModel> toModelList() {
96+
List<WorkflowModel> models = new ArrayList<>(node.size());
97+
node.forEach(n -> models.add(new JacksonModel(n)));
98+
return models;
99+
}
100+
118101
@Override
119102
public Object[] toArray() {
120-
throw new UnsupportedOperationException("toArray() is not supported yet");
103+
return toModelList().toArray();
121104
}
122105

123106
@Override
124107
public <T> T[] toArray(T[] a) {
125-
throw new UnsupportedOperationException("toArray() is not supported yet");
108+
return toModelList().toArray(a);
126109
}
127110

128111
@Override

0 commit comments

Comments
 (0)