【问题标题】:sp_MSforeachdb query helpsp_MSforeachdb 查询帮助
【发布时间】:2010-10-01 08:47:28
【问题描述】:

我正在使用许多相同的数据库,因此我使用 sp_MSforeachdb 过程以便从表中检索信息。

我遇到的问题是盒子上有其他数据库没有表,所以我抛出了无效对象错误。

这是我目前所拥有的,我正在过滤 LoginDatabase,因为它具有相同的表,但我不希望在查询中使用它。

我的问题是,我怎样才能将它限制在我想从中获取信息的表的数据库中。

SET NOCOUNT ON

CREATE TABLE #tmpData
(
    DbName VARCHAR(30),
    DbVersion FLOAT
)

exec sp_msforeachdb @command1='
    USE ?;

    INSERT INTO #tmpData
    SELECT ''?'', (SELECT Setting 
        FROM ?.dbo.gl_SysParams 
        WHERE Keyword = ''DatabaseSchema'')
    FROM sysobjects o
    WHERE type=''U'' 
    AND [name] = ''gl_SysParams'' 
    AND ''?'' <> ''LoginDatabase'' ORDER BY [name]
    '   

SET NOCOUNT OFF

SELECT DbName, DbVersion FROM #tmpData ORDER BY DbName

DROP TABLE #tmpData

【问题讨论】:

    标签: sql-server tsql sp-msforeachdb


    【解决方案1】:

    您可以在每个数据库中使用对 sp_MSforeachtable 的调用,在其中使用 @WhereAnd 参数过滤到您感兴趣的表 - 它不会存在于您不感兴趣的数据库中,所以sp_MSforeachtable 将在其中运行 0 次,并在每个带有该表的数据库中运行 1 次。

    编辑简单的例子只是针对我的一个随机服务器运行,我知道只有一个数据库有一个 tblClient 表,有一个 ClientID 列(原谅命名):

    create table #t (
        ID int not null
    )
    exec sp_MSforeachdb 'use ? exec sp_MSforeachtable ''insert into #t(ID) select ClientID from ~'',''~'',@whereand=''and o.name=''''tblClient''''''','?'
    select * from #t
    drop table #t
    

    【讨论】:

    • 所以将 sp_MSforeachtable 包装在 sp_MSforeachdb 的 @command1 中?
    • @Sres - 是的。引号可能有点混乱,当然,您需要为存储的过程之一指定@replacechar
    • 我现在遇到了歧义列名称“名称”的问题,我已经为上面原始的 sysobjects 起别名,@whereand 正在寻找什么表?
    • @Sres - @whereand 附加到针对 sysobjects 的查询,别名为“o”,位于 sp_MSforeachtable 的正文中。我建议避免在您自己的查询中使用别名“o”,并确保为所有表引用使用别名。如果您需要查看 sp_MSforeachtable(和 db)的工作方式,可以检查它们的代码。
    • 如果我能隔着屏幕拥抱你,我会拥抱达米安,效果很好。我现在将发布解决方案。谢谢
    【解决方案2】:

    在 Damien_the_Unbeliever 的帮助下解决问题

    SET NOCOUNT ON
    
    CREATE TABLE #tmpData
    (
        DbName VARCHAR(30),
        DbVersion FLOAT
    )
    
    exec sp_MSforeachdb @command1 = '
        USE ?;
    
        exec sp_MSforeachtable @command1 = ''INSERT INTO #tmpData
        SELECT ''''?'''', (SELECT Setting 
            FROM ?.dbo.gl_SysParams 
            WHERE Keyword = ''''DatabaseSchema'''')
        FROM sysobjects p
        WHERE type=''''U'''' 
        AND p.[name] = ''''gl_SysParams'''' 
        AND ''''?'''' <> ''''LoginDatabase'''' ORDER BY [name]
        '',
        @whereand = ''AND o.[name] = ''''gl_SysParams''''''
        '
    
    SET NOCOUNT OFF
    
    SELECT DbName, DbVersion FROM #tmpData ORDER BY DbName
    
    DROP TABLE #tmpData
    

    【讨论】:

      猜你喜欢
      • 2010-10-05
      • 1970-01-01
      • 2011-11-07
      • 2011-07-19
      • 2011-04-28
      • 2011-02-01
      • 2010-12-24
      • 2010-10-20
      • 1970-01-01
      相关资源
      最近更新 更多