代码之家  ›  专栏  ›  技术社区  ›  Jason Irwin

tsql-解析执行计划以确定存储过程返回的列

  •  2
  • Jason Irwin  · 技术社区  · 15 年前

    有没有一种方法(从.NET代码或TSQL)动态地确定存储过程将返回的列?我想在.NET中为我的存储过程动态生成包装函数。获取过程名/参数等很容易,但我还想知道当一个过程返回数据(不执行该sp)时,需要哪些列。这有可能吗?

    5 回复  |  直到 15 年前
        1
  •  4
  •   gbn    15 年前

    我已经看到了,然后我对做了这件事的客户开发人员大喊大叫,然后我们就离开了这个想法。

    说真的,我们在嵌套过程、添加列或参数(供以后使用等)以及其他方面遇到了问题,因为反射会再次猜测我们的意图。

    但是,上面有一些关于它的msdn文章:

    编辑:根据其他答案,我们通常不会根据if语句更改输出。我们将视图存储过程视为方法(当然是明智的),因此需要一个稳定的签名…

        2
  •  4
  •   Marc Gravell    15 年前

    这实际上是出了名的棘手。它与UDF一起工作很好,因为它们有更强的元数据,但是存储过程可以做很多讨厌的事情:

    • 分支机构( IF 等),返回完全不同的形状
    • 执行另一个存储过程
    • 执行动态SQL

    所以非常非常棘手。有两种常见的方法:

    • 试图解析tsql;痛苦的
    • 使用默认值(空等)执行并检查结果

    这个 SET FMTONLY ON 选项通常用于第二个(以避免更新等),但请注意,系统存储过程仍在执行(可能 xp_sendmail ?)所以你冒着做不想要的事情的风险…

        3
  •  1
  •   Remus Rusanu    15 年前

    这是一场势不可挡的艰苦战斗。想象一下这样的过程:

    create procedure usp_foo
         @p int
    as
    begin
    if @p=1
      select col1 from table1;
    if @p=2
      select col2 from table2;
    if @p=3
      select col3 from table3;
    end
    
        4
  •  0
  •   AlexS    15 年前

    我不这么认为。

    给定一个查询执行计划,您可以确定要在结果中获取哪些列。但是存储过程通常结合了许多查询,并且可以返回多个结果集。

    但是,如果您知道您正在处理的每个过程都只返回一个结果集,那么您可以“完成工作”,所以这将是您的约定。在这种情况下,您可以尝试分析它的代码,查找select并确定输出列的列表。

        5
  •  0
  •   onupdatecascade    15 年前

    从视图而不是存储过程返回结果的好例子。(这两种方法都有参数,但是视图具有良好的属性,如闭包和可预测结构。)