001/*
002 *    GeoAPI - Java interfaces for OGC/ISO standards
003 *    Copyright © 2004-2024 Open Geospatial Consortium, Inc.
004 *    http://www.geoapi.org
005 *
006 *    Licensed under the Apache License, Version 2.0 (the "License");
007 *    you may not use this file except in compliance with the License.
008 *    You may obtain a copy of the License at
009 *
010 *        http://www.apache.org/licenses/LICENSE-2.0
011 *
012 *    Unless required by applicable law or agreed to in writing, software
013 *    distributed under the License is distributed on an "AS IS" BASIS,
014 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 *    See the License for the specific language governing permissions and
016 *    limitations under the License.
017 */
018package org.opengis.annotation;
019
020import java.util.Optional;
021import org.opengis.util.ControlledVocabulary;
022
023import static org.opengis.annotation.Specification.*;
024
025
026/**
027 * Whether an element is mandatory, optional or have other obligation.
028 *
029 * @author  Martin Desruisseaux (IRD)
030 * @version 3.1
031 * @since   2.0
032 */
033@UML(identifier="MD_ObligationCode", specification=ISO_19115)
034public enum Obligation implements ControlledVocabulary {
035    /*
036     * Implementation note: Enum or CodeList elements are usually declared with
037     * Obligation.CONDITIONAL. However, such declaration in the Obligation enum
038     * causes a recursive dependency. Some compilers (like Oracle javac) accept
039     * this recursive dependency while some other (Eclipse, Scala...) reject it.
040     * For better portability, we have to omit the Obligation declarations here.
041     */
042
043    /**
044     * Element is always required.
045     */
046    @UML(identifier="mandatory", specification=ISO_19115)
047    MANDATORY("mandatory"),
048
049    /**
050     * Element is not required.
051     */
052    @UML(identifier="optional", specification=ISO_19115)
053    OPTIONAL("optional"),
054
055    /**
056     * Element is required when a specific condition is met.
057     */
058    @UML(identifier="conditional", specification=ISO_19115)
059    CONDITIONAL("conditional"),
060
061    /**
062     * The element should always be {@code null}. This obligation code is used only when
063     * a sub-interface overrides an association and force it to a {@code null} value.
064     * An example is {@link org.opengis.referencing.datum.TemporalDatum#getAnchorDefinition()}.
065     *
066     * @departure constraint
067     *   ISO specifications sometimes override a parent method with a comment saying that the method
068     *   is not allowed for a particular class. Since there is no construct in Java for expressing
069     *   this constraint in the method signature, GeoAPI defines a {@code FORBIDDEN} obligation
070     *   (not in original ISO specifications) to be used with the {@code @UML} annotation and
071     *   which adds a flag in the Java documentation.
072     */
073    FORBIDDEN(null);
074
075    /**
076     * The UML identifier.
077     */
078    private final String identifier;
079
080    /**
081     * Creates a new constant with the given UML identifier.
082     *
083     * @param identifier  the UML identifier.
084     */
085    private Obligation(final String identifier) {
086        this.identifier = identifier;
087    }
088
089    /**
090     * Returns the UML identifier for this enumeration constant.
091     *
092     * @since 3.1
093     */
094    @Override
095    public Optional<String> identifier() {
096        return Optional.ofNullable(identifier);
097    }
098
099    /**
100     * Returns all constants defined by this enumeration type.
101     * Invoking this method is equivalent to invoking {@link #values()}, except that this
102     * method can be invoked on an instance of the {@code ControlledVocabulary} interface
103     * (i.e. the enumeration type does not need to be known at compile-time).
104     *
105     * @return all {@linkplain #values() values} for this enumeration.
106     *
107     * @since 3.1
108     */
109    @Override
110    public Obligation[] family() {
111        return values();
112    }
113}