KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > net > sf > saxon > sql > SQLInsert


1 package net.sf.saxon.sql;
2 import net.sf.saxon.expr.Expression;
3 import net.sf.saxon.expr.SimpleExpression;
4 import net.sf.saxon.expr.XPathContext;
5 import net.sf.saxon.instruct.Executable;
6 import net.sf.saxon.om.Axis;
7 import net.sf.saxon.om.AxisIterator;
8 import net.sf.saxon.om.Item;
9 import net.sf.saxon.om.NodeInfo;
10 import net.sf.saxon.style.ExtensionInstruction;
11 import net.sf.saxon.trans.XPathException;
12 import net.sf.saxon.value.AtomicValue;
13 import net.sf.saxon.value.ObjectValue;
14
15 import java.sql.Connection JavaDoc;
16 import java.sql.PreparedStatement JavaDoc;
17 import java.sql.SQLException JavaDoc;
18 import java.util.ArrayList JavaDoc;
19 import java.util.List JavaDoc;
20 /**
21 * An sql:insert element in the stylesheet.
22 */

23
24 public class SQLInsert extends ExtensionInstruction {
25
26     Expression connection;
27     String JavaDoc table;
28
29     public void prepareAttributes() throws XPathException {
30
31         table = getAttributeList().getValue("", "table");
32         if (table==null) {
33             reportAbsence("table");
34         }
35         String JavaDoc connectAtt = getAttributeList().getValue("", "connection");
36         if (connectAtt==null) {
37             reportAbsence("connection");
38         } else {
39             connection = makeExpression(connectAtt);
40         }
41     }
42
43     public void validate() throws XPathException {
44         super.validate();
45         connection = typeCheck("connection", connection);
46     }
47
48     public Expression compile(Executable exec) throws XPathException {
49
50         // Collect names of columns to be added
51

52         StringBuffer JavaDoc statement = new StringBuffer JavaDoc(120);
53         statement.append("INSERT INTO " + table + " (");
54
55         AxisIterator kids = iterateAxis(Axis.CHILD);
56         NodeInfo child;
57         int cols = 0;
58         while (true) {
59             child = (NodeInfo)kids.next();
60             if (child == null) {
61                 break;
62             }
63             if (child instanceof SQLColumn) {
64                 if (cols++ > 0) statement.append(',');
65                 String JavaDoc colname = ((SQLColumn)child).getColumnName();
66                 statement.append(colname);
67             }
68         }
69         statement.append(") VALUES (");
70
71         // Add "?" marks for the variable parameters
72

73         for(int i=0; i<cols; i++) {
74             if (i!=0) {
75                 statement.append(',');
76             }
77             statement.append('?');
78         };
79
80         statement.append(')');
81
82         return new InsertInstruction(connection, statement.toString(), getColumnInstructions(exec));
83     }
84
85     public List JavaDoc getColumnInstructions(Executable exec) throws XPathException {
86         List JavaDoc list = new ArrayList JavaDoc(10);
87
88         AxisIterator kids = iterateAxis(Axis.CHILD);
89         NodeInfo child;
90         while (true) {
91             child = (NodeInfo)kids.next();
92             if (child == null) {
93                 break;
94             }
95             if (child instanceof SQLColumn) {
96                 list.add(((SQLColumn)child).compile(exec));
97             }
98         }
99
100         return list;
101     }
102
103     private static class InsertInstruction extends SimpleExpression {
104
105         public static final int CONNECTION = 0;
106         public static final int FIRST_COLUMN = 1;
107         String JavaDoc statement;
108
109         public InsertInstruction(Expression connection, String JavaDoc statement, List JavaDoc columnInstructions) {
110             Expression[] sub = new Expression[columnInstructions.size() + 1];
111             sub[CONNECTION] = connection;
112             for (int i=0; i<columnInstructions.size(); i++) {
113                 sub[i+FIRST_COLUMN] = (Expression)columnInstructions.get(i);
114             }
115             this.statement = statement;
116             setArguments(sub);
117         }
118
119         /**
120          * A subclass must provide one of the methods evaluateItem(), iterate(), or process().
121          * This method indicates which of the three is provided.
122          */

123
124         public int getImplementationMethod() {
125             return Expression.EVALUATE_METHOD;
126         }
127
128         public String JavaDoc getExpressionType() {
129             return "sql:insert";
130         }
131
132         public Item evaluateItem(XPathContext context) throws XPathException {
133
134             // Prepare the SQL statement (only do this once)
135

136             Item conn = arguments[CONNECTION].evaluateItem(context);
137             if (!(conn instanceof ObjectValue && ((ObjectValue)conn).getObject() instanceof Connection JavaDoc) ) {
138                 dynamicError("Value of connection expression is not a JDBC Connection", context);
139             }
140             Connection JavaDoc connection = (Connection JavaDoc)((ObjectValue)conn).getObject();
141             PreparedStatement JavaDoc ps = null;
142
143             try {
144                 ps=connection.prepareStatement(statement);
145
146                 // Add the actual column values to be inserted
147

148                 int i = 1;
149                 for (int c=FIRST_COLUMN; c<arguments.length; c++) {
150                     AtomicValue v = (AtomicValue)((SQLColumn.ColumnInstruction)arguments[c]).getSelectValue(context);
151
152                     // TODO: the values are all strings. There is no way of adding to a numeric column
153
String JavaDoc val = v.getStringValue();
154
155                     // another hack: setString() doesn't seem to like single-character string values
156
if (val.length()==1) val += " ";
157                     //System.err.println("Set statement parameter " + i + " to " + val);
158
ps.setObject(i++, val);
159
160                 }
161
162                 ps.executeUpdate();
163                 if (!connection.getAutoCommit()) {
164                     connection.commit();
165                 }
166
167             } catch (SQLException JavaDoc ex) {
168                 dynamicError("(SQL INSERT) " + ex.getMessage(), context);
169             } finally {
170                if (ps != null) {
171                    try {
172                        ps.close();
173                    } catch (SQLException JavaDoc ignore) {}
174                }
175             }
176
177             return null;
178         }
179
180     }
181
182
183 }
184
185 //
186
// The contents of this file are subject to the Mozilla Public License Version 1.0 (the "License");
187
// you may not use this file except in compliance with the License. You may obtain a copy of the
188
// License at http://www.mozilla.org/MPL/
189
//
190
// Software distributed under the License is distributed on an "AS IS" basis,
191
// WITHOUT WARRANTY OF ANY KIND, either express or implied.
192
// See the License for the specific language governing rights and limitations under the License.
193
//
194
// The Original Code is: all this file.
195
//
196
// The Initial Developer of the Original Code is Michael H. Kay.
197
//
198
// Portions created by (your name) are Copyright (C) (your legal entity). All Rights Reserved.
199
//
200
// Contributor(s): none.
201
//
202
Popular Tags