Power BI 嵌入角色,允许行级安全

时间:2021-05-13 20:36:31

标签: c# powerbi powerbi-embedded

我已经从 Github 为您的客户实现了 Microsoft Example for Embed,它运行良好。 Link

我现在正在扩展它,有文章显示使用 API 的 V1 和 V2,两者都导致相同的错误:

<块引用>

操作返回了无效的状态代码“BadRequest”
在 Microsoft.PowerBI.Api.ReportsOperations.GenerateTokenInGroupWithHttpMessagesAsync(Guid groupId, Guid reportId, GenerateTokenRequest requestParameters, Dictionary`2 customHeaders, CancellationToken 取消Token)

        [HttpGet]
    public async Task<string> GetEmbedInfo()
    {
        try
        {
            // Validate whether all the required configurations are provided in appsettings.json
            string configValidationResult = ConfigValidatorService.ValidateConfig(azureAd, powerBI);
            if (configValidationResult != null)
            {
                HttpContext.Response.StatusCode = 400;
                return configValidationResult;
            }

            EmbedParams embedParams = await pbiEmbedService.GetEmbedParams(new Guid(powerBI.Value.WorkspaceId), new Guid(powerBI.Value.ReportId));
            //EmbedParams embedParams = await pbiEmbedService.GetEmbedToken4(new Guid(powerBI.Value.WorkspaceId), new Guid(powerBI.Value.ReportId));
            return JsonSerializer.Serialize<EmbedParams>(embedParams);
        }
        catch (Exception ex)
        {
            HttpContext.Response.StatusCode = 500;
            return ex.Message + "\n\n" + ex.StackTrace;
        }
    }

上面的代码被调用并根据演示。

        public async Task<EmbedParams> GetEmbedParams(Guid workspaceId, Guid reportId, [Optional] Guid additionalDatasetId)
    {
        PowerBIClient pbiClient = this.GetPowerBIClient();

        // Get report info
        var pbiReport = await pbiClient.Reports.GetReportInGroupAsync(workspaceId, reportId);
        //var generateTokenRequestParameters = new GenerateTokenRequest("View", null, identities: new List<EffectiveIdentity> { new EffectiveIdentity(username: "**************", roles: new List<string> { "****", "****" }, datasets: new List<string> { "datasetId" }) });

        //var tokenResponse = pbiClient.Reports.GenerateTokenInGroupAsync("groupId", "reportId", generateTokenRequestParameters);

        // Create list of datasets
        var datasetIds = new List<Guid>();

        // Add dataset associated to the report
        datasetIds.Add(Guid.Parse(pbiReport.DatasetId));

        // Append additional dataset to the list to achieve dynamic binding later
        if (additionalDatasetId != Guid.Empty)
        {
            datasetIds.Add(additionalDatasetId);
        }

        // Add report data for embedding
        var embedReports = new List<EmbedReport>() {
            new EmbedReport
            {
                ReportId = pbiReport.Id, ReportName = pbiReport.Name, EmbedUrl = pbiReport.EmbedUrl
            }
        };

        // Get Embed token multiple resources
        var embedToken = await GetEmbedToken4(workspaceId, reportId);

        // Capture embed params
        var embedParams = new EmbedParams
        {
            EmbedReport = embedReports,
            Type = "Report",
            EmbedToken = embedToken
        };

        return embedParams;
    }

上面的代码是每个演示,除了一行,它调用了下一个方法:

var embedToken = await GetEmbedToken4(workspaceId, reportId);

        public EmbedToken GetEmbedToken(Guid reportId, IList<Guid> datasetIds, [Optional] Guid targetWorkspaceId)
    {
        PowerBIClient pbiClient = this.GetPowerBIClient();

        // Create a request for getting Embed token 
        // This method works only with new Power BI V2 workspace experience
        var tokenRequest = new GenerateTokenRequestV2(

            reports: new List<GenerateTokenRequestV2Report>() { new GenerateTokenRequestV2Report(reportId) },

            datasets: datasetIds.Select(datasetId => new GenerateTokenRequestV2Dataset(datasetId.ToString())).ToList(),

            targetWorkspaces: targetWorkspaceId != Guid.Empty ? new List<GenerateTokenRequestV2TargetWorkspace>() { new GenerateTokenRequestV2TargetWorkspace(targetWorkspaceId) } : null


        );

        // Generate Embed token
        var embedToken = pbiClient.EmbedToken.GenerateToken(tokenRequest);

        return embedToken;
    }

以上代码是每个示例,没有传入角色或 EffectiveIdentity。这有效。

        public async Task<EmbedToken> GetEmbedToken4(Guid workspaceId, Guid reportId, string accessLevel = "view")
    {
        PowerBIClient pbiClient = this.GetPowerBIClient();

        var pbiReport = pbiClient.Reports.GetReportInGroup(workspaceId, reportId);

        string dataSet = pbiReport.DatasetId.ToString();

        // Generate token request for RDL Report
        var generateTokenRequestParameters = new GenerateTokenRequest(
            accessLevel: accessLevel,
            datasetId: dataSet,
            identities: new List<EffectiveIdentity> { new EffectiveIdentity(username: "******", roles: new List<string> { "********" }) }
            

        );

        // Generate Embed token
        var embedToken = pbiClient.Reports.GenerateTokenInGroup(workspaceId, reportId, generateTokenRequestParameters);

        return embedToken;
    }

这是返回带有角色和有效身份的令牌的方法。这会导致错误,但没有消息或有用的反馈。

1 个答案:

答案 0 :(得分:0)

好的,经过一夜的大量研究,Bad Request 响应确实隐藏了一条未在浏览器中显示的英文消息。调试器没有导致错误的部分的符号,但是当实际 API 响应请求时,我通过使用 Fiddler 代理找到了它。在我的情况下,如果您发送一个 ID 来启用 RLS,但服务器上的报告版本没有它,这不会忽略它,它拒绝为任何东西提供令牌。通过阅读许多帖子,当 API 本身的实际响应(不是包或示例使用的示例代码提供)时,错误请求只是一个糟糕的错误消息。希望这对未来的人有所帮助。

相关问题