Я отлаживал движок Ruby on Rails, у которого есть проблемы при работе на Sqlite, у него есть проблема с поиском записей, которые создает само приложение. При запуске на MySQL все работает, но тот же запрос на SQLite не выполняется.
Я разыскал проблему и обнаружил, что проблема заключается в простом запросе WHERE, который не найдет созданную запись. По сути, структура таблицы имеет столбец с именем key, в котором хранятся некоторые хеши md5. Неудачная спецификация вставляет запись с заданным хешем, затем по следующей инструкции выполняет запрос SELECT для того же хеша, но SQLite не возвращает записи для того же ключа. Я извлек сгенерированную базу данных и ошибочный запрос из приложения, и это копия базы данных приложения:
http://dl.dropbox.com/u/2289657/combustion_test.sqlite
Вот расшифровка запросов, выполненных программным обеспечением (сделанных с помощью утилиты командной строки):
# Here I'm selecting all the records from the table
# there is a single record in it, the key is the third field
$ sqlite3 combustion_test.sqlite 'SELECT * FROM tr8n_translation_keys'
1||b56c67d10759f8012aff28fc03f26cbf|Hello World|We must start with this sentence!||||en-US|0|2012-03-14 11:49:50.335322|2012-03-14 11:49:50.335322|
# Here I'm selecting the record with that key and it doesn't return anything
$ sqlite3 combustion_test.sqlite "SELECT * FROM tr8n_translation_keys WHERE key = 'b56c67d10759f8012aff28fc03f26cbf'"
# Here I'selecting the record with a LIKE clause and it finds the record
$ sqlite3 combustion_test.sqlite "SELECT * FROM tr8n_translation_keys WHERE key LIKE 'b56c67d10759f8012aff28fc03f26cbf'"
1||b56c67d10759f8012aff28fc03f26cbf|Hello World|We must start with this sentence!||||en-US|0|2012-03-14 11:49:50.335322|2012-03-14 11:49:50.335322|
Должен ли я сообщить об этом как об ошибке на сайт SQLite?
P.S. Я пробовал также на другой системе с другой версией SQLite, но результаты те же.
Обновление
Вот схема таблицы
sqlite> .schema tr8n_translation_keys
CREATE TABLE "tr8n_translation_keys" (
"id" INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
"type" varchar(255), "key" varchar(255) NOT NULL,
"label" text NOT NULL,
"description" text,
"verified_at" datetime,
"translation_count" integer,
"admin" boolean,
"locale" varchar(255),
"level" integer DEFAULT 0,
"created_at" datetime,
"updated_at" datetime,
"synced_at" datetime
);
CREATE UNIQUE INDEX "index_tr8n_translation_keys_on_key" ON "tr8n_translation_keys" ("key");
CREATE INDEX "index_tr8n_translation_keys_on_synced_at" ON "tr8n_translation_keys" ("synced_at");
Обновление 2
Вот код rails, который вычисляет значение ключа, вставленное в таблицу (я удалил некоторый код, полный метод здесь )
def self.find_or_create(label, desc = "", options = {})
key = generate_key(label, desc).to_s
# IF I UNCOMMENT THIS LINE EVERYTHING WORKS
#key = 'b56c67d10759f8012aff28fc03f26cbf'
tkey = Tr8n::Cache.fetch("translation_key_#{key}") do
existing_key = where(:key => key).first ### THIS IS THE FAILING WHERE
existing_key ||= begin
new_tkey = create(:key => key.to_s,
:label => label,
:description => desc,
:locale => locale,
:level => level,
:admin => Tr8n::Config.block_options[:admin])
# rest of method...
А вот метод generate_key, комментарий о sqlite от автора, а не от меня)
def self.generate_key(label, desc = "")
# TODO: there is something iffy going on with the strings from the hash
# without the extra ~ = the strings are not seen in the sqlite database - wtf?
"#{Digest::MD5.hexdigest("#{label};;;#{desc}")}"
end