CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR(255));
INSERT INTO TEST VALUES(1, 'Hello');
Full Text Search
INSERT INTO TEST VALUES(2, 'HelloHello');
H2 supports Lucene full text search and native full text search implementation.
SELECT * FROM TEST WHERE NAME REGEXP 'He';
Using the Native Full Text Search
java.util.ConcurrentModificationException
To initialize, call:
at java.util.HashMap$HashIterator.nextEntry(HashMap.java:841)
at java.util.HashMap$ValueIterator.next(HashMap.java:871)
CREATE ALIAS IF NOT EXISTS FT_INIT FOR "org.h2.fulltext.FullText.init";
at java.util.AbstractCollection.toArray(AbstractCollection.java:176)
CALL FT_INIT();
at org.h2.util.FileUtils.listFiles(FileUtils.java:395)
at org.h2.engine.Database.deleteOldTempFiles(Database.java:1055)
Afterwards, you can create a full text index for a table using:
at org.h2.engine.Database.closeOpenFilesAndUnlock(Database.java:853)
at org.h2.engine.Database.close(Database.java:814)
CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR);
at org.h2.engine.Database.removeSession(Database.java:755)
INSERT INTO TEST VALUES(1, 'Hello World');
at org.h2.engine.Session.close(Session.java:260)
at org.h2.engine.Database.close(Database.java:783)
CALL FT_CREATE_INDEX('PUBLIC', 'TEST', NULL);
where PUBLIC is the schema, TEST is the table name. The list of column names (column separated) is optional, in this case all columns are indexed. The index is updated in read time. To search the index, use the following query:
SCRIPT: append ; also in result set (copy paste problem)
SELECT * FROM FT_SEARCH('Hello', 0, 0);
java org.h2.tools.RunScript -url jdbc:h2:file:bug -user SA -script \temp\test\data.sql
You can also call the index from within a Java application:
I have a big problem with PreparedStatements and version 2007-07-12 or above.
Using the Lucene Full Text Search
With 2007-04-29 or lower it works as expected.
To use the Lucene full text search, you first need to rename the file FullTextLucene.java.txt to FullTestLucene.java and compile it. Also, you need the Lucene library in the classpath.
In the test query i use a UNION ALL (i know, not well tested), but also with a simple SELECT/UPDATE/INSERT prepared statement with a where clause and parameters the problem happens, if i run the query more than once with different parameters. It always returns the result from the first executeQuery() or updates the rows return from the first query.
To initialize, call:
But the funny thing is, i cannot reproduce the bug with a simple SELECT in the test app.
If i run the test app, the output is with ver 2007-07-12:
CREATE ALIAS IF NOT EXISTS FTL_INIT FOR "org.h2.fulltext.FullTextLucene.init";
Row Count 9
CALL FTL_INIT();
Sum 714.8621259
Row Count 9
Afterwards, you can create a full text index for a table using:
Sum 714.8621259
Row Count 9
CREATE TABLE TEST(ID INT PRIMARY KEY, NAME VARCHAR);
Sum 714.8621259
INSERT INTO TEST VALUES(1, 'Hello World');
(looks like it takes every time the first result)
with ver 2007-04-29
CALL FTL_CREATE_INDEX('PUBLIC', 'TEST', NULL);
Row Count 9
Sum 714.8621259
where PUBLIC is the schema, TEST is the table name. The list of column names (column separated) is optional, in this case all columns are indexed. The index is updated in read time. To search the index, use the following query:
Row Count 7
Sum 0.0
SELECT * FROM FTL_SEARCH('Hello', 0, 0);
Row Count 10
Sum 381.230477
You can also call the index from within a Java application:
> CREATE INDEX PUBLIC.IDXNAME ON PUBLIC.TEST(NAME)
> CREATE INDEX PUBLIC.IDXNAME ON PUBLIC.TEST(NAME);
> CREATE MEMORY TABLE PUBLIC.TEST( ID INT NOT NULL, NAME VARCHAR(255) DEFAULT 1, CREATEDATE VARCHAR(255) DEFAULT '2001-01-01' NOT NULL, MODIFY_DATE TIMESTAMP )
> CREATE MEMORY TABLE PUBLIC.TEST( ID INT NOT NULL, NAME VARCHAR(255) DEFAULT 1, CREATEDATE VARCHAR(255) DEFAULT '2001-01-01' NOT NULL, MODIFY_DATE TIMESTAMP );
> CREATE MEMORY TABLE PUBLIC.TEST_SEQ( ID INT DEFAULT 20, DATA VARCHAR )
> CREATE MEMORY TABLE PUBLIC.TEST_SEQ( ID INT DEFAULT 20, DATA VARCHAR );
> ALTER TABLE PUBLIC.B_TEST ADD CONSTRAINT PUBLIC.B_UNIQUE UNIQUE(B_INT)
> ALTER TABLE PUBLIC.B_TEST ADD CONSTRAINT PUBLIC.B_UNIQUE UNIQUE(B_INT);
> ALTER TABLE PUBLIC.B_TEST ADD CONSTRAINT PUBLIC.C3 FOREIGN KEY(B_INT) REFERENCES PUBLIC.A_TEST(A_INT) ON DELETE SET DEFAULT ON UPDATE SET DEFAULT NOCHECK
> ALTER TABLE PUBLIC.B_TEST ADD CONSTRAINT PUBLIC.C3 FOREIGN KEY(B_INT) REFERENCES PUBLIC.A_TEST(A_INT) ON DELETE SET DEFAULT ON UPDATE SET DEFAULT NOCHECK;