В настоящее время я создаю базу данных и пишу хранимые процедуры для приложения Android.Я давно программист и создал несколько баз данных несколько лет назад, но до сих пор не работал с хранимыми процедурами.Проблема, с которой я столкнулся на данный момент, заключается в том, что я не могу найти правильный способ проверить, не существует ли заданная строка (указанная с помощью stringId) и заданный язык (заданный с помощью languageId), и если переведенная строка уже существует, прежде чем я продолжуи вставьте новую переведенную строку в таблицу TranslatedStrings .Я просмотрел много похожих вопросов и множество других веб-сайтов, и хотя некоторые из них, похоже, имели ту же самую проблему, их решение работало для них, но не для меня.
Вот мой текущий сценарий создания процедуры:
create procedure `InsertTranslatedString`(in stringId int(10) unsigned, in translationSource tinyint(3) unsigned, in translationLanguageId int(10) unsigned,
in translatedString mediumtext, out insertedTranslatedStringId int(10) unsigned, out returnValue int(10))
reads sql data
modifies sql data
begin
-- if the string id does not exists
if (select count(1) from `Strings` where `stringId` = stringId) = 0
then
-- return error code
set returnValue = -1;
set insertedTranslatedStringId = 0;
-- if the language id does not exists
elseif (select count(1) from `Languages` where `languageId` = translationLanguageId) = 0
then
-- return error code
set returnValue = -2;
set insertedTranslatedStringId = 0;
-- if the translated string already exists
elseif (select count(1) from `TranslatedStrings` where `stringId` = stringId and `languageId` = translationLanguageId) > 0
then
-- return error code
set returnValue = -3;
set insertedTranslatedStringId = 0;
-- if we are ready to go
else
-- insert the actual translated string
insert into TranslatedStrings (`stringId`, `languageId`, `value`, `translationSource`, `createdDateTime`)
values (stringId, translationLanguageId, translatedString, translationSource, now());
select @newTranslatedStringId := last_insert_id();
-- give back output parameters
set insertedTranslatedStringId = @newTranslatedStringId;
set returnValue = 0;
end if;
end $$
Создание процедуры работает как charm.
Я вызываю процедуру с call InsertTranslatedString(76, 0, 1, 'German (Germany)', @insertedTranslatedStringId, @returnValue);
И stringId 76, и languageId 1. не существуют.
Когда я делаю этот вызовЯ заметил, что блок if-elseif-elseif-else
пропускает первый if
(проверка stringId), даже если он должен войти в свой блок then
.Однако процедура входит в первую elseif
(проверку languageId), которая работает нормально.
Я также опробовал if-проверки следующим образом: if not exists (select 1 from 'Strings' where 'stringId' = stringId)
но там функция exists()
, казалось, всегда возвращала true, неважноесли select
вернул строку или нет строки;Затем процедура будет переходить ко второму elseif
только потому, что я использовал elseif exists (select...
.Однако фактический select
не возвращает ни одной строки, если я запускаю ее отдельно.Очень запутанно.
Вот три ссылочные таблицы:
CREATE TABLE `Languages` (
`languageId` int(10) unsigned NOT NULL,
`nameStringId` int(10) unsigned NOT NULL,
`languageCode` varchar(5) DEFAULT NULL,
`hiddenInSettings` tinyint(1) DEFAULT '0',
PRIMARY KEY (`languageId`),
KEY `FK_Languages_nameStringId` (`nameStringId`),
CONSTRAINT `FK_Languages_nameStringId` FOREIGN KEY (`nameStringId`) REFERENCES `Strings` (`stringId`) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='contains all supported and automatically translated languages'
CREATE TABLE `Strings` (
`stringId` int(10) unsigned NOT NULL AUTO_INCREMENT,
`originalValue` mediumtext NOT NULL,
`originalLanguageId` int(10) unsigned NOT NULL,
PRIMARY KEY (`stringId`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8 COMMENT='contains all language-independent strings instances'
CREATE TABLE `TranslatedStrings` (
`stringId` int(10) unsigned NOT NULL,
`languageId` int(10) unsigned NOT NULL,
`value` mediumtext NOT NULL,
`translationSource` tinyint(3) unsigned DEFAULT '0',
`createdDateTime` datetime DEFAULT NULL,
`lastModifiedDateTime` datetime DEFAULT NULL,
`incorrectTranslationState` tinyint(3) unsigned DEFAULT '0',
`incorrectTranslationReporterId` int(10) unsigned DEFAULT NULL,
`incorrectTranslationReportedDateTime` datetime DEFAULT NULL,
PRIMARY KEY (`stringId`,`languageId`),
KEY `FK_TranslatedStrings_languageId` (`languageId`),
KEY `FK_TranslatedStrings_incorrectTranslationReporterId` (`incorrectTranslationReporterId`),
CONSTRAINT `FK_TranslatedStrings_incorrectTranslationReporterId` FOREIGN KEY (`incorrectTranslationReporterId`) REFERENCES `Users` (`userId`) ON DELETE CASCADE,
CONSTRAINT `FK_TranslatedStrings_languageId` FOREIGN KEY (`languageId`) REFERENCES `Languages` (`languageId`) ON DELETE CASCADE,
CONSTRAINT `FK_TranslatedStrings_stringId` FOREIGN KEY (`stringId`) REFERENCES `Strings` (`stringId`) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='contains all localized and automatically translated strings'
Когда я создавал таблицы, я, кстати, не создавал эти KEY
записи, они были созданы MySQL Server.Странно, что они похожи только на некоторые из CONSTRAINT
записей, а не на все.
Поскольку Strings имеет только первичный ключ, состоящий из одного столбца, и никаких внешних ключей, я озадачен тем, что соответствующий ему оператор if не сработал,Что я делаю не так?