001 /*
002 * CDDL HEADER START
003 *
004 * The contents of this file are subject to the terms of the
005 * Common Development and Distribution License, Version 1.0 only
006 * (the "License"). You may not use this file except in compliance
007 * with the License.
008 *
009 * You can obtain a copy of the license at
010 * docs/licenses/cddl.txt
011 * or http://www.opensource.org/licenses/cddl1.php.
012 * See the License for the specific language governing permissions
013 * and limitations under the License.
014 *
015 * When distributing Covered Code, include this CDDL HEADER in each
016 * file and include the License file at
017 * docs/licenses/cddl.txt. If applicable,
018 * add the following below this CDDL HEADER, with the fields enclosed
019 * by brackets "[]" replaced with your own identifying information:
020 * Portions Copyright [yyyy] [name of copyright owner]
021 *
022 * CDDL HEADER END
023 *
024 *
025 * Copyright 2012-2013 UnboundID Corp.
026 */
027 package com.unboundid.directory.sdk.ds.scripting;
028
029
030
031 import java.util.List;
032
033 import com.unboundid.directory.sdk.common.internal.Reconfigurable;
034 import com.unboundid.directory.sdk.common.types.Entry;
035 import com.unboundid.directory.sdk.ds.config.UncachedEntryCriteriaConfig;
036 import com.unboundid.directory.sdk.ds.internal.DirectoryServerExtension;
037 import com.unboundid.directory.sdk.ds.types.DirectoryServerContext;
038 import com.unboundid.ldap.sdk.LDAPException;
039 import com.unboundid.ldap.sdk.ResultCode;
040 import com.unboundid.util.Extensible;
041 import com.unboundid.util.ThreadSafety;
042 import com.unboundid.util.ThreadSafetyLevel;
043 import com.unboundid.util.args.ArgumentException;
044 import com.unboundid.util.args.ArgumentParser;
045
046
047
048 /**
049 * This class defines an API that must be implemented by scripted extensions
050 * which have the ability to determine which entries should be stored in the
051 * uncached-id2entry database of a local DB backend, rather than in the id2entry
052 * database. In environments with data sets too large to fit in available
053 * memory, this can help the server better use the memory it does have for
054 * entries that are more likely to be accessed.
055 * <BR>
056 * <H2>Configuring Groovy-Scripted Uncached Entry Criteria</H2>
057 * In order to configure a scripted uncached entry criteria object based on
058 * this API and written in the Groovy scripting language, use a command like:
059 * <PRE>
060 * dsconfig create-uncached-entry-criteria \
061 * --criteria-name "<I>{criteria-name}</I>" \
062 * --type groovy-scripted \
063 * --set enabled:true \
064 * --set "script-class:<I>{class-name}</I>" \
065 * --set "script-argument:<I>{name=value}</I>"
066 * </PRE>
067 * where "<I>{handler-name}</I>" is the name to use for the uncached entry
068 * criteria instance, "<I>{class-name}</I>" is the fully-qualified name of the
069 * Groovy class written using this API, and "<I>{name=value}</I>" represents
070 * name-value pairs for any arguments to provide to the uncached entry criteria
071 * object. If multiple arguments should be provided to the uncached entry
072 * criteria, then the "<CODE>--set script-argument:<I>{name=value}</I></CODE>"
073 * option should be provided multiple times.
074 *
075 * @see com.unboundid.directory.sdk.ds.api.UncachedEntryCriteria
076 */
077 @Extensible()
078 @DirectoryServerExtension()
079 @ThreadSafety(level=ThreadSafetyLevel.INTERFACE_THREADSAFE)
080 public abstract class ScriptedUncachedEntryCriteria
081 implements Reconfigurable<UncachedEntryCriteriaConfig>
082 {
083 /**
084 * Creates a new instance of this uncached entry criteria. All uncached entry
085 * criteria implementations must include a default constructor, but any
086 * initialization should generally be done in the
087 * {@code initializeUncachedEntryCriteria} method.
088 */
089 public ScriptedUncachedEntryCriteria()
090 {
091 // No implementation is required.
092 }
093
094
095
096 /**
097 * {@inheritDoc}
098 */
099 public void defineConfigArguments(final ArgumentParser parser)
100 throws ArgumentException
101 {
102 // No arguments will be allowed by default.
103 }
104
105
106
107 /**
108 * Initializes this uncached entry criteria.
109 *
110 * @param serverContext A handle to the server context for the server in
111 * which this extension is running.
112 * @param config The general configuration for this uncached entry
113 * criteria.
114 * @param parser The argument parser which has been initialized from
115 * the configuration for this uncached entry criteria.
116 *
117 * @throws LDAPException If a problem occurs while initializing this
118 * uncached entry criteria.
119 */
120 public void initializeUncachedEntryCriteria(
121 final DirectoryServerContext serverContext,
122 final UncachedEntryCriteriaConfig config,
123 final ArgumentParser parser)
124 throws LDAPException
125 {
126 // No initialization will be performed by default.
127 }
128
129
130
131 /**
132 * {@inheritDoc}
133 */
134 public boolean isConfigurationAcceptable(
135 final UncachedEntryCriteriaConfig config,
136 final ArgumentParser parser,
137 final List<String> unacceptableReasons)
138 {
139 // No extended validation will be performed.
140 return true;
141 }
142
143
144
145 /**
146 * {@inheritDoc}
147 */
148 public ResultCode applyConfiguration(
149 final UncachedEntryCriteriaConfig config,
150 final ArgumentParser parser,
151 final List<String> adminActionsRequired,
152 final List<String> messages)
153 {
154 // By default, no configuration changes will be applied. If there are any
155 // arguments, then add an admin action message indicating that the extension
156 // needs to be restarted for any changes to take effect.
157 if (! parser.getNamedArguments().isEmpty())
158 {
159 adminActionsRequired.add(
160 "No configuration change has actually been applied. The new " +
161 "configuration will not take effect until this uncached " +
162 "entry criteria is disabled and re-enabled or until the " +
163 "server is restarted.");
164 }
165
166 return ResultCode.SUCCESS;
167 }
168
169
170
171 /**
172 * Performs any cleanup which may be necessary when this uncached entry
173 * criteria instance is to be taken out of service.
174 */
175 public void finalizeUncachedEntryCriteria()
176 {
177 // No implementation is required.
178 }
179
180
181
182 /**
183 * Indicates whether the provided entry should be written into the
184 * uncached-id2entry database rather than into id2entry. This method may be
185 * used both for new entries (e.g., from add operations or LDIF imports) or
186 * existing entries (e.g., from modify, modify DN, or soft delete operations,
187 * or from re-encode processing).
188 *
189 * @param previousEntry A read-only representation of the entry as it
190 * existed before the update. If the entry is
191 * unchanged or did not previously exist, then this
192 * will be the same as {@code updatedEntry}.
193 * @param updatedEntry A read-only representation of the entry as it will
194 * be written into either the id2entry or
195 * uncached-id2entry database.
196 *
197 * @return {@code true} if the entry should be written into the
198 * uncached-id2entry database, or {@code false} if it should be
199 * written into the id2entry database.
200 */
201 public abstract boolean shouldBeUncached(final Entry previousEntry,
202 final Entry updatedEntry);
203 }