Pull to refresh

Comments 5

Спасибо за статью. Хотел бы обратить Ваше внимание на несколько нюансов (insertRandomData).

Системное представление sys.all_objects содержит в себе и пользовательские и системные объекты. А поскольку фильтром Вы оставляете только пользовательские таблицы (type = 'U'), то целесообразно делать выборку из sys.objects. За счет этого Вы получите более эффективный план выполнения.

Также меня немного настораживает соединение с systypes. Возможно Вы хотели сделать соединение по user_type_id. В противном случае, возможна ситуация когда можно получить дублирование строк.

В общем, мой вариант Вашего запроса:

SELECT c.column_id
     , c.name
     , TYPE_NAME(c.user_type_id)
     , c.max_length
FROM sys.objects o
JOIN sys.columns c ON c.[object_id] = o.[object_id]
WHERE o.[type] = 'U'
    AND TYPE_NAME(c.system_type_id) != 'sysname'
    AND o.name LIKE @childTableName 
ORDER BY c.column_id;
www.mssqltips.com/sqlservertip/2190/generating-sql-server-test-data-with-visual-studio-2010/
www.red-gate.com/products/sql-development/sql-data-generator/
www.datanamic.com/datagenerator-for-mssql/

Зачастую пишем через шарп — удобнее…
Таблица на 50 млн строк (50 колонок) генерируется порядка 5 минут.
А так можно использовать оффсеты, фетч и CTE для скоростей.

Используйте временную таблицу и вставляйте без Values.
INSERT INTO tbl
SELECT * FROM #tbl

Либо через CTE и даты формируйте блоки данных нужной длины.
Либо вставляйте по 100 строк хотя бы (блочный принцип).

INSERT INTO Production.UnitMeasure
VALUES (N'FT2', N'Square Feet ', '20080923'),
(N'Y', N'Yards', '20080923'),
(N'Y3', N'Cubic Yards', '20080923');

Ну и если можно вместо курсора использовать WHILE — используйте.
вот можно эту доработать dba.stackexchange.com/questions/19938/a-script-to-insert-dummy-data-in-all-tables-of-database,
А вот так можно вычленить сначала справочники без ключей.

ALTER PROCEDURE [dbo].[FillRandomData]
@DatabaseName NVARCHAR(50) = 'TestData'
AS
BEGIN
DECLARE sql NVARCHAR(512) = 'USE [' + @DatabaseName + '];' + ' SELECT name, object_id FROM sys.tables WHERE name <> ''sysdiagrams'' AND type = ''U'''
DECLARE @tblData TABLE(name nvarchar(255), object_id int)
DECLARE @TablesWithFK TABLE(name nvarchar(255), object_id int)
DECLARE @TablesWithoutFK TABLE(name nvarchar(255), object_id int)

INSERT INTO @tblData
EXEC (sql)

INSERT INTO @TablesWithFK
SELECT t.name, t.object_id
FROM @tblData t
LEFT JOIN sys.foreign_key_columns fc ON fc.referenced_object_id = t.object_id
WHERE fc.constraint_column_id IS NULL
GROUP BY t.name, t.object_id

INSERT INTO @TablesWithoutFK
SELECT t.name, t.object_id
FROM @tblData t
LEFT JOIN sys.foreign_key_columns fc ON fc.referenced_object_id = t.object_id
WHERE fc.constraint_column_id IS NOT NULL
GROUP BY t.name, t.object_id

DECLARE cur CURSOR READ_ONLY FOR SELECT name FROM @TablesWithoutFK
DECLARE name NVARCHAR(50)
OPEN cur

FETCH NEXT FROM cur INTO name
WHILE (@@fetch_status <> -1)
BEGIN
IF (@@fetch_status <> -2)
BEGIN
PRINT name
END
FETCH NEXT FROM cur INTO name
END

CLOSE cur
DEALLOCATE cur

END
Для того, чтобы не тратить время и нервы на генерацию тестовых данных, можно воспользоваться замечательным инструментом — dbForge Data Generator for SQL Server. Этот инструмент имеет более 200 встроеных генераторов на все слуаи жизни. Важным фактом является то, что он генерирует т.н. meaningful тестовые данные, т.е. не рандомные стринги и инты, а осознанные данные с поддержкой всех типов констреинтов. Каждый из генераторов очень гибко настраивается под индивидуальные нужды. MUST HAVE TOOL для DB Dev и QA.
Поддерживаю… тул достаточно эффективно генерирует тестовые данные, вставляет большие куски через BULK INSERT… за это и нравится. Есть мелкие приколы, но на фоне конкурентов весьма хорош.
Sign up to leave a comment.

Articles