2

その場で DDL を生成するのに役立つソースまたはライブラリはありますか?

ローカル サーバーにコピーする必要がある数百のリモート データベースがあります。フィールドでのアップグレード手順は、新しいデータベースを作成することです。地元では、私も同じことをしています。

したがって、フィールド内のすべての異なる DB バージョンの DDL を生成する代わりに、ソース テーブルから DDL を読み取り、同一のテーブルをローカルに作成したいと考えています。

そのようなライブラリまたはソースはありますか?

4

3 に答える 3

3

実際、これは自分でできることに気づき、その過程で何かを学ぶでしょう。私が管理しているいくつかのデータベースでこれを使用しています。DDL スタイル情報を使用して見やすいビューを作成します。

create view vw_help as
select 
  Table_Name as TableName
, Column_Name as ColName
, Ordinal_Position as ColNum
, Data_Type as DataType
, Character_Maximum_Length as MaxChars
, coalesce(Datetime_Precision, Numeric_Precision) as [Precision]
, Numeric_Scale as Scale
, Is_Nullable as Nullable
, case when (Data_Type in ('varchar', 'nvarchar', 'char', 'nchar', 'binary', 'varbinary')) then
       case when (Character_Maximum_Length = -1) then Data_Type + '(max)'
                  else Data_Type + '(' + convert(varchar(6),Character_Maximum_Length) + ')'
                  end
       when (Data_Type in ('decimal', 'numeric')) then
            Data_Type + '(' + convert(varchar(4), Numeric_Precision) + ',' + convert(varchar(4), Numeric_Scale) + ')'
       when (Data_Type in ('bit', 'money', 'smallmoney', 'int', 'smallint', 'tinyint', 'bigint', 'date', 'time', 'datetime', 'smalldatetime', 'datetime2', 'datetimeoffset', 'datetime2', 'float', 'real', 'text', 'ntext', 'image', 'timestamp', 'uniqueidentifier', 'xml')) then Data_Type
  else 'unknown type'
  end as DeclA
, case when (Is_Nullable = 'YES') then 'null' else 'not null' end as DeclB
, Collation_Name as Coll
-- ,* 
from Information_Schema.Columns
GO

そして、次を使用して「テーブル構造を表示」します

/*

exec ad_Help TableName, 1

*/

ALTER proc [dbo].[ad_Help] (@TableName nvarchar(128), @ByOrdinal int = 0) as
begin
set nocount on

declare @result table
(
  TableName nvarchar(128)
, ColName nvarchar(128)
, ColNum int
, DataType nvarchar(128)
, MaxChars int
, [Precision] int
, Scale int
, Nullable varchar(3)
, DeclA varchar(max)
, DeclB varchar(max)
, Coll varchar(128)
)

insert @result
select TableName, ColName, ColNum, DataType, MaxChars, [Precision], Scale, Nullable, DeclA, DeclB, Coll
from dbo.vw_help
where TableName like @TableName

if (select count(*) from @result) <= 0
begin
  select 'No tables matching ''' + @TableName + '''' as Error
  return
end

if (@ByOrdinal > 0)
begin
  select * from @result order by TableName, ColNum
end else begin
  select * from @result order by TableName, ColName
end

end
GO

外部キーなども生成する必要がある場合は、InformationSchemas で他の情報を使用できます。これは少し複雑で、DDL の生成に必要なすべてを具体化することは決してしませんでしたが、正しい考えを得る必要があります。もちろん、すでに提案されているものを使用できるのであれば、自分で作成する必要はありません。

コメントを追加しました -- 正確な回答はできませんでしたが、喜んでお手伝いします。これを機能させるには、多くの動的文字列操作を生成する必要があります -- varchar(max) が役に立ちます。TSQL は、この種のプロジェクトに適した言語ではないことを指摘しておきます。個人的には、完全なテーブル DDL を生成する必要がある場合、これを CLR proc として記述し、C# で重い文字列操作を実行したくなるかもしれません。これがあなたにとって理にかなっていれば、私はまだ SQL サーバーの外部でプロセスをデバッグします (たとえば、テストと調査のためのフォーム プロジェクト)。CLR プロシージャは Net 2.0 フレームワークであることを覚えておいてください。

結果のセットを返すストアド プロシージャを絶対に作成できます。つまり、テーブルの列に対して 1、外部キーに対して 1 などです。次に、その結​​果のセットを C# で使用し、DDL ステートメントを作成します。C# コードで。

于 2013-08-29T18:36:48.953 に答える
2

Gary Walker さん、あなたのスクリプトに基づいて、まさに必要なものを作成しました。ご助力ありがとうございます。

他の誰かがそれを必要とする場合は、次のとおりです。

with ColumnDef (TableName, ColName, ColNum, DeclA, DeclB)
as
(
    select 
      Table_Name as TableName
    , Column_Name as ColName
    , Ordinal_Position as ColNum
    , case when (Data_Type in ('varchar', 'nvarchar', 'char', 'nchar', 'binary', 'varbinary')) then
           case when (Character_Maximum_Length = -1) then Data_Type + '(max)'
                      else Data_Type + '(' + convert(varchar(6),Character_Maximum_Length) + ')'
                      end
           when (Data_Type in ('decimal', 'numeric')) then
                Data_Type + '(' + convert(varchar(4), Numeric_Precision) + ',' + convert(varchar(4), Numeric_Scale) + ')'
           when (Data_Type in ('bit', 'money', 'smallmoney', 'int', 'smallint', 'tinyint', 'bigint', 'date', 'time', 'datetime', 'smalldatetime', 'datetime2', 'datetimeoffset', 'datetime2', 'float', 'real', 'text', 'ntext', 'image', 'timestamp', 'uniqueidentifier', 'xml')) then Data_Type
      else 'unknown type'
      end as DeclA
    , case when (Is_Nullable = 'YES') then 'null' else 'not null' end as DeclB
    from Information_Schema.Columns
)
select 'CREATE TABLE ' + TableName + ' (' + 
substring((select ', ' + ColName + ' ' + declA + ' ' + declB
from ColumnDef
where tablename = t.TableName
order by ColNum
for xml path ('')),2,8000) + ') '
from 
(select distinct TableName from ColumnDef) t
于 2013-08-29T20:16:33.743 に答える