Opposite of HEX() in SQLite? - sqlite

I have this simple query that returns a bunch of guids as hexadecimal strings:
SELECT HEX(guid) FROM table;
One of them is for instance 43F4124307108902B7A919F4D4D0770D. Then imagine I want to get the record with this guid, so I write a query like this:
SELECT * FROM table WHERE guid = '43F4124307108902B7A919F4D4D0770D';
Of course, this will not work, since the string is directly interpreted as a blob and not converted to it's hex value. I looked here, but couldn't find anything that looks like a method that takes a hexadecimal string and converts it to a blob.

While writing the question I found the answer. I simply had to add an X before the string. Like this:
SELECT * FROM table WHERE guid = X'43F4124307108902B7A919F4D4D0770D';
I figured I should post the question anyway, since non of the "Similar Questions" answers this. What I was looking for was not a function, but a literal and when I realized this I quickly found the answer here.

In the upcoming version it's supported:
SQLite version 3.41.0 2023-02-08 12:47:37
Enter ".help" for usage hints.
Connected to a transient in-memory database.
Use ".open FILENAME" to reopen on a persistent database.
sqlite> select unhex('41')
...> ;
A
sqlite> select hex('a')
...> ;
61
sqlite> .q

Related

Searching for blob field in SQLite

I have column in my database that stores BLOB.
I want to run a query to check if specific byte array value is present in the table.
The value is b'\xf4\x8f\xc6{\xc2mH(\x97\x9c\x83hkE\x8b\x95' (python bytes).
I tried to run this query:
SELECT * from received_message
WHERE "EphemeralID"
LIKE HEX('\xf4\x8f\xc6{\xc2mH(\x97\x9c\x83hkE\x8b\x95');
But I get 0 results though I 100% sure that I store this value in the database.
Is there something wrong with my query?
Your search string is a bit weird-- you appear to have some complex things in there like { and (. Maybe you should search through the blob the way it is stored instead?
From the Sqlite documentation:
BLOB literals are string literals containing hexadecimal data and
preceded by a single "x" or "X" character. Example: X'53514C697465'
So maybe do a like with the ascii representation of the hex value you want? Maybe start with looking for just f48f or F48F if your sqlite stores it upper case.

SQLIte : Query to find all keywords in sqlite

I am working with SQLite. I need to know a query that retrieves all KEYWORDS in SQLite. Ex:
For Oracle: select * from v$reserved_words
For MySQL: select * from mysql.help_keyword
Above query will show all keywords in the corresponding database. Like this, I need a query for SQLite. Anyone knows please let me know.
There is no way to dynamically retrieve the list of reserved words, with a system table or a pragma.
The documentation lists the (currently) 124 keywords. It seems that the actual list also depends on the compile-time options.

Sqlite: adding COMMENT ON descriptions to tables and columns?

In MySQL Workbench you can add COMMENTs to tables and columns in a MySQL database.
Does Sqlite support adding comments to tables and columns?
I don't think it does. The "SQL As Understood By SQLite" page makes no mention of table or column comments nor does the CREATE TABLE or ALTER TABLE documentation.
Also, the Unsupported SQL wiki page has this:
2009-08-04: Table and column comments - I have scoured the doco and can't find anything about applying comments to tables or their columns.
Yes, that's a wiki page from 2009 but that note is supported by the rest of the documentation.
However, SQLite does preserve SQL comments that you put in your DDL. If you feed this to the sqlite3 CLI tool:
CREATE TABLE User
-- A table comment
(
uid INTEGER, -- A field comment
flags INTEGER -- Another field comment
);
Then you get exactly that back from a .schema command:
sqlite> .schema
CREATE TABLE User
-- A table comment
(
uid INTEGER, -- A field comment
flags INTEGER -- Another field comment
);
So you should be able to fake it if you can control the DDL used to create your tables.
When creating a table using sqlite (I'm using sqlite3 in python), the COMMENT section is not supported.
This fails (works in full MySql syntax):
CREATE TABLE `Info` (
`Test` VARCHAR(512) NOT NULL COMMENT 'Column info here'
);
This works (no COMMENT in the column declaration):
CREATE TABLE `Info` (
`Test` VARCHAR(512) NOT NULL
);
(This isn't what the original poster was asking, but this is what I was looking for when I first found this question based on the keywords in the title.)
How to make comments in SQLite
There are two ways to make comments in SQLite code:
Hyphens
-- this is my comment
SELECT * FROM employees;
C-style
/* this is my comment */
SELECT * FROM employees;
I appreciate that this is an old post but for what it's worth, you can add comments when creating a table in SQLITE3, in Python and in Java. Probably works for other languages as well.
You need to add new lines to your sql string as you would if you were typing in the command at the SQLITE3 prompt -
sql_str = 'CREATE TABLE properties (\nproperty TEXT NOT NULL, -- A property\nvalue TEXT -- The value of the property\n);'
When executed the table is created like so:
sqlite> .schema
CREATE TABLE properties (
property TEXT NOT NULL, -- A property
value TEXT -- The value of the property
);
I suspect that this works because the connector is actually echoing in the commands via the command prompt, rather than some sort of API.

How do I quote a UTF-8 String Literal in Sqlite3

I'm looking to encode and store Unicode in a Sqlite database. Is there any way to raw encode a UTF-8 (unicode) string literal in a sql query.
I'm looking for something similar to java where I can toss a \u00E9 into a string and have it automagically upconvert to Unicode.
What language are you using? SQLite handles Unicode just fine, creating the literals in your hosting language is less obvious.
$ sqlite3 junk.sqlite
SQLite version 3.6.22
sqlite> create table names (id integer primary key, name string);
sqlite> insert into names values (null,
'î℉ yõù g𐌹ѷЄ ΣϘГくטƏ UTF-8, it stores it');
sqlite> select * from names;
1|î℉ yõù g𐌹ѷЄ ΣϘГくטƏ UTF-8, it stores it
SQLite doesn't have escape sequences. But your programming language probably does.
# in Python
db.execute("INSERT INTO MyTable(MyColumn) VALUES('\u00E9')")
or
db.execute("INSERT INTO MyTable(MyColumn) VALUES(?)", ['\u00E9'])
If for some reason you have to write a UTF-8 literal in pure SQL, you can do something like:
sqlite> SELECT CAST(X'C3A9' AS TEXT);
é
Edit: Since this answer was originally written, a CHAR function has been added to SQLite. So now, you could write
INSERT INTO MyTable(MyColumn) VALUES(CHAR(233))
If your problem is reinterpretation of escape sequences in sqlite you can (ab)use json_extract eg.
UPDATE `tableToFix` SET `columnToFix` = json_extract('"' || `columnToFix` || '"', '$');
INSERT INTO test VALUE (json_extract('"P\u0159\u00edli\u0161 \u017elu\u0165ou\u010dk\u00fd k\u016f\u0148 \u00fap\u011bl \u010f\u00e1belsk\u00e9 \u00f3dy."', '$'));
Notice: quotes handling. Valid json string starts and ends with " so you must add them before use of json_extract
If you configure your database to use UTF-8 (I believe this is default for many installations; do PRAGMA encoding="UTF-8"; at schema creation time to be certain), this shouldn't be an issue.
If you send SQLite3 a set of characters encoded in UTF-8, it should have no problem dealing with it.
If Java has the ability to allow you to "toss a \u0039 into a string", I'd just use that, and ensure that when you try to place the string into the database, that you have the string convert to a UTF-8 byte encoding using whatever mechanism Java provides. I do not believe SQLite provides or needs to provide this for you.

sqlite Query optimisation

The query
SELECT * FROM Table WHERE Path LIKE 'geo-Africa-Egypt-%'
can be optimized as:
SELECT * FROM Table WHERE Path >= 'geo-Africa-Egypt-' AND Path < 'geo-Africa-Egypt-zzz'
But how can be this done:
select * from foodDb where Food LIKE '%apples%";
how this can be optimized?
One option is redundant data. If you're querying a lot for some fixed set of strings occuring in the middle of some column, add another column that contains the information whether a particular string can be found in the other column.
Another option, for arbitrary but still tokenizable strings is to create a dictionary table where you have the tokens (e.g. apples) and foreign key references to the actual table where the token occurs.
In general, sqlite is by design not very good at full text searches.
It would surprise me if it was faster, but you could try GLOB instead of LIKE and compare;
SELECT * FROM foodDb WHERE Food GLOB '*apples*';

Resources