I have a users dimension, which represents the hierarchy of many shops. For instance, shops are split into Country - > Region -> Town/Village - > Actual Shop. So when you look at it from a hierarchy perspective, it is Level1, Level2, Level3, Level4 etc.
Now the strange thing is, if I execute the MDX query and filtering in the WHERE clause, by the hierarchy, for a specific user no data displays. However, if I execute the same exact MDX not filtering by the hierarchy, but filtering by the attributes, records are shown.
It is important to mention that the user hierarchy [UserIdHierarchy] contains a hierarchy of the following members
[UserLevel1Id]
[UserLevel2Id]
[UserLevel3Id]
[UserLevel4Id]
[UserLevel5Id]
These are the 2 cases, which should return exactly the same results...
Where clause filtering with user hierarchy :
where
(
DESCENDANTS([Dim User].[UserIdHierarchy].&[#12345],0, self)
)
Where clause filtering without user hierarchy :
where
(
DESCENDANTS([Dim User].[UserLevel3Id].&[#12345],0, self)
)
Why don't both of the filters, bring up the same data for this particular user?
The reason was that the User hierarchy was using historical approach. Therefore, when a user had more then one hierarchy (as shown below), for some strange reason the MDX got messed up and stood with the first item in the dimension hierarchy. Below, I am showing 3 different setups of a user, after his registration into the system. To fix my problem, instead of just doing
[Dim User].[UserIdHierarchy].&[#12345]
I'm filtering in the where clause all user members, i.e.
{[Dim User].[UserIdHierarchy].[UserLevel1Id].&[#12345],
[Dim User].[UserIdHierarchy].[UserLevel2Id].&[#12345],
[Dim User].[UserIdHierarchy].[UserLevel3Id].&[#12345]}
Then the actual filtering is done on the FACT data. This way I include all data for all members in the user hierarchy which match my user - which in this case was #12345.
Related
I found this little code where it dynamically calculates TOTALs for all Dimension/Hierarchy I want.
This is close to what I need but will not work for Dimensions that have different number of Hierarchy Levels (Attribute Hierarchy). Current Code only works if there is only one Attribute Hierarchy because of CurrentMember.Parent. I could use CurrentMember.Parent.Parent for Dimension.Hierarchy that have two levels and so on but would not work for the the ones with only one Attribute Hierarchy (Level).
CALCULATE;
CREATE MEMBER CURRENTCUBE.[Measures].[Total On Hand Amount]
AS ([Measures].[On Hand Amount],Axis(1).Item(0).Item(0).Dimension.CurrentMember.Parent),
FORMAT_STRING = "#,#",
VISIBLE = 1 ;
I would like to make this MDX code work for any Dimension.Hierarchy regardless of number of Attribute Hierarchy (Level/s).
Any help is appreciated!!
You can use the ancestors function instead of parent. It takes a dimension parameter and a second parameter which shows how many levels you want to get (how deep in the tree to go). So if you know how many levels your dimension has you can use something like:
Ancestors(Axis(1).Item(0).Item(0).Dimension.CurrentMember, 5)
Instead of a number you can also add a dimension level as a second parameter. Then it will go as deep as the dimension level specified - so if you add the root dimension level it should get to there
(Axis(1).Item(0).Item(0).Dimension.Levels(0).Item(0), [Measures].[On Hand Amount])
Above gave me the correct answer, total for a measure for dynamic selection of any dimension but this MDX calculation would not work from PowerBI(DAX) report, which is merely PowerBI's limitation.
I got the TOTAL working now with this -
SCOPE(DESCENDANTS([Warehouses].[Warehouses],,AFTER));
[Measures].[Total On Hand Amount] = (ROOT([Warehouses]),[Measures].[On Hand Amount]);
END SCOPE;
I just have to repeat this SCOPE for each [Dimension].[Hierarchy] in the cube to make the TOTAL work for any selection including multiple dimensions from Power BI. It does not have dynamic functionality like Axis() did, but it yields the result I needed.
Hope this would help someone else too!!
I am on an MDX adventure and I'm at a point where I need to ask some questions.
I have a very basic dimension named Car. The attributes which comprise Car are as follows-
-Manufacturer
-Make
-Color
-Year
My fact table contains a sales measure ([Measures].[Sales]). I would like to know , without explicitly defining a user hierarchy, how to sum the sales from
a specific group in this hierarchy
For example, I want to sum the sales of all red Trucks made in 2002. My attempt errors out-
sum([Cars].[Make].[Make].&[Truck]&[Red]&[2002], [Measures].[Sales])
How can I navigate the attribute hierarchy in this way? I will be browsing the cube in excel
Thanks
If you open an mdx query in SSMS and drag a member from one of your attribute hierarchies into the query pain you will see the full name.
You definitely cannot chain hierarchies like this ...].&[Truck]&[Red]&[2002]
Each full name will likely be similar to what MrHappyHead has detailed but usually the attribute name is repeated e.g. for Make:
[Cars].[Make].[Make].&[Truck]
MrHappyHead have wrapped it all in the Sum function but this is not required - just wrap the coordinates in braces and a tuple is then formed which will point to the required area of the cube:
(
[Cars].[Make].[Make].&[Truck],
[Cars].[Color].[Color].&[Red],
[Cars].[Year].[Year].&[2002],
[Measures].[sales]
)
note: square brackets are pretty standard in mdx.
Is it something like:
Sum(
Cars.make.&[truck],
Cars.color.&[red],
Cars.year.[2002],
Measures.sales
)
How to hide measure or a scope if user choose certain dimension or go to certain dimension hierarchy level?
Thanks.
Try something like this in your MDX script:
FREEZE([Measures].[My Measure], [Product].[Subcategory].[All]);
([Measures].[My Measure], [Product].[Product].Members, [Product].[Subcategory].[Subcategory].Members) = null;
Freeze ensures the next statement won't null out the category level totals. The next statement bulls out that measure for the whole product dimension up to the subcategory totals but not above.
Note this is fine for nulling out meaningless numbers but isn't a security feature. A savvy user could do a drillthrough command to get the product level numbers. Or a savvy user could connect in a special way and clear the whole MDX script for his session so he sees the detailed product data.
For a more secure approach:
If you can null out product data for all measures then setup role based security. In dimension data security only grant access to member Subcategory.All only but uncheck visual totals on the advanced tab so that the subcategory grand total is the real total.
Or setup a second slimmed down Product dimension that only has the top levels not the detailed product levels. Then only tie that dimension to this measure group.
Or create a second measure group that does a group by in SQL and joins to the Product dimension only at the Category level. Thus there is no detailed data only rollups. Then with security control whether a used sees the detailed measures or the summary measures.
On measure properties you can set set visible property to false for the measure you want to hide. Another option is to use perspective and choose again what you want to hide or not.
This question uses the parent-child schema enclosed here.
I want to restrict access for a user on the 'dim (all)' hierarchy to view all the data at a certain level and below, but not the data above this member. For example, view 'Europe' and below this level, but I not the parent 'World'.
I managed to make a role that gives access to Europe and below, using the formula:
{[dim (ALL)].[Hierarchy].[ Level - 1].&[3].descendants}
and default member:
[dim (ALL)].[Hierarchy].[ Level - 1].&[3]
and apply to celss = Yes
But using this role, I still can see the World:
select [Measures].[value] on 0
, [dim (ALL)].[Hierarchy].allmembers on 1
from [cube]
result:
What do I need to do to 'redefine' the 'root' to 'Europe', if it is possible at all?
Sorry, it's currently not possible with security to convert a sub-tree into a tree. When allowing a member you do it for all ancestors.
In your example, if you allow [Europe] you allow [World]
I am running Analysis Services 2008 R2 and have come across some behavior that I really do not understand and I can't seem to get to the bottom of it. I have a dimension called Segment which is a simple Parent-child dimension where only one of the four top-level members has any children. This one member, has two children. Only leaf nodes have any values.
In the dimension I have used AttributeAllMemberName to allow "All Segments" to be used to refer to the top-level members. There are three dimensions used in the cube: Segment, Country and Year.
When I run:
SELECT {{Descendants([Country].[Global],, SELF_BEFORE_AFTER)}} ON ROWS,
{[Segment].[All Segments].children}*{[Measures].[Volume tonnes]} ON COLUMNS
FROM [Market]
WHERE [Year].[2012]
I see all members on the columns but the one node that has children has an empty column. My understanding is that "children" should show me only one level not two. If, on the other hand I run
SELECT {{Descendants([Country].[Global],, SELF_BEFORE_AFTER)}} ON ROWS,
{[Segment].[(all)].[All Segments].children}*{[Measures].[Volume tonnes]} ON COLUMNS
FROM [Market]
WHERE [Year].[2012]
I see exactly what I would expect; the four top-level children with correctly aggregated values for the one child that has its own children. No grand-children are shown. In either case the right number of rows are displayed.
The only difference between the two queries is that the "[(all)]" level has been explicitly listed in the second query. Given that the "all" member is defined as the only member of the "(all)" level set, these two queries should return the same values but they don't. I must be missing something in the dimension config, but what? Can someone point me in the right direction to fix this? I need the query to work properly without having to use "[(all)]".
To stop this post becoming too bloated, I have posted some screen-grabs of BIDS to my own website to show the configuration of the dimension. There are three attributes and the dimension itself that require configuration but I can only post two links so have linked them all in from this page: http://coolwire.co.uk/share/BIDS.html
The Hierarchy and the Ordering are related to the Key by rigid attribute-relationships.
It all looks okay to me but the problem must be in here somewhere.