Я пытаюсь написать хранимую процедуру, которая вставляет данные, но с некоторыми довольно простыми проверками, которые выглядят как хорошая практика.Проверка дубликатов при вставке хранимой процедуры
В таблице в настоящее время имеет 300 столбцов, из которых Eсть последовательный primary_key_id
, столбец, что мы хотим, чтобы проверить, прежде чем вставить, скажем address
, child_of
столбец используется, когда есть новые данные (то, что мы вставляем), а затем Остальные 297 столбцов.
Так скажем, таблица в настоящее время выглядит следующим образом:
----------------------------------------------------------------------
|PK |Address |child_of |other_attr_1|other_attr2|...
----------------------------------------------------------------------
|1 | 123 Main St |NULL |... |... |...
|2 | 234 South Rd |NULL |... |... |...
|3 | 345 West Rd |NULL |... |... |...
----------------------------------------------------------------------
и мы хотим, чтобы добавить эту строку, где адрес имеет новый атрибут new
в other_attr_1
колонки. Мы использовали бы child_of
для ссылки на primary_key_id
предыдущей записи строки. Это позволит создать базовую историю (надеюсь).
|4 | 123 Main St |1 |new |... |...
Как проверить дублирование хранимой процедуры? Я перебираю каждый входной параметр с тем, что уже находится в БД, если оно есть?
Вот код, у меня до сих пор:
USE [databaseINeed]
-- SET some_stuff ON --or off :)
-- ....
-- GO
CREATE Procedure [dbo].[insertNonDuplicatedData]
@address text, @other_attr_1 numeric = NULL, @other_attr_2 numeric = NULL, @other_attr_3 numeric = NULL,....;
AS
BEGIN TRY
-- If the address already exists, lets check for updated data
IF EXISTS (SELECT 1 FROM tableName WHERE address = @address)
BEGIN
-- Look at the incoming data vs the data already in the record
--HERE IS WHERE I THINK THE CODE SHOULD GO, WITH SOMETHING LIKE the following pseudocode:
if any attribute parameter values is different than what is already stored
then Insert into tableName (address, child_of, attrs) Values (@address, THE_PRIMARY_KEY_OF_THE_RECORD_THAT_SHARES_THE_ADDRESS, @other_attrs...)
RETURN
END
-- We don't have any data like this, so lets create a new record altogther
ELSE
BEGIN
-- Every time a SQL statement is executed it returns the number of rows that were affected. By using "SET NOCOUNT ON" within your stored procedure you can shut off these messages and reduce some of the traffic.
SET NOCOUNT ON
INSERT INTO tableName (address, other_attr_1, other_attr_2, other_attr_3, ...)
VALUES(@address,@other_attr_1,@other_attr_2,@other_attr_3,...)
END
END TRY
BEGIN CATCH
...
END CATCH
Я попытался добавить CONSTRAINT
на самой таблице для всех 297 атрибутов, которые должны быть уникальными при проверке против address
колонн через:
ALTER TABLE tableName ADD CONSTRAINT
uniqueAddressAttributes UNIQUE -- tried also with NONCLUSTERED
(other_attr_1,other_attr_2,...)
, но я получаю сообщение об ошибке
ERROR: cannot use more than 32 columns in an index SQL state: 54011
, и я думаю, что я могу пойти по неверному пути, пытаясь опираться на уникальное ограничение.
Один из осложнения состоят в том, что таблица имеет 297 столбцов. Трудно понять, почему можно построить таблицу с таким количеством столбцов, а не нормализовать ее не только для производительности, но и для упрощения работы с данными. Я бы настоятельно рекомендовал вам создать резервную копию в вашем дизайне. Конечно, я не подвергаюсь вашим требованиям. – CLaFarge
Я этого не делал! Я унаследовал это. Но я пытаюсь работать с ним медленно, но верно :) –