提交 8f043e40 authored 作者: Thomas Mueller's avatar Thomas Mueller

MVStore mode: in-memory databases now also use the MVStore.

上级 b5ab23dc
...@@ -18,7 +18,8 @@ Change Log ...@@ -18,7 +18,8 @@ Change Log
<h1>Change Log</h1> <h1>Change Log</h1>
<h2>Next Version (unreleased)</h2> <h2>Next Version (unreleased)</h2>
<ul><li>In server mode, appending ";autocommit=false" to the database URL was working, <ul><li>MVStore mode: in-memory databases now also use the MVStore.
</li><li>In server mode, appending ";autocommit=false" to the database URL was working,
but the return value of Connection.getAutoCommit() was wrong. but the return value of Connection.getAutoCommit() was wrong.
</li><li>OSGi: the import package declaration of org.h2 excluded version 1.4. </li><li>OSGi: the import package declaration of org.h2 excluded version 1.4.
</li><li>Issue 558: with the MVStore, a NullPointerException could occur when using LOBs </li><li>Issue 558: with the MVStore, a NullPointerException could occur when using LOBs
......
...@@ -20,9 +20,9 @@ public class Constants { ...@@ -20,9 +20,9 @@ public class Constants {
public static final String BUILD_DATE = "2014-04-12"; public static final String BUILD_DATE = "2014-04-12";
/** /**
* The build date is updated for each public release. * The build date of the last stable release.
*/ */
public static final String BUILD_DATE_STABLE = "2014-01-18"; public static final String BUILD_DATE_STABLE = "2014-04-05";
/** /**
* The build id is incremented for each public release. * The build id is incremented for each public release.
......
...@@ -669,6 +669,7 @@ public class Database implements DataHandler { ...@@ -669,6 +669,7 @@ public class Database implements DataHandler {
} }
traceSystem = new TraceSystem(null); traceSystem = new TraceSystem(null);
trace = traceSystem.getTrace(Trace.DATABASE); trace = traceSystem.getTrace(Trace.DATABASE);
getPageStore();
} }
systemUser = new User(this, 0, SYSTEM_USER_NAME, true); systemUser = new User(this, 0, SYSTEM_USER_NAME, true);
mainSchema = new Schema(this, 0, Constants.SCHEMA_MAIN, systemUser, true); mainSchema = new Schema(this, 0, Constants.SCHEMA_MAIN, systemUser, true);
......
...@@ -110,7 +110,7 @@ public class UndoLogRecord { ...@@ -110,7 +110,7 @@ public class UndoLogRecord {
try { try {
table.addRow(session, row); table.addRow(session, row);
table.fireAfterRow(session, null, row, true); table.fireAfterRow(session, null, row, true);
// reset session id, otherwise other session think // reset session id, otherwise other sessions think
// that this row was inserted by this session // that this row was inserted by this session
row.commit(); row.commit();
} catch (DbException e) { } catch (DbException e) {
......
...@@ -54,7 +54,6 @@ MVStore: ...@@ -54,7 +54,6 @@ MVStore:
- automated 'kill process' and 'power failure' test - automated 'kill process' and 'power failure' test
- test and possibly improve compact operation (for large dbs) - test and possibly improve compact operation (for large dbs)
- possibly split chunk metadata into immutable and mutable
- compact: avoid processing pages using a counting bloom filter - compact: avoid processing pages using a counting bloom filter
- defragment (re-creating maps, specially those with small pages) - defragment (re-creating maps, specially those with small pages)
- store number of write operations per page (maybe defragment - store number of write operations per page (maybe defragment
...@@ -109,6 +108,9 @@ MVStore: ...@@ -109,6 +108,9 @@ MVStore:
- test chunk id rollover - test chunk id rollover
- feature to auto-compact from time to time and on close - feature to auto-compact from time to time and on close
- compact very small chunks - compact very small chunks
- Page: to save memory, combine keys & values into one array
(also children & counts). Maybe remove some other
fields (childrenCount for example)
*/ */
......
...@@ -90,6 +90,11 @@ public class Page { ...@@ -90,6 +90,11 @@ public class Page {
*/ */
private long[] children; private long[] children;
/**
* The entry count for the given children.
*/
private long[] counts;
/** /**
* The child pages. * The child pages.
* <p> * <p>
...@@ -97,11 +102,6 @@ public class Page { ...@@ -97,11 +102,6 @@ public class Page {
*/ */
private Page[] childrenPages; private Page[] childrenPages;
/**
* The entry count for the given children.
*/
private long[] counts;
Page(MVMap<?, ?> map, long version) { Page(MVMap<?, ?> map, long version) {
this.map = map; this.map = map;
this.version = version; this.version = version;
...@@ -318,7 +318,7 @@ public class Page { ...@@ -318,7 +318,7 @@ public class Page {
// the default value is used // the default value is used
int x = cachedCompare - 1; int x = cachedCompare - 1;
if (x < 0 || x > high) { if (x < 0 || x > high) {
x = (low + high) >>> 1; x = high >>> 1;
} }
Object[] k = keys; Object[] k = keys;
while (low <= high) { while (low <= high) {
......
...@@ -119,6 +119,7 @@ public class MVTableEngine implements TableEngine { ...@@ -119,6 +119,7 @@ public class MVTableEngine implements TableEngine {
public TableBase createTable(CreateTableData data) { public TableBase createTable(CreateTableData data) {
Database db = data.session.getDatabase(); Database db = data.session.getDatabase();
if (!data.persistData) { if (!data.persistData) {
; // TODO need in-memory tables for persistent stores
return new RegularTable(data); return new RegularTable(data);
} }
Store store = init(db); Store store = init(db);
......
...@@ -569,7 +569,7 @@ public class Schema extends DbObjectBase { ...@@ -569,7 +569,7 @@ public class Schema extends DbObjectBase {
} }
data.schema = this; data.schema = this;
if (data.tableEngine == null) { if (data.tableEngine == null) {
if (database.getSettings().mvStore && database.isPersistent()) { if (database.getSettings().mvStore) {
data.tableEngine = MVTableEngine.class.getName(); data.tableEngine = MVTableEngine.class.getName();
} }
} }
......
...@@ -281,7 +281,7 @@ public class TestCases extends TestBase { ...@@ -281,7 +281,7 @@ public class TestCases extends TestBase {
private void testMaxMemoryRows() throws SQLException { private void testMaxMemoryRows() throws SQLException {
deleteDb("cases"); deleteDb("cases");
Connection conn = getConnection( Connection conn = getConnection(
"cases;max_memory_rows=1"); "cases;MAX_MEMORY_ROWS=1");
Statement stat = conn.createStatement(); Statement stat = conn.createStatement();
stat.execute("create table test(id int primary key)"); stat.execute("create table test(id int primary key)");
stat.execute("insert into test values(1), (2)"); stat.execute("insert into test values(1), (2)");
......
...@@ -11,6 +11,8 @@ import java.sql.ResultSet; ...@@ -11,6 +11,8 @@ import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import java.sql.Savepoint; import java.sql.Savepoint;
import java.sql.Statement; import java.sql.Statement;
import org.h2.api.ErrorCode;
import org.h2.test.TestBase; import org.h2.test.TestBase;
/** /**
...@@ -31,6 +33,7 @@ public class TestMvcc3 extends TestBase { ...@@ -31,6 +33,7 @@ public class TestMvcc3 extends TestBase {
@Override @Override
public void test() throws SQLException { public void test() throws SQLException {
testFailedUpdate();
testConcurrentUpdate(); testConcurrentUpdate();
testInsertUpdateRollback(); testInsertUpdateRollback();
testCreateTableAsSelect(); testCreateTableAsSelect();
...@@ -40,6 +43,25 @@ public class TestMvcc3 extends TestBase { ...@@ -40,6 +43,25 @@ public class TestMvcc3 extends TestBase {
deleteDb("mvcc3"); deleteDb("mvcc3");
} }
private void testFailedUpdate() throws SQLException {
deleteDb("mvcc3");
Connection conn = getConnection("mvcc3");
conn.setAutoCommit(false);
Statement stat = conn.createStatement();
stat.execute("create table test(id int primary key, a int unique, b int)");
stat.execute("insert into test values(1, 1, 1)");
stat.execute("insert into test values(2, 2, 2)");
assertThrows(ErrorCode.DUPLICATE_KEY_1, stat).execute("update test set a = 1 where id = 2");
ResultSet rs;
rs = stat.executeQuery("select * from test where id = 2");
assertTrue(rs.next());
rs = stat.executeQuery("select * from test where a = 2");
assertTrue(rs.next());
rs = stat.executeQuery("select * from test where b = 2");
assertTrue(rs.next());
conn.close();
}
private void testConcurrentUpdate() throws SQLException { private void testConcurrentUpdate() throws SQLException {
if (!config.mvcc) { if (!config.mvcc) {
return; return;
......
...@@ -69,11 +69,10 @@ public class TestJmx extends TestBase { ...@@ -69,11 +69,10 @@ public class TestJmx extends TestBase {
getAttribute(name, "FileWriteCount").toString()); getAttribute(name, "FileWriteCount").toString());
assertEquals("0", mbeanServer. assertEquals("0", mbeanServer.
getAttribute(name, "FileWriteCountTotal").toString()); getAttribute(name, "FileWriteCountTotal").toString());
assertEquals("0", mbeanServer. assertEquals("1", mbeanServer.
getAttribute(name, "LogMode").toString()); getAttribute(name, "LogMode").toString());
// ignored for in-memory databases mbeanServer.setAttribute(name, new Attribute("LogMode", 2));
mbeanServer.setAttribute(name, new Attribute("LogMode", 1)); assertEquals("2", mbeanServer.
assertEquals("0", mbeanServer.
getAttribute(name, "LogMode").toString()); getAttribute(name, "LogMode").toString());
assertEquals("REGULAR", mbeanServer. assertEquals("REGULAR", mbeanServer.
getAttribute(name, "Mode").toString()); getAttribute(name, "Mode").toString());
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论