1 //
2 // Copyright 1998, 1999 CDS Networks, Inc., Medford Oregon
3 //
4 // All rights reserved.
5 //
6 // Redistribution and use in source and binary forms, with or without
7 // modification, are permitted provided that the following conditions are met:
8 // 1. Redistributions of source code must retain the above copyright
9 // notice, this list of conditions and the following disclaimer.
10 // 2. Redistributions in binary form must reproduce the above copyright
11 // notice, this list of conditions and the following disclaimer in the
12 // documentation and/or other materials provided with the distribution.
13 // 3. All advertising materials mentioning features or use of this software
14 // must display the following acknowledgement:
15 // This product includes software developed by CDS Networks, Inc.
16 // 4. The name of CDS Networks, Inc. may not be used to endorse or promote
17 // products derived from this software without specific prior
18 // written permission.
19 //
20 // THIS SOFTWARE IS PROVIDED BY CDS NETWORKS, INC. ``AS IS'' AND
21 // ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 // ARE DISCLAIMED. IN NO EVENT SHALL CDS NETWORKS, INC. BE LIABLE
24 // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 // OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 // HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 // LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 // OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 // SUCH DAMAGE.
31 //
32
33
34 package com.internetcds.jdbc.tds;
35
36 import java.sql.*;
37 import java.util.Properties;
38 import java.util.Vector;
39
40 class TdsInstance
41 {
42 public static final String cvsVersion = "$Id: Connection_base.html,v 1.1 2003/05/12 16:19:44 sinisa Exp $";
43
44 public boolean inUse = false;
45 public Tds tds = null;
46
47 public TdsInstance(Tds tds_)
48 {
49 tds = tds_;
50 inUse = false;
51 }
52 }
53
54
55
56
57 /***
58 * <P>A Connection represents a session with a specific
59 * database. Within the context of a Connection, SQL statements are
60 * executed and results are returned.
61 *
62 * <P>A Connection's database is able to provide information
63 * describing its tables, its supported SQL grammar, its stored
64 * procedures, the capabilities of this connection, etc. This
65 * information is obtained with the getMetaData method.
66 *
67 * <P><B>Note:</B> By default the Connection automatically commits
68 * changes after executing each statement. If auto commit has been
69 * disabled, an explicit commit must be done or database changes will
70 * not be saved.
71 *
72 * @author Craig Spannring
73 * @author Igor Petrovski
74 * @author The FreeTDS project
75 * @version $Id: Connection_base.html,v 1.1 2003/05/12 16:19:44 sinisa Exp $
76 *
77 * @see DriverManager#getConnection
78 * @see Statement
79 * @see ResultSet
80 * @see DatabaseMetaData
81 */
82 public class Connection_base implements ConnectionHelper
83 {
84 public static final String cvsVersion = "$Id: Connection_base.html,v 1.1 2003/05/12 16:19:44 sinisa Exp $";
85
86
87 String host = null;
88 int serverType = -1; // Can be either Driver.SYBASE or Driver.SQLSERVER
89 int port = -1; // Port numbers are _unsigned_ 16 bit, short is too small
90 String database = null;
91 Properties initialProps = null;
92
93
94 Vector tdsPool = null;
95 DatabaseMetaData databaseMetaData = null;
96 Vector allStatements = null;
97 Tds tdsAll = null;
98
99 boolean autoCommit = true;
100 int transactionIsolationLevel = java.sql.Connection.TRANSACTION_READ_COMMITTED;
101 boolean isClosed = false;
102
103 private SQLWarningChain warningChain;
104
105 protected void NotImplemented() throws java.sql.SQLException
106 {
107 throw new java.sql.SQLException("Not Implemented");
108 }
109
110
111
112
113
114 /***
115 * Connect via TDS to a database server.
116 *
117 * @return a valid connection profile
118 * @exception SQLException if a database access error occurs
119 */
120 public Connection_base(
121 Properties props_)
122 throws SQLException, com.internetcds.jdbc.tds.TdsException
123 {
124 host = props_.getProperty("HOST");
125 serverType = Integer.parseInt(props_.getProperty("SERVERTYPE"));
126 port = Integer.parseInt(props_.getProperty("PORT"));
127 database = props_.getProperty("DBNAME");
128 String user = props_.getProperty("user");
129 String password = props_.getProperty("password");
130 initialProps = props_;
131
132 warningChain = new SQLWarningChain();
133
134 if (user == null)
135 {
136 user = props_.getProperty("USER");
137 if (user == null)
138 {
139 throw new SQLException("Need a username.");
140 }
141 props_.put("user", user);
142 }
143
144 if (password == null)
145 {
146 password = props_.getProperty("PASSWORD");
147 if (password == null)
148 {
149 throw new SQLException("Need a password.");
150 }
151 props_.put("password", password);
152 }
153
154 if (tdsPool == null)
155 {
156 tdsPool = new Vector(20);
157 }
158
159 if (allStatements == null)
160 {
161 allStatements = new Vector(2);
162 }
163
164 try
165 {
166 //sinisa
167 // Tds tmpTds = this.allocateTds();
168 tdsAll = this.allocateTds();
169 // freeTds(tmpTds);
170 freeTds(tdsAll);
171 }
172 catch (java.net.UnknownHostException e)
173 {
174 throw new SQLException("Unknown host");
175 }
176 catch (java.io.IOException e)
177 {
178 throw new SQLException("Network error- " + e.getMessage());
179 }
180 }
181
182 protected String sqlStatementToInitialize()
183 {
184 return serverType==Tds.SYBASE ? "set quoted_identifier on set textsize 50000" : "";
185 }
186
187 protected String sqlStatementToSetTransactionIsolationLevel()
188 throws SQLException
189 {
190 String sql = "set transaction isolation level ";
191
192 if (serverType == Tds.SYBASE)
193 {
194 switch (transactionIsolationLevel)
195 {
196 case java.sql.Connection.TRANSACTION_READ_UNCOMMITTED:
197 {
198 throw new SQLException("Bad transaction level");
199 }
200 case java.sql.Connection.TRANSACTION_READ_COMMITTED:
201 {
202 sql = sql + "1";
203 break;
204 }
205 case java.sql.Connection.TRANSACTION_REPEATABLE_READ:
206 {
207 throw new SQLException("Bad transaction level");
208 }
209 case java.sql.Connection.TRANSACTION_SERIALIZABLE:
210 {
211 sql = sql + "3";
212 break;
213 }
214 case java.sql.Connection.TRANSACTION_NONE:
215 default:
216 {
217 throw new SQLException("Bad transaction level");
218 }
219 }
220 }
221 else
222 {
223 switch (transactionIsolationLevel)
224 {
225 case java.sql.Connection.TRANSACTION_READ_UNCOMMITTED:
226 {
227 sql = sql + " read uncommitted ";
228 break;
229 }
230 case java.sql.Connection.TRANSACTION_READ_COMMITTED:
231 {
232 sql = sql + " read committed ";
233 break;
234 }
235 case java.sql.Connection.TRANSACTION_REPEATABLE_READ:
236 {
237 sql = sql + " repeatable read ";
238 break;
239 }
240 case java.sql.Connection.TRANSACTION_SERIALIZABLE:
241 {
242 throw new SQLException("SQLServer does not support " +
243 "TRANSACTION_SERIALIZABLE");
244 }
245 case java.sql.Connection.TRANSACTION_NONE:
246 default:
247 {
248 throw new SQLException("Bad transaction level");
249 }
250 }
251 }
252 return sql;
253 }
254
255
256 protected String sqlStatementToSetCommit()
257 {
258 String result;
259
260 if (serverType == Tds.SYBASE)
261 {
262 if (autoCommit)
263 {
264 result = "set CHAINED off ";
265 }
266 else
267 {
268 result = "set CHAINED on ";
269 }
270 }
271 else
272 {
273 if (autoCommit)
274 {
275 result = "set implicit_transactions off ";
276 }
277 else
278 {
279 result = "set implicit_transactions on ";
280 }
281 }
282 return result;
283 }
284
285 protected String sqlStatementForSettings()
286 throws SQLException
287 {
288 return
289 sqlStatementToInitialize() + " " +
290 // sqlStatementToSetTransactionIsolationLevel();
291 //sinisa
292 // "set quoted_identifier,ansi_null_dflt_on,ansi_padding,ansi_warnings,ansi_nulls on set textsize 2147483647 " +
293 sqlStatementToSetTransactionIsolationLevel() + " " +
294 sqlStatementToSetCommit();
295 }
296
297
298 public String getUrl()
299 {
300 // XXX Is it legal to return something that might not be
301 // exactly the URL used to connect?
302 return
303 ("jdbc:freetds:"
304 + (serverType==Tds.SYBASE?"sybase":"sqlserver")
305 + "://" + host + ":" + port + "/" + database);
306 }
307
308 /***
309 * allocate a tds instance to the calling thread.
310 * <br>
311 * The routine tries to reuse an available tds instance. If there
312 * are no tds instances that aren't in use it will create a new
313 * instance.
314 *
315 * @exception java.sql.SQLException
316 * @exception java.net.UnknownHostException
317 * @exception com.internetcds.jdbc.tds.TdsException
318 * @exception java.io.IOException
319 *
320 * @return A tds instance to use for database communications.
321 */
322 synchronized private Tds allocateTds()
323 throws java.sql.SQLException, java.net.UnknownHostException,
324 com.internetcds.jdbc.tds.TdsException, java.io.IOException
325 {
326 Tds result;
327 int i;
328
329
330 i = findAnAvailableTds();
331 if (i == -1)
332 {
333 Tds tmpTds = null;
334 try
335 {
336 tmpTds = new Tds((java.sql.Connection)this,
337 initialProps, sqlStatementForSettings());
338 }
339 catch (SQLException e)
340 {
341 throw new SQLException(e.getMessage() + "\n" + tdsPool.size()
342 + " connection are in use by this program");
343 }
344 TdsInstance tmp = new TdsInstance(tmpTds);
345 tdsPool.addElement(tmp);
346 i = findAnAvailableTds();
347 }
348 if (i == -1)
349 {
350 throw new TdsException("Internal Error. Couldn't get tds instance");
351 }
352 if (((TdsInstance)tdsPool.elementAt(i)).inUse)
353 {
354 throw new TdsException("Internal Error. tds " + i
355 + " is already allocated");
356 }
357 ((TdsInstance)tdsPool.elementAt(i)).inUse = true;
358 result = ((TdsInstance)(tdsPool.elementAt(i))).tds;
359
360 result.changeSettings(null, sqlStatementForSettings());
361
362 return result;
363 }
364
365 /***
366 * Find a tds in the TdsPool that is not in use.
367 *
368 * @return -1 if none were found, otherwise return the index a tds
369 */
370 private int findAnAvailableTds()
371 {
372 int i;
373
374 for(i=tdsPool.size()-1;
375 i>=0 && ((TdsInstance)tdsPool.elementAt(i)).inUse;
376 i--)
377 {
378 // nop
379 }
380 return i;
381 }
382
383
384
385 public void markAsClosed(java.sql.Statement stmt) throws TdsException
386 {
387 if (!allStatements.removeElement(stmt))
388 {
389 throw new TdsException("Statement was not known by the connection");
390 }
391 }
392
393 /***
394 * return a tds instance back to the tds pool for reuse.
395 *
396 * @see allocateTds
397 */
398 private void freeTds(Tds tds)
399 throws TdsException
400 {
401 int i;
402
403 i = -1;
404 do
405 {
406 i++;
407 } while(i<tdsPool.size()
408 && tds != ((TdsInstance)tdsPool.elementAt(i)).tds);
409
410 if (i<tdsPool.size())
411 {
412 ((TdsInstance)tdsPool.elementAt(i)).inUse = false;
413
414 // XXX Should also send a cancel to the server and throw out any
415 // data that has already been sent.
416 }
417 else
418 {
419 throw new TdsException("Tried to free a tds that wasn't in use");
420 }
421 }
422
423 /***
424 * return a tds instance back to the tds pool for reuse.
425 *
426 * A thread that is using a tds instance should return the
427 * instance back to the tds pool when it is finished using it.
428 *
429 * @see allocateTds
430 */
431 public void relinquish(Tds tds)
432 throws TdsException
433 {
434 freeTds(tds);
435 }
436
437
438 /***
439 * SQL statements without parameters are normally executed using
440 * Statement objects. If the same SQL statement is executed many
441 * times, it is more efficient to use a PreparedStatement
442 *
443 * JDBC 2.0
444 *
445 * Result sets created using the returned Statement will have
446 * forward-only type, and read-only concurrency, by default.
447 *
448 * @return a new Statement object
449 * @exception SQLException passed through from the constructor
450 */
451 public java.sql.Statement createStatement() throws SQLException
452 {
453 //sinisa
454 // Tds tmpTds = null;
455 // try
456 // {
457 // tmpTds = this.allocateTds();
458 // }
459 // catch(com.internetcds.jdbc.tds.TdsException e)
460 // {
461 // throw new SQLException(e.getMessage());
462 // }
463 // catch(java.io.IOException e)
464 // {
465 // throw new SQLException(e.getMessage());
466 // }
467 //sinisa
468 com.internetcds.jdbc.tds.Statement result;
469 // result = new com.internetcds.jdbc.tds.Statement(this, tmpTds);
470 result = new com.internetcds.jdbc.tds.Statement(this, tdsAll);
471
472 allStatements.addElement(result);
473 return result;
474 }
475
476
477
478 /***
479 * A SQL statement with or without IN parameters can be
480 * pre-compiled and stored in a PreparedStatement object. This
481 * object can then be used to efficiently execute this statement
482 * multiple times.
483 *
484 * <P><B>Note:</B> This method is optimized for handling
485 * parametric SQL statements that benefit from precompilation. If
486 * the driver supports precompilation, prepareStatement will send
487 * the statement to the database for precompilation. Some drivers
488 * may not support precompilation. In this case, the statement may
489 * not be sent to the database until the PreparedStatement is
490 * executed. This has no direct affect on users; however, it does
491 * affect which method throws certain SQLExceptions.
492 *
493 * JDBC 2.0
494 *
495 * Result sets created using the returned PreparedStatement will have
496 * forward-only type and read-only concurrency, by default.
497 *
498 * @param sql a SQL statement that may contain one or more '?' IN
499 * parameter placeholders
500 * @return a new PreparedStatement object containing the
501 * pre-compiled statement
502 * @exception SQLException if a database-access error occurs.
503 */
504 public java.sql.PreparedStatement prepareStatement(String sql)
505 throws SQLException
506 {
507 java.sql.PreparedStatement result;
508
509 //sinisa
510 // Tds tmpTds = null;
511 // try
512 // {
513 // tmpTds = this.allocateTds();
514 // }
515 // catch (java.io.IOException e)
516 // {
517 // throw new SQLException(e.getMessage());
518 // }
519 // catch (com.internetcds.jdbc.tds.TdsException e)
520 // {
521 // throw new SQLException(e.getMessage());
522 // }
523
524 // result = Constructors.newPreparedStatement(this, tmpTds, sql);
525 result = Constructors.newPreparedStatement(this, tdsAll, sql);
526
527 allStatements.addElement(result);
528
529 return result;
530 }
531
532 /***
533 * A SQL stored procedure call statement is handled by creating a
534 * CallableStatement for it. The CallableStatement provides methods
535 * for setting up its IN and OUT parameters and methods for executing
536 * it.
537 *
538 * <B>Note:</B> This method is optimised for handling stored procedure
539 * call statements. Some drivers may send the call statement to the
540 * database when the prepareCall is done; others may wait until the
541 * CallableStatement is executed. This has no direct effect on users;
542 * however, it does affect which method throws certain SQLExceptions
543 *
544 * JDBC 2.0
545 *
546 * Result sets created using the returned CallableStatement will have
547 * forward-only type and read-only concurrency, by default.
548 *
549 * @param sql a SQL statement that may contain one or more '?' parameter
550 * placeholders. Typically this statement is a JDBC function call
551 * escape string.
552 * @return a new CallableStatement object containing the pre-compiled
553 * SQL statement
554 * @exception SQLException if a database access error occurs
555 */
556 public java.sql.CallableStatement prepareCall(String sql) throws SQLException
557 {
558 java.sql.CallableStatement result;
559
560 //sinisa
561 // Tds tmpTds = null;
562 // try
563 // {
564 // tmpTds = this.allocateTds();
565 // }
566 // catch (java.io.IOException e)
567 // {
568 // throw new SQLException(e.getMessage());
569 // }
570 // catch (com.internetcds.jdbc.tds.TdsException e)
571 // {
572 // throw new SQLException(e.getMessage());
573 // }
574
575 // result = Constructors.newCallableStatement(this, tmpTds, sql);
576 result = Constructors.newCallableStatement(this, tdsAll, sql);
577 allStatements.addElement(result);
578
579 return result;
580 }
581
582 /***
583 * A driver may convert the JDBC sql grammar into its system's
584 * native SQL grammar prior to sending it; nativeSQL returns the
585 * native form of the statement that the driver would have sent.
586 *
587 * @param sql a SQL statement that may contain one or more '?'
588 * parameter placeholders
589 * @return the native form of this statement
590 * @exception SQLException if a database access error occurs
591 */
592
593 public String nativeSQL(String sql) throws SQLException
594 {
595 return Tds.toNativeSql(sql, serverType);
596 }
597
598
599 /***
600 * If a connection is in auto-commit mode, then all its SQL
601 * statements will be executed and committed as individual
602 * transactions. Otherwise, its SQL statements are grouped into
603 * transactions that are terminated by either commit() or
604 * rollback(). By default, new connections are in auto-commit
605 * mode.
606 *
607 * The commit occurs when the statement completes or the next
608 * execute occurs, whichever comes first. In the case of
609 * statements returning a ResultSet, the statement completes when
610 * the last row of the ResultSet has been retrieved or the
611 * ResultSet has been closed. In advanced cases, a single
612 * statement may return multiple results as well as output
613 * parameter values. Here the commit occurs when all results and
614 * output param values have been retrieved.
615 *
616 * @param value true enables auto-commit; false disables
617 * auto-commit.
618 * @exception SQLException if a database-access error occurs.
619 */
620 public void setAutoCommit(boolean value) throws SQLException
621 {
622 int i;
623 String sql = null;
624
625 autoCommit = value;
626 sql = sqlStatementToSetCommit();
627 //sinisa
628 // for(i=0; i<allStatements.size(); i++)
629 // {
630 // Statement stmt = (Statement)allStatements.elementAt(i);
631 Statement stmt = (com.internetcds.jdbc.tds.Statement)this.createStatement();
632
633 // {
634 // Note- stmt.execute implicitly eats the END_TOKEN
635 // that will come back from the commit command
636 stmt.execute(sql);
637 // stmt.execute("BEGIN TRAN");
638 // }
639 // }
640 }
641
642
643 /***
644 * Get the current auto-commit state.
645 *
646 * @return Current state of auto-commit mode.
647 * @exception SQLException if a database-access error occurs.
648 * @see #setAutoCommit
649 */
650 public boolean getAutoCommit() throws SQLException
651 {
652 return autoCommit;
653 }
654
655
656 /***
657 * Commit makes all changes made since the previous
658 * commit/rollback permanent and releases any database locks
659 * currently held by the Connection. This method should only be
660 * used when auto commit has been disabled.
661 *
662 * @exception SQLException if a database-access error occurs.
663 * @see #setAutoCommit
664 */
665 public void commit() throws SQLException
666 {
667 commitOrRollback(true);
668 }
669
670
671 /***
672 * Rollback drops all changes made since the previous
673 * commit/rollback and releases any database locks currently held
674 * by the Connection. This method should only be used when auto
675 * commit has been disabled.
676 *
677 * @exception SQLException if a database-access error occurs.
678 * @see #setAutoCommit
679 */
680 public void rollback() throws SQLException
681 {
682 commitOrRollback(false);
683 }
684
685 private void commitOrRollback(boolean commit)
686 throws SQLException
687 {
688 int i;
689 SQLException exception = null;
690
691 if (autoCommit)
692 {
693 throw new SQLException("This method should only be " +
694 " used when auto commit has been disabled.");
695 }
696
697
698 // XXX race condition here. It is possible that a statement could
699 // close while running this for loop.
700 //sinisa
701 // for(i=0; i<allStatements.size(); i++)
702 //{
703 // Statement stmt = (Statement)allStatements.elementAt(i);
704 String sql = "IF @@TRANCOUNT > 0 COMMIT TRAN";
705 String sqlRollback = "IF @@TRANCOUNT > 0 ROLLBACK TRAN ";
706 Statement stmt = (com.internetcds.jdbc.tds.Statement)this.createStatement();
707
708 try
709 {
710 if (commit)
711 {
712 stmt.commit();
713 // stmt.executeQuery(sql);
714 }
715 else
716 {
717 stmt.rollback();
718 // stmt.executeQuery(sqlRollback);
719 }
720 }
721 // XXX need to put all of these into the warning chain.
722 //
723 // Don't think so, the warnings would belong to Statement anyway -- SB
724 catch (java.sql.SQLException e)
725 {
726 exception = e;
727 }
728 catch (java.io.IOException e)
729 {
730 exception = new SQLException(e.getMessage());
731 }
732 catch (com.internetcds.jdbc.tds.TdsException e)
733 {
734 exception = new SQLException(e.getMessage());
735 }
736
737 /* if (stmt instanceof CallableStatement)
738 {
739 ((PreparedStatementHelper)stmt).dropAllProcedures();
740 throw new SQLException("Not implemented");
741 }
742 else if (stmt instanceof PreparedStatement)
743 {
744 ((PreparedStatementHelper)stmt).dropAllProcedures();
745 }
746 }
747 */ if (exception != null)
748 {
749 throw exception;
750 }
751 }
752
753 /***
754 * In some cases, it is desirable to immediately release a
755 * Connection's database and JDBC resources instead of waiting for
756 * them to be automatically released; the close method provides this
757 * immediate release.
758 *
759 * <P><B>Note:</B> A Connection is automatically closed when it is
760 * garbage collected. Certain fatal errors also result in a closed
761 * Connection.
762 *
763 * @exception SQLException if a database-access error occurs.
764 */
765 public void close() throws SQLException
766 {
767 int i;
768
769
770 for(i=0; i<allStatements.size(); i++)
771 {
772 Statement stmt = (Statement)allStatements.elementAt(i);
773
774 {
775 stmt.close();
776 }
777 }
778
779 for(i=0; i<tdsPool.size(); i++)
780 {
781 ((TdsInstance)tdsPool.elementAt(i)).tds.close();
782 }
783
784 clearWarnings();
785 isClosed = true;
786 }
787
788 /***
789 * Tests to see if a Connection is closed.
790 *
791 * @return true if the connection is closed; false if it's still open
792 * @exception SQLException if a database-access error occurs.
793 */
794 public boolean isClosed() throws SQLException
795 {
796 return isClosed;
797 }
798
799 /***
800 * A connection's database is able to provide information describing
801 * its tables, its supported SQL grammar, its stored procedures, the
802 * capabilities of this connection, etc. This information is made
803 * available through a DatabaseMetaData object.
804 *
805 * @return a DatabaseMetaData object for this connection
806 * @exception SQLException if a database access error occurs
807 */
808 public java.sql.DatabaseMetaData getMetaData() throws SQLException
809 {
810 try
811 {
812 if (databaseMetaData == null)
813 {
814 // The DatabaseMetaData may need the tds connection
815 // at some later time. Therefore we shouldn't relinquish the
816 // tds.
817 Tds tds = this.allocateTds();
818 databaseMetaData = new com.internetcds.jdbc.tds.DatabaseMetaData(this, tds);
819 }
820 return databaseMetaData;
821 }
822 catch(java.io.IOException e)
823 {
824 throw new SQLException(e.getMessage());
825 }
826 catch(com.internetcds.jdbc.tds.TdsException e)
827 {
828 throw new SQLException(e.getMessage());
829 }
830 // catch(java.net.UnknownHostException e)
831 // {
832 // throw new SQLException(e.getMessage());
833 // }
834 }
835
836 /***
837 * You can put a connection in read-only mode as a hint to enable
838 * database optimizations
839 *
840 * <B>Note:</B> setReadOnly cannot be called while in the middle
841 * of a transaction
842 *
843 * @param readOnly - true enables read-only mode; false disables it
844 * @exception SQLException if a database access error occurs
845 */
846 public void setReadOnly (boolean readOnly) throws SQLException
847 {
848 throw new SQLException("Not implemented (setReadOnly)");
849 }
850
851 /***
852 * Tests to see if the connection is in read-only mode.
853 *
854 * @return true if connection is read-only
855 * @exception SQLException if a database-access error occurs.
856 */
857 public boolean isReadOnly() throws SQLException
858 {
859 throw new SQLException("Not implemented (isReadOnly)");
860 }
861
862
863
864 /***
865 * A sub-space of this Connection's database may be selected by setting a
866 * catalog name. If the driver does not support catalogs it will
867 * silently ignore this request.
868 *
869 * @exception SQLException if a database-access error occurs.
870 */
871 public void setCatalog(String catalog) throws SQLException
872 {
873 throw new SQLException("Not implemented (setCatalog)");
874 }
875
876 /***
877 * Return the Connection's current catalog name.
878 *
879 * @return the current catalog name or null
880 * @exception SQLException if a database-access error occurs.
881 */
882 public String getCatalog() throws SQLException
883 {
884 throw new SQLException("Not implemented (getCatalog)");
885 }
886
887
888 /***
889 * You can call this method to try to change the transaction
890 * isolation level using one of the TRANSACTION_* values.
891 *
892 * <P><B>Note:</B> setTransactionIsolation cannot be called while
893 * in the middle of a transaction.
894 *
895 * @param level one of the TRANSACTION_* isolation values with the
896 * exception of TRANSACTION_NONE; some databases may not support
897 * other values
898 * @exception SQLException if a database-access error occurs.
899 * @see DatabaseMetaData#supportsTransactionIsolationLevel
900 */
901 public void setTransactionIsolation(int level)
902 throws SQLException
903 {
904 int i;
905 String sql;
906
907 transactionIsolationLevel = level;
908
909 sql = sqlStatementToSetTransactionIsolationLevel();
910
911 for(i=0; i<allStatements.size(); i++)
912 {
913 Statement stmt = (Statement)allStatements.elementAt(i);
914
915 {
916 // Note- stmt.execute implicitly eats the END_TOKEN
917 // that will come back from the commit command
918 stmt.execute(sql);
919 }
920 }
921 }
922
923
924
925 /***
926 * Get this Connection's current transaction isolation mode.
927 *
928 * @return the current TRANSACTION_* mode value
929 * @exception SQLException if a database-access error occurs.
930 */
931 public int getTransactionIsolation() throws SQLException
932 {
933 return transactionIsolationLevel;
934 }
935
936
937 /***
938 * The first warning reported by calls on this Connection is
939 * returned.
940 *
941 * <P><B>Note:</B> Subsequent warnings will be chained to this
942 * SQLWarning.
943 *
944 * @return the first SQLWarning or null
945 * @exception SQLException if a database-access error occurs.
946 */
947 public SQLWarning getWarnings() throws SQLException
948 {
949 return warningChain.getWarnings();
950 }
951
952 /***
953 * After this call, getWarnings returns null until a new warning
954 * is reported for this connection.
955 *
956 * @exception SQLException if a database access error occurs
957 */
958 public void clearWarnings() throws SQLException
959 {
960 warningChain.clearWarnings();
961 }
962
963 //--------------------------JDBC 2.0-----------------------------
964
965 /***
966 * JDBC 2.0
967 *
968 * Creates a <code>Statement</code> object that will generate
969 * <code>ResultSet</code> objects with the given type and concurrency.
970 * This method is the same as the <code>createStatement</code> method
971 * above, but it allows the default result set
972 * type and result set concurrency type to be overridden.
973 *
974 * @param resultSetType a result set type; see ResultSet.TYPE_XXX
975 * @param resultSetConcurrency a concurrency type; see ResultSet.CONCUR_XXX
976 * @return a new Statement object
977 * @exception SQLException if a database access error occurs
978 */
979 public java.sql.Statement createStatement(
980 int resultSetType,
981 int resultSetConcurrency)
982 throws SQLException
983 {
984
985 Tds tmpTds = null;
986 try
987 {
988 tmpTds = this.allocateTds();
989 }
990 catch(com.internetcds.jdbc.tds.TdsException e)
991 {
992 throw new SQLException(e.getMessage());
993 }
994 catch(java.io.IOException e)
995 {
996 throw new SQLException(e.getMessage());
997 }
998 com.internetcds.jdbc.tds.Statement result;
999 result = new com.internetcds.jdbc.tds.Statement(this, tmpTds);
1000
1001 allStatements.addElement(result);
1002
1003 return result;
1004 }
1005
1006
1007 /***
1008 * JDBC 2.0
1009 *
1010 * Creates a <code>PreparedStatement</code> object that will generate
1011 * <code>ResultSet</code> objects with the given type and concurrency.
1012 * This method is the same as the <code>prepareStatement</code> method
1013 * above, but it allows the default result set
1014 * type and result set concurrency type to be overridden.
1015 *
1016 * @param resultSetType a result set type; see ResultSet.TYPE_XXX
1017 * @param resultSetConcurrency a concurrency type; see ResultSet.CONCUR_XXX
1018 * @return a new PreparedStatement object containing the
1019 * pre-compiled SQL statement
1020 * @exception SQLException if a database access error occurs
1021 */
1022 public java.sql.PreparedStatement prepareStatement(
1023 String sql,
1024 int resultSetType,
1025 int resultSetConcurrency)
1026 throws SQLException
1027 {
1028 NotImplemented();
1029 return null;
1030 }
1031
1032
1033 /***
1034 * JDBC 2.0
1035 *
1036 * Creates a <code>CallableStatement</code> object that will generate
1037 * <code>ResultSet</code> objects with the given type and concurrency.
1038 * This method is the same as the <code>prepareCall</code> method
1039 * above, but it allows the default result set
1040 * type and result set concurrency type to be overridden.
1041 *
1042 * @param resultSetType a result set type; see ResultSet.TYPE_XXX
1043 * @param resultSetConcurrency a concurrency type; see ResultSet.CONCUR_XXX
1044 * @return a new CallableStatement object containing the
1045 * pre-compiled SQL statement
1046 * @exception SQLException if a database access error occurs
1047 */
1048 public java.sql.CallableStatement prepareCall(
1049 String sql,
1050 int resultSetType,
1051 int resultSetConcurrency) throws SQLException
1052 {
1053 NotImplemented();
1054 return null;
1055 }
1056
1057
1058 }
1059
1060
This page automatically generated by Maven