1   /**
2    * Copyright (c) 2000-2010 Liferay, Inc. All rights reserved.
3    *
4    * The contents of this file are subject to the terms of the Liferay Enterprise
5    * Subscription License ("License"). You may not use this file except in
6    * compliance with the License. You can obtain a copy of the License by
7    * contacting Liferay, Inc. See the License for the specific language governing
8    * permissions and limitations under the License, including but not limited to
9    * distribution rights of the Software.
10   *
11   *
12   *
13   */
14  
15  package com.liferay.portal.service.persistence.impl;
16  
17  import com.liferay.portal.NoSuchModelException;
18  import com.liferay.portal.SystemException;
19  import com.liferay.portal.kernel.dao.db.DB;
20  import com.liferay.portal.kernel.dao.db.DBFactoryUtil;
21  import com.liferay.portal.kernel.dao.orm.Dialect;
22  import com.liferay.portal.kernel.dao.orm.DynamicQuery;
23  import com.liferay.portal.kernel.dao.orm.ORMException;
24  import com.liferay.portal.kernel.dao.orm.OrderFactoryUtil;
25  import com.liferay.portal.kernel.dao.orm.ProjectionFactoryUtil;
26  import com.liferay.portal.kernel.dao.orm.Session;
27  import com.liferay.portal.kernel.dao.orm.SessionFactory;
28  import com.liferay.portal.kernel.log.Log;
29  import com.liferay.portal.kernel.log.LogFactoryUtil;
30  import com.liferay.portal.kernel.util.ListUtil;
31  import com.liferay.portal.kernel.util.OrderByComparator;
32  import com.liferay.portal.kernel.util.StringBundler;
33  import com.liferay.portal.model.BaseModel;
34  import com.liferay.portal.model.ModelListener;
35  import com.liferay.portal.service.persistence.BasePersistence;
36  
37  import java.io.Serializable;
38  
39  import java.sql.Connection;
40  
41  import java.util.List;
42  
43  import javax.sql.DataSource;
44  
45  /**
46   * <a href="BasePersistenceImpl.java.html"><b><i>View Source</i></b></a>
47   *
48   * @author Brian Wing Shun Chan
49   * @author Shuyang Zhou
50   */
51  public class BasePersistenceImpl<T extends BaseModel<T>>
52      implements BasePersistence<T>, SessionFactory {
53  
54      public static final String COUNT_COLUMN_NAME = "COUNT_VALUE";
55  
56      public void clearCache() {
57      }
58  
59      public void clearCache(T model) {
60      }
61  
62      public void closeSession(Session session) {
63          _sessionFactory.closeSession(session);
64      }
65  
66      public int countWithDynamicQuery(DynamicQuery dynamicQuery)
67          throws SystemException {
68  
69          dynamicQuery.setProjection(ProjectionFactoryUtil.rowCount());
70  
71          List<Integer> results = findWithDynamicQuery(dynamicQuery);
72  
73          if (results.isEmpty()) {
74              return 0;
75          }
76          else {
77              return (results.get(0)).intValue();
78          }
79      }
80  
81      @SuppressWarnings("unused")
82      public T fetchByPrimaryKey(Serializable primaryKey) throws SystemException {
83          throw new UnsupportedOperationException();
84      }
85  
86      @SuppressWarnings("unused")
87      public T findByPrimaryKey(Serializable primaryKey)
88          throws NoSuchModelException, SystemException {
89  
90          throw new UnsupportedOperationException();
91      }
92  
93      @SuppressWarnings("rawtypes")
94      public List findWithDynamicQuery(DynamicQuery dynamicQuery)
95          throws SystemException {
96  
97          Session session = null;
98  
99          try {
100             session = openSession();
101 
102             dynamicQuery.compile(session);
103 
104             return dynamicQuery.list();
105         }
106         catch (Exception e) {
107             throw processException(e);
108         }
109         finally {
110             closeSession(session);
111         }
112     }
113 
114     @SuppressWarnings("rawtypes")
115     public List findWithDynamicQuery(
116             DynamicQuery dynamicQuery, int start, int end)
117         throws SystemException {
118 
119         Session session = null;
120 
121         try {
122             session = openSession();
123 
124             dynamicQuery.setLimit(start, end);
125 
126             dynamicQuery.compile(session);
127 
128             return dynamicQuery.list();
129         }
130         catch (Exception e) {
131             throw processException(e);
132         }
133         finally {
134             closeSession(session);
135         }
136     }
137 
138     @SuppressWarnings("rawtypes")
139     public List findWithDynamicQuery(
140             DynamicQuery dynamicQuery, int start, int end,
141             OrderByComparator orderByComparator)
142         throws SystemException {
143 
144         OrderFactoryUtil.addOrderByComparator(dynamicQuery, orderByComparator);
145 
146         return findWithDynamicQuery(dynamicQuery, start, end);
147     }
148 
149     public DataSource getDataSource() {
150         return _dataSource;
151     }
152 
153     public DB getDB() {
154         return _db;
155     }
156 
157     public Dialect getDialect() {
158         return _dialect;
159     }
160 
161     public ModelListener<T>[] getListeners() {
162         return listeners;
163     }
164 
165     public Session openNewSession(Connection connection) throws ORMException {
166         return _sessionFactory.openNewSession(connection);
167     }
168 
169     public Session openSession() throws ORMException {
170         return _sessionFactory.openSession();
171     }
172 
173     public SystemException processException(Exception e) {
174         if (!(e instanceof ORMException)) {
175             _log.error("Caught unexpected exception " + e.getClass().getName());
176         }
177 
178         if (_log.isDebugEnabled()) {
179             _log.debug(e, e);
180         }
181 
182         return new SystemException(e);
183     }
184 
185     public void registerListener(ModelListener<T> listener) {
186         List<ModelListener<T>> listenersList = ListUtil.fromArray(listeners);
187 
188         listenersList.add(listener);
189 
190         listeners = listenersList.toArray(
191             new ModelListener[listenersList.size()]);
192     }
193 
194     @SuppressWarnings("unused")
195     public T remove(Serializable primaryKey)
196         throws NoSuchModelException, SystemException {
197 
198         throw new UnsupportedOperationException();
199     }
200 
201     public T remove(T model) throws SystemException {
202         for (ModelListener<T> listener : listeners) {
203             listener.onBeforeRemove(model);
204         }
205 
206         model = removeImpl(model);
207 
208         for (ModelListener<T> listener : listeners) {
209             listener.onAfterRemove(model);
210         }
211 
212         return model;
213     }
214 
215     public void setDataSource(DataSource dataSource) {
216         _dataSource = dataSource;
217     }
218 
219     public void setSessionFactory(SessionFactory sessionFactory) {
220         _sessionFactory = sessionFactory;
221         _dialect = _sessionFactory.getDialect();
222         _db = DBFactoryUtil.getDB(_dialect);
223     }
224 
225     public void unregisterListener(ModelListener<T> listener) {
226         List<ModelListener<T>> listenersList = ListUtil.fromArray(listeners);
227 
228         ListUtil.remove(listenersList, listener);
229 
230         listeners = listenersList.toArray(
231             new ModelListener[listenersList.size()]);
232     }
233 
234     /**
235      * Add, update, or merge, the model. This method also calls the model
236      * listeners to trigger the proper events associated with adding, deleting,
237      * or updating a model.
238      *
239      * @param  model the model to add, update, or merge
240      * @param  merge boolean value for whether to merge the entity. The default
241      *         value is false. Setting merge to true is more expensive and
242      *         should only be true when model is transient. See LEP-5473 for a
243      *         detailed discussion of this method.
244      * @return the model that was added, updated, or merged
245      */
246     public T update(T model, boolean merge) throws SystemException {
247         boolean isNew = model.isNew();
248 
249         for (ModelListener<T> listener : listeners) {
250             if (isNew) {
251                 listener.onBeforeCreate(model);
252             }
253             else {
254                 listener.onBeforeUpdate(model);
255             }
256         }
257 
258         model = updateImpl(model, merge);
259 
260         for (ModelListener<T> listener : listeners) {
261             if (isNew) {
262                 listener.onAfterCreate(model);
263             }
264             else {
265                 listener.onAfterUpdate(model);
266             }
267         }
268 
269         return model;
270     }
271 
272     protected void appendOrderByComparator(
273         StringBundler query, String entityAlias,
274         OrderByComparator orderByComparator) {
275 
276         query.append(ORDER_BY_CLAUSE);
277 
278         String[] orderByFields = orderByComparator.getOrderByFields();
279 
280         for (int i = 0; i < orderByFields.length; i++) {
281             query.append(entityAlias);
282             query.append(orderByFields[i]);
283 
284             if ((i + 1) < orderByFields.length) {
285                 if (orderByComparator.isAscending()) {
286                     query.append(ORDER_BY_ASC_HAS_NEXT);
287                 }
288                 else {
289                     query.append(ORDER_BY_DESC_HAS_NEXT);
290                 }
291             }
292             else {
293                 if (orderByComparator.isAscending()) {
294                     query.append(ORDER_BY_ASC);
295                 }
296                 else {
297                     query.append(ORDER_BY_DESC);
298                 }
299             }
300         }
301     }
302 
303     @SuppressWarnings("unused")
304     protected T removeImpl(T model) throws SystemException {
305         throw new UnsupportedOperationException();
306     }
307 
308     @SuppressWarnings("unused")
309     protected T updateImpl(T model, boolean merge) throws SystemException {
310         throw new UnsupportedOperationException();
311     }
312 
313     protected static final String ORDER_BY_ASC = " ASC";
314 
315     protected static final String ORDER_BY_ASC_HAS_NEXT = " ASC, ";
316 
317     protected static final String ORDER_BY_CLAUSE = " ORDER BY ";
318 
319     protected static final String ORDER_BY_DESC = " DESC";
320 
321     protected static final String ORDER_BY_DESC_HAS_NEXT = " DESC, ";
322 
323     protected static final String WHERE_AND = " AND ";
324 
325     protected static final String WHERE_LESSER_THAN = " <= ? ";
326 
327     protected static final String WHERE_LESSER_THAN_HAS_NEXT = " <= ? AND ";
328 
329     protected static final String WHERE_GREATER_THAN = " >= ? ";
330 
331     protected static final String WHERE_GREATER_THAN_HAS_NEXT = " >= ? AND ";
332 
333     protected ModelListener<T>[] listeners = new ModelListener[0];
334 
335     private static Log _log = LogFactoryUtil.getLog(BasePersistenceImpl.class);
336 
337     private DataSource _dataSource;
338     private DB _db;
339     private Dialect _dialect;
340     private SessionFactory _sessionFactory;
341 
342 }