KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > versant > core > jdbc > metadata > JdbcRefField


1
2 /*
3  * Copyright (c) 1998 - 2005 Versant Corporation
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v1.0
6  * which accompanies this distribution, and is available at
7  * http://www.eclipse.org/legal/epl-v10.html
8  *
9  * Contributors:
10  * Versant Corporation - initial API and implementation
11  */

12 package com.versant.core.jdbc.metadata;
13
14 import com.versant.core.metadata.ClassMetaData;
15 import com.versant.core.metadata.FieldMetaData;
16 import com.versant.core.common.OID;
17 import com.versant.core.jdbc.sql.JdbcNameGenerator;
18 import com.versant.core.jdbc.sql.SqlDriver;
19 import com.versant.core.jdbc.sql.exp.ColumnExp;
20 import com.versant.core.jdbc.sql.exp.SelectExp;
21 import com.versant.core.jdbc.sql.exp.SqlExp;
22 import com.versant.core.jdbc.JdbcOID;
23 import com.versant.core.util.CharBuf;
24 import com.versant.core.common.State;
25 import com.versant.core.common.Debug;
26
27 import java.util.ArrayList JavaDoc;
28 import java.io.PrintStream JavaDoc;
29 import java.sql.PreparedStatement JavaDoc;
30 import java.sql.SQLException JavaDoc;
31
32 import com.versant.core.common.BindingSupportImpl;
33
34 /**
35  * A field that is a reference to another PC class.
36  */

37 public class JdbcRefField extends JdbcField {
38
39     /**
40      * The columns used to store the primary key of the referenced (target)
41      * table. These must be in the same order as the pk array of the target
42      * table.
43      */

44     public JdbcColumn[] cols;
45     /**
46      * This is the class that we reference. Note that this may be for a
47      * different Store (e.g. LDAP).
48      */

49     public ClassMetaData targetClass;
50     /**
51      * The foreign key constraint for this reference (null if none).
52      */

53     public JdbcConstraint constraint;
54     /**
55      * If this reference is being used to complete a collection mapped using
56      * a foreign key reference then this is the collection field.
57      */

58     public JdbcFKCollectionField masterCollectionField;
59     public String JavaDoc constraintName;
60     public boolean createConstraint;
61
62     public String JavaDoc toString() {
63         StringBuffer JavaDoc s = new StringBuffer JavaDoc();
64         s.append(super.toString());
65         switch (useJoin) {
66             case USE_JOIN_INNER:
67                 s.append(" INNER");
68             case USE_JOIN_OUTER:
69                 s.append(" OUTER");
70         }
71         return s.toString();
72     }
73
74     /**
75      * Set the table field on all our main table columns.
76      */

77     public void setMainTable(JdbcTable table) {
78         super.setMainTable(table);
79         for (int i = 0; i < cols.length; i++) {
80             cols[i].setTable(table);
81         }
82     }
83
84     /**
85      * Init the mainTableCols field to all our main table columns.
86      */

87     public void initMainTableCols() {
88         mainTableCols = cols;
89         super.initMainTableCols();
90     }
91
92     /**
93      * Flatten all of this fields main table columns to a.
94      */

95     public void addMainTableCols(ArrayList JavaDoc a) {
96         int n = cols.length;
97         for (int i = 0; i < n; i++) a.add(cols[i]);
98     }
99
100     /**
101      * Make sure all of this fields main table columns have names.
102      */

103     public void nameColumns(String JavaDoc tableName, JdbcNameGenerator nameGen) {
104         // check if there are other fields referencing our targetClass
105
int refs = 0;
106         FieldMetaData[] fields = fmd.classMetaData.fields;
107         for (int i = fields.length - 1; i >= 0; i--) {
108             JdbcField f = (JdbcField)fields[i].storeField;
109             if (f instanceof JdbcRefField) {
110                 JdbcRefField rf = (JdbcRefField)f;
111                 if (rf.targetClass == targetClass) {
112                     if (++refs == 2) break;
113                 }
114             }
115         }
116         boolean otherRefs = refs >= 2;
117
118         // extract the current names of the columns and the
119
// matching referenced column names
120
String JavaDoc[] names = new String JavaDoc[cols.length];
121         String JavaDoc[] refPkNames = null;
122         JdbcClass tjc = (JdbcClass)targetClass.storeClass;
123         if (tjc != null) {
124             refPkNames = new String JavaDoc[cols.length];
125             for (int i = 0; i < cols.length; i++) {
126                 names[i] = cols[i].name;
127                 refPkNames[i] = tjc.table.pk[i].name;
128             }
129         }
130
131         // generate the names for the unnamed columns
132
if (tjc == null) {
133             nameGen.generateRefFieldColumnNames(tableName, fmd.name, names,
134                     null, null, otherRefs);
135         } else {
136             nameGen.generateRefFieldColumnNames(tableName, fmd.name, names,
137                     tjc.tableName, refPkNames, otherRefs);
138         }
139
140         // set our simple column names
141
for (int i = 0; i < cols.length; i++) cols[i].name = names[i];
142     }
143
144     /**
145      * Make sure all of this fields main table constraints have names and
146      * add them to cons.
147      */

148     public void addConstraints(ArrayList JavaDoc cons) {
149         if (constraint != null) cons.add(constraint);
150     }
151
152     public void dump(PrintStream JavaDoc out, String JavaDoc indent) {
153         super.dump(out, indent);
154         String JavaDoc is = indent + " ";
155         out.println(is + "targetClass = " + targetClass);
156         out.println(is + "constraint = " + constraint);
157         if (cols != null) {
158             out.println(is + cols.length + " cols(s)");
159             for (int i = 0; i < cols.length; i++) {
160                 out.println(is + "[" + i + "] " + cols[i]);
161             }
162         }
163     }
164
165     /**
166      * Append part of an update statement for us to s (e.g col = ?).
167      */

168     public boolean appendUpdate(CharBuf s, State state) {
169         int nc = mainTableColsForUpdate.length;
170         s.append(mainTableColsForUpdate[0].name);
171         s.append("=?");
172         for (int i = 1; i < nc; i++) {
173             s.append(", ");
174             s.append(mainTableColsForUpdate[i].name);
175             s.append("=?");
176         }
177         return false;
178     }
179
180     /**
181      * Append part of a where clause for us to s (e.g cola = ? and colb = ?).
182      * This is used for generating the where clause for changed locking.
183      */

184     public void appendWhere(CharBuf s, SqlDriver sqlDriver) {
185         int nc = mainTableColsForUpdate.length;
186         JdbcColumn c = mainTableColsForUpdate[0];
187         s.append(c.name);
188         s.append('=');
189         sqlDriver.appendWhereParam(s, c);
190         for (int i = 1; i < nc; i++) {
191             c = mainTableColsForUpdate[i];
192             s.append(" and ");
193             s.append(c.name);
194             s.append('=');
195             sqlDriver.appendWhereParam(s, c);
196         }
197     }
198
199     /**
200      * Append part of a is null where clause for us to s (e.g cola is null
201      * and colb is null).
202      * This is used for generating the where clause for changed locking.
203      */

204     public void appendWhereIsNull(CharBuf s, SqlDriver sqlDriver) {
205         int nc = mainTableColsForUpdate.length;
206         JdbcColumn c = mainTableColsForUpdate[0];
207         s.append(c.name);
208         s.append(" is null");
209         for (int i = 1; i < nc; i++) {
210             c = mainTableColsForUpdate[i];
211             s.append(" and ");
212             s.append(c.name);
213             s.append(" is null");
214         }
215     }
216
217     /**
218      * Append part of the insert list for us to s (e.g. cola, colb)).
219      */

220     public void appendInsertColumnList(CharBuf s) {
221         int nc = mainTableColsForUpdate.length;
222         s.append(mainTableColsForUpdate[0].name);
223         for (int i = 1; i < nc; i++) {
224             s.append(", ");
225             s.append(mainTableColsForUpdate[i].name);
226         }
227     }
228
229     /**
230      * Append part of the insert value list for us to s (e.g. ?, ?)). This
231      * must return true if a replacable parameter was <b>not</b> added (e.g.
232      * columns using Oracle LOBs which put in empty_clob() or whatever).
233      */

234     public boolean appendInsertValueList(CharBuf s, State state) {
235         s.append('?');
236         int nc = mainTableColsForUpdate.length;
237         for (int i = 1; i < nc; i++) s.append(", ?");
238         return false;
239     }
240
241     /**
242      * Check to see if the supplied table is a subclass table of the supplied
243      * ClassMetaData.
244      */

245     public static boolean isSubTableOf(JdbcTable table, ClassMetaData cmd) {
246         if (table == ((JdbcClass)cmd.storeClass).table) return true;
247         ClassMetaData[] pcSubs = cmd.pcSubclasses;
248         for (int i = 0; i < pcSubs.length; i++) {
249             ClassMetaData pcSub = pcSubs[i];
250             if (((JdbcClass)pcSub.storeClass).table == table) {
251                 return true;
252             }
253         }
254         return false;
255     }
256
257     /**
258      * Convert this field into a list of ColumnExp's or null if this is
259      * not possible.
260      */

261     public ColumnExp toColumnExp(SelectExp se, boolean joinToSuper) {
262         if (Debug.DEBUG) {
263             if (!isSubTableOf(se.table, fmd.classMetaData)) {
264                 throw BindingSupportImpl.getInstance().internal("The table '" + se.table.name
265                         + "'of the suplied selectExp is not equal or a subClass " +
266                         "table of table '"
267                         + ((JdbcClass)fmd.classMetaData.storeClass).table.name + "'");
268             }
269         }
270         if (joinToSuper) se = SelectExp.createJoinToSuperTable(se, this);
271         return createOwningTableColumnExpList(se);
272     }
273
274     public ColumnExp createOwningTableColumnExpList(SelectExp se) {
275         ColumnExp ans = new ColumnExp(cols[0], se, this);
276         SqlExp e = ans;
277         int nc = cols.length;
278         for (int i = 1; i < nc; i++) {
279             e = e.next = new ColumnExp(cols[i], se, this);
280         }
281         return ans;
282     }
283
284     /**
285      * Convert this field into a list of ColumnExp's to be compared to
286      * a null literal. This should only include non-shared columns i.e.
287      * columns that are updated. If all columns are shared then all should
288      * be included.
289      */

290     public ColumnExp toColumnExpForNullLiteralCompare(SelectExp se) {
291         se = SelectExp.createJoinToSuperTable(se, this);
292
293         if (mainTableColsForUpdate == null) return toColumnExp(se, true);
294         ColumnExp ans = new ColumnExp(mainTableColsForUpdate[0], se, this);
295         SqlExp e = ans;
296         int nc = mainTableColsForUpdate.length;
297         for (int i = 1; i < nc; i++) {
298             e = e.next = new ColumnExp(mainTableColsForUpdate[i], se, this);
299         }
300         return ans;
301     }
302
303     /**
304      * Set this field on a PreparedStatement. This is used to set parameters
305      * for queries.
306      *
307      * @return Index of the parameter after the last one we set in ps
308      */

309     public int setQueryParam(PreparedStatement JavaDoc ps, int firstParam,
310             Object JavaDoc value)
311             throws SQLException JavaDoc {
312         OID oid = (OID)value;
313         if (oid != null) {
314             firstParam = ((JdbcOID)oid).setParams(ps, firstParam);
315         } else {
316             int nc = cols.length;
317             for (int i = 0; i < nc; i++) {
318                 ps.setNull(firstParam++, cols[i].jdbcType);
319             }
320         }
321         return firstParam;
322     }
323 }
324
325
326
Popular Tags