Первая огромная проблема - вы строите запрос конкатенацией, а значит подвергаете себя риску SQL-инъекций. Используйте
PDO.
Вторая огромная проблема - вы в наглую игнорируете возникающие ошибки при вставке, в результате у вас и растет номер ключа. Потому как БД сначала создает новый номер, потом пытается вставить, получает ошибку и идет дальше.
Если вы столь заинтересованы в отсутствии утечки номеров (хоть это и не верно с точки зрения архитектуры), вам придется (серьезно потеряв производительность) проверять перед вставкой каждой строки ее возможность наличия в БД.
Если же вы решите просто уменьшать счетчик при возникновении ошибки в момент попытки вставить дубль, вы совершите ошибку, так как можете испортить этот самый счетчик, создав
гонку.