提交 029f4b22 authored 作者: Thomas Mueller's avatar Thomas Mueller

Result sets are now read-only by default.

上级 9352fe27
......@@ -18,7 +18,13 @@ Change Log
<h1>Change Log</h1>
<h2>Next Version (unreleased)</h2>
<ul><li>If a pooled connection was not closed but garbage collected, a NullPointerException could occur.
<ul><li>Result sets are now read-only except if the statement or prepared statement was created
with the concurrency ResultSet.CONCUR_UPDATABLE. This change is required because the old behavior
(all result set are updatable) violated the JDBC spec. For backward compatibility, use the
system property h2.defaultResultSetConcurrency.
</li><li>New system property h2.defaultResultSetConcurrency to change the default result set concurrency.
</li><li>JDBC: using an invalid result set type or concurrency now throws an exception.
</li><li>If a pooled connection was not closed but garbage collected, a NullPointerException could occur.
</li><li>Fulltext search: a NullPointerException was thrown when updating a value that
was NULL previously.
</li><li>The Recover tool did not work with .data.db files of the wrong size.
......
......@@ -149,7 +149,7 @@
90125=Invalid class, expected {0} but got {1}
90126=Database is not persistent
90127=The result set is not updatable. The query must select all columns from a unique key. Only one table may be selected.
90128=The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=Transaction {0} not found
90130=This method is not allowed for a prepared statement; use a regular statement instead.
90131=Concurrent update in table {0}\: another transaction has updated or deleted the same row
......@@ -161,6 +161,7 @@
90137=Can only assign to a variable, not to\: {0}
90138=Invalid database name\: {0}
90139=The public static Java method was not found\: {0}
90140=The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=General error\: {0}
HY004=Unknown data type\: {0}
HYC00=Feature not supported\: {0}
......
......@@ -1706,7 +1706,9 @@ public class ErrorCode {
/**
* The error with code <code>90127</code> is thrown when
* trying to update or delete a row in a result set if the result set is
* not updatable.
* not updatable. Result sets are only updatable if the statement was
* created with updatable concurrency, and if the result set contains
* all columns of the primary key or of a unique index of a table.
*/
public static final int RESULT_SET_NOT_UPDATABLE = 90127;
......@@ -1855,6 +1857,15 @@ public class ErrorCode {
*/
public static final int PUBLIC_STATIC_JAVA_METHOD_NOT_FOUND_1 = 90139;
/**
* The error with code <code>90140</code> is thrown when trying to update or
* delete a row in a result set if the statement was not created with
* updatable concurrency. Result sets are only updatable if the statement
* was created with updatable concurrency, and if the result set contains
* all columns of the primary key or of a unique index of a table.
*/
public static final int RESULT_SET_READONLY = 90140;
// next is 90140
private ErrorCode() {
......
......@@ -6,6 +6,7 @@
*/
package org.h2.constant;
import java.sql.ResultSet;
import org.h2.engine.Constants;
import org.h2.message.TraceSystem;
import org.h2.util.MathUtils;
......@@ -180,6 +181,14 @@ public class SysProperties {
*/
public static final int DEFAULT_MAX_OPERATION_MEMORY = getIntSetting("h2.defaultMaxOperationMemory", 100000);
/**
* System property <code>h2.defaultResultSetConcurrency</code> (default:
* ResultSet.CONCUR_READ_ONLY).<br />
* The default result set concurrency for statements created with
* Connection.createStatement() or prepareStatement(String sql).
*/
public static final int DEFAULT_RESULT_SET_CONCURRENCY = getIntSetting("h2.defaultResultSetConcurrency", ResultSet.CONCUR_READ_ONLY);
/**
* System property <code>h2.dataSourceTraceLevel</code> (default: 1).<br />
* The trace level of the data source implementation. Default is 1 for
......
......@@ -35,9 +35,9 @@ import org.h2.message.TraceObject;
*/
public class JdbcCallableStatement extends JdbcPreparedStatement implements CallableStatement {
JdbcCallableStatement(JdbcConnection conn, String sql, int resultSetType, int id)
JdbcCallableStatement(JdbcConnection conn, String sql, int id, int resultSetType, int resultSetConcurrency)
throws SQLException {
super(conn, sql, resultSetType, id, false);
super(conn, sql, id, resultSetType, resultSetConcurrency, false);
setTrace(session.getTrace(), TraceObject.CALLABLE_STATEMENT, id);
}
......
......@@ -161,7 +161,7 @@ public class JdbcConnection extends TraceObject implements Connection {
debugCodeAssign("Statement", TraceObject.STATEMENT, id, "createStatement()");
}
checkClosed();
return new JdbcStatement(this, ResultSet.TYPE_FORWARD_ONLY, id, false);
return new JdbcStatement(this, id, ResultSet.TYPE_FORWARD_ONLY, SysProperties.DEFAULT_RESULT_SET_CONCURRENCY, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -181,8 +181,9 @@ public class JdbcConnection extends TraceObject implements Connection {
if (isDebugEnabled()) {
debugCodeAssign("Statement", TraceObject.STATEMENT, id, "createStatement(" + resultSetType + ", " + resultSetConcurrency + ")");
}
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkClosed();
return new JdbcStatement(this, resultSetType, id, false);
return new JdbcStatement(this, id, resultSetType, resultSetConcurrency, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -204,9 +205,10 @@ public class JdbcConnection extends TraceObject implements Connection {
debugCodeAssign("Statement", TraceObject.STATEMENT, id,
"createStatement(" + resultSetType + ", " + resultSetConcurrency + ", " + resultSetHoldability + ")");
}
checkClosed();
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkHoldability(resultSetHoldability);
return new JdbcStatement(this, resultSetType, id, false);
checkClosed();
return new JdbcStatement(this, id, resultSetType, resultSetConcurrency, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -227,7 +229,7 @@ public class JdbcConnection extends TraceObject implements Connection {
}
checkClosed();
sql = translateSQL(sql);
return new JdbcPreparedStatement(this, sql, ResultSet.TYPE_FORWARD_ONLY, id, false);
return new JdbcPreparedStatement(this, sql, id, ResultSet.TYPE_FORWARD_ONLY, SysProperties.DEFAULT_RESULT_SET_CONCURRENCY, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -248,7 +250,7 @@ public class JdbcConnection extends TraceObject implements Connection {
}
checkClosed();
sql = translateSQL(sql);
return new JdbcPreparedStatement(this, sql, ResultSet.TYPE_FORWARD_ONLY, id, true);
return new JdbcPreparedStatement(this, sql, id, ResultSet.TYPE_FORWARD_ONLY, SysProperties.DEFAULT_RESULT_SET_CONCURRENCY, true);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -573,9 +575,10 @@ public class JdbcConnection extends TraceObject implements Connection {
if (isDebugEnabled()) {
debugCodeAssign("PreparedStatement", TraceObject.PREPARED_STATEMENT, id, "prepareStatement(" + quote(sql) + ", " + resultSetType + ", " + resultSetConcurrency + ")");
}
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkClosed();
sql = translateSQL(sql);
return new JdbcPreparedStatement(this, sql, resultSetType, id, false);
return new JdbcPreparedStatement(this, sql, id, resultSetType, resultSetConcurrency, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -789,7 +792,7 @@ public class JdbcConnection extends TraceObject implements Connection {
}
checkClosed();
sql = translateSQL(sql);
return new JdbcCallableStatement(this, sql, ResultSet.TYPE_FORWARD_ONLY, id);
return new JdbcCallableStatement(this, sql, id, ResultSet.TYPE_FORWARD_ONLY, SysProperties.DEFAULT_RESULT_SET_CONCURRENCY);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -810,9 +813,10 @@ public class JdbcConnection extends TraceObject implements Connection {
if (isDebugEnabled()) {
debugCodeAssign("CallableStatement", TraceObject.CALLABLE_STATEMENT, id, "prepareCall(" + quote(sql) + ", " + resultSetType + ", " + resultSetConcurrency + ")");
}
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkClosed();
sql = translateSQL(sql);
return new JdbcCallableStatement(this, sql, resultSetType, id);
return new JdbcCallableStatement(this, sql, id, resultSetType, resultSetConcurrency);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -836,10 +840,11 @@ public class JdbcConnection extends TraceObject implements Connection {
"prepareCall(" + quote(sql) + ", " + resultSetType + ", " + resultSetConcurrency + ", "
+ resultSetHoldability + ")");
}
checkClosed();
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkHoldability(resultSetHoldability);
checkClosed();
sql = translateSQL(sql);
return new JdbcCallableStatement(this, sql, resultSetType, id);
return new JdbcCallableStatement(this, sql, id, resultSetType, resultSetConcurrency);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -951,10 +956,11 @@ public class JdbcConnection extends TraceObject implements Connection {
"prepareStatement(" + quote(sql) + ", " + resultSetType + ", " + resultSetConcurrency + ", "
+ resultSetHoldability + ")");
}
checkClosed();
checkTypeConcurrency(resultSetType, resultSetConcurrency);
checkHoldability(resultSetHoldability);
checkClosed();
sql = translateSQL(sql);
return new JdbcPreparedStatement(this, sql, resultSetType, id, false);
return new JdbcPreparedStatement(this, sql, id, resultSetType, resultSetConcurrency, false);
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -1256,6 +1262,24 @@ public class JdbcConnection extends TraceObject implements Connection {
return sql.regionMatches(true, start, other, 0, other.length());
}
private void checkTypeConcurrency(int resultSetType, int resultSetConcurrency) throws SQLException {
switch (resultSetType) {
case ResultSet.TYPE_FORWARD_ONLY:
case ResultSet.TYPE_SCROLL_INSENSITIVE:
case ResultSet.TYPE_SCROLL_SENSITIVE:
break;
default:
throw Message.getInvalidValueException("" + resultSetType, "resultSetType");
}
switch (resultSetConcurrency) {
case ResultSet.CONCUR_READ_ONLY:
case ResultSet.CONCUR_UPDATABLE:
break;
default:
throw Message.getInvalidValueException("" + resultSetConcurrency, "resultSetConcurrency");
}
}
private void checkHoldability(int resultSetHoldability) throws SQLException {
// TODO compatibility / correctness: DBPool uses
// ResultSet.HOLD_CURSORS_OVER_COMMIT
......
......@@ -66,9 +66,9 @@ public class JdbcPreparedStatement extends JdbcStatement implements PreparedStat
private CommandInterface command;
private ObjectArray<Value[]> batchParameters;
JdbcPreparedStatement(JdbcConnection conn, String sql, int resultSetType, int id,
boolean closeWithResultSet) throws SQLException {
super(conn, resultSetType, id, closeWithResultSet);
JdbcPreparedStatement(JdbcConnection conn, String sql, int id, int resultSetType,
int resultSetConcurrency, boolean closeWithResultSet) throws SQLException {
super(conn, id, resultSetType, resultSetConcurrency, closeWithResultSet);
setTrace(session.getTrace(), TraceObject.PREPARED_STATEMENT, id);
this.sql = sql;
command = conn.prepareCommand(sql, fetchSize);
......@@ -92,6 +92,7 @@ public class JdbcPreparedStatement extends JdbcStatement implements PreparedStat
closeOldResultSet();
ResultInterface result;
boolean scrollable = resultSetType != ResultSet.TYPE_FORWARD_ONLY;
boolean updatable = resultSetConcurrency == ResultSet.CONCUR_UPDATABLE;
synchronized (session) {
try {
setExecutingStatement(command);
......@@ -100,7 +101,7 @@ public class JdbcPreparedStatement extends JdbcStatement implements PreparedStat
setExecutingStatement(null);
}
}
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable, updatable);
return resultSet;
} catch (Exception e) {
throw logAndConvert(e);
......@@ -168,8 +169,9 @@ public class JdbcPreparedStatement extends JdbcStatement implements PreparedStat
if (command.isQuery()) {
returnsResultSet = true;
boolean scrollable = resultSetType != ResultSet.TYPE_FORWARD_ONLY;
boolean updatable = resultSetConcurrency == ResultSet.CONCUR_UPDATABLE;
ResultInterface result = command.executeQuery(maxRows, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable, updatable);
} else {
returnsResultSet = false;
updateCount = command.executeUpdate();
......
......@@ -33,17 +33,19 @@ public class JdbcStatement extends TraceObject implements Statement {
protected int maxRows;
protected int fetchSize = SysProperties.SERVER_RESULT_SET_FETCH_SIZE;
protected int updateCount;
protected int resultSetType;
protected final int resultSetType;
protected final int resultSetConcurrency;
protected boolean closedByResultSet;
private CommandInterface executingCommand;
private ObjectArray<String> batchCommands;
private boolean escapeProcessing = true;
JdbcStatement(JdbcConnection conn, int resultSetType, int id, boolean closeWithResultSet) {
JdbcStatement(JdbcConnection conn, int id, int resultSetType, int resultSetConcurrency, boolean closeWithResultSet) {
this.conn = conn;
this.session = conn.getSession();
setTrace(session.getTrace(), TraceObject.STATEMENT, id);
this.resultSetType = resultSetType;
this.resultSetConcurrency = resultSetConcurrency;
this.closedByResultSet = closeWithResultSet;
}
......@@ -68,6 +70,7 @@ public class JdbcStatement extends TraceObject implements Statement {
CommandInterface command = conn.prepareCommand(sql, fetchSize);
ResultInterface result;
boolean scrollable = resultSetType != ResultSet.TYPE_FORWARD_ONLY;
boolean updatable = resultSetConcurrency == ResultSet.CONCUR_UPDATABLE;
setExecutingStatement(command);
try {
result = command.executeQuery(maxRows, scrollable);
......@@ -75,7 +78,7 @@ public class JdbcStatement extends TraceObject implements Statement {
setExecutingStatement(null);
}
command.close();
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable, updatable);
}
return resultSet;
} catch (Exception e) {
......@@ -151,8 +154,9 @@ public class JdbcStatement extends TraceObject implements Statement {
if (command.isQuery()) {
returnsResultSet = true;
boolean scrollable = resultSetType != ResultSet.TYPE_FORWARD_ONLY;
boolean updatable = resultSetConcurrency == ResultSet.CONCUR_UPDATABLE;
ResultInterface result = command.executeQuery(maxRows, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable);
resultSet = new JdbcResultSet(conn, this, result, id, closedByResultSet, scrollable, updatable);
} else {
returnsResultSet = false;
updateCount = command.executeUpdate();
......@@ -415,14 +419,13 @@ public class JdbcStatement extends TraceObject implements Statement {
/**
* Gets the result set concurrency created by this object.
*
* @return ResultSet.CONCUR_UPDATABLE
* @throws SQLException if this object is closed
* @return the concurrency
*/
public int getResultSetConcurrency() throws SQLException {
try {
debugCodeCall("getResultSetConcurrency");
checkClosed();
return ResultSet.CONCUR_UPDATABLE;
return resultSetConcurrency;
} catch (Exception e) {
throw logAndConvert(e);
}
......@@ -646,7 +649,7 @@ public class JdbcStatement extends TraceObject implements Statement {
}
checkClosed();
ResultInterface result = conn.getGeneratedKeys();
ResultSet rs = new JdbcResultSet(conn, this, result, id, false, true);
ResultSet rs = new JdbcResultSet(conn, this, result, id, false, true, false);
return rs;
} catch (Exception e) {
throw logAndConvert(e);
......
......@@ -149,7 +149,7 @@
90125=Ung\u00FCltig Klasse, erwartet {0} erhalten {1}
90126=Datenbank ist nicht persistent
90127=Die Resultat-Zeilen k\u00F6nnen nicht ver\u00E4ndert werden. Die Abfrage muss alle Felder eines eindeutigen Schl\u00FCssels enthalten, und nur eine Tabelle enthalten.
90128=Kann nicht an den Anfang der Resultat-Zeilen springen. M\u00F6gliche L\u00F6sung\: conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=Kann nicht an den Anfang der Resultat-Zeilen springen. M\u00F6gliche L\u00F6sung\: conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=Transaktion {0} nicht gefunden
90130=Diese Methode ist nicht erlaubt f\u00FCr ein PreparedStatement; ben\u00FCtzen Sie ein Statement.
90131=Gleichzeitige \u00C4nderung in Tabelle {0}\: eine andere Transaktion hat den gleichen Datensatz ge\u00E4ndert oder gel\u00F6scht
......@@ -161,6 +161,7 @@
90137=Werte k\u00F6nnen nur einer Variablen zugewiesen werden, nicht an\: {0}
90138=Ung\u00FCltiger Datenbank Name\: {0}
90139=Die (public static) Java Funktion wurde nicht gefunden\: {0}
90140=Die Resultat-Zeilen k\u00F6nnen nicht ver\u00E4ndert werden. M\u00F6gliche L\u00F6sung\: conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=Allgemeiner Fehler\: {0}
HY004=Unbekannter Datentyp\: {0}
HYC00=Dieses Feature wird unterst\u00FCtzt\: {0}
......
......@@ -149,7 +149,7 @@
90125=Invalid class, expected {0} but got {1}
90126=Database is not persistent
90127=The result set is not updatable. The query must select all columns from a unique key. Only one table may be selected.
90128=The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=Transaction {0} not found
90130=This method is not allowed for a prepared statement; use a regular statement instead.
90131=Concurrent update in table {0}\: another transaction has updated or deleted the same row
......@@ -161,6 +161,7 @@
90137=Can only assign to a variable, not to\: {0}
90138=Invalid database name\: {0}
90139=The public static Java method was not found\: {0}
90140=The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=General error\: {0}
HY004=Unknown data type\: {0}
HYC00=Feature not supported\: {0}
......
......@@ -149,7 +149,7 @@
90125=Clase Invalida, se esperaba {0} pero se obtuvo {1}
90126=La base de datos no es persistente
90127=El conjunto de resultados NO es actualizable. El query debe seleccionar todas la columnas desde una clave de unicidad. Solo una tabla puede ser seleccionada.
90128=El conjunto de resultados NO es scrollable y no puede ser reseteada. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=El conjunto de resultados NO es scrollable y no puede ser reseteada. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=Transacci\u00F3n {0} no encontrada
90130=Este metodo no esta permitido para una sentencia preparada; en su lugar use una sentencia regular.
90131=Actualizaci\u00F3n concurrente sobre la tabla {0}\: otra transacci\u00F3n ha actualizado \u00F3 borrado la misma fila
......@@ -161,6 +161,7 @@
90137=Solo puede asignarse a una variable, no a\: {0}
90138=Nombre de base de datos Invalido\: {0}
90139=El metodo Java (publico y estatico) \: {0} no fue encontrado
90140=\#The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=Error General \: {0}
HY004=Tipo de dato desconocido \: {0}
HYC00=Caracteristica no soportada\: {0}
......
......@@ -149,7 +149,7 @@
90125=\u7121\u52B9\u306A\u30AF\u30E9\u30B9, {0} \u304C\u671F\u5F85\u3055\u308C\u3066\u3044\u308B\u306B\u3082\u304B\u304B\u308F\u3089\u305A {1} \u3092\u53D6\u5F97\u3057\u307E\u3057\u305F
90126=\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u306F\u6C38\u7D9A\u7684\u3067\u306F\u3042\u308A\u307E\u305B\u3093
90127=\u30EA\u30B6\u30EB\u30C8\u30BB\u30C3\u30C8\u304C\u66F4\u65B0\u53EF\u80FD\u3067\u306F\u3042\u308A\u307E\u305B\u3093\u3002\u30AF\u30A8\u30EA\u306F\u5358\u4E00\u306E\u30C6\u30FC\u30D6\u30EB\u304B\u3089\u3001\u30E6\u30CB\u30FC\u30AF\u30AD\u30FC\u3092\u5168\u3066select\u3057\u306A\u3051\u308C\u3070\u306A\u308A\u307E\u305B\u3093
90128=\u30EA\u30B6\u30EB\u30C8\u30BB\u30C3\u30C8\u304C\u30B9\u30AF\u30ED\u30FC\u30EB\u3001\u30EA\u30BB\u30C3\u30C8\u53EF\u80FD\u3067\u306F\u3042\u308A\u307E\u305B\u3093\u3002conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY) \u3092\u4F7F\u3046\u5FC5\u8981\u304C\u3042\u308B\u304B\u3082\u3057\u308C\u307E\u305B\u3093
90128=\u30EA\u30B6\u30EB\u30C8\u30BB\u30C3\u30C8\u304C\u30B9\u30AF\u30ED\u30FC\u30EB\u3001\u30EA\u30BB\u30C3\u30C8\u53EF\u80FD\u3067\u306F\u3042\u308A\u307E\u305B\u3093\u3002conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..) \u3092\u4F7F\u3046\u5FC5\u8981\u304C\u3042\u308B\u304B\u3082\u3057\u308C\u307E\u305B\u3093
90129=\u30C8\u30E9\u30F3\u30B6\u30AF\u30B7\u30E7\u30F3 {0} \u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093
90130=\u30D7\u30EA\u30DA\u30A2\u30C9\u30B9\u30C6\u30FC\u30C8\u30E1\u30F3\u30C8\u306B\u3053\u306E\u30E1\u30BD\u30C3\u30C9\u306F\u8A31\u3055\u308C\u3066\u3044\u307E\u305B\u3093; \u304B\u308F\u308A\u306B\u901A\u5E38\u306E\u30B9\u30C6\u30FC\u30C8\u30E1\u30F3\u30C8\u3092\u4F7F\u7528\u3057\u3066\u304F\u3060\u3055\u3044
90131=\u30C6\u30FC\u30D6\u30EB {0} \u306B\u4E26\u884C\u3057\u3066\u66F4\u65B0\u304C\u884C\u308F\u308C\u307E\u3057\u305F\: \u5225\u306E\u30C8\u30E9\u30F3\u30B6\u30AF\u30B7\u30E7\u30F3\u304C\u3001\u540C\u3058\u884C\u306B\u66F4\u65B0\u304B\u524A\u9664\u3092\u884C\u3044\u307E\u3057\u305F
......@@ -161,6 +161,7 @@
90137=\u5272\u308A\u5F53\u3066\u306F\u5909\u6570\u306B\u306E\u307F\u53EF\u80FD\u3067\u3059\u3002{0} \u306B\u306F\u3067\u304D\u307E\u305B\u3093
90138=\u4E0D\u6B63\u306A\u30C7\u30FC\u30BF\u30D9\u30FC\u30B9\u540D\: {0}
90139=public static\u3067\u3042\u308BJava\u30E1\u30BD\u30C3\u30C9\u304C\u898B\u3064\u304B\u308A\u307E\u305B\u3093\: {0}
90140=\#The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=\u4E00\u822C\u30A8\u30E9\u30FC\: {0}
HY004=\u4E0D\u660E\u306A\u30C7\u30FC\u30BF\u578B\: {0}
HYC00=\u6A5F\u80FD\u306F\u30B5\u30DD\u30FC\u30C8\u3055\u308C\u3066\u3044\u307E\u305B\u3093\: {0}
......
......@@ -149,7 +149,7 @@
90125=Nieprawidlowa klasa, oczekiwano {0} a jest {1}
90126=Baza danych nie jest trwala
90127=\#The result set is not updatable. The query must select all columns from a unique key. Only one table may be selected.
90128=\#The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=\#The result set is not scrollable and can not be reset. You may need to use conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=\#Transaction {0} not found
90130=\#This method is not allowed for a prepared statement; use a regular statement instead.
90131=\#Concurrent update in table {0}\: another transaction has updated or deleted the same row
......@@ -161,6 +161,7 @@
90137=\#Can only assign to a variable, not to\: {0}
90138=\#Invalid database name\: {0}
90139=\#The public static Java method was not found\: {0}
90140=\#The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=Blad ogolny\: {0}
HY004=Nieznany typ danyche\: {0}
HYC00=Cecha nie jest wspierana\: {0}
......
......@@ -149,7 +149,7 @@
90125=Classe inv\u00E1lida, experada {0} mas est\u00E1 {1}
90126=Base de dados n\u00E3o \u00E9 persistente
90127=O resultado definido n\u00E3o \u00E9 atualiz\u00E1vel. A consulta deve selecionar todas as colunas de chave prim\u00E1ria. Somente uma tabela pode ser selecionada.
90128=O resultado n\u00E3o \u00E9 naveg\u00E1vel e n\u00E3o pode ser resetado. Voc\u00EA pode usar conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY).
90128=O resultado n\u00E3o \u00E9 naveg\u00E1vel e n\u00E3o pode ser resetado. Voc\u00EA pode usar conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ..).
90129=Transa\u00E7\u00E3o {0} n\u00E3o encontrada
90130=Este m\u00E9todo n\u00E3o \u00E9 permitido para um statement preparado; Utilize um statement instanciado.
90131=Atualiza\u00E7\u00E3o concorrente na tabela {0}\: outra transa\u00E7\u00E3o atualizou ou deletou a mesma linha
......@@ -161,6 +161,7 @@
90137=\#Can only assign to a variable, not to\: {0}
90138=\#Invalid database name\: {0}
90139=\#The public static Java method was not found\: {0}
90140=\#The result set is readonly. You may need to use conn.createStatement(.., ResultSet.CONCUR_UPDATABLE).
HY000=Erro geral\: {0}
HY004=Tipo de dados desconhecido\: {0}
HYC00=Recurso n\u00E3o suportado\: {0}
......
......@@ -911,6 +911,7 @@ public class TestResultSet extends TestBase {
trace("Test CLOB");
ResultSet rs;
String string;
Statement stat = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_UPDATABLE);
stat.execute("CREATE TABLE TEST(ID INT PRIMARY KEY,VALUE CLOB)");
stat.execute("INSERT INTO TEST VALUES(1,'Test')");
stat.execute("INSERT INTO TEST VALUES(2,'Hello')");
......
......@@ -172,7 +172,7 @@ public class TestStatement extends TestBase {
Statement stat2 = conn.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_READ_ONLY, ResultSet.HOLD_CURSORS_OVER_COMMIT);
assertEquals(ResultSet.TYPE_SCROLL_SENSITIVE, stat2.getResultSetType());
assertEquals(ResultSet.HOLD_CURSORS_OVER_COMMIT, stat2.getResultSetHoldability());
assertEquals(ResultSet.CONCUR_UPDATABLE, stat2.getResultSetConcurrency());
assertEquals(ResultSet.CONCUR_READ_ONLY, stat2.getResultSetConcurrency());
assertEquals(0, stat.getMaxFieldSize());
assertTrue(!((JdbcStatement) stat2).isClosed());
stat2.close();
......@@ -195,7 +195,7 @@ public class TestStatement extends TestBase {
if (config.jdk14) {
assertEquals(stat.getResultSetHoldability(), ResultSet.HOLD_CURSORS_OVER_COMMIT);
}
assertEquals(stat.getResultSetConcurrency(), ResultSet.CONCUR_UPDATABLE);
assertEquals(stat.getResultSetConcurrency(), ResultSet.CONCUR_READ_ONLY);
stat.cancel();
stat.setQueryTimeout(10);
......
......@@ -76,7 +76,7 @@ public class TestUpdatableResultSet extends TestBase {
private void testUpdateResetRead() throws SQLException {
deleteDb("updatableResultSet");
Connection conn = getConnection("updatableResultSet");
Statement stat = conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
Statement stat = conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE);
stat.execute("CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR(255))");
stat.execute("INSERT INTO TEST VALUES(1, 'Hello')");
stat.execute("INSERT INTO TEST VALUES(2, 'World')");
......@@ -208,7 +208,7 @@ public class TestUpdatableResultSet extends TestBase {
private void testUpdateDataType() throws SQLException {
deleteDb("updatableResultSet");
Connection conn = getConnection("updatableResultSet");
Statement stat = conn.createStatement();
Statement stat = conn.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_UPDATABLE);
stat.execute("CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR(255), "
+ "DEC DECIMAL(10,2), BOO BIT, BYE TINYINT, BIN BINARY(100), "
+ "D DATE, T TIME, TS TIMESTAMP, DB DOUBLE, R REAL, L BIGINT, "
......@@ -347,7 +347,7 @@ public class TestUpdatableResultSet extends TestBase {
deleteDb("updatableResultSet");
Connection c1 = getConnection("updatableResultSet");
Connection c2 = getConnection("updatableResultSet");
Statement stat = c1.createStatement();
Statement stat = c1.createStatement(ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_UPDATABLE);
stat.execute("DROP TABLE IF EXISTS TEST");
stat.execute("CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR(255))");
int max = 8;
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论