View Javadoc

1   /***
2    *  Copyright 2003-2010 Terracotta, Inc.
3    *
4    *  Licensed under the Apache License, Version 2.0 (the "License");
5    *  you may not use this file except in compliance with the License.
6    *  You may obtain a copy of the License at
7    *
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *  Unless required by applicable law or agreed to in writing, software
11   *  distributed under the License is distributed on an "AS IS" BASIS,
12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *  See the License for the specific language governing permissions and
14   *  limitations under the License.
15   */
16  
17  package net.sf.ehcache.config;
18  
19  import java.util.Collections;
20  import java.util.HashMap;
21  import java.util.Map;
22  
23  import net.sf.ehcache.CacheException;
24  import net.sf.ehcache.search.Query;
25  import net.sf.ehcache.search.attribute.KeyObjectAttributeExtractor;
26  import net.sf.ehcache.search.attribute.ValueObjectAttributeExtractor;
27  
28  /***
29   * Search configuration for a Cache
30   *
31   * @author teck
32   */
33  public class Searchable {
34  
35      /***
36       * Default for auto-searchable keys
37       */
38      public static final boolean KEYS_DEFAULT = true;
39  
40      /***
41       * Default for auto-searchable values
42       */
43      public static final boolean VALUES_DEFAULT = true;
44  
45      /***
46       * The defined search attributes (if any) indexed by name
47       */
48      private final Map<String, SearchAttribute> searchAttributes = new HashMap<String, SearchAttribute>();
49      private boolean frozen;
50      private boolean keys;
51      private boolean values;
52  
53      /***
54       * Constructor
55       */
56      public Searchable() {
57          setKeys(KEYS_DEFAULT);
58          setValues(VALUES_DEFAULT);
59      }
60  
61      /***
62       * Add the given search attribute
63       *
64       * @throws InvalidConfigurationException if an attribute already exists for the same name
65       * @param searchAttribute to add
66       */
67      public void addSearchAttribute(SearchAttribute searchAttribute) throws InvalidConfigurationException {
68          checkDynamicChange();
69  
70          String attributeName = searchAttribute.getName();
71  
72          if (attributeName == null) {
73              throw new InvalidConfigurationException("Search attribute has null name");
74          }
75  
76          disallowBuiltins(attributeName);
77  
78          if (searchAttributes.containsKey(attributeName)) {
79              throw new InvalidConfigurationException("Repeated searchAttribute name: " + attributeName);
80          }
81  
82          searchAttributes.put(attributeName, searchAttribute);
83      }
84  
85      private void disallowBuiltins(String attributeName) {
86          if (Query.KEY.getAttributeName().equals(attributeName) || Query.VALUE.getAttributeName().equals(attributeName)) {
87              throw new InvalidConfigurationException("\"" + attributeName + "\" is a reserved attribute name");
88          }
89      }
90  
91      private void checkDynamicChange() {
92          if (frozen) {
93              throw new CacheException("Dynamic configuration changes are disabled for this cache");
94          }
95      }
96  
97      /***
98       * Get the defined search attributes indexed by attribute name
99       *
100      * @return search attributes
101      */
102     public Map<String, SearchAttribute> getSearchAttributes() {
103         return Collections.unmodifiableMap(searchAttributes);
104     }
105 
106     /***
107      * Add a search attribute
108      *
109      * @param searchAttribute attribute to add
110      * @return this
111      */
112     public Searchable searchAttribute(SearchAttribute searchAttribute) {
113         addSearchAttribute(searchAttribute);
114         return this;
115     }
116 
117     /***
118      * Freeze this configuration. Any subsequent changes will throw a CacheException
119      */
120     public void freezeConfiguration() {
121         frozen = true;
122     }
123 
124     /***
125      * Get the defined search attributes indexed by attribute name *excluding* any search attributes that are automatically/implicitly
126      * defined (eg. key and value attributes)
127      *
128      * @return search attributes
129      */
130     public Map<String, SearchAttribute> getUserDefinedSearchAttributes() {
131         Map<String, SearchAttribute> copy = new HashMap<String, SearchAttribute>(searchAttributes);
132         copy.remove(Query.KEY.getAttributeName());
133         copy.remove(Query.VALUE.getAttributeName());
134         return copy;
135     }
136 
137     /***
138      * Are keys searchable?
139      *
140      * @return true if keys are searchable
141      */
142     public boolean keys() {
143         return keys;
144     }
145 
146     /***
147      * Are values searchable?
148      *
149      * @return true if values are searchable
150      */
151     public boolean values() {
152         return values;
153     }
154 
155     /***
156      * Toggle searchable values
157      *
158      * @param b
159      */
160     public void values(boolean b) {
161         setValues(b);
162     }
163 
164     /***
165      * Toggle searchable keys
166      *
167      * @param b
168      */
169     public void keys(boolean b) {
170         setKeys(b);
171     }
172 
173     /***
174      * Toggle searchable keys
175      *
176      * @param keys
177      */
178     public void setKeys(boolean keys) {
179         checkDynamicChange();
180         this.keys = keys;
181         if (!keys) {
182             searchAttributes.remove(Query.KEY.getAttributeName());
183         } else {
184             String keyAttr = Query.KEY.getAttributeName();
185             searchAttributes.put(keyAttr, new SearchAttribute().name(keyAttr).className(KeyObjectAttributeExtractor.class.getName()));
186         }
187     }
188 
189     /***
190      * Toggle searchable values
191      *
192      * @param values
193      */
194     public void setValues(boolean values) {
195         checkDynamicChange();
196         this.values = values;
197         if (!values) {
198             searchAttributes.remove(Query.VALUE.getAttributeName());
199         } else {
200             String valueAttr = Query.VALUE.getAttributeName();
201             searchAttributes.put(valueAttr, new SearchAttribute().name(valueAttr).className(ValueObjectAttributeExtractor.class.getName()));
202         }
203     }
204 }