1

私はこれを行うことに慣れています:

use MyDb
go
create type table_list as table (name sysname)
go
create proc rebuild_indexes
    @ls table_list readonly
as
  [...]

しかし今、私はマスターでprocを作成し、他のデータベースでそれを使用したいと思います:

use master
go
create type table_list as table (name sysname)
go
create proc sp_rebuild_indexes
    @ls table_list readonly
as
  [...]

...正常に構築されますが、使用できません。

use MyDb
go
declare @ls table_list

収量:

メッセージ2715、レベル16、状態3、行1列、パラメーター、または変数#1:データ型table_listが見つかりません。パラメータまたは変数'@ls'のデータ型が無効です。

そこで、同義語を作成してみました。これは、作成中に文句を言うことはありませんが、役に立ちません。

create synonym table_list for master.dbo.table_list

誰か考えますか?

4

2 に答える 2

2

異なるデータベースで宣言されたテーブル型は、同じ名前と構造を共有していても、SQL Server では同じものとして扱われません。

create database DB1
go
use DB1
go
create type TT1 as table (ID int not null)
go
create procedure Echo
    @T TT1 readonly
as
    select * from @T
go
create database DB2
go
use DB2
go
create type TT1 as table (ID int not null)
go
declare @T TT1
insert into @T(ID) values (1)
exec DB1..Echo @T

結果:

(1 row(s) affected)
Msg 206, Level 16, State 2, Procedure Echo, Line 0
Operand type clash: TT1 is incompatible with TT1

私が知る限り、別のデータベースのテーブル型定義を使用してデータベースで変数を宣言する方法はありません。(たとえば、ユーザー定義のテーブル型を使用できる場所はどこでも使用できます。名前は or としてのみ使用でき<table type>ます<schema>.<table type>。3 つまたは 4 つの部分の名前は許可されません)。

(上記は 2008 および 2012 に当てはまります。明らかに、将来のバージョンではこれに対処するために何かが行われる可能性があります)


回避策として、「貧弱な」方法でそれを行うことができます-ユーザー定義のテーブルタイプではなく、一時テーブルに対してマスター定義のストアドプロシージャを機能させます。

use Master
go
create procedure sp_Echo
as
    select DB_NAME(),* from #t
go
create database DB1
go
use DB1
go
create table #t (ID int not null)
insert into #t (ID) values (1),(2)
exec sp_Echo

結果:

------------- -----------
DB1           1
DB1           2
于 2012-10-04T06:15:40.030 に答える
1

AFAIK、ユーザー定義の型は、それらが作成されたデータベースのコンテキスト外では使用できません。

各データベースにUDTを作成する必要がある場合がありますが、sProcはマスターのままにしておきます。

sp_命名規則を使用している特定の理由はありますか?

ピート

于 2012-10-04T05:55:20.917 に答える