Couchbase N1QL: index and query on array fields - couchbase

Platform: Couchbase Server 4.0 beta, Java client 2.1.3
I am looking for something similar to SQL JOIN. For example I have documents of the form where field2 is embedded in the document instead of in a separate table as you would have in a relational DB:
{field1:" ..", field2:[{key:1, ...},{key:3, ...},..],...}.
How can I achieve something like this:
select * from bucket where field2.key=3;
And how can I index the key, a hypothetical example:
create index idx_key on bucket(field2.key);

What if you did something like this:
SELECT
*
FROM `your-bucket-here` AS fields
WHERE
ANY field IN fields.field2 SATISFIES field.key = 3 END
This way as long as one nested array item contains your value, it will be returned.
In terms of creating an index, are you looking to create a secondary index or a primary index? You could always do something like this:
CREATE PRIMARY INDEX index_name ON `your-bucket-name-here` USING GSI;
CREATE INDEX index_name ON `your-bucket-name-here` USING GSI;
Let me know how all that goes!
Best,

Related

How to use multiple columns in an index?

I am trying to speed up query processing in a database using an index.
CREATE INDEX PASSENGER_INDEX ON Passengers USING hash (name);
I need to use not only the first name but also the last name and patronymic, if possible. How can I do this?

Couchbase N1ql queries

I have two question regarding N1QL query in Couchbase.
1: Let suppose I have user table where userid is document key and then i
fire a query like this
select * from mybucket use keys["1234"];
2: Let suppose userid is not a document key and then i create a secondary index on userid
select * from mybucket where userid=1234;
So my question is, which query would perform faster ?
Second question is,
Let suppose I have user table where userid is document key
select * from mybucket where meta().id="1234";
This query does not run and give me "No index available on keyspace".
It is a document key, it should run like "use keys". I tried to create a secondary index on userid but it says index can not be created since this field is not the part of document(obviously, it is a document key)
The first query will run fastest. Naming the specific key directly in a USE KEYS clause lets Couchbase retrieve the record directly in a single request. The second approach, using an index, will be slightly slower, because the system will first have to make a request to the index to get the document id, and then retrieve the record itself. The second approach will still be very very fast, but not quite as fast as the first one.
Yeah, depending on what version you are using, we may not be fully optimizing that third case. Use USE KEYS if you can.

MariaDB - is it possible to index JSON arrays?

When working with JSON in MariaDB it is possible to index single-point values using virtual columns e.g.
ALTER TABLE features ADD feature_street VARCHAR(30) AS (JSON_UNQUOTE(feature->"$.properties.STREET"));
ALTER TABLE features ADD INDEX (feature_street);
Does anybody know whether it is possible to index JSON arrays in the same way so that when querying based on the values of the array members, each array does not have to be scanned?
I can't find anything in the docs which suggests this is possible.
Create a "virtual" column of the element of the JSON column and index it.
https://mariadb.com/kb/en/mariadb/virtual-computed-columns/
The elements of an array inside a JSON string -- That is another matter.

Hibernate mapping with partitioned MySQL tables

I have a MySQL database where (most) tables are partitioned on a column TENANT_ID. Each table also has an ID field which uses AUTO_INCREMENT and is therefore unique across all partitions. The database primary key is a combination (ID, TENANT_ID) due to MySQL's requirement to have the partition column part of the primary key.
In my Java code I have mapped only the ID column with the #Id annotation. This was mostly to avoid the many problems around composite keys in Hibernate. The problem I am facing now is that most SQL statements generated by Hibernate only use the ID column. For example, an UPDATE statement generated by Hibernate would read as
UPDATE object SET value = ? WHERE ID = ?
However, since this query excludes any predicate on TENANT_ID, it does not take full advantage of the partitioning and will need to scan every partition until it finds the ID. I would like for the generated query to yield:
UPDATE object SET value = ? WHERE ID = ? AND TENANT_ID = ?
My question is whether or not there is an easy way to do this without having to resort to composite keys in JPA as I know many people discourage their use.
You can use an embedded entity, for instance ObjectPK that encompasses the id and EntityId. than use #EmbeddedId to reference it from the Object entity.

What is the significance of the index name when creating an index in MySQL?

I've done something like this in order to use on duplicate key update:
CREATE UNIQUE INDEX blah on mytable(my_col_to_make_an_index);
and its worked just fine. I'm just not sure what the purpose of the index name is -- in this case 'blah'. The stuff I've read says to use one but I can't fathom why. It doesn't seem to be used in queries, although I can see it if I export the schema.
So ... what purpose does the index name serve? If it helps the line in the CREATE TABLE ends up looking like:
UNIQUE KEY `clothID` (`clothID`)
The index name is used to reference the index for future commands. Like drop index.
http://dev.mysql.com/doc/refman/5.0/en/drop-index.html
Just think of index names like table names. You can just as easily make a table called 'blah'.
CREATE TABLE blah (f1 int);
But 'blah' isn't very helpful for future reference. Just be consistent. something like
CREATE UNIQUE INDEX field_uniq on mytable(field);
or
CREATE INDEX field1_field2_inx on mytable(field1, field2);
The naming is to allow global namespace, and help better understand on the table schema.
The index name is very useful for forcing index hint. Try not using the same name for both index and column (ambiguous), and camel case is meaningless for system like Windows (which does not allow case sensitivity).
For example, like this:
unique key cloth_id_uniq (cloth_id);
>>allow people knowing this an unique key on column cloth_id
fulltext key description_ft (description);
>>allow people knowing this index is fulltext on column description
I do not think there is a standard naming convention, whatever seems intuitive will help most.
You are correct. The index name is only used as an identifier, so you can refer to it if you need to edit, delete or query on it later. It isn't used for any other purpose.
You can name the index whatever is most convenient for you, but some consistency would probably help you (naming your index 'blah' is perfectly valid, but you won't have a clue where it is, what it does, or why you created it).