提交 48d406c3 authored 作者: Thomas Mueller's avatar Thomas Mueller

LINKED TABLE: the schema name can now be set.

上级 44403978
......@@ -18,7 +18,10 @@ Change Log
<h1>Change Log</h1>
<h2>Next Version (unreleased)</h2>
<ul><li>LINKED TABLE: worked around a bug in Oracle with the CHAR data type.
<ul><li>Result sets with just a unique index can now be updated (previously a primary key was required).
</li><li>LINKED TABLE: the schema name can now be set. When multiple tables exist in different schema,
and the schema name is not set, an exception is thrown.
</li><li>LINKED TABLE: worked around a bug in Oracle with the CHAR data type.
</li><li>Faster hash code calculation for large binary arrays.
</li><li>Faster storage re-use algorithm thanks to Greg Dhuse from cleversafe.com.
</li><li>The database supports the SHOW command for better MySQL and PostgreSQL compatibility.
......
......@@ -4517,7 +4517,12 @@ public class Parser {
read(",");
command.setPassword(readString());
read(",");
command.setOriginalTable(readString());
String originalTable = readString();
if (readIf(",")) {
command.setOriginalSchema(originalTable);
originalTable = readString();
}
command.setOriginalTable(originalTable);
read(")");
if (readIf("EMIT")) {
read("UPDATES");
......
......@@ -22,7 +22,7 @@ import org.h2.table.TableLink;
public class CreateLinkedTable extends SchemaCommand {
private String tableName;
private String driver, url, user, password, originalTable;
private String driver, url, user, password, originalSchema, originalTable;
private boolean ifNotExists;
private String comment;
private boolean emitUpdates;
......@@ -75,7 +75,7 @@ public class CreateLinkedTable extends SchemaCommand {
tableName);
}
int id = getObjectId(false, true);
TableLink table = getSchema().createTableLink(id, tableName, driver, url, user, password, originalTable, emitUpdates, force);
TableLink table = getSchema().createTableLink(id, tableName, driver, url, user, password, originalSchema, originalTable, emitUpdates, force);
table.setTemporary(temporary);
table.setGlobalTemporary(globalTemporary);
table.setComment(comment);
......@@ -112,4 +112,8 @@ public class CreateLinkedTable extends SchemaCommand {
this.readOnly = readOnly;
}
public void setOriginalSchema(String originalSchema) {
this.originalSchema = originalSchema;
}
}
......@@ -1197,6 +1197,8 @@ public class ErrorCode {
* The error with code <code>90080</code> is thrown when
* trying to rename a object to a different schema, or when trying to
* create a related object in another schema.
* For CREATE LINKED TABLE, it is thrown when multiple tables with that
* name exist in different schemas.
* Example:
* <pre>
* CREATE SCHEMA TEST_SCHEMA;
......
......@@ -404,11 +404,12 @@ CREATE INDEX IDXNAME ON TEST(NAME)
"Commands (DDL)","CREATE LINKED TABLE","
CREATE [[GLOBAL | LOCAL] TEMPORARY] LINKED TABLE [IF NOT EXISTS]
name(driverString, urlString,
userString, passwordString, originalTableString)
userString, passwordString, [originalSchemaString,] originalTableString)
[EMIT UPDATES | READONLY]
","
Creates a table link to an external table.
The driver name may be empty if the driver is already loaded.
If the schema name is not set, only one table with that name may exist in the target database.
Usually, for update statements, the old rows are deleted first
and then the new rows inserted. It is possible to emit update
statements (however this is not possible on rollback), however
......
......@@ -466,8 +466,8 @@ public class Schema extends DbObjectBase {
* @return the {@link TableLink} object
*/
public TableLink createTableLink(int id, String tableName, String driver, String url, String user, String password,
String originalTable, boolean emitUpdates, boolean force) throws SQLException {
return new TableLink(this, id, tableName, driver, url, user, password, originalTable, emitUpdates, force);
String originalSchema, String originalTable, boolean emitUpdates, boolean force) throws SQLException {
return new TableLink(this, id, tableName, driver, url, user, password, originalSchema, originalTable, emitUpdates, force);
}
}
......@@ -39,7 +39,7 @@ import org.h2.value.DataType;
*/
public class TableLink extends Table {
private String driver, url, user, password, originalTable, qualifiedTableName;
private String driver, url, user, password, originalSchema, originalTable, qualifiedTableName;
private Connection conn;
private HashMap prepared = new HashMap();
private final ObjectArray indexes = new ObjectArray();
......@@ -53,12 +53,13 @@ public class TableLink extends Table {
private boolean readOnly;
public TableLink(Schema schema, int id, String name, String driver, String url, String user, String password,
String originalTable, boolean emitUpdates, boolean force) throws SQLException {
String originalSchema, String originalTable, boolean emitUpdates, boolean force) throws SQLException {
super(schema, id, name, false);
this.driver = driver;
this.url = url;
this.user = user;
this.password = password;
this.originalSchema = originalSchema;
this.originalTable = originalTable;
this.emitUpdates = emitUpdates;
try {
......@@ -81,7 +82,12 @@ public class TableLink extends Table {
storesLowerCase = meta.storesLowerCaseIdentifiers();
storesMixedCase = meta.storesMixedCaseIdentifiers();
supportsMixedCaseIdentifiers = meta.supportsMixedCaseIdentifiers();
ResultSet rs = meta.getColumns(null, null, originalTable, null);
ResultSet rs = meta.getTables(null, originalSchema, originalTable, null);
if (rs.next() && rs.next()) {
throw Message.getSQLException(ErrorCode.SCHEMA_NAME_MUST_MATCH, originalTable);
}
rs.close();
rs = meta.getColumns(null, originalSchema, originalTable, null);
int i = 0;
ObjectArray columnList = new ObjectArray();
HashMap columnMap = new HashMap();
......@@ -114,6 +120,7 @@ public class TableLink extends Table {
columnList.add(col);
columnMap.put(n, col);
}
rs.close();
if (originalTable.indexOf('.') < 0 && !StringUtils.isNullOrEmpty(schema)) {
qualifiedTableName = schema + "." + originalTable;
} else {
......@@ -143,6 +150,7 @@ public class TableLink extends Table {
columnMap.put(n, col);
}
}
rs.close();
} catch (SQLException e) {
throw Message.getSQLException(ErrorCode.TABLE_OR_VIEW_NOT_FOUND_1, new String[] { originalTable + "("
+ e.toString() + ")" }, e);
......@@ -156,7 +164,7 @@ public class TableLink extends Table {
linkedIndex = new LinkedIndex(this, id, IndexColumn.wrap(cols), IndexType.createNonUnique(false));
indexes.add(linkedIndex);
try {
rs = meta.getPrimaryKeys(null, null, originalTable);
rs = meta.getPrimaryKeys(null, originalSchema, originalTable);
} catch (SQLException e) {
// Some ODBC bridge drivers don't support it:
// some combinations of "DataDirect SequeLink(R) for JDBC"
......@@ -182,9 +190,10 @@ public class TableLink extends Table {
list.set(idx - 1, column);
} while (rs.next());
addIndex(list, IndexType.createPrimaryKey(false, false));
rs.close();
}
try {
rs = meta.getIndexInfo(null, null, originalTable, false, true);
rs = meta.getIndexInfo(null, originalSchema, originalTable, false, true);
} catch (SQLException e) {
// Oracle throws an exception if the table is not found or is a
// SYNONYM
......@@ -193,25 +202,28 @@ public class TableLink extends Table {
String indexName = null;
list = new ObjectArray();
IndexType indexType = null;
while (rs != null && rs.next()) {
String newIndex = rs.getString("INDEX_NAME");
if (pkName.equals(newIndex)) {
continue;
}
if (indexName != null && !indexName.equals(newIndex)) {
addIndex(list, indexType);
indexName = null;
}
if (indexName == null) {
indexName = newIndex;
list.clear();
if (rs != null) {
while (rs.next()) {
String newIndex = rs.getString("INDEX_NAME");
if (pkName.equals(newIndex)) {
continue;
}
if (indexName != null && !indexName.equals(newIndex)) {
addIndex(list, indexType);
indexName = null;
}
if (indexName == null) {
indexName = newIndex;
list.clear();
}
boolean unique = !rs.getBoolean("NON_UNIQUE");
indexType = unique ? IndexType.createUnique(false, false) : IndexType.createNonUnique(false);
String col = rs.getString("COLUMN_NAME");
col = convertColumnName(col);
Column column = (Column) columnMap.get(col);
list.add(column);
}
boolean unique = !rs.getBoolean("NON_UNIQUE");
indexType = unique ? IndexType.createUnique(false, false) : IndexType.createNonUnique(false);
String col = rs.getString("COLUMN_NAME");
col = convertColumnName(col);
Column column = (Column) columnMap.get(col);
list.add(column);
rs.close();
}
if (indexName != null) {
addIndex(list, indexType);
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论