1   /*
2    * Copyright 2003 - 2014 The eFaps Team
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   * Revision:        $Rev$
17   * Last Changed:    $Date$
18   * Last Changed By: $Author$
19   */
20  
21  package org.efaps.db;
22  
23  import java.util.List;
24  import java.util.UUID;
25  import java.util.concurrent.TimeUnit;
26  
27  import org.efaps.admin.datamodel.Type;
28  import org.efaps.util.EFapsException;
29  import org.efaps.util.cache.CacheReloadException;
30  import org.infinispan.Cache;
31  
32  /**
33   * TODO comment!
34   *
35   * @author The eFaps Team
36   * @version $Id$
37   */
38  public class CachedInstanceQuery
39      extends InstanceQuery
40      implements ICacheDefinition
41  {
42  
43      /**
44       * Key used for the QueryKey instance.
45       */
46      private String key;
47  
48      /**
49       * lifespan of the entry. Negative values are interpreted as unlimited
50       * lifespan. 0 means do not apply
51       */
52      private long lifespan = 0;
53  
54      /**
55       * time unit for lifespan.
56       */
57      private TimeUnit lifespanUnit;
58  
59      /**
60       * the maximum amount of time this key is allowed to be idle for before it
61       * is considered as expired. 0 means do not apply
62       */
63      private long maxIdleTime = 0;
64  
65      /**
66       * time unit for max idle time.
67       */
68      private TimeUnit maxIdleTimeUnit;
69  
70      /**
71       * Constructor setting the type by his UUID.
72       *
73       * @param _typeUUI UUID of the Type the query is based on
74       * @throws CacheReloadException on error
75       */
76      public CachedInstanceQuery(final UUID _typeUUI)
77          throws CacheReloadException
78      {
79          super(_typeUUI);
80      }
81  
82      /**
83       * Constructor setting the type.
84       *
85       * @param _type TYpe the query is based on
86       */
87      public CachedInstanceQuery(final Type _type)
88      {
89          super(_type);
90      }
91  
92      /**
93       * @param _key key to the cache
94       * @param _typeUUID UUID of the Type the query is based on
95       * @throws CacheReloadException on error
96       */
97      public CachedInstanceQuery(final String _key,
98                                 final UUID _typeUUID)
99          throws CacheReloadException
100     {
101         this(_typeUUID);
102         this.key = _key;
103     }
104 
105     /**
106      * @param _key key to the cache
107      * @param _type TYpe the query is based on
108      * @throws CacheReloadException on error
109      */
110     public CachedInstanceQuery(final String _key,
111                                final Type _type)
112         throws CacheReloadException
113     {
114         this(_type);
115         this.key = _key;
116     }
117 
118     /**
119      * The instance method executes the query without an access check.
120      *
121      * @return true if the query contains values, else false
122      * @throws EFapsException on error
123      */
124     @Override
125     public List<Instance> executeWithoutAccessCheck()
126         throws EFapsException
127     {
128         prepareQuery();
129         final String sql = createSQLStatement();
130         final QueryKey querykey = QueryKey.get(getKey(), sql);
131         final Cache<QueryKey, Object> cache = QueryCache.getSqlCache();
132         if (cache.containsKey(querykey)) {
133             final Object object = cache.get(querykey);
134             if (object instanceof List) {
135                 final List<?> values = (List<?>) object;
136                 for (final Object value : values) {
137                     if (value instanceof Instance) {
138                         getValues().add((Instance) value);
139                     }
140                 }
141             }
142         } else {
143             executeOneCompleteStmt(sql);
144             QueryCache.put(this, querykey, getValues());
145         }
146         return getValues();
147     }
148 
149     /**
150      * Getter method for the instance variable {@link #key}.
151      *
152      * @return value of instance variable {@link #key}
153      */
154     public String getKey()
155     {
156         return this.key;
157     }
158 
159     /**
160      * Setter method for instance variable {@link #key}.
161      *
162      * @param _key value for instance variable {@link #key}
163      */
164     public void setKey(final String _key)
165     {
166         this.key = _key;
167     }
168 
169     /**
170      * {@inheritDoc}
171      */
172     @Override
173     public long getLifespan()
174     {
175         return this.lifespan;
176     }
177 
178     /**
179      * {@inheritDoc}
180      */
181     @Override
182     public TimeUnit getLifespanUnit()
183     {
184         return this.lifespanUnit;
185     }
186 
187     /**
188      * {@inheritDoc}
189      */
190     @Override
191     public long getMaxIdleTime()
192     {
193         return this.maxIdleTime;
194     }
195 
196     /**
197      * {@inheritDoc}
198      */
199     @Override
200     public TimeUnit getMaxIdleTimeUnit()
201     {
202         return this.maxIdleTimeUnit;
203     }
204 
205     /**
206      * Setter method for instance variable {@link #lifespan}.
207      *
208      * @param _lifespan value for instance variable {@link #lifespan}
209      * @return this instance to allow chaining
210      */
211     public CachedInstanceQuery setLifespan(final long _lifespan)
212     {
213         this.lifespan = _lifespan;
214         return this;
215     }
216 
217     /**
218      * Setter method for instance variable {@link #lifespanUnit}.
219      *
220      * @param _lifespanUnit value for instance variable {@link #lifespanUnit}
221      * @return this instance to allow chaining
222      */
223     public CachedInstanceQuery setLifespanUnit(final TimeUnit _lifespanUnit)
224     {
225         this.lifespanUnit = _lifespanUnit;
226         return this;
227     }
228 
229     /**
230      * Setter method for instance variable {@link #maxIdleTime}.
231      *
232      * @param _maxIdleTime value for instance variable {@link #maxIdleTime}
233      * @return this instance to allow chaining
234      */
235     public CachedInstanceQuery setMaxIdleTime(final long _maxIdleTime)
236     {
237         this.maxIdleTime = _maxIdleTime;
238         return this;
239     }
240 
241     /**
242      * Setter method for instance variable {@link #maxIdleTimeUnit}.
243      *
244      * @param _maxIdleTimeUnit value for instance variable
245      *            {@link #maxIdleTimeUnit}
246      * @return this instance to allow chaining
247      */
248     public CachedInstanceQuery setMaxIdleTimeUnit(final TimeUnit _maxIdleTimeUnit)
249     {
250         this.maxIdleTimeUnit = _maxIdleTimeUnit;
251         return this;
252     }
253 
254     /**
255      * Get a CachedInstanceQuery that will only cache during a request.
256      * @param _type Type the query is based on
257      * @throws CacheReloadException on error
258      */
259     public static CachedInstanceQuery get4Request(final Type _type)
260         throws EFapsException
261     {
262         return new CachedInstanceQuery(Context.getThreadContext().getRequestId(), _type).setLifespan(5)
263                         .setLifespanUnit(TimeUnit.MINUTES);
264     }
265 
266     /**
267      * Get a CachedInstanceQuery that will only cache during a request.
268      * @param _typeUUID uuid of the Type the query is based on
269      * @throws CacheReloadException on error
270      */
271     public static CachedInstanceQuery get4Request(final UUID _typeUUID)
272         throws EFapsException
273     {
274         return new CachedInstanceQuery(Context.getThreadContext().getRequestId(), _typeUUID).setLifespan(5)
275                         .setLifespanUnit(TimeUnit.MINUTES);
276     }
277 }