2

2つのSQLServeratabases AとBがあり、SQLのみを使用してデータベースAからデータベースBにビューをコピーしたいと考えています。Bは履歴データベースとして使用され、AのすべてのテーブルもBにあります。

Aからの既存のビューは、Bのデータを指すように、Bにコピー(再作成)する必要があります。

このタスクはSQLManagementStudio(ここなど)を使用して簡単に解決できますが、独自のプログラムを使用してこれらのビューをコピーできる必要があります。

CREATE VIEWステートメントを生成するために必要な情報はどこに保存されていますか?

SELECTINTOまたはINSERTINTOは私の問題の解決策を提供できますか?

4

4 に答える 4

9
USE DatabaseA;
GO

DECLARE @sql NVARCHAR(MAX);

SELECT @sql = definition
FROM sys.sql_modules
WHERE [object_id] = OBJECT_ID('dbo.ViewName');

EXEC DatabaseB..sp_executesql @sql;

すべてのビューを作成する場合は、次のようにします。

USE DatabaseA;
GO

DECLARE @sql NVARCHAR(MAX);

SET @sql = N'';

SELECT @sql = @sql + CHAR(13) + CHAR(10) + 'GO'
    + CHAR(13) + CHAR(10) + m.definition
FROM sys.sql_modules AS s
INNER JOIN sys.objects AS o
ON s.[object_id] = o.[object_id]
WHERE o.type_desc = 'VIEW';

EXEC DatabaseB..sp_executesql @sql;

これを繰り返し可能にしたい場合、宛先データベースに既に存在する場合は、最初に各ビューを削除する必要もあります。たとえば、次のようになります。

USE DatabaseA;
GO

DECLARE @sql NVARCHAR(MAX);

SET @sql = N'';

SELECT @sql = @sql + CHAR(13) + CHAR(10) + 'IF OBJECT_ID('''
    + QUOTENAME(SCHEMA_NAME(o.[schema_id]))
    + '.' + QUOTENAME(o.name) + ''') IS NOT NULL
      BEGIN
        DROP VIEW ' 
        + QUOTENAME(SCHEMA_NAME(o.[schema_id]))
        + '.' + QUOTENAME(o.name) + ';
      END'
    + CHAR(13) + CHAR(10) + 'GO'
    + CHAR(13) + CHAR(10) + s.definition
FROM sys.sql_modules AS s
INNER JOIN sys.objects AS o
ON s.[object_id] = o.[object_id]
WHERE o.type_desc = 'VIEW';

EXEC DatabaseB..sp_executesql @sql;

これらのいずれかがインデックス付きビューである場合、これはインデックスを作成しないことに注意してください。また、ビューが他のデータベースで実際に作成できるかどうかも検証しません (すべての依存オブジェクトが 2 つの間で同一であることが確実でない限り)。データベース)、および作成の順序は保証されません (ViewA が ViewB を呼び出す場合、正しい順序で作成されない可能性があります)。これを自動化するには、スキーマ比較ツールを使用する方がはるかに優れています。私はこれについてここに書いた:

http://bertrandaaron.wordpress.com/2012/04/20/re-blog-the-cost-of-reinventing-the-wheel/

于 2012-05-01T16:58:39.400 に答える
1

アーロン・ベルトランの答えはいつものように素晴らしいです。ただし、完全を期すために、RedGateのSQLCompareはこれを非常にうまく実行し、SMOは、これを比較的単純にするscripterクラスなどの機能を提供します。

于 2012-05-01T17:25:37.627 に答える
0

これは、少なくとも SQL2005 以降で機能しますが、以前のバージョンについては不明です。

SELECT definition
FROM sys.sql_modules
WHERE object_id = OBJECT_ID('<schema_name.object_name>')

ビューはテーブルではなく、それ自体はデータを保持しないため、SELECT INTO または INSERT INTO は使用できません。

于 2012-05-01T16:42:59.250 に答える
0

宛先データベース (databaseB) からこれを実行します。

DECLARE @sql NVARCHAR(MAX)
SELECT  @sql = OBJECT_DEFINITION(OBJECT_ID)
FROM    [databaseA].sys.views
WHERE   name = 'View_1'
EXEC (@sql)
于 2012-05-01T16:43:32.787 に答える