• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

AuthMe / ConfigMe / 5849278287

13 Aug 2023 08:02PM UTC coverage: 99.449% (-0.07%) from 99.523%
5849278287

push

github

ljacqu
#229 Remove option to split map keys by "."

558 of 574 branches covered (97.21%)

10 of 10 new or added lines in 4 files covered. (100.0%)

1444 of 1452 relevant lines covered (99.45%)

4.59 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

96.43
/src/main/java/ch/jalu/configme/resource/MapNormalizer.java
1
package ch.jalu.configme.resource;
2

3
import org.jetbrains.annotations.NotNull;
4
import org.jetbrains.annotations.Nullable;
5

6
import java.util.LinkedHashMap;
7
import java.util.Map;
8
import java.util.Objects;
9
import java.util.Optional;
10

11
/**
12
 * Normalizes the keys of maps, splitting compound keys and ensuring that all keys are Strings.
13
 */
14
public class MapNormalizer {
3✔
15

16
    /**
17
     * Normalizes the raw map read from a property resource for further use in a property reader.
18
     *
19
     * @param loadedMap the map to normalize
20
     * @return new map with sanitized structure (or same if no changes are needed)
21
     */
22
    @SuppressWarnings("unchecked")
23
    public @Nullable Map<String, Object> normalizeMap(@Nullable Map<Object, Object> loadedMap) {
24
        if (loadedMap == null) {
2✔
25
            return null;
2✔
26
        }
27
        // Cast to Map<String, Object> if we have an empty optional as the method guarantees to return a new Map
28
        // if it does not exclusively use String keys
29
        return createNormalizedMapIfNeeded(loadedMap).orElse((Map) loadedMap);
7✔
30
    }
31

32
    /**
33
     * Processes the given value if it is a Map and returns an Optional with a new Map if the input
34
     * value is not in its "normalized form". Recursively visits and replaces nested maps.
35
     *
36
     * @param value the value to process
37
     * @return optional with a new map to replace the given one with, empty optional if not needed or not applicable
38
     */
39
    protected @NotNull Optional<Map<String, Object>> createNormalizedMapIfNeeded(@NotNull Object value) {
40
        if (!(value instanceof Map<?, ?>)) {
3✔
41
            return Optional.empty();
2✔
42
        }
43

44
        Map<Object, Object> map = (Map<Object, Object>) value;
3✔
45
        boolean mapNeedsModification = false;
2✔
46
        for (Map.Entry<Object, Object> entry : map.entrySet()) {
11✔
47
            createNormalizedMapIfNeeded(entry.getValue())
7✔
48
                .ifPresent(newMap -> map.put(entry.getKey(), newMap));
8✔
49

50
            if (!mapNeedsModification && isKeyInvalid(entry.getKey())) {
7✔
51
                mapNeedsModification = true;
2✔
52
            }
53
        }
1✔
54

55
        if (mapNeedsModification) {
2✔
56
            Map<String, Object> cleanedMap = new LinkedHashMap<>(map.size());
6✔
57
            for (Map.Entry<Object, Object> entry : map.entrySet()) {
11✔
58
                addValueIntoMap(cleanedMap, Objects.toString(entry.getKey()), entry.getValue());
8✔
59
            }
1✔
60
            return Optional.of(cleanedMap);
3✔
61
        }
62
        return Optional.empty();
2✔
63
    }
64

65
    protected boolean isKeyInvalid(@NotNull Object key) {
66
        return !(key instanceof String);
7✔
67
    }
68

69
    /**
70
     * Adds the provided value into the given map, splitting the path into periods appropriately and keeping
71
     * any intermediate nested maps which may already exist.
72
     *
73
     * @param map the map to add the value to
74
     * @param path the path to store the value under
75
     * @param value the value to store
76
     */
77
    protected void addValueIntoMap(@NotNull Map<String, Object> map, @NotNull String path, @NotNull Object value) {
78
        if (value instanceof Map<?, ?>) {
3✔
79
            Map<String, Object> mapAtPath = getOrInsertMap(map, path);
5✔
80
            Map<?, ?> mapValue = (Map<?, ?>) value;
3✔
81
            mapValue.forEach((entryKey, entryValue) ->
5✔
82
                addValueIntoMap(mapAtPath, Objects.toString(entryKey), entryValue));
7✔
83
        } else { // value is not a map: just insert it
1✔
84
            map.put(path, value);
5✔
85
        }
86
    }
1✔
87

88
    /**
89
     * Returns the nested map in the given {@code parentMap} at the given {@code path}, inserting
90
     * one if none is yet present. Periods in the path argument are not handled by this method.
91
     * Note that this method overrides any non-Map values stored at the given path.
92
     *
93
     * @param parentMap the map to retrieve the nested map from
94
     * @param path the key with which the value should be looked up from the map
95
     * @return the nested map, as stored under the path in the given map
96
     */
97
    protected @NotNull Map<String, Object> getOrInsertMap(@NotNull Map<String, Object> parentMap,
98
                                                          @NotNull String path) {
99
        Object value = parentMap.get(path);
4✔
100
        if (value instanceof Map<?, ?>) {
3!
101
            return (Map<String, Object>) value;
×
102
        }
103
        Map<String, Object> newMap = new LinkedHashMap<>();
4✔
104
        parentMap.put(path, newMap);
5✔
105
        return newMap;
2✔
106
    }
107
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc