Package org.apache.sis.internal.jaxb.referencing

Source Code of org.apache.sis.internal.jaxb.referencing.Code

/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements.  See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License.  You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.sis.internal.jaxb.referencing;

import javax.xml.bind.annotation.XmlType;
import javax.xml.bind.annotation.XmlValue;
import javax.xml.bind.annotation.XmlAttribute;
import org.opengis.metadata.citation.Citation;
import org.opengis.referencing.ReferenceIdentifier;
import org.apache.sis.internal.util.DefinitionURI;
import org.apache.sis.referencing.NamedIdentifier;
import org.apache.sis.metadata.iso.citation.Citations;

import static org.apache.sis.internal.metadata.ReferencingUtilities.toURNType;


/**
* The {@code gml:CodeType}, which is made of a code space and a code value.
*
* @author  Guilhem Legal (Geomatys)
* @author  Cédric Briançon (Geomatys)
* @author  Martin Desruisseaux (Geomatys)
* @since   0.4 (derived from geotk-3.00)
* @version 0.4
* @module
*/
@XmlType(name = "CodeType")
public final class Code {
    /**
     * The identifier code.
     *
     * <p><b>Note:</b> GML (the target of this class) represents that code as an XML value, while
     * {@link org.apache.sis.metadata.iso.ImmutableIdentifier} represents it as an XML element.</p>
     */
    @XmlValue
    String code;

    /**
     * The code space, which is often {@code "EPSG"} with the version in use.
     *
     * <p><b>Note:</b> GML (the target of this class) represents that code as an XML attribute, while
     * {@link org.apache.sis.metadata.iso.ImmutableIdentifier} represents it as an XML element.</p>
     */
    @XmlAttribute
    String codeSpace;

    /**
     * Empty constructor for JAXB.
     */
    Code() {
    }

    /**
     * Creates a wrapper initialized to the values of the given identifier.
     * Version number, if presents, will be appended after the codespace with a semicolon separator.
     * The {@link #getIdentifier()} method shall be able to perform the opposite operation (split the
     * above in separated codespace and version attributes).
     *
     * @param identifier The identifier from which to get the values.
     */
    Code(final ReferenceIdentifier identifier) {
        code      = identifier.getCode();
        codeSpace = identifier.getCodeSpace();
        String version = identifier.getVersion();
        if (version != null) {
            final StringBuilder buffer = new StringBuilder();
            if (codeSpace != null) {
                buffer.append(codeSpace);
            }
            codeSpace = buffer.append(DefinitionURI.SEPARATOR).append(version).toString();
        }
    }

    /**
     * Returns the identifier for this value. This method is the converse of the constructor.
     * If the {@link #codeSpace} contains a semicolon, then the part after the last semicolon
     * will be taken as the authority version number. This is for consistency with what the
     * constructor does.
     *
     * @return The identifier, or {@code null} if none.
     */
    public ReferenceIdentifier getIdentifier() {
        String c = code;
        if (c == null) {
            return null;
        }
        Citation authority = null;
        String version = null, cs = codeSpace;
        final DefinitionURI parsed = DefinitionURI.parse(c);
        if (parsed != null) {
            authority = Citations.fromName(cs); // May be null.
            cs        = parsed.authority;
            version   = parsed.version;
            c         = parsed.code;
        } else if (cs != null) {
            final int s = cs.lastIndexOf(DefinitionURI.SEPARATOR);
            if (s >= 0) {
                version = cs.substring(s+1);
                cs = cs.substring(0, s);
            }
            authority = Citations.fromName(cs);
        }
        return new NamedIdentifier(authority, cs, c, version, null);
    }

    /**
     * Returns a {@code <gml:identifier>} for the given identified object, or {@code null} if none.
     * This method searches for the following identifiers, in preference order:
     * <ul>
     *   <li>The first identifier having a code that begin with {@code "urn:"}.</li>
     *   <li>The first identifier having a code that begin with {@code "http:"}.</li>
     *   <li>The first identifier, converted to the {@code "urn:} syntax if possible.</li>
     * </ul>
     *
     * @param  type The type of the identified object.
     * @param  identifiers The object identifiers, or {@code null} if none.
     * @return The {@code <gml:identifier>} as a {@code Code} instance, or {@code null} if none.
     */
    public static Code forIdentifiedObject(final Class<?> type, final Iterable<? extends ReferenceIdentifier> identifiers) {
        if (identifiers != null) {
            boolean isHTTP = false;
            ReferenceIdentifier fallback = null;
            for (final ReferenceIdentifier identifier : identifiers) {
                final String code = identifier.getCode();
                if (code == null) continue; // Paranoiac check.
                if (code.regionMatches(true, 0, "urn:", 0, 4)) {
                    return new Code(identifier);
                }
                if (!isHTTP) {
                    isHTTP = code.regionMatches(true, 0, "http:", 0, 5);
                    if (isHTTP || fallback == null) {
                        fallback = identifier;
                    }
                }
            }
            /*
             * If no "urn:" or "http:" form has been found, try to create a "urn:" form the first identifier.
             * For example "EPSG:4326" may be converted to "urn:ogc:def:crs:EPSG:8.2:4326". If the first identifier
             * can not be converted to a "urn:" form, then it will be returned as-is.
             */
            if (fallback != null) {
                if (!isHTTP) {
                    final String urn = DefinitionURI.format(toURNType(type), fallback);
                    if (urn != null) {
                        final Code code = new Code();
                        code.codeSpace = Citations.getIdentifier(fallback.getAuthority());
                        code.code = urn;
                        return code;
                    }
                }
                return new Code(fallback);
            }
        }
        return null;
    }
}
TOP

Related Classes of org.apache.sis.internal.jaxb.referencing.Code

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.