Forum Discussion
Filter values from one table in another without relationship DAX
- 2 years ago
Hi talespin Please see the solution below. As you mentioned earlier creating a measure using the formula wasn't the right way and creating a role and applying RLS was the right approach. Since no one was able to provide a RLS DAX query for this requirement we have itself come up with a DAX solution to achieve the requirement. Please see below.
1.) All semi-colon values in DIM_ACT columns must be replaced by "|" symbol for this formula to work. Either change the source data or create a calculated column to replace ";" with "|".
2.) Eliminated DIM_USER table and brought in EMAIL ID column to DIM_ACT table itself.
3.) There is only 1 record for a single user in DIM_ACT under a single GROUP.
4.) Create a ROLE in Manage roles and apply below DAX under FACT_ACTUALS table. Using the below DAX , when the user logs in he will be able to see only the values separated using "|" in the respective columns of DIM_ACT and when ALL is present in any of the columns, he will be able to see all the values available in FACT ACTUALS./* FILTER DIM_ACT TO FETCH THE RECORD HAVING ONLY THE LOGGED IN USER EMAIL ID & VALUES ASSIGNED UNDER LEVEL COLUMN */
&& [LEVEL]
IN(
VAR _LEV =
MAXX (
FILTER
( 'DIM_ACT',
[EMAIL ID] = USERPRINCIPALNAME () ),
'DIM_ACT'[_LEV]
)/* TAKE THE PATH LENGTH OF LEVEL COLUMN. THIS IS DONE BECAUSE THERE COULD BE N NUMBER OF VALUES SEPARATED BY | SYMBOL IN DIM_ACT TABLE
AND WE NEED TO SEPARATE THEM AS INDIVIDUAL VALUES */VAR _LEVLEN = PATHLENGTH (_LEV )
/* CREATE A VIRTUAL TABLE WITH COLUMN NAME LEVLIST HAVING THE LIST OF LEVEL COLUMN VALUES */
VAR _LEVTABLE = ADDCOLUMNS ( GENERATESERIES ( 1, _LEVLEN ), "LEVLIST", PATHITEM ( _LEV, [Value] ) )
/* SELECT THE COLUMN VALUES AND PASS THE VALUES TO LIST */
VAR _LEV_list = SELECTCOLUMNS ( _LEVTABLE, "LEVEL", [LEVLIST] )
/* ADD ALL THE LEVEL VALUES FROM FACT_ACTUALS. THIS IS FOR A USER WHO HAS VALUE "ALL" ASSIGNED TO HIM UNDER LEVEL IN DIM_ACT TABLE */
VAR _ALLFACTLEV = ADDCOLUMNS ( VALUES ( FACT_ACTUALS[LEVEL] ), "ALL", "ALL" )
/* RETURN ONLY THE VALUES ASSIGNED IN LEVEL COLUMN IN DIM_ACT FROM FACT TABLE FOR LOGGED IN USER OR RETURN ALL THE VALUES FROM FACT TABLE WHEN THE LEVEL COLUMN IS PROVIDED AS ALL */
RETURN
SELECTCOLUMNS
(
FILTER ( _ALLFACTLEV, [LEVEL] IN _LEV_LIST || [ALL] IN _LEV_LIST ),
[LEVEL]
)
)
&& [LABEL]
IN (
VAR _LAB =
MAXX (
FILTER ( 'DIM_ACT', [EMAIL ID] = USERPRINCIPALNAME () ),
'DIM_ACT'[LABEL]
)
VAR _LABLEN = PATHLENGTH ( _LAB )
VAR _LABTABLE =
ADDCOLUMNS ( GENERATESERIES ( 1, _LABLEN ), "LABLIST", PATHITEM ( _LAB, [Value] ) )
VAR _LAB_LIST =
SELECTCOLUMNS ( _LABTABLE, "LABEL", [LABLIST] )
VAR _ALLFACTLAB =
ADDCOLUMNS ( VALUES ( FACT_ACTUALS[LABEL] ), "ALL", "ALL" )
RETURN
SELECTCOLUMNS (
FILTER ( _ALLFACTLAB, [LABEL] IN _LAB_LIST || [ALL] IN _LAB_LIST ),
[LABEL]
)
)&& [SOURCE] IN ------ Similarly repeat the above code for other columns in DIM_ACT
Thank you for your immediate reply. However when I tried to create a new measure using the above query it says "Multiple columns cannot be converted to scalar value". I think its because my DIM_ACT contains multiple rows with same ID & LEVEL. It works while creating a New Table but when I tried to include additional filter using USERPRINCIPALNAME(), it throws below error. Could you pls suggest a way around ?
If your DIM_ACT table contains multiple rows with the same ID and LEVEL combination, it can cause issues when trying to create a measure that expects a scalar value. In such cases, you might need to aggregate or summarize the data to ensure that a single value is returned for each combination of ID and LEVEL.
Here's how you can modify the DAX formula to aggregate the data from DIM_ACT before filtering FACT_ACTUALS:
Filtered_FACT_ACTUALS =
FILTER(
FACT_ACTUALS,
COUNTROWS(
SUMMARIZE(
DIM_ACT,
DIM_ACT[ID],
DIM_ACT[LEVEL],
DIM_ACT[LABEL],
DIM_ACT[SOURCE],
DIM_ACT[CC],
DIM_ACT[ORG]
)
& FILTER(
DIM_ACT,
DIM_ACT[LEVEL] = FACT_ACTUALS[LEVEL] &&
DIM_ACT[LABEL] = FACT_ACTUALS[LABEL] &&
DIM_ACT[SOURCE] = FACT_ACTUALS[SOURCE] &&
DIM_ACT[CC] = FACT_ACTUALS[CC] &&
DIM_ACT[ORG] = FACT_ACTUALS[ORG] &&
DIM_ACT[USER] = USERPRINCIPALNAME()
)
) > 0
)
In this modified formula, we use the SUMMARIZE function to aggregate the data from DIM_ACT based on the columns ID, LEVEL, LABEL, SOURCE, CC, and ORG. This helps in ensuring that only unique combinations of these columns are considered.
Then, we apply the filter conditions to both the aggregated data and the original DIM_ACT table. Additionally, I've included a filter condition based on the USERPRINCIPALNAME() function to filter rows based on the logged-in user.
This approach should help you avoid the "Multiple columns cannot be converted to scalar value" error and apply additional filtering based on the logged-in user.
If this post helps, then please consider Accepting it as the solution to help the other members find it more quickly.
In case there is still a problem, please feel free and explain your issue in detail, It will be my pleasure to assist you in any way I can.