2 * Copyright (c) 2018 Pantheon Technologies, s.r.o. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.yangtools.yang.model.export;
10 import static com.google.common.base.Preconditions.checkArgument;
11 import static java.util.Objects.requireNonNull;
13 import com.google.common.collect.ImmutableListMultimap;
14 import com.google.common.collect.Iterators;
15 import com.google.common.collect.ListMultimap;
16 import java.util.Collection;
17 import java.util.Iterator;
19 import java.util.Map.Entry;
20 import javax.xml.XMLConstants;
21 import javax.xml.namespace.NamespaceContext;
22 import org.eclipse.jdt.annotation.NonNull;
23 import org.opendaylight.yangtools.yang.common.QNameModule;
24 import org.opendaylight.yangtools.yang.common.YangConstants;
25 import org.opendaylight.yangtools.yang.model.api.stmt.ModuleEffectiveStatement;
27 final class ModuleNamespaceContext implements NamespaceContext {
28 private static final Entry<String, String> YIN_PREFIX_AND_NAMESPACE =
29 Map.entry(XMLConstants.DEFAULT_NS_PREFIX, YangConstants.RFC6020_YIN_NAMESPACE_STRING);
31 private final ListMultimap<@NonNull String, @NonNull String> namespaceToPrefix;
32 private final ModuleEffectiveStatement module;
34 ModuleNamespaceContext(final ModuleEffectiveStatement module) {
35 this.module = requireNonNull(module);
37 final var namespaces = ImmutableListMultimap.<String, String>builder();
38 for (var entry : module.namespacePrefixes()) {
39 namespaces.put(entry.getKey().namespace().toString(), entry.getValue());
41 namespaceToPrefix = namespaces.build();
45 public String getNamespaceURI(final String prefix) {
46 checkArgument(prefix != null);
48 return switch (prefix) {
49 case XMLConstants.DEFAULT_NS_PREFIX -> YangConstants.RFC6020_YIN_NAMESPACE_STRING;
50 case XMLConstants.XML_NS_PREFIX -> XMLConstants.XML_NS_URI;
51 case XMLConstants.XMLNS_ATTRIBUTE -> XMLConstants.XMLNS_ATTRIBUTE_NS_URI;
52 default -> module.findReachableModule(prefix)
53 .map(importedModule -> importedModule.localQNameModule().namespace().toString())
54 .orElse(XMLConstants.NULL_NS_URI);
59 public String getPrefix(final String namespaceURI) {
60 checkArgument(namespaceURI != null);
62 return switch (namespaceURI) {
63 case YangConstants.RFC6020_YIN_NAMESPACE_STRING -> XMLConstants.DEFAULT_NS_PREFIX;
64 case XMLConstants.XML_NS_URI -> XMLConstants.XML_NS_PREFIX;
65 case XMLConstants.XMLNS_ATTRIBUTE_NS_URI -> XMLConstants.XMLNS_ATTRIBUTE;
67 final var prefixes = namespaceToPrefix.get(namespaceURI);
68 yield prefixes.isEmpty() ? null : prefixes.get(0);
74 public Iterator<String> getPrefixes(final String namespaceURI) {
75 checkArgument(namespaceURI != null);
77 return switch (namespaceURI) {
78 case YangConstants.RFC6020_YIN_NAMESPACE_STRING ->
79 Iterators.singletonIterator(XMLConstants.DEFAULT_NS_PREFIX);
80 case XMLConstants.XML_NS_URI -> Iterators.singletonIterator(XMLConstants.XML_NS_PREFIX);
81 case XMLConstants.XMLNS_ATTRIBUTE_NS_URI -> Iterators.singletonIterator(XMLConstants.XMLNS_ATTRIBUTE);
82 default -> namespaceToPrefix.get(namespaceURI).iterator();
86 Entry<String, String> prefixAndNamespaceFor(final QNameModule namespace) {
87 if (YangConstants.RFC6020_YIN_MODULE.equals(namespace)) {
88 return YIN_PREFIX_AND_NAMESPACE;
91 final String prefix = module.findNamespacePrefix(namespace)
92 .orElseThrow(() -> new IllegalArgumentException("Module " + namespace + " does not map to a prefix"));
93 return Map.entry(prefix, namespace.namespace().toString());
96 Collection<Entry<String, ModuleEffectiveStatement>> importedModules() {
97 return module.reachableModules();