1   /*
2    * SPDX-FileCopyrightText: none
3    * SPDX-License-Identifier: CC0-1.0
4    */
5   
6   package dev.metaschema.schemagen.json.impl;
7   
8   import com.fasterxml.jackson.databind.node.ObjectNode;
9   
10  import java.util.List;
11  import java.util.Set;
12  import java.util.stream.Collectors;
13  import java.util.stream.Stream;
14  
15  import dev.metaschema.core.model.IChoiceGroupInstance;
16  import dev.metaschema.core.util.ObjectUtils;
17  import edu.umd.cs.findbugs.annotations.NonNull;
18  
19  /**
20   * Supports generation of a JSON schema based on a Metaschema
21   * {@link IChoiceGroupInstance}, which can be generated inline or as a JSON
22   * schema definition.
23   */
24  public class JsonSchemaPropertyChoiceGroup
25      extends AbstractJsonSchemaPropertyNamed<IChoiceGroupInstance> {
26    @NonNull
27    private final List<IJsonSchemaPropertyGrouped> choiceInstances;
28  
29    /**
30     * Construct a new JSON schema property.
31     *
32     * @param instance
33     *          the instance to construct the property for
34     * @param state
35     *          the JSON generation state used to get JSON schema information
36     */
37    public JsonSchemaPropertyChoiceGroup(
38        @NonNull IChoiceGroupInstance instance,
39        @NonNull IJsonGenerationState state) {
40      super(instance, instance.getGroupAsName() == null ? "[unknown]" : ObjectUtils.notNull(instance.getGroupAsName()));
41      this.choiceInstances = ObjectUtils.notNull(instance.getNamedModelInstances().stream()
42          .map(state::getJsonSchemaPropertyGrouped)
43          .collect(Collectors.toUnmodifiableList()));
44    }
45  
46    @Override
47    public boolean isRequired() {
48      return getInstance().getMinOccurs() > 0;
49    }
50  
51    @Override
52    public Stream<IJsonSchemaDefinable> collectDefinitions(
53        Set<IJsonSchemaDefinitionAssembly> visited,
54        IJsonGenerationState state) {
55      return ObjectUtils.notNull(choiceInstances.stream()
56          .flatMap(choice -> choice.collectDefinitions(visited, state)));
57    }
58  
59    @Override
60    protected void generateMetadata(ObjectNode obj, IJsonGenerationState state) {
61      // do nothing
62    }
63  
64    @Override
65    protected void generateBody(ObjectNode obj, IJsonGenerationState state) {
66      ICardinalityBehavior.behaviorFor(getInstance())
67          .generate(obj, getInstance(), choiceInstances, state);
68      assert !obj.isEmpty();
69    }
70  }