#SQLCoop this month has decided to post on a “something new you found really useful”. So, here is my bit from the Analysis Services world.
Customising Drillthrough
Recently, I have just come across a requirement to make a drillthrough to return better column names. This drillthrough would be generated from an area in the Pivot Table that is connected to SSAS Multidimensional Model. Then, the extension to this requirement is to create a separate drillthrough that filters the dataset to be context aware. As an example, if a user accesses the drillthrough on “Quality Reason” measure for Internet Sales, it should provide all the internet sale transactions that are associated to “Quality Reason” sales.
Luckily the two requirements above are easily solvable if you have Analysis Services Stored Procedure (ASSP) installed. You can download ASSP from Codeplex and also follow the thorough Installation Instructions.
Big thank you to the people involved in the ASSP project: Chris Webb (t | b), Greg Galloway (b), Darren Gosbell (t | b) and team.
Introduction To The Data
In this article, we use Adventure Works dataset (AdventureWorksDW2012 that you can download from CodePlex). We will create a new view that retrieve the Internet Sales Reason and perform counts on the three main reasons for the Sales, such as Quality, Marketing and Promotion. This is a fairly typical request from business.
The view looks like this:
USE AdventureWorksDW2012 GO CREATE VIEW vInternetSalesReason AS WITH SalesReason AS ( SELECT isr.[SalesOrderNumber], MAX(IIF(sr_o.[SalesReasonKey] IS NOT NULL, 1, 0)) SalesReasonQuality, MAX(IIF(sr_p.[SalesReasonKey] IS NOT NULL, 1, 0)) SalesReasonPromotion, MAX(IIF(sr_m.[SalesReasonKey] IS NOT NULL, 1, 0)) SalesReasonMarketing FROM dbo.[FactInternetSalesReason] isr LEFT OUTER JOIN dbo.[DimSalesReason] sr_o ON sr_o.[SalesReasonKey] = isr.[SalesReasonKey] AND sr_o.[SalesReasonReasonType] = 'Other' AND sr_o.[SalesReasonName] = 'Quality' LEFT OUTER JOIN dbo.[DimSalesReason] sr_p ON sr_p.[SalesReasonKey] = isr.[SalesReasonKey] AND sr_p.[SalesReasonReasonType] = 'Promotion' LEFT OUTER JOIN dbo.[DimSalesReason] sr_m ON sr_p.[SalesReasonKey] = isr.[SalesReasonKey] AND sr_p.[SalesReasonReasonType] = 'Marketing' GROUP BY isr.[SalesOrderNumber]) SELECT fis.[SalesOrderNumber], fis.[OrderDateKey], SUM(fis.[SalesAmount]) AS SalesAmount, SUM(fis.[OrderQuantity]) AS OrderQuantity, ISNULL(m.[SalesReasonQuality], 0) AS [SalesReasonQuality], ISNULL(m.[SalesReasonPromotion], 0) AS [SalesReasonPromotion], ISNULL(m.[SalesReasonMarketing], 0) AS [SalesReasonMarketing] FROM dbo.[FactInternetSales] fis LEFT OUTER JOIN SalesReason m ON m.[SalesOrderNumber] = fis.[SalesOrderNumber] GROUP BY fis.[SalesOrderNumber], fis.[OrderDateKey], ISNULL(m.[SalesReasonQuality], 0), ISNULL(m.[SalesReasonPromotion], 0), ISNULL(m.[SalesReasonMarketing], 0)
You can use an existing Multidimensional Analysis Services solution on Adventure Works and add the new view to it; or you could create a fairly simple SSAS solution just like what I have here: SSAS Solution for Sales Reason (zip file).
Nice Headers In Drillthrough
There is a list of fields that we want to retrieve, such as Order Date, Sales Order Number, Sales Amount, Order Quantity, Quality Reason, Promotion Reason and Marketing Reason.
Field Name | Description |
---|---|
Order Date | The date of order of each internet sales transaction |
Sales Order Number | Sales Order Number of the transaction |
Sales Amount | The sales amount of the transaction |
Sales Order Quantity | Total Quantity Ordered in the transaction |
Quantity Reason (1=Y,0=N) | 1 represents that the transaction is ordered for a Quality reason |
Promotion Reason (1=Y,0=N) | 1 represents that the transaction is ordered for a Promotion reason |
Marketing Reason (1=Y,0=N) | 1 represents that the transaction is ordered for a Marketing reason |
The objective is to create a drillthrough with the set of fields above, as illustrated below:
The steps are very easy and are also mentioned on the ASSP CodePlex website. To summarise,
1. Create a New Action. Provide a name (in this instance it is “Drillthrough Internet Sales”
2. Action Target is set to “Cells” with Target Object of “All Cells”.
3. Optionally you can provide Condition where the drillthrough can be accessed from. In this instance, we do not need to provide anything since we want to make the drillthrough accessible from all cells in the Pivot Table.
4. In the Action Content section, choose “Rowset” for the Type.
5. In the Action Expression, use the ASSP.GetCustomDrillthroughMDX function and provide the attributes or measures to be displayed with their new names. Please note that [Sales Amount] measure in the cube has Currency format. As far as I know the currency formatting is not being exposed to the DRILLTHROUGH command (which is what ASSP is generating). For further discussion on formatting, please see here.
ASSP.GetCustomDrillthroughMDX(" NAME([$Date].[Date]) as [Order Date] ,NAME([$Sales Reasons].[Sales Order Number]) as [Sales Order Number] ,[Internet Sales Reason].[Sales Amount] as [Sales Amount] ,[Internet Sales Reason].[Order Quantity] as [Sales Order Quantity] ,[Internet Sales Reason].[Quality Reason] as [Quality Reason (1=Y, 0=N)] ,[Internet Sales Reason].[Promotion Reason] as [Promotion Reason (1=Y, 0=N)] ,[Internet Sales Reason].[Marketing Reason] as [Marketing Reason (1=Y, 0=N)] ")
6. In the Pivot Table, you should be able to access “Show Internet Sales” now, which will display the data.
Context Aware Drillthrough
Another good use case for ASSP is where the drillthrough needs to be context aware. As an example, if a user right clicks on one of the cells under “Quality Reason” for Year 2002, the drillthrough should only return Sales information relating to those that are associated with Quality Reason in 2002.
The steps are similar to the above, except for the Action Expression section, where the ASSP.ExecuteDrillthroughAndFixcolumns function is used.
The Action Expression looks like this:
'call ASSP.ExecuteDrillthroughAndFixcolumns("' + ASSP.GetDefaultDrillthroughMDX( ( IIF ([Measures].CurrentMember.Name = 'Quality Reason', ([Sales Reasons].[Sales Reason Quality].&[1], [Measures].[Quality Reason]), IIF ([Measures].CurrentMember.Name = 'Promotion Reason', ([Sales Reasons].[Sales Reason Promotion].&[1], [Measures].[Promotion Reason]), IIF ([Measures].CurrentMember.Name = 'Marketing Reason', ([Sales Reasons].[Sales Reason Marketing].&[1], [Measures].[Marketing Reason]), ([Sales Reasons].[Sales Reason Quality].&[0], [Measures].[Quality Reason]) ))) ) ) + '")'
Once the above Action is setup, the Drillthrough menu is available from the Additional Action menu. If the user moves the right click on a “Marketing Reason” cell, the caption will change to “Sales made based on Marketing Reason”.
The expected output for the “Sales made based on Quality Reason” looks something like below:
Wrap Up
Analysis Services Stored Procedure (ASSP) is one of the most useful extension for Multidimension project. One of its incredibly useful features is enabling customisation on Drillthrough. In this article, we solve customisation on the columns to be brought by a drillthrough, and context aware drillthrough.
What other interesting learnings do the rest of #SQLCoop peeps have to share?
- Alerts – Who Knew? by Chris Yates
- Change data through CTE’s by Jeffrey Verheul
- Data Models, SQL Server, SQLite, and PowerShell by Mickey Stuewe
What is #SQLCoop? Check out how we start here.
Further Reading
Analysis Services Stored Procedure (ASSP) on CodePlex
Preserve Measure formatting on drill through action from Excel on TechNet Forum
9 Responses
[…] Julie Koesmarno: Context Aware And Customised Drillthrough […]
[…] Context Aware And Customised Drillthrough […]
Hi to all.
Thanks for your useful blog.
I work with SSAS 2008 R2 but i am new of ASAS.
I installed them and i am trying to use.
My goal is to obtain a drilltrough action with:
a measure called [Importo Venduto]
1 hierarchy and an attrbute of a dimension.
(Tessere Clienti )
I created an Action like this specyfing ROWSET ..cells ..All Cells as in your examples..
but i receive an error ..Excel tell me that VENDITE is not a table…
So if i define a rowset i need to specify name table of fact ??? How can i specify a measure of my cube ???
ASSP.GetCustomDrillthroughMDX(
“[Vendite].[Importo Venduto] as [Importo Venduto]
,NAME([$TessereClienti].[Codice Tessera]) as [Codice Tessera]
,NAME([$TessereClienti].[Codice Tipo Tessera]) as [Tipo Tessera]”
)
Regards in advance
Hi Mauro,
Apologies for the delayed reply.
Can you please double check that [Vendite] is a Measure Group? In my earlier example (shown on the picture: https://www.mssqlgirl.com/wp-content/uploads/2014/06/SSAS_Solution_SalesReason.png), I’m referring to [Internet Sales Reason] Measure Group and a few measures underneath it (e.g. [Quality Reason]) for the code below:
ASSP.GetCustomDrillthroughMDX(
"NAME([$Date].[Date]) as [Order Date]
,NAME([$Sales Reasons].[Sales Order Number]) as [Sales Order Number]
,[Internet Sales Reason].[Sales Amount] as [Sales Amount]
,[Internet Sales Reason].[Order Quantity] as [Sales Order Quantity]
,[Internet Sales Reason].[Quality Reason] as [Quality Reason (1=Y, 0=N)]
,[Internet Sales Reason].[Promotion Reason] as [Promotion Reason (1=Y, 0=N)]
,[Internet Sales Reason].[Marketing Reason] as [Marketing Reason (1=Y, 0=N)] ")
If you’d like further information, please feel free to send me an email and I’ll do my best to help you through it.
Hope this helps.
Julie
Hi, do you know if there’s any way to store the drillthrough query result into SQL table or in CSV file somewhere on network shared drive so that another application can use it to process those data further?
Hi Chirag,
Apologies for the delay in getting back to you. I have been away overseas and am just catching up with a few outstanding things.
One way that I could think of is to create a parameterised SSRS report where it can be linked from the drillthrough. So the user can open the SSRS report and save the result as a CSV file.
Have you come up with a solution/strategy for it yet? If so, please do share it here. I’d really appreciate that.
Once again, I apologise for the delay in getting back to you. Hope this helps.
Kind regards,
Julie
Thanks for customise drill though dll.
I have used this in my cube and its working fine, but I am not able to get data more than 10003 rows.
How to increase number of rows in drill through?
I have tried changing the property in Excel, but no luck.
Thanks,
Ankit
Hi Ankit,
Have you tried customizing the MAXROWS of DRILLTHROUGH or the server setting on drilldown’s max rows? Check out DRILLTHROUGH on MSDN.
Let me know how it works.
Thank you,
Julie
Thanks Julie.
I have increased default drill through rows setting in server and it is working fine.
Ankit