1   /**
2    * Copyright (c) 2000-2009 Liferay, Inc. All rights reserved.
3    *
4    *
5    *
6    *
7    * The contents of this file are subject to the terms of the Liferay Enterprise
8    * Subscription License ("License"). You may not use this file except in
9    * compliance with the License. You can obtain a copy of the License by
10   * contacting Liferay, Inc. See the License for the specific language governing
11   * permissions and limitations under the License, including but not limited to
12   * distribution rights of the Software.
13   *
14   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20   * SOFTWARE.
21   */
22  
23  package com.liferay.portal.spring.hibernate;
24  
25  import com.liferay.portal.dao.orm.hibernate.DB2Dialect;
26  import com.liferay.portal.kernel.dao.db.DBFactoryUtil;
27  import com.liferay.portal.kernel.dao.jdbc.DataAccess;
28  import com.liferay.portal.kernel.log.Log;
29  import com.liferay.portal.kernel.log.LogFactoryUtil;
30  import com.liferay.portal.kernel.util.GetterUtil;
31  
32  import java.sql.Connection;
33  import java.sql.DatabaseMetaData;
34  
35  import java.util.Properties;
36  
37  import javax.sql.DataSource;
38  
39  import org.hibernate.dialect.DB2400Dialect;
40  import org.hibernate.dialect.Dialect;
41  import org.hibernate.dialect.SybaseASE15Dialect;
42  import org.hibernate.dialect.resolver.DialectFactory;
43  
44  /**
45   * <a href="DialectDetector.java.html"><b><i>View Source</i></b></a>
46   *
47   * @author Brian Wing Shun Chan
48   */
49  public class DialectDetector {
50  
51      public static String determineDialect(DataSource dataSource) {
52          Dialect dialect = getDialect(dataSource);
53  
54          DBFactoryUtil.setDB(dialect);
55  
56          if (_log.isInfoEnabled()) {
57              _log.info("Using dialect " + dialect.getClass().getName());
58          }
59  
60          return dialect.getClass().getName();
61      }
62  
63      public static Dialect getDialect(DataSource dataSource) {
64          Dialect dialect = null;
65  
66          Connection connection = null;
67  
68          try {
69              connection = dataSource.getConnection();
70  
71              DatabaseMetaData databaseMetaData = connection.getMetaData();
72  
73              String dbName = databaseMetaData.getDatabaseProductName();
74              int dbMajorVersion = databaseMetaData.getDatabaseMajorVersion();
75  
76              if (_log.isInfoEnabled()) {
77                  _log.info(
78                      "Determining dialect for " + dbName + " " + dbMajorVersion);
79              }
80  
81              if (dbName.startsWith("HSQL")) {
82                  if (_log.isWarnEnabled()) {
83                      StringBuilder sb = new StringBuilder();
84  
85                      sb.append("Liferay is configured to use Hypersonic as ");
86                      sb.append("its database. Do NOT use Hypersonic in ");
87                      sb.append("production. Hypersonic is an embedded ");
88                      sb.append("database useful for development and demo'ing ");
89                      sb.append("purposes. The database settings can be ");
90                      sb.append("changed in portal.properties.");
91  
92                      _log.warn(sb.toString());
93                  }
94              }
95  
96              if (dbName.equals("ASE") && (dbMajorVersion == 15)) {
97                  dialect = new SybaseASE15Dialect();
98              }
99              else if (dbName.startsWith("DB2") && (dbMajorVersion == 9)) {
100                 dialect = new DB2Dialect();
101             }
102             else {
103                 dialect = DialectFactory.buildDialect(
104                     new Properties(), connection);
105             }
106         }
107         catch (Exception e) {
108             String msg = GetterUtil.getString(e.getMessage());
109 
110             if (msg.indexOf("explicitly set for database: DB2") != -1) {
111                 dialect = new DB2400Dialect();
112 
113                 if (_log.isWarnEnabled()) {
114                     _log.warn(
115                         "DB2400Dialect was dynamically chosen as the " +
116                             "Hibernate dialect for DB2. This can be " +
117                                 "overriden in portal.properties");
118                 }
119             }
120             else {
121                 _log.error(e, e);
122             }
123         }
124         finally {
125             DataAccess.cleanUp(connection);
126         }
127 
128         if (dialect == null) {
129             throw new RuntimeException("No dialect found");
130         }
131 
132         return dialect;
133     }
134 
135     private static Log _log = LogFactoryUtil.getLog(DialectDetector.class);
136 
137 }