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 2010-2011 ApexIdentity Inc.
015 * Portions Copyright 2011-2014 ForgeRock AS.
016 */
017
018package org.forgerock.openig.resolver;
019
020import org.forgerock.http.util.Indexed;
021
022/**
023 * Exposes an object's elements for access through dynamic expressions and
024 * scripts.
025 */
026@SuppressWarnings("rawtypes")
027public interface Resolver extends Indexed<Class> {
028
029    /**
030     * Singleton that is returned to indicate an element is not resolved by a
031     * resolver.
032     */
033    Object UNRESOLVED = new Object() {
034        @Override
035        public String toString() {
036            return null;
037        }
038    };
039
040    /**
041     * Returns the type of object that the resolver supports. This does not
042     * necessarily guarantee that the resolver will provide resolution; rather
043     * this is how a resolver specifies what type of object it may resolve.
044     * Resolvers for more specific classes and interfaces are called earlier
045     * than those of more general classes and interfaces.
046     *
047     * @return the type of object that the resolver supports.
048     */
049    @Override
050    Class<?> getKey();
051
052    /**
053     * Attempts to resolve an element of an object. The {@code object} argument
054     * references an object for which a named or indexed element is being
055     * requested. The {@code element} argument specifies the element that is
056     * being requested from the referenced object.
057     * <p>
058     * The {@code element} argument can be either a {@link String} or an
059     * {@link Integer} object. A string represents a named element of an
060     * associative array; an integer represents the index of an ordered array.
061     * <p>
062     * If the resolver cannot resolve the requested element, then
063     * {@link #UNRESOLVED} should be returned. This allows other resovlers of
064     * more generic classes or interfaces to potentially resolve the requested
065     * element.
066     *
067     * @param object the object in which to resolve the specified element.
068     * @param element the element to resolve within the specified object.
069     * @return the value of the resolved element, or {@link #UNRESOLVED} if it
070     * cannot be resolved.
071     */
072    Object get(Object object, Object element);
073
074    /**
075     * Attempts to set the value of an element of an object. The {@code object}
076     * argument references an object for which a named or indexed element is to
077     * be set. The {@code element} argument specifies which element value is to
078     * be set. The {@code value} argument specifies the value to be set.
079     * <p>
080     * The {@code element} argument can be either a {@link String} or an
081     * {@link Integer} object. A string represents a named element of an
082     * associative array; an integer represents the index of an ordered array.
083     * <p>
084     * If the resolver cannot resolve the requested element or set its value,
085     * then {@link #UNRESOLVED} should be returned. This allows other resovlers
086     * of more generic classes or interfaces to potentially resolve the
087     * requested element.
088     *
089     * @param object the object in which to resolve the specified element.
090     * @param element the element within the specified object whose value is to be
091     * set.
092     * @param value the value to set the element to.
093     * @return the previous value of the element, {@code null} if no previous
094     * value, or {@link #UNRESOLVED} if it cannot be resolved.
095     */
096    Object put(Object object, Object element, Object value);
097}