Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/sql-server-2008/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql server 2008 替换SQL Azure中的上下文信息_Sql Server 2008_Azure_Azure Sql Database_Context Info - Fatal编程技术网

Sql server 2008 替换SQL Azure中的上下文信息

Sql server 2008 替换SQL Azure中的上下文信息,sql-server-2008,azure,azure-sql-database,context-info,Sql Server 2008,Azure,Azure Sql Database,Context Info,我目前正在使用主数据库的CONTEXT_INFO属性来存储登录的用户名,以便稍后在表触发器中使用它进行审核 在迁移到SQLAzure时,出现了跨数据库连接的问题,我找不到解决这个问题的直接方法 详情如下: 我从数据访问层调用存储过程XXX,并将用户名作为参数传递 用户名用于设置XXX中的上下文信息值 然后在表Insert/Update/Delete触发器中使用CONTEXT_INFO值来存储用于应用程序审核的用户名 到目前为止我找到的解决方案: 在数据库中创建表以用作上下文信息 在数据访问层中使

我目前正在使用主数据库的CONTEXT_INFO属性来存储登录的用户名,以便稍后在表触发器中使用它进行审核

在迁移到SQLAzure时,出现了跨数据库连接的问题,我找不到解决这个问题的直接方法

详情如下:

  • 我从数据访问层调用存储过程XXX,并将用户名作为参数传递
  • 用户名用于设置XXX中的上下文信息值
  • 然后在表Insert/Update/Delete触发器中使用CONTEXT_INFO值来存储用于应用程序审核的用户名
  • 到目前为止我找到的解决方案:

  • 在数据库中创建表以用作上下文信息
  • 在数据访问层中使用2个连接字符串,一个用于主数据库(用于设置上下文信息),另一个用于应用程序,每次打开到我的应用程序的连接之前都执行设置的上下文信息
  • 但我发现这两种解决方案都有风险,特别是将来在多个SQLAzure数据库上扩展数据库时


    感谢您的支持。

    我采取的方法如下所示。诀窍是检查是否在SQLAzure上运行,然后我们需要调用“SET CONTEXT\u INFO…”。这允许在本地SQLServerExpress和Azure上执行相同的代码,而无需更改

  • 创建一个表来存储上下文信息(不是在master中,而是在同一数据库中)

  • 创建一个存储过程以“设置上下文信息”,该过程从应用程序调用

    CREATE PROCEDURE [dbo].[SetContextInfo]
      @ApplicationUsername nvarchar(128)
    AS
    
    SET NOCOUNT ON
    
    -- Remove all context items older than an 5 minutes ago
    DELETE
      FROM [dbo].[ContextInfo]
     WHERE [UpdatedAt] < DATEADD(mi, -5, GETUTCDATE())
    
    --
    -- Use the MERGE command to do an update/insert
    -- See: http://technet.microsoft.com/en-us/library/bb510625.aspx
    --
    
    IF SERVERPROPERTY('edition') <> 'SQL Azure'
    BEGIN
        DECLARE @b varbinary(128)
        SET @b = CONVERT(varbinary(128),newid())
        EXEC sp_executesql @statement=N'SET CONTEXT_INFO @b',@params=N'@b varbinary(128)',@b=@b
    END
    
    DECLARE @ContextInfo varbinary(128)
    SELECT @ContextInfo = CONTEXT_INFO()
    
    MERGE [dbo].[ContextInfo] AS target
    USING (SELECT @ContextInfo, @ApplicationUsername) AS source ([ContextInfo], [ApplicationUsername])
       ON (target.[ContextInfo] = source.[ContextInfo])
     WHEN MATCHED THEN 
            UPDATE SET [ApplicationUsername] = source.[ApplicationUsername], [UpdatedAt] = GETUTCDATE()
     WHEN NOT MATCHED THEN  
            INSERT ([ContextInfo], [ApplicationUsername], [UpdatedAt])
            VALUES (source.[ContextInfo], source.[ApplicationUsername], GETUTCDATE());
    
  • 在触发器源中,使用:

    DECLARE @UserContext TABLE ([Username] VARCHAR(128))
    INSERT INTO @UserContext (Username)
    EXEC [dbo].[GetContextInfo]
    

  • 现在,用户名存储在表变量中。如果更改是由应用程序之外的管理员应用的,您可能还需要检查用户名是否未设置,是否默认为*SYSTEM\u USER*

    谢谢Phil,但是如果我使用表格解决方案,则无需再使用上下文信息。
    CREATE PROCEDURE [dbo].[GetContextInfo]
    AS
        SET NOCOUNT ON
        DECLARE @ContextInfo varbinary(128)
        SELECT @ContextInfo = CONTEXT_INFO()
    
        SELECT [ApplicationUsername]
          FROM [dbo].[ContextInfo]
         WHERE [ContextInfo] = @ContextInfo
    GO
    
    DECLARE @UserContext TABLE ([Username] VARCHAR(128))
    INSERT INTO @UserContext (Username)
    EXEC [dbo].[GetContextInfo]