Skip to content

Commit 1248fe7

Browse files
MDEV-27582 Fulltext DDL decrements the FTS_DOC_ID value
- InnoDB FTS DDL decrements the FTS_DOC_ID when there is a deleted marked record involved. FTS_DOC_ID must never be reused. The purpose of FTS_DOC_ID is to be a unique row identifier that will be changed whenever a fulltext indexed column is updated.
1 parent 0635088 commit 1248fe7

File tree

6 files changed

+90
-53
lines changed

6 files changed

+90
-53
lines changed

mysql-test/suite/innodb_fts/r/innodb-fts-ddl.result

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -289,3 +289,32 @@ ENGINE=InnoDB;
289289
ALTER TABLE t1 ADD c SERIAL;
290290
DROP TABLE t1;
291291
# End of 10.3 tests
292+
#
293+
# MDEV-27582 Fulltext DDL decrements the FTS_DOC_ID value
294+
#
295+
CREATE TABLE t1 (
296+
f1 INT NOT NULL PRIMARY KEY,
297+
f2 VARCHAR(64), FULLTEXT ft(f2)) ENGINE=InnoDB;
298+
INSERT INTO t1 VALUES (1,'foo'),(2,'bar');
299+
connect con1,localhost,root,,,;
300+
START TRANSACTION WITH CONSISTENT SNAPSHOT;
301+
connection default;
302+
DELETE FROM t1 WHERE f1 = 2;
303+
ALTER TABLE t1 DROP INDEX ft;
304+
ALTER TABLE t1 ADD FULLTEXT INDEX ft (f2);
305+
INSERT INTO t1 VALUES (3, 'innodb fts search');
306+
SET GLOBAL innodb_optimize_fulltext_only=ON;
307+
OPTIMIZE TABLE t1;
308+
Table Op Msg_type Msg_text
309+
test.t1 optimize status OK
310+
SET GLOBAL innodb_ft_aux_table = 'test/t1';
311+
SELECT max(DOC_ID) FROM INFORMATION_SCHEMA.INNODB_FT_INDEX_TABLE;
312+
max(DOC_ID)
313+
3
314+
SELECT * FROM t1 WHERE MATCH(f2) AGAINST("+innodb +search" IN BOOLEAN MODE);
315+
f1 f2
316+
3 innodb fts search
317+
DROP TABLE t1;
318+
disconnect con1;
319+
SET GLOBAL innodb_optimize_fulltext_only=OFF;
320+
SET GLOBAL innodb_ft_aux_table = default;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
--enable-plugin-innodb-sys-tables
2+
--innodb_ft_index_table

mysql-test/suite/innodb_fts/t/innodb-fts-ddl.test

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -357,3 +357,28 @@ ALTER TABLE t1 ADD c SERIAL;
357357
DROP TABLE t1;
358358

359359
--echo # End of 10.3 tests
360+
361+
--echo #
362+
--echo # MDEV-27582 Fulltext DDL decrements the FTS_DOC_ID value
363+
--echo #
364+
CREATE TABLE t1 (
365+
f1 INT NOT NULL PRIMARY KEY,
366+
f2 VARCHAR(64), FULLTEXT ft(f2)) ENGINE=InnoDB;
367+
INSERT INTO t1 VALUES (1,'foo'),(2,'bar');
368+
connect(con1,localhost,root,,,);
369+
START TRANSACTION WITH CONSISTENT SNAPSHOT;
370+
371+
connection default;
372+
DELETE FROM t1 WHERE f1 = 2;
373+
ALTER TABLE t1 DROP INDEX ft;
374+
ALTER TABLE t1 ADD FULLTEXT INDEX ft (f2);
375+
INSERT INTO t1 VALUES (3, 'innodb fts search');
376+
SET GLOBAL innodb_optimize_fulltext_only=ON;
377+
OPTIMIZE TABLE t1;
378+
SET GLOBAL innodb_ft_aux_table = 'test/t1';
379+
SELECT max(DOC_ID) FROM INFORMATION_SCHEMA.INNODB_FT_INDEX_TABLE;
380+
SELECT * FROM t1 WHERE MATCH(f2) AGAINST("+innodb +search" IN BOOLEAN MODE);
381+
DROP TABLE t1;
382+
disconnect con1;
383+
SET GLOBAL innodb_optimize_fulltext_only=OFF;
384+
SET GLOBAL innodb_ft_aux_table = default;

storage/innobase/fts/fts0fts.cc

Lines changed: 8 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -243,18 +243,6 @@ fts_add_doc_by_id(
243243
/*==============*/
244244
fts_trx_table_t*ftt,/*!< in: FTS trx table */
245245
doc_id_tdoc_id);/*!< in: doc id */
246-
/******************************************************************//**
247-
Update the last document id. This function could create a new
248-
transaction to update the last document id.
249-
@return DB_SUCCESS if OK */
250-
static
251-
dberr_t
252-
fts_update_sync_doc_id(
253-
/*===================*/
254-
const dict_table_t* table,/*!< in: table */
255-
doc_id_tdoc_id,/*!< in: last document id */
256-
trx_t* trx)/*!< in: update trx, or NULL */
257-
MY_ATTRIBUTE((nonnull(1)));
258246

259247
/** Tokenize a document.
260248
@param[in,out] doc document to tokenize
@@ -2552,27 +2540,6 @@ fts_get_max_cache_size(
25522540
}
25532541
#endif
25542542

2555-
/*********************************************************************//**
2556-
Update the next and last Doc ID in the CONFIG table to be the input
2557-
"doc_id" value (+ 1). We would do so after each FTS index build or
2558-
table truncate */
2559-
void
2560-
fts_update_next_doc_id(
2561-
/*===================*/
2562-
trx_t* trx,/*!< in/out: transaction */
2563-
const dict_table_t* table,/*!< in: table */
2564-
doc_id_tdoc_id)/*!< in: DOC ID to set */
2565-
{
2566-
table->fts->cache->synced_doc_id = doc_id;
2567-
table->fts->cache->next_doc_id = doc_id + 1;
2568-
2569-
table->fts->cache->first_doc_id = table->fts->cache->next_doc_id;
2570-
2571-
fts_update_sync_doc_id(
2572-
table, table->fts->cache->synced_doc_id, trx);
2573-
2574-
}
2575-
25762543
/*********************************************************************//**
25772544
Get the next available document id.
25782545
@return DB_SUCCESS if OK */
@@ -2731,17 +2698,17 @@ fts_cmp_set_sync_doc_id(
27312698
return(error);
27322699
}
27332700

2734-
/*********************************************************************//**
2735-
Update the last document id. This function could create a new
2701+
/** Update the last document id. This function could create a new
27362702
transaction to update the last document id.
2737-
@return DB_SUCCESS if OK */
2738-
static
2703+
@param table table to be updated
2704+
@param doc_id last document id
2705+
@param trx update trx or null
2706+
@retval DB_SUCCESS if OK */
27392707
dberr_t
27402708
fts_update_sync_doc_id(
2741-
/*===================*/
2742-
const dict_table_t* table,/*!< in: table */
2743-
doc_id_tdoc_id,/*!< in: last document id */
2744-
trx_t* trx)/*!< in: update trx, or NULL */
2709+
const dict_table_t* table,
2710+
doc_id_tdoc_id,
2711+
trx_t* trx)
27452712
{
27462713
byte id[FTS_MAX_ID_LEN];
27472714
pars_info_t* info;

storage/innobase/include/fts0fts.h

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -402,17 +402,6 @@ fts_get_next_doc_id(
402402
/*================*/
403403
const dict_table_t* table,/*!< in: table */
404404
doc_id_t* doc_id);/*!< out: new document id */
405-
/*********************************************************************//**
406-
Update the next and last Doc ID in the CONFIG table to be the input
407-
"doc_id" value (+ 1). We would do so after each FTS index build or
408-
table truncate */
409-
void
410-
fts_update_next_doc_id(
411-
/*===================*/
412-
trx_t* trx,/*!< in/out: transaction */
413-
const dict_table_t* table,/*!< in: table */
414-
doc_id_tdoc_id)/*!< in: DOC ID to set */
415-
MY_ATTRIBUTE((nonnull(2)));
416405

417406
/******************************************************************//**
418407
Create a new fts_doc_ids_t.
@@ -976,4 +965,16 @@ bool fts_check_aux_table(const char *name,
976965
table_id_t *table_id,
977966
index_id_t *index_id);
978967

968+
/** Update the last document id. This function could create a new
969+
transaction to update the last document id.
970+
@param table table to be updated
971+
@param doc_id last document id
972+
@param trx update trx or null
973+
@retval DB_SUCCESS if OK */
974+
dberr_t
975+
fts_update_sync_doc_id(const dict_table_t *table,
976+
doc_id_t doc_id,
977+
trx_t *trx)
978+
MY_ATTRIBUTE((nonnull(1)));
979+
979980
#endif /*!< fts0fts.h */

storage/innobase/row/row0merge.cc

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2862,7 +2862,21 @@ row_merge_read_clustered_index(
28622862
err = fts_sync_table(const_cast<dict_table_t*>(new_table));
28632863

28642864
if (err == DB_SUCCESS) {
2865-
fts_update_next_doc_id(NULL, new_table, max_doc_id);
2865+
new_table->fts->cache->synced_doc_id = max_doc_id;
2866+
2867+
/* Update the max value as next FTS_DOC_ID */
2868+
if (max_doc_id >= new_table->fts->cache->next_doc_id) {
2869+
new_table->fts->cache->next_doc_id =
2870+
max_doc_id + 1;
2871+
}
2872+
2873+
new_table->fts->cache->first_doc_id =
2874+
new_table->fts->cache->next_doc_id;
2875+
2876+
err= fts_update_sync_doc_id(
2877+
new_table,
2878+
new_table->fts->cache->synced_doc_id,
2879+
NULL);
28662880
}
28672881
}
28682882

0 commit comments

Comments
 (0)