I’m trying to create a FULLTEXT index on an attribute of a table. Mysql returns
ERROR 1214: The used table type doesn’t support FULLTEXT indexes.
Any idea what I’m doing wrong?
You’re using the wrong type of table. Mysql supports a few different types of tables, but the most commonly used are MyISAM and InnoDB. MyISAM (in MySQL 5.6+also InnoDB tables) are the types of tables that Mysql supports for Full-text indexes.
To check your table’s type issue the following sql query:
SHOW TABLE STATUS
Looking at the result returned by the query, find your table and corresponding value in the Engine column. If this value is anything except MyISAM or InnoDB then Mysql will throw an error if your trying to add FULLTEXT indexes.
To correct this, you can use the sql query below to change the engine type:
ALTER TABLE <table name> ENGINE = [MYISAM | INNODB]
Additional information (thought it might be useful):
Mysql using different engine storage types to optimize for the needed functionality of specific tables. Example MyISAM is the default type for operating systems (besides windows), preforms SELECTs and INSERTs quickly; but does not handle transactions. InnoDB is the default for windows, can be used for transactions. But InnoDB does require more disk space on the server.
Up until MySQL 5.6, MyISAM was the only storage engine with support for full-text search (FTS) but it is true that InnoDB FTS in MySQL 5.6 is syntactically identical to MyISAM FTS. Please read below for more details.
InnoDB Full-text Search in MySQL 5.6
On MySQL <= 5.5, the mysql manual says that FULLTEXT indexes can only be created on tables with the mylsam engine.
Are you using InnoDB? The only table type that supports FULLTEXT is MyISAM.
apart from MyISAM table PARTITIONING also not support full-text index.
Related
I have a table like this.
ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
Later i have created a HASH index like this.
CREATE INDEX index ON table (column) USING HASH;
Latter i have try some explain queries.
Like
explain Select * from table where column=132;
And i see the engine is using the index on possible_keys and in the key stuff says the name of the index!!
But in the docs says that InnoDB doesn't allow hash index now i wonder why my innoDB Supposedly allows the hash index?
InnoDB silently changes "HASH" into "BTree". A BTree index does what a HASH does, plus more. Or do you think there is some good reason to want Hash?
"Good reason" -- MySQL was created many years ago. It was designed to be 'lean and mean'. Many features were boiled down to "one size fits all": BTree for indexing; Nested Loop Join for JOINing, etc.
Meanwhile, for future expansion and pseudo compatibility, some common syntax variants were included -- HASH for indexing, DESC for index ordering, etc. Even though those "lie" about what will happen, the database engine still gives you the 'right' answer.
Over time, the most glaring shortcuts have been remedied.
Replication (3.xx?)
Transactions (Adding InnoDB in 4.0) (MyISAM had LOCK TABLES, but that was not really adequate.)
information_schema (4.1?) (versus a variety of SHOW commands) Note: 8.0 overhauled it with the "data dictionary")
Character sets and collations (4.1) (vs "latin_swedish_ci", which was good enough for the implementor.)
Stored routines (vs client code) (5.0)
Subqueries (TEMPORARY TABLEs were not adequate)
Various JOIN optimizations (5.6, 5,7, 8.0)
only_full_group_by (MariaDB 10.1?, 5.7)
ALTER not 'always' copying the table over (mostly 5.7)
"Generated" columns (5.7)
"Tablespaces" (5.7)
JSON datatype and functions
FULLTEXT and SPATIAL indexing in InnoDB (5.7, 8.0) (so MyISAM can be deprecated)
DESC in INDEXes (8.0) (very few use cases really need this)
"Windowing" functions (MariaDB 10.2, then MySQL 8.0)
CTEs (MariaDB 10.2, then MySQL 8.0)
Security: Better password handling (4.1?, 5.6, 8.0)
HA (High Availability) (MariaDB with Galera; 8.0 with InnoDB Cluster)
At-rest encryption (8.0?)
Notice how the list is somewhat ordered from "must have" to "nice to have". Yet to come may include
Multi-threaded execution (Useless if you are I/O-bound anyway) (a very few use cases in 8.0)
HASH indexing (and other types) (MariaDB 10.4, only for UNIQUE on TEXT/BLOB)
Global UNIQUE and FOREIGN KEY for PARTITIONing. (Not that partitioning is very useful.)
More syntax compatibility with standards and other vendors (MariaDB already does a much better job of this)
Meanwhile, some things are going away (or have already gone away -- either in MariaDB or MySQL)
Compiling for a large variety of computers -- such as Atari
The Query Cache -- Handy for benchmarking, but not really useful in Production environments. And a major hassle to implement in any 'cluster' topology.
MyISAM has major deficiencies relative to InnoDB, and has very few benefits. (Arguably, the only benefit is less disk space needed.)
The feature in InnoDB is called Adaptive Hash Index,
Whether to use hash index depends on the scale of the table and query frequency, it's a completely internal strategy and normally out of configuration.
https://dev.mysql.com/doc/refman/5.7/en/innodb-adaptive-hash.html
ALTER TABLE [tbl_name] TYPE=innodb
I have just read somewhere that using above alter table statement will optimize an existing table. I am not very sure that this would work and if yes, does it work even if table type is already InnoDB?
InnoDB:
The InnoDB storage engine in MySQL.
Support for transactions (giving you support for the ACID property).
Row-level locking. Having a more fine grained locking-mechanism gives you higher concurrency compared to, for instance, MyISAM.
Foreign key constraints. Allowing you to let the database ensure the integrity of the state of the database, and the relationships between tables.
InnoDB is more resistant to table corruption than MyISAM.
Support for large buffer pool for both data and indexes. MyISAM key buffer is only for indexes.
Another point is that MyISAM is stagnant; all future enhancements will be in InnoDB
InnoDB Limitations:
No full text indexing (Below-5.6 mysql version)
Cannot be compressed for fast, read-only
For more info on this:
http://www.kavoir.com/2009/09/mysql-engines-innodb-vs-myisam-a-comparison-of-pros-and-cons.html
When to use MyISAM and InnoDB?
http://dev.mysql.com/doc/refman/5.0/en/innodb-file-defragmenting.html
If your DB is already a innoDB you do not need to make that statement again. As for other suggestions you should use ENGINE instead of TYPE.
ALTER TABLE `table_name` ENGINE = InnoDB;
I am not sure for optimizing existing table but I can corrected your query.
ALTER TABLE `mytable` ENGINE = InnoDB;
Use the ENGINE keyword since TYPE is not supported any more
As of MySQL 5.1.8, TYPE = engine_name is still accepted as a synonym for the ENGINE = engine_name table option but generates a warning. You should note that this option is not available in MySQL 5.1.7, and is removed altogether in MySQL 5.5 and produces a syntax error.
After that your query should work and change the engine for an existing table.
In PostgreSQL, we can search table based on full text search like this -
SELECT title
FROM pgweb
WHERE to_tsvector('english', body) ## to_tsquery('english', 'friend');
Source - http://www.postgresql.org/docs/current/static/textsearch-tables.html
How can we do similar search in MySQL 5.5 which is quite easily done in PostgreSQL?
You probably want MySQL's full text search functionality. Essentially you create a FULLTEXT index then search against it using MATCH() ... AGAINST.
I'm not aware of a facility to set the search language per-query in MySQL, but that doesn't mean no such support exists. It wasn't clear if per-query language settings were a requirement for you.
The latest stable release of MySQL supports full text search on the modern transactional and crash-safe InnoDB table type as well as the unsafe MyISAM table type. If your MySQL only does FTS on MyISAM it's time to upgrade. 5.6 supports full text search on InnoDB.
Alternately, if you really can't upgrade, you can store your important data in InnoDB tables and run a periodic query to update a MyISAM table you use as a materialized view for fulltext search only:
Create a new MyISAM table
INSERT INTO ... SELECT the data from the InnoDB table into the new MyISAM table
CREATE the fulltext index on the new MyISAM table
DROP the old MyISAM table you were using for fulltext indexing; and
finally ALTER TABLE ... RENAME the new MyISAM table to have the name of the old one.
You'll have a very short window during which the fulltext index is unavailable between when you drop the old table and re-create the new one. Your data also gets out of date and stale between view refreshes, though it's possible you can work around that with triggers (I don't use MySQL enough to know). If you can't live with these limitations, upgrade to 5.6.
MySQL's full text search offers control of stopwords and other tuning. It's a solid offering that should do the job nicely.
I have MySQL running on my machine configured with MyISAM as its default tables.
Now I want to ask few of questions:
1) If I change the default table to InnoDB in the configuration file (my.conf), clear the log file and restart mysql, would that harm any of my previous database or tables?
2) If I alter few tables' engine to InnoDB using the following command, would that affect its data at all?
ALTER TABLE table_name ENGINE = InnoDB;
3) Is it a good idea to keep few tables as MyISAM (for read and write) and the rest as InnoDB (more for selecting data) or is it preferred to select one engine for all the tables in the database?
2) It will only affect the internal representation. Nothing that you will notice on the outside.
3) It is a perfectly good idea, if it enhances performance.
2) You can mix database types. i.e. innoDB and MyISAM.
3) innoDB supposedly keeps data safer. I think it is the default on latest versions of mySQL.
I've done some searching into fulltext searches for MySQL InnoDB and found a few on stack overflow, but they either don't provide an exact solution or they are a bit dated and I think it's time to rediscuss.
All of my tables are InnoDB and I'd prefer not to lock the entire database with MyISAM. What are my options in regards to fulltext searching? Are there any simple solutions? I'd like to do the equivalant of MATCH (content) AGAINST ("my search query" IN BOOLEAN MODE)
There is no equivalant of MATCH AGAINST in Innodb. Fulltext searching is one of pros of using MyIsam. So you should use standalone seaching server like Sphinx or Solr
InnoDB full-text search (FTS) is finally available in MySQL 5.6.4 release.
These indexes are physically represented as entire InnoDB tables, which are acted upon by SQL keywords such as the FULLTEXT clause of the CREATE INDEX statement, the MATCH() ... AGAINST syntax in a SELECT statement, and the OPTIMIZE TABLE statement.
From FULLTEXT Indexes