001/*
002 * The contents of this file are subject to the terms of the Common Development and
003 * Distribution License (the License). You may not use this file except in compliance with the
004 * License.
005 *
006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
007 * specific language governing permission and limitations under the License.
008 *
009 * When distributing Covered Software, include this CDDL Header Notice in each file and include
010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
011 * Header, with the fields enclosed by brackets [] replaced by your own identifying
012 * information: "Portions Copyright [year] [name of copyright owner]".
013 *
014 * Copyright 2008 Sun Microsystems, Inc.
015 * Portions Copyright 2015 ForgeRock AS.
016 */
017
018package org.opends.server.admin;
019
020
021
022import java.io.BufferedInputStream;
023import java.io.IOException;
024import java.io.InputStream;
025import java.util.HashMap;
026import java.util.Map;
027import java.util.MissingResourceException;
028import java.util.Properties;
029
030
031
032/**
033 * A class for retrieving non-internationalized resource properties
034 * associated with a managed object definition.
035 * <p>
036 * Resource properties are not available for the {@link TopCfgDefn}.
037 */
038public final class ManagedObjectDefinitionResource {
039
040  /** Mapping from definition to property tables. */
041  private final Map<AbstractManagedObjectDefinition<?, ?>, Properties> properties = new HashMap<>();
042  /** The resource name prefix. */
043  private final String prefix;
044
045  /**
046   * Creates a new resource instance for the named profile.
047   *
048   * @param profile
049   *          The name of the profile.
050   * @return Returns the resource instance for the named profile.
051   */
052  public static ManagedObjectDefinitionResource createForProfile(String profile) {
053    return new ManagedObjectDefinitionResource("admin.profiles." + profile);
054  }
055
056  /** Private constructor. */
057  private ManagedObjectDefinitionResource(String prefix) {
058    this.prefix = prefix;
059  }
060
061  /**
062   * Get the resource value associated with the specified key.
063   *
064   * @param d
065   *          The managed object definition.
066   * @param key
067   *          The resource key.
068   * @return Returns the resource value associated with the specified
069   *         key.
070   * @throws MissingResourceException
071   *           If the key was not found.
072   * @throws UnsupportedOperationException
073   *           If the provided managed object definition was the
074   *           {@link TopCfgDefn}.
075   */
076  public String getString(AbstractManagedObjectDefinition<?, ?> d, String key)
077      throws MissingResourceException, UnsupportedOperationException {
078    if (d.isTop()) {
079      throw new UnsupportedOperationException(
080          "Profile resources are not available for the "
081              + "Top configuration definition");
082    }
083
084    Properties p = getProperties(d);
085    String result = p.getProperty(key);
086
087    if (result == null) {
088      String baseName = prefix + "." + d.getClass().getName();
089      String path = baseName.replace('.', '/') + ".properties";
090
091      throw new MissingResourceException("Can't find resource "
092          + path + ", key " + key, baseName, key);
093    }
094
095    return result;
096  }
097
098
099
100  /**
101   * Retrieve the properties table associated with a managed object,
102   * lazily loading it if necessary.
103   */
104  private synchronized Properties getProperties(
105      AbstractManagedObjectDefinition<?, ?> d)
106      throws MissingResourceException {
107    Properties p = properties.get(d);
108
109    if (p == null) {
110      // Load the resource file.
111      String baseName = prefix + "." + d.getClass().getName();
112      String path = baseName.replace('.', '/') + ".properties";
113      InputStream stream = ClassLoaderProvider.getInstance()
114          .getClassLoader().getResourceAsStream(path);
115
116      if (stream == null) {
117        throw new MissingResourceException("Can't find resource "
118            + path, baseName, "");
119      }
120
121      p = new Properties();
122      try {
123        p.load(new BufferedInputStream(stream));
124      } catch (IOException e) {
125        throw new MissingResourceException("Can't load resource "
126            + path + " due to IO exception: " + e.getMessage(),
127            baseName, "");
128      }
129
130      // Cache the resource.
131      properties.put(d, p);
132    }
133
134    return p;
135  }
136}