Skip to main content
cancel
Showing results for 
Search instead for 
Did you mean: 

Get certified in Microsoft Fabric—for free! For a limited time, get a free DP-600 exam voucher to use by the end of 2024. Register now

Reply
Zirochka
Frequent Visitor

Generate Embed Token For Create Issue

Hello.
I have an issue with getting embed token. I've done what's described in this link (https://powerbi.microsoft.com/en-us/documentation/powerbi-developer-walkthrough-push-data/) and everything works perfectly: datasets creates, tables creates and fills with data without any problems.
I have a task to embed a datasets (not reports) to web page and here I'm getting an error.
I found this page (https://microsoft.github.io/PowerBI-JavaScript/demo/v2-demo/index.html) which shows how embed report/dataset/dashboard/tile will look like. And on this page there is an embed token.
I googled a little and found this page (https://msdn.microsoft.com/library/mt784614.aspx) which describes the looks oh HTTP POST requests. I did the part for datasets. Here is my code example:
 
 
private static void generateEmbedToken()
        {
            // TokenCredentials Initializes a new instance of the
            // Microsoft.Rest.TokenCredentials class with
            // the given 'Bearer' token.
            var credentials = new TokenCredentials(token);
            // Initialize PowerBIClient with credentials
            var powerBIclient = new Microsoft.PowerBI.Api.V2.PowerBIClient(credentials)
            {
                // BaseUri is the api endpoint, default is https://api.powerbi.com
                BaseUri = new Uri("https://api.powerbi.com")
            };
            try
            {
                // Create body where accessLevel = View, datasetId = "" by default
                var requestParameters = new GenerateTokenRequest(TokenAccessLevel.Create, datasetId, true);
                // Generate EmbedToken This function sends the POST message
                //with all parameters and returns the token
                EmbedToken token = powerBIclient.Reports.GenerateTokenForCreate(requestParameters);
                embedToken = token.Token;
            }
            catch (Exception exc)
            {
                Console.WriteLine(exc.ToString());
            }
        }
 
and I got next issue:
 
Microsoft.Rest.HttpOperationException: Operation returned an invalid status code 'NotFound'
at Microsoft.PowerBI.Api.V2.Reports.<GenerateTokenForCreateWithHttpMessagesAsync>d__8.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.PowerBI.Api.V2.ReportsExtensions.<GenerateTokenForCreateAsync>d__7.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at Microsoft.PowerBI.Api.V2.ReportsExtensions.GenerateTokenForCreate(IReports operations, GenerateTokenRequest requestParameters)
at PushDataApp.Program.generateEmbedToken() in C:\Users\PC\Documents\Visual Studio 2017\Projects\PushDataApp\PushDataApp\Program.cs:line 388
 
line 388 here:
 
EmbedToken token = powerBIclient.Reports.GenerateTokenForCreate(requestParameters);
 
I don't know why it's happening.
I got this code from here (https://msdn.microsoft.com/library/mt784614.aspx), but I did some changes for my purposes (because I need dataset and not report).
 
I'll appreciate any help.

 

1 ACCEPTED SOLUTION
Eric_Zhang
Microsoft Employee
Microsoft Employee

@Zirochka

I may doubt that there's some issue with the Power BI API lib, as I've found the token generation functions for reports, dashboards, tiles but not for datasets.

 

powerBIclient.Reports.GenerateTokenxxxxx
powerBIclient.Dashboards.GenerateTokenxxxxx
powerBIclient.Tiles.GenerateTokenxxxxx

So I guess for Datasets, it should be
powerBIclient.Datasets.GenerateTokenxxxxx
Unfortunately, I'm not finding any GenerateTokenxxxxx for datasets

 

Instead of using the API lib, call the REST API directly.

using System;
//Install-Package Newtonsoft.Json 
using Newtonsoft.Json;
using System.Net;
using System.IO;

namespace GenerateEmbeddedToken
{
    class Program
    {
        static void Main(string[] args)
        {
            string EmbedTokenForDataSet = generateEmbedTokenForDataSet("the groupID", "the datasetID", "eyxxxxxxxxxtoken");

            Console.WriteLine(EmbedTokenForDataSet);
            Console.ReadKey();
        }


        private static string generateEmbedTokenForDataSet(string groupID, string datasetID, string accessBearerToken)
        {
            string embedToken = "";
            HttpWebRequest request = System.Net.HttpWebRequest.CreateHttp(String.Format("https://api.powerbi.com/v1.0/myorg/groups/{0}/reports/GenerateToken", groupID));
            //POST web request to create a datasource.
            request.KeepAlive = true;
            request.Method = "POST";
            request.ContentType = "application/json";
             
            //Add token to the request header
            request.Headers.Add("Authorization", String.Format("Bearer {0}", accessBearerToken));

            string PostData = "{"+
                                      "\"accessLevel\": \"Create\","+
                                      "\"datasetId\": \""+datasetID+"\","+
                                      "\"allowSaveAs\": true"+
                                    "}";

            byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(PostData); 

            try
            {
                //Write JSON byte[] into a Stream
                using (Stream writer = request.GetRequestStream())
                {
                    writer.Write(byteArray, 0, byteArray.Length);
                    var response = (HttpWebResponse)request.GetResponse(); 
                    var responseJson = new StreamReader(response.GetResponseStream()).ReadToEnd();
                    dynamic responseString = JsonConvert.DeserializeObject<dynamic>(responseJson.ToString());
                    embedToken = responseString["token"];
                }
            }
            catch (WebException wex)
            {
                if (wex.Response != null)
                {
                    using (var errorResponse = (HttpWebResponse)wex.Response)
                    {
                        using (var reader = new StreamReader(errorResponse.GetResponseStream()))
                        {
                            string errorString = reader.ReadToEnd();
                            dynamic respJson = JsonConvert.DeserializeObject<dynamic>(errorString);
                            Console.WriteLine(respJson.toString());
                            //TODO: use JSON.net to parse this string and look at the error message
                        }
                    }
                }
            }

            return embedToken;
        }
    }
}

 

 

View solution in original post

5 REPLIES 5
Eric_Zhang
Microsoft Employee
Microsoft Employee

@Zirochka

I may doubt that there's some issue with the Power BI API lib, as I've found the token generation functions for reports, dashboards, tiles but not for datasets.

 

powerBIclient.Reports.GenerateTokenxxxxx
powerBIclient.Dashboards.GenerateTokenxxxxx
powerBIclient.Tiles.GenerateTokenxxxxx

So I guess for Datasets, it should be
powerBIclient.Datasets.GenerateTokenxxxxx
Unfortunately, I'm not finding any GenerateTokenxxxxx for datasets

 

Instead of using the API lib, call the REST API directly.

using System;
//Install-Package Newtonsoft.Json 
using Newtonsoft.Json;
using System.Net;
using System.IO;

namespace GenerateEmbeddedToken
{
    class Program
    {
        static void Main(string[] args)
        {
            string EmbedTokenForDataSet = generateEmbedTokenForDataSet("the groupID", "the datasetID", "eyxxxxxxxxxtoken");

            Console.WriteLine(EmbedTokenForDataSet);
            Console.ReadKey();
        }


        private static string generateEmbedTokenForDataSet(string groupID, string datasetID, string accessBearerToken)
        {
            string embedToken = "";
            HttpWebRequest request = System.Net.HttpWebRequest.CreateHttp(String.Format("https://api.powerbi.com/v1.0/myorg/groups/{0}/reports/GenerateToken", groupID));
            //POST web request to create a datasource.
            request.KeepAlive = true;
            request.Method = "POST";
            request.ContentType = "application/json";
             
            //Add token to the request header
            request.Headers.Add("Authorization", String.Format("Bearer {0}", accessBearerToken));

            string PostData = "{"+
                                      "\"accessLevel\": \"Create\","+
                                      "\"datasetId\": \""+datasetID+"\","+
                                      "\"allowSaveAs\": true"+
                                    "}";

            byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(PostData); 

            try
            {
                //Write JSON byte[] into a Stream
                using (Stream writer = request.GetRequestStream())
                {
                    writer.Write(byteArray, 0, byteArray.Length);
                    var response = (HttpWebResponse)request.GetResponse(); 
                    var responseJson = new StreamReader(response.GetResponseStream()).ReadToEnd();
                    dynamic responseString = JsonConvert.DeserializeObject<dynamic>(responseJson.ToString());
                    embedToken = responseString["token"];
                }
            }
            catch (WebException wex)
            {
                if (wex.Response != null)
                {
                    using (var errorResponse = (HttpWebResponse)wex.Response)
                    {
                        using (var reader = new StreamReader(errorResponse.GetResponseStream()))
                        {
                            string errorString = reader.ReadToEnd();
                            dynamic respJson = JsonConvert.DeserializeObject<dynamic>(errorString);
                            Console.WriteLine(respJson.toString());
                            //TODO: use JSON.net to parse this string and look at the error message
                        }
                    }
                }
            }

            return embedToken;
        }
    }
}

 

 

I tried to use your function, but it didn't help.

 

using System;
//Install-Package Newtonsoft.Json 
using Newtonsoft.Json;
using System.Net;
using System.IO;

namespace GenerateEmbeddedToken
{
    class Program
    {
        static void Main(string[] args)
        {
            string EmbedTokenForDataSet = generateEmbedTokenForDataSet("the groupID", "the datasetID", "eyxxxxxxxxxtoken");

            Console.WriteLine(EmbedTokenForDataSet);
            Console.ReadKey();
        }


        private static string generateEmbedTokenForDataSet(string groupID, string datasetID, string accessBearerToken)
        {
            string embedToken = "";
            HttpWebRequest request = System.Net.HttpWebRequest.CreateHttp(String.Format("https://api.powerbi.com/v1.0/myorg/groups/{0}/reports/GenerateToken", groupID));
            //POST web request to create a datasource.
            request.KeepAlive = true;
            request.Method = "POST";
            request.ContentType = "application/json";
             
            //Add token to the request header
            request.Headers.Add("Authorization", String.Format("Bearer {0}", accessBearerToken));

            string PostData = "{"+
                                      "\"accessLevel\": \"Create\","+
                                      "\"datasetId\": \""+datasetID+"\","+
                                      "\"allowSaveAs\": true"+
                                    "}";

            byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(PostData); 

            try
            {
                //Write JSON byte[] into a Stream
                using (Stream writer = request.GetRequestStream())
                {
                    writer.Write(byteArray, 0, byteArray.Length);
                    var response = (HttpWebResponse)request.GetResponse(); 
                    var responseJson = new StreamReader(response.GetResponseStream()).ReadToEnd();
                    dynamic responseString = JsonConvert.DeserializeObject<dynamic>(responseJson.ToString());
                    embedToken = responseString["token"];
                }
            }
            catch (WebException wex)
            {
                if (wex.Response != null)
                {
                    using (var errorResponse = (HttpWebResponse)wex.Response)
                    {
                        using (var reader = new StreamReader(errorResponse.GetResponseStream()))
                        {
                            string errorString = reader.ReadToEnd();
                            dynamic respJson = JsonConvert.DeserializeObject<dynamic>(errorString);
                            Console.WriteLine(respJson.toString());
                            //TODO: use JSON.net to parse this string and look at the error message
                        }
                    }
                }
            }

            return embedToken;
        }
    }
}

On line: 

using (Stream writer = request.GetRequestStream())

program thinks for approximately 30 seconds and then goes to catch block.

In catch block if statement is false (so, Response == null) and program just goes out from catch.

That's all.

 

I still don't understant why it happens because I just use this guide for POST requests (https://msdn.microsoft.com/library/mt784614.aspx). And it's up to date (Updated: July 21, 2017), so, I don't understand.

 

I'll appresiate any help.

 


@Zirochka wrote:

I tried to use your function, but it didn't help.

 

using System;
//Install-Package Newtonsoft.Json 
using Newtonsoft.Json;
using System.Net;
using System.IO;

namespace GenerateEmbeddedToken
{
    class Program
    {
        static void Main(string[] args)
        {
            string EmbedTokenForDataSet = generateEmbedTokenForDataSet("the groupID", "the datasetID", "eyxxxxxxxxxtoken");

            Console.WriteLine(EmbedTokenForDataSet);
            Console.ReadKey();
        }


        private static string generateEmbedTokenForDataSet(string groupID, string datasetID, string accessBearerToken)
        {
            string embedToken = "";
            HttpWebRequest request = System.Net.HttpWebRequest.CreateHttp(String.Format("https://api.powerbi.com/v1.0/myorg/groups/{0}/reports/GenerateToken", groupID));
            //POST web request to create a datasource.
            request.KeepAlive = true;
            request.Method = "POST";
            request.ContentType = "application/json";
             
            //Add token to the request header
            request.Headers.Add("Authorization", String.Format("Bearer {0}", accessBearerToken));

            string PostData = "{"+
                                      "\"accessLevel\": \"Create\","+
                                      "\"datasetId\": \""+datasetID+"\","+
                                      "\"allowSaveAs\": true"+
                                    "}";

            byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(PostData); 

            try
            {
                //Write JSON byte[] into a Stream
                using (Stream writer = request.GetRequestStream())
                {
                    writer.Write(byteArray, 0, byteArray.Length);
                    var response = (HttpWebResponse)request.GetResponse(); 
                    var responseJson = new StreamReader(response.GetResponseStream()).ReadToEnd();
                    dynamic responseString = JsonConvert.DeserializeObject<dynamic>(responseJson.ToString());
                    embedToken = responseString["token"];
                }
            }
            catch (WebException wex)
            {
                if (wex.Response != null)
                {
                    using (var errorResponse = (HttpWebResponse)wex.Response)
                    {
                        using (var reader = new StreamReader(errorResponse.GetResponseStream()))
                        {
                            string errorString = reader.ReadToEnd();
                            dynamic respJson = JsonConvert.DeserializeObject<dynamic>(errorString);
                            Console.WriteLine(respJson.toString());
                            //TODO: use JSON.net to parse this string and look at the error message
                        }
                    }
                }
            }

            return embedToken;
        }
    }
}

On line: 

using (Stream writer = request.GetRequestStream())

program thinks for approximately 30 seconds and then goes to catch block.

In catch block if statement is false (so, Response == null) and program just goes out from catch.

That's all.

 

I still don't understant why it happens because I just use this guide for POST requests (https://msdn.microsoft.com/library/mt784614.aspx). And it's up to date (Updated: July 21, 2017), so, I don't understand.

 

I'll appresiate any help.

 


@Zirochka

Have you got any API console tool for testing purpose? If not, I'd suggest using POSTMAN.

So beforing coding in C#, can you test this GenerateToken in postman? For any issue, feel free to post.

Thanks for this Postman. It's really useful tool. Thanks a lot.

I tried to sent in this postman post request (from here https://msdn.microsoft.com/library/mt784614.aspx for dataset) and I got an answer with embed token. I checked this token here (https://microsoft.github.io/PowerBI-JavaScript/demo/v2-demo/index.html) and it works. Dataset loads to this example.

 

But I don't understand why from C# it doesn't works.

In my code I have another POST requests: when I create dataset (first POST) and when I push data to the dataset (second POST). And they works perfectly (I checked hundred times). But this (when I get embed token) POST (it's third POST in my code) does't work. And I found out that API works fine (thanks to postman).

Do you have any idea?

 

I'll appreciate any help.


@Zirochka wrote:

Thanks for this Postman. It's really useful tool. Thanks a lot.

I tried to sent in this postman post request (from here https://msdn.microsoft.com/library/mt784614.aspx for dataset) and I got an answer with embed token. I checked this token here (https://microsoft.github.io/PowerBI-JavaScript/demo/v2-demo/index.html) and it works. Dataset loads to this example.

 

But I don't understand why from C# it doesn't works.

In my code I have another POST requests: when I create dataset (first POST) and when I push data to the dataset (second POST). And they works perfectly (I checked hundred times). But this (when I get embed token) POST (it's third POST in my code) does't work. And I found out that API works fine (thanks to postman).

Do you have any idea?

 

I'll appreciate any help.


@Zirochka

I'd say the C# code in my first indeed works as long as the groupid and datesetid are correct. In your case, as the generate embedtoken POST request works in POSTMAN, so I think you could debug your code and figure it out.

 

As to your "another POST requests", this is one issue as I tested in this thread and you can use the workaround from orginal poster.

Helpful resources

Announcements
November Carousel

Fabric Community Update - November 2024

Find out what's new and trending in the Fabric Community.

Live Sessions with Fabric DB

Be one of the first to start using Fabric Databases

Starting December 3, join live sessions with database experts and the Fabric product team to learn just how easy it is to get started.

Las Vegas 2025

Join us at the Microsoft Fabric Community Conference

March 31 - April 2, 2025, in Las Vegas, Nevada. Use code MSCUST for a $150 discount! Early Bird pricing ends December 9th.

Nov PBI Update Carousel

Power BI Monthly Update - November 2024

Check out the November 2024 Power BI update to learn about new features.