【问题标题】:Reporting Services Cscading Parameter refreshReporting Services Cscading 参数刷新
【发布时间】:2012-06-29 03:17:56
【问题描述】:

我用谷歌搜索了很多,发现通常无法完成。我在这里遇到了其中一个黑客:

http://www.bp-msbi.com/2011/04/ssrs-cascading-parameters-refresh-solved/

但它在 ssrs 2005 中对我不起作用。只是想知道是否有人在 2005 年尝试过。 或者有没有其他可以尝试的技巧。

根据本文,依赖参数仅在其值被第一个参数中的选择无效时才会刷新。如果我们可以在每次参数更改时使相关参数无效,我们将强制执行完全刷新。一种简单的方法是附加一个值,例如使用 NEWID() T-SQL 函数获得的 GUID。

所以基本上我们想在两个真实参数之间引入一个假参数。这个假参数应该每次都返回新值,因为它后面的存储过程会在每次调用 proc 时向结果集添加一个 guid。所以它会强制完全刷新其他参数。

现在我面临的主要问题是:

设置这个伪参数的默认值。 对于可用的值,伪参数后面的存储过程会运行,并以如下格式返回数据:result1,result2_GUIDFROMSQL

现在看起来如果我要求它从查询中获取默认值,则再次调用相同的存储过程来设置默认值。但是随着存储过程再次运行,新的 guid 出现了,因此无法找到旧值,因此它没有按需要设置。

我只需要找出一种机制,将这个 guid 从引入的参数传递到下一个参数。

这就是我失败的地方。

我的问题可以通过创建一个数据源是这个查询字符串的参数来简单地复制。

select getdate() id, @name nid 

那么在这种情况下如何为这个参数设置一个默认值。

【问题讨论】:

  • 您能否详细说明您要解决的确切问题,也许还引用您链接中的相关位,以便如果链接失效,这个问题本身仍然有意义?
  • 感谢 Jeroen 的关注。我根据您的 cmets 编辑了问题。希望现在更清楚。
  • 感谢您的更新,这应该会有所帮助。我必须承认这个问题仍然有点难以阅读,而且我不太理解这个问题,但也许其他人可以提供帮助?

标签: reporting-services reportingservices-2005


【解决方案1】:

下面我将展示一个详细的场景,然后我将展示基于 Visser 和 Abbi 的答案的示例实现。

假设我有一份报告,其中每一行都是一个项目。一个项目有一个状态列,其值为“进行中”或“完成”,还有一个项目经理列,其值为一个人的姓名。以下是表格中的行:

  • 项目 A(状态 = 进行中,项目经理 = Bob)
  • 项目 B(状态 = 进行中,项目经理 = Tom)
  • 项目 C(状态 = 完成,项目经理 = Jack)
  • 项目 D(状态 = 完成,项目经理 = Tom)
  • 项目 E(状态 = 完成,项目经理 = Jill)

我想在我的报告中有 2 个参数

  1. 显示已完成的项目? - 这是一个布尔参数
    • false 将仅显示“进行中”项目 A 和 B 时
    • true 将显示“正在进行”项目 A 和 B 以及“完成”项目 C、D 和 E 时。
  2. Project Manager - 这是一个多值文本参数,其选项和默认值需要根据它所依赖的 Show Completed Projects? 参数进行更改。
    • 如果 Show Completed Projects? 设置为 false,则只会显示“Bob”和“Tom”选项,因为他们分别是正在进行的项目 Project A 和 B 的项目经理.
    • 如果 Show Completed Projects? 设置为 true,那么除了“Bob”和“Tom”之外,您还会看到“Jack”和“Jill”作为选项,因为它们是分别负责非活动项目 Project C 和 Project E 的项目经理。

现在开始实施:

  1. 显示已完成的项目?参数

  2. 项目经理数据集查询(有关如何生成将根据独立参数更改并强制 SSRS 重新加载默认值的密钥的详细信息,请参阅 Visser 和 Abbi 的答案)

    SELECT 
        [ProjectManager_Key] = 
            pOuterAlias.[ProjectManager_Key] + '_' + 
            CAST(ROW_NUMBER() OVER(ORDER BY pOuterAlias.[ProjectManager_Key] DESC) AS NVARCHAR(MAX)),
        [ProjectManager] =  pOuterAlias.[ProjectManager]
    FROM 
        (
            SELECT 
                [ProjectManager_Key] = 
                    pInnerAlias.ProjectManager + '_' + 
                    CAST(ROW_NUMBER() OVER(ORDER BY pInnerAlias.ProjectManager ASC) AS NVARCHAR(MAX)),
                [ProjectManager] = pInnerAlias.ProjectManager
            FROM 
            (
                SELECT 
                    [ProjectManager] 
                FROM 
                    [dbo].[Project]
                WHERE
                    Status = 'In Progress' OR
                    @ShowCompletedProjects = 1
            ) pInnerAlias
        ) pOuterAlias
    ORDER BY 
        pOuterAlias.[ProjectManager]
    
  3. 项目经理参数

    • 一般

    • 可用值

    • 默认值

  4. 项目数据集

    • 查询

      SELECT 
          *
      FROM 
          [dbo].[Project]
      WHERE
      (
          Status = 'In Progress' OR
          @ShowCompletedProjects = 1
      ) AND
      Project Manager IN (@ProjectManager)
      
    • 参数(请务必注意[@ProjectManager.Label] 部分,这将使其与数据库中实际项目经理值的项目匹配,而不是我们生成的键。

【讨论】:

    【解决方案2】:

    @Abbi 的第二个链接不再有效。现在可以在以下位置找到该文章: http://www.optimusinfo.com/multilevel-cascading-select/

    不幸的是,图像已损坏,没有它们,文章有点不完整。我可以在其移动位置找到一张图片(即使尝试了适当的变化,我也找不到其他图片):http://www.optimusinfo.com/wp-content/uploads/2012/07/Multilevel-Cascading-with-Select-All-18.jpeg

    这为我提供了使该技术发挥作用所需的最后一条线索:当您设置数据集参数属性时,您需要手动指定参数值,例如[@City.Label] 而不是通常的普通旧 [@City](对应于 [@City.Value]。

    这是因为该技术将“值”更改为无法再在数据库中查找的自定义值!因此,您需要使用用户友好、数据库现有的“标签”作为参数。 (可能应该很明显,但是......)如果您了解报告生成器,其余的都是非常标准的。

    另请注意,此链接目前不适用于多值级联参数。然而,它可以很容易地修改为:只需更改参数存储的过程以加入值拆分函数。我从 SQL Server - In clause with a declared variable 给出的 udf_splitvarible 函数改编了我的

    修改相当简单,但我会举个例子。这是来自文章(修复了糟糕的格式)。

    SELECT 
        l11.CompanyName1+'_'+ CAST(row_number() over( order by  l11.CompanyName1 desc) AS VARCHAR(50) )as CompanyName11
        ,l11.CompanyName
    FROM 
    (
        SELECT 
            l1.CompanyName+'_'+ CAST(row_number() over( order by  l1.CompanyName asc) AS VARCHAR(50) )as CompanyName1
            ,l1.CompanyName
        FROM 
        (
            SELECT DISTINCT CompanyName
            FROM Customers
            WHERE City IN(@City)
        )l1
    )l11
    ORDER BY l11.CompanyName ASC
    

    变化:

    SELECT DISTINCT CompanyName
    FROM Customers
    WHERE City IN(@City)
    

    到:

    SELECT DISTINCT CompanyName
    FROM Customers
    INNER JOIN udf_SplitVariable(@City,',') v ON City = v.Value
    

    这也适用于 SQL Server 2008/Report Builder 3。

    我无法理解/应用@borkmark 的回答。这些限制似乎不适用于我的情况。

    【讨论】:

    • 我会欢迎任何人解释为什么双 ASC/DESC 排序是必要的,或者它是否可以被剥离。没有空闲时间花在上面。
    【解决方案3】:

    有一种解决方法可以在所有情况下解决此问题。

    请注意,之前提供的答案以某种方式编写查询参数,以便每次更改其父参数时依赖参数都会更改其值,这适用于某些情况,但并非所有情况。如果从属参数的“可用”值由于另一个参数而改变并且从属参数是可见的,则它可以工作,如果从属参数是隐藏的或内部的,或者如果“可用”值没有因为另一个参数而改变参数,它不起作用。

    万无一失的解决方法是在报表中定义一个自定义函数,并在依赖参数的表达式中调用它。自定义函数将参数(依赖参数所依赖的参数)的值作为参数,并简单地返回其值。即使函数只是获取值并返回它,SSRS 也不会检查代码并假设代码可以做任何事情(生成随机数,从磁盘中提取文件等)。因此,SSRS 每次值变化时都会调用该函数,而不管依赖参数的“可用”值是否变化,也不管依赖参数是可见的、隐藏的还是内部的。

    类似这样的:

    public function returnArg(ByVal TheArg As String) As String
      return TheArg
    end function
    

    假设你有两个参数:

    参数1 参数2

    而 Parameter2 取决于 Parameter1。

    将 Parameter2 的值设置为包含对 Parameter1 的函数调用的表达式,例如:

    =CODE.returnArg(Parameters!Parameter1.Value)
    

    现在在这种情况下 Parameter2 只是显示 Parameter1 中的值,但是这个逻辑可以扩展到更复杂的表达式和多个参数。只要表达式中的每个参数都有 CODE.returnArg(...) 函数调用,SSRS 就会一直刷新值。

    【讨论】:

      【解决方案4】:

      最后我能够解决这个问题。这个链接是一个有用的开始。 http://www.optimusbi.com/2012/07/16/multilevel-cascading-select/

      基本上它的作用是:以某种方式编写参数查询,以便每次更改其父参数时依赖参数都会更改其值。

      查询添加行号,前面带有“_”。因此,每次用户选择其他值时,行号都会发生变化,因此查询结果集也会发生变化。

      然后在使用结果集的时候去掉下划线后面的文字就可以得到真实的代码了。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-09-15
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多