2016-01-20 52 views
2

我的公司使用來自衆多客戶的數據,並忽略記錄我們的數據庫表和字段所代表的內容。爲了解決這個問題,我編寫了一些存儲過程,這些存儲過程似乎只適用於他們所在的數據庫。我想在服務器上有一個存儲過程的實例,可以在其所有數據庫上使用,但無法弄清楚如何實現這一點。下面是程序:SQL存儲過程 - 從多個數據庫執行

步驟1 - sp_GetTableDocumentation

Create Procedure sp_GetTableDocumentation(@TableName SYSNAME) 
AS 

SELECT 
    @TableName AS [Table Name] 
    ,'' AS [Column Name] 
    ,CONVERT(NVARCHAR(MAX), ISNULL(D.value, '')) AS [Description] 
FROM sys.Tables AS T 
OUTER APPLY (SELECT TOP 1 * FROM ::fn_listextendedproperty('Description', 'SCHEMA', 'dbo', 'TABLE', @TableName, NULL, NULL)) AS D 
WHERE T.Name = @TableName 

UNION ALL 

SELECT 
    @TableName AS [Table Name] 
    ,C.Name AS [Column Name] 
    ,CONVERT(NVARCHAR(MAX), ISNULL(D.value, '')) AS [Description] 
FROM sys.Tables AS T 
INNER JOIN sys.Columns AS C ON T.Object_id = C.Object_id 
OUTER APPLY (SELECT TOP 1 * FROM ::fn_listextendedproperty('Description', 'SCHEMA', 'dbo', 'TABLE', @TableName, 'COLUMN', C.Name)) AS D 
WHERE T.Name = @TableName 
GO 

步驟2 - sp_SetTableDocumentation

Create Procedure sp_SetTableDescription(
    @schemaName sysname 
    , @tableName sysname 
    , @description sql_variant 
) 
As 
    If Exists (
     Select 1 
     From fn_listextendedproperty('Description','SCHEMA',@schemaName,'TABLE',@tableName,NULL,NULL) 
    ) 
     exec sp_DropExtendedProperty 'Description','SCHEMA',@schemaName,'TABLE',@tableName 
     If (Not @description Is Null) And (Not @description = '') 
     exec sp_AddExtendedProperty 'Description', @description,'SCHEMA',@schemaName,'TABLE',@tableName 
GO 

程序3 - sp_SetTableDescription

Create Procedure sp_SetTableDescription(
    @schemaName sysname 
    , @tableName sysname 
    , @description sql_variant 
) 
As 
If Exists (
    Select 1 
    From fn_listextendedproperty('Description','SCHEMA',@schemaName,'TABLE',@tableName,NULL,NULL) 
) 
    exec sp_DropExtendedProperty 'Description','SCHEMA',@schemaName,'TABLE',@tableName 
If (Not @description Is Null) And (Not @description = '') 
exec sp_AddExtendedProperty 'Description', @description,'SCHEMA',@schemaName,'TABLE',@tableName 
GO 

步驟4 - sp_SetColumnDescription

CREATE PROCEDURE sp_SetColumnDescription (
    @schemaName SYSNAME 
    ,@tableName SYSNAME 
    ,@columnName SYSNAME 
    ,@description SQL_VARIANT 
    ) 
AS 
IF EXISTS (
     SELECT 1 
     FROM fn_listextendedproperty('Description', 'SCHEMA', @schemaName, 'TABLE', @tableName, 'COLUMN', @columnName) 
     ) 
    EXEC sp_DropExtendedProperty 'Description','SCHEMA',@schemaName,'TABLE',@tableName,'COLUMN',@columnName 

IF (NOT @description IS NULL) AND (NOT @description = '') 
    EXEC sp_AddExtendedProperty 'Description',@description,'SCHEMA',@schemaName,'TABLE',@tableName,'COLUMN',@columnName 
GO 

感謝

+0

對於用戶定義的db對象,'sp_'命名約定是不好的做法 – lad2025

+0

這裏是一篇文章,介紹爲什麼sp_是不好的做法。 http://sqlperformance.com/2012/10/t-sql-queries/sp_prefix –

+0

你將不得不實現動態sql來使其成爲一組通用的過程,以便您可以定義它將針對哪個數據庫執行。它可以完成,但會是一個相當大的工作,因爲除了實際使它與動態SQL功能,它也需要從SQL注入安全。 –

回答

1

系統存儲過程可以做你想做的事情。

通常情況下,存儲過程是針對它編譯的數據庫執行的(正如您已經注意到的那樣)。 如果過程名稱以「sp_」開頭,位於主數據庫中並且標記有sys.sp_MS_MarkSystemObject,則它可以調用這樣的:

Exec somedb.dbo.sp_GetTableDocumentation 
Exec anotherdb.dbo.sp_GetTableDocumentation 

參見:https://www.mssqltips.com/sqlservertip/1612/creating-your-own-sql-server-system-stored-procedures/

這是如果你能接受把你的存儲過程中進入主無一不精。

+0

這對我想要做的事很合適。該文章也非常豐富。謝謝你的幫助! – fireflyfiend

0

您可以使用存儲過程sp_MSforeachdb的無證系統,但被警告,這是未記錄隨時都可能消失(儘管它一直在SQL Server至少自2005年甚至更早)。

這是一個使用sp_MSforeachdb你的第一個存儲過程的一部分的例子:

DECLARE @Tablename VARCHAR(100) = 'tblPolicy' 
DECLARE @sql VARCHAR(MAX) = 
'USE [?] 

SELECT 
    T.TABLE_NAME AS [Table Name], 
    '''' AS [Column Name], 
    CONVERT(NVARCHAR(MAX), ISNULL(D.value, '''')) AS Description 
FROM 
    INFORMATION_SCHEMA.TABLES T 
OUTER APPLY (SELECT TOP 1 * FROM ::fn_listextendedproperty(''Description'', ''SCHEMA'', ''dbo'', ''TABLE'', ''' + @TableName + ''', NULL, NULL)) AS D 
WHERE 
    TABLE_NAME = ''' + @Tablename + '''' 

EXEC master.sys.sp_MSforeachdb @sql 

另外,還要留意SQL注入不同的地方是@Tablename值是從哪裏來的威脅。爲什麼這不是一個好主意,可能還有一些其他的警告,但我現在會堅持這些。 ;)

+0

謝謝你的反饋,湯姆。我最終將我的存儲過程標記爲系統對象,以促進所需的功能。在做了一些更深入的研究之後,我不認爲SQL注入將成爲我最終解決方案的重要問題。感謝您的建議和謹慎的話語。 – fireflyfiend

相關問題