Source code: org/jdbf/engine/keygen/MaxKeyGenerator.java
1 /*
2 * 11/14/2002 - 09:40:11
3 *
4 * MaxKeyGenerator.java - JDBF Object Relational mapping system
5 * Copyright (C) 2002 Giovanni Martone
6 * giovannimartone@hotmail.com
7 * http://jdbf.sourceforge.net
8 *
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU Lesser General Public License
11 * as published by the Free Software Foundation; either version 2
12 * of the License, or (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU Lesser General Public License for more details.
18 *
19 * You should have received a copy of the GNU Lesser General Public License
20 * along with this program; if not, write to the Free Software
21 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 */
23 package org.jdbf.engine.keygen;
24
25 import java.math.BigDecimal;
26 import java.sql.Connection;
27 import java.sql.ResultSet;
28 import java.sql.Statement;
29 import java.sql.SQLException;
30 import java.util.ArrayList;
31
32
33 import org.jdbf.castor.Messages;
34 import org.jdbf.engine.database.DatabaseImpl;
35 import org.jdbf.engine.mapping.*;
36 import org.jdbf.engine.repository.RepositoryView;
37 import org.jdbf.engine.sql.SqlInterface;
38
39
40 /**
41 * <code>MaxKeyGenerator</code> representes the key generator that creates OID
42 * Obtains a key by adding 1 to the highest key in the table. This class has been
43 * developed on Max approach described by Scott Ambler in
44 * <a href="http://www.ambysoft.com/mappingObjects.pdf"> Mapping Objects To Relational
45 * Databases</a>.
46 *
47 * @author Giovanni Martone
48 * @version $id$
49 *
50 */
51 public class MaxKeyGenerator implements KeyGenerator{
52
53 /**
54 * Return true if before insert., false otherwise
55 *
56 * @return boolean
57 */
58 public boolean isBeforeInsert() { return true; }
59
60
61 /**
62 * Obtains a key by adding 1 to the highest key in the table. This method
63 * obtain a key creating a MAX select statement.
64 *
65 * @param view RepositoryView object
66 * @param conn Connection the databas
67 * @param vendor name of database vendor may be null
68 * @return the key
69 * @exception MappingException if an error occurs
70 */
71 public synchronized Object generateKey(RepositoryView view, Connection conn,String vendor)
72 throws MappingException{
73
74 Object identity = null;
75 BeanDescriptor beanDesc = view.getBeanDescriptor();
76 String tableName = beanDesc.getTableName();
77 String keyName = "";
78 ArrayList itemDescriptors = beanDesc.getItemDescriptors();
79
80 for(int i = 0; i < itemDescriptors.size(); i++){
81 ItemDescriptor item = (ItemDescriptor)itemDescriptors.get(i);
82 if(item.isPrimaryKey()){
83 keyName = item.getColumnTableName();
84 break;
85 }
86 }
87
88 // "SELECT MAX(pk) FROM table t"
89 StringBuffer condition = new StringBuffer(32);
90 condition.append("SELECT ")
91 .append(SqlInterface.MAX + "(" + keyName + ") ")
92 .append(SqlInterface.FROM).append(tableName);
93
94 String sql = condition.toString();
95
96 ResultSet rs = null;
97 Statement stmt = null;
98 try {
99 stmt = conn.createStatement();
100 rs = stmt.executeQuery(sql);
101 if (rs.next()) {
102 identity = rs.getObject(1);
103 if(identity == null){
104 identity = ONE;
105 }
106 else{
107 Class identClass = identity.getClass();
108 if (identClass.equals(Integer.class)) {
109 identity = new Integer(((Integer)identity).intValue() + 1);
110 }
111 else
112 if (identClass.equals(BigDecimal.class)) {
113 identity = ((BigDecimal)identity).add(ONE);
114 }
115 else{
116 throw new MappingException(
117 Messages.format("mapping.keyGenWrongType",
118 getClass().getName(), identity.getClass()));
119 }
120 }
121 }
122 }
123 catch (SQLException excep) {
124 throw new MappingException(excep);
125 }
126 finally {
127 try {
128 rs.close();
129 if (stmt != null) {
130 stmt.close();
131 }
132 stmt = null;
133 }
134 catch (SQLException excep) {}
135 }
136 return identity;
137 }
138 }