Git Product home page Git Product logo

akshay5995 / powerbi-report-component Goto Github PK

View Code? Open in Web Editor NEW
53.0 7.0 28.0 3.28 MB

Easily embed your Microsoft PowerBI Report, Dashbord or Tile in your React App

Home Page: http://akshay5995.github.io/powerbi-report-component

License: MIT License

JavaScript 76.21% HTML 0.49% CSS 1.48% TypeScript 21.82%
powerbi-report dashboard react props filter reports embed fullscreen powerbi powerbi-embedded powerbi-client tile microsoft-powerbi-report report-visuals

powerbi-report-component's Introduction

PowerBI Report Component

downloads license vulnerabilities bundlephobia

It's a minimalistic React component for embedding a Microsoft PowerBI report, dashboard or tile into your React application.

Installation

npm i powerbi-report-component

Usage for Report

import React, {Component} from 'react';
import { Report } from 'powerbi-report-component';

class MyComponent extends Component {
  constructor(props) {
    super(props);
    this.report = null; // to store the loaded report's object to perform operations like print, full screen etc..
  }
  ...
  handleDataSelected = (data) => {
    // will be called when some chart or data element in your report clicked
  }

  handleReportLoad = (report) => {
    // will be called when report loads:
    // - scripts and data received from server, visuals are rendered on the browser
    // - flickering Power BI logo stops appearing but report is not fully ready to be consumed

    this.report = report; // get the report object from callback and store it.(optional)
  }

  handleReportRender = (report) => {
    // will be called when report renders:
    // - visuals finish rendering
    // - report is fully visible and ready for consumption

    this.report = report; // get the report object from callback and store it.(optional)
  }

  handlePageChange = (data) => {
    // will be called when pages in your report changes
  }

  handleTileClicked = (data) => {
    console.log('Data from tile', data);
  }

  render() {
    const reportStyle = {
        // style object for report component
    };
    const extraSettings = {
            filterPaneEnabled: false, //true
            navContentPaneEnabled: false, //true
            hideErrors: false // Use this *only* when you want to override error experience i.e, use onError
            // ... more custom settings
    };
    return (
    <div className="root">
        <Report
            tokenType="Embed" // "Aad"
            accessToken="" // accessToken goes here
            embedUrl="" // embedUrl goes here
            embedId="" // report or dashboard Id goes here
            pageName="" // set as current page of the report. Name to be obtained from the original report URL
            reportMode="View" // open report in a particular mode View/Edit/Create
            datasetId={datasetId} // required for reportMode = "Create" and optional for dynamic databinding in `report` on `View` mode
            groupId={groupId} // optional. Used when reportMode = "Create" and to chose the target workspace when the dataset is shared. 
            extraSettings={extraSettings}
            permissions="All" // View, For "Edit" mode permissions should be "All"
            style={reportStyle}
            onLoad={this.handleReportLoad}
            onRender={this.handleReportRender} // not allowed in "Create" mode
            onSelectData={this.handleDataSelected}
            onPageChange={this.handlePageChange}
            onTileClicked={this.handleTileClicked}
            onSave={this.handleReportSave} // works for "Edit" and "Create"
        />
    </div>
    );
  }
}

Visit here for more details on creating reports with shared dataset

Usage for Dashboard

import { Dashboard } from 'powerbi-report-component';

// inside render
<Dashboard
  tokenType={tokenType}
  accessToken={accessToken}
  embedUrl={embedUrl}
  embedId={embedId}
  style={style} // style object for dashboard component
  pageView={pageView} // 'fitToWidth' (default) , 'oneColumn', 'actualSize'
  onLoad={(dashboard) => {
    console.log('Dashboard Loaded!');
    this.dashboard = dashboard; // get the dashboard object from callback and store it.(optional)
  }}
  onTileClicked={(data) => {
    console.log('Data from tile', data);
  }}
/>

Usage for Tile

import { Tile } from 'powerbi-report-component';

// inside render
<Tile
  tokenType={tokenType}
  accessToken={accessToken}
  embedUrl={embedUrl}
  embedId={embedId}
  dashboardId={dashboardId}
  style={style} // style for tile component
  onClick={(data) => {
    console.log('Data from tile', data);
  }}
  onLoad={(data) => {
    console.log('Tile loaded', data);
  }}
/>

Usage for ReportVisual

import { ReportVisual } from 'powerbi-report-component';

// inside render
<ReportVisual
  tokenType={tokenType}
  accessToken={accessToken}
  embedUrl={embedUrl}
  embedId={embedId}
  pageName={pageName}
  visualName={visualName}
  style={style} // style for report visual component
  onSelectData={(data) => {
    console.log('Data from ReportVisual', data);
  }}
  onLoad={(reportVisual) => {
    console.log('ReportVisual loaded', data);
  }}
  onRender={(reportVisual) => {
    console.log('ReportVisual rendered', reportVisual);
  }}
/>

Like hooks ? You'll love this :)

useReport

Provides a more fine grained approach for embedding. (where you're in control)

import React, { useEffect, useRef } from 'react';
import { useReport } from 'powerbi-report-component';

const MyReport = ({ accessToken, embedUrl, embedId }) => {
  const reportRef = useRef(null);
  const [report, embed] = useReport();

  const myReportConfig = {
    embedType: 'report',
    tokenType: 'Embed',
    accessToken: accessToken,
    embedUrl: embedUrl,
    embedId: embedId,
    reportMode: "View", // "Edit"
    permissions: "View", // "All" (when using "Edit" mode)
    extraSettings: {
      filterPaneEnabled: false,
      navContentPaneEnabled: false,
    },
  };

  // important
  useEffect(() => {
    // call inside useEffect so the we have the reportRef (reference available)
    embed(reportRef, myReportConfig);
  }, []);

  const handleClick = () => {
    // you can use "report" from useReport like
    if (report) report.print();
  };

  return (
    <div className="report-container">
      <div className="report" ref={reportRef} />
      <button onClick={handleClick}>Print my report</button>
    </div>
  );
};

export default MyReport;

Passing in custom layout for useReport hook.

Example is taken from powerbi js wiki: Custom-Layout.

import { models } from 'powerbi-client'; // Import from the dependency

// Example layout config 
const layoutSettings = {
  layoutType: models.LayoutType.Custom,
  customLayout: {
    pageSize: {
      type: models.PageSizeType.Custom,
      width: 1600,
      height: 1200,
    },
    displayOption: models.DisplayOption.ActualSize,
    pagesLayout: {
      ReportSection1: {
        defaultLayout: {
          displayState: {
            mode: models.VisualContainerDisplayMode.Hidden,
          },
        },
        visualsLayout: {
          VisualContainer1: {
            x: 1,
            y: 1,
            z: 1,
            width: 400,
            height: 300,
            displayState: {
              mode: models.VisualContainerDisplayMode.Visible,
            },
          },
          VisualContainer2: {
            displayState: {
              mode: models.VisualContainerDisplayMode.Visible,
            },
          },
        },
      },
    },
  },
};

// Create your config
const myReportConfig = {
  embedType: 'report',
  tokenType: 'Embed',
  accessToken: accessToken,
  embedUrl: embedUrl,
  embedId: embedId,
  extraSettings: {
    filterPaneEnabled: false,
    navContentPaneEnabled: false,
    ...layoutSettings, // layout config
  },
};


// Inside your component
useEffect(() => {
  embed(reportRef, myReportConfig);
}, []);

useBootstrap

Provided performance gains on loading in an async way

import React, { useEffect, useRef } from 'react';
import { useBootstrap } from 'powerbi-report-component';

// Your configuration from server
const simulateAjaxCall = () => new Promise(function(resolve) {
  setTimeout(resolve.bind(null, {
    accessToken: "accessToken",
    embedUrl: "embedUrl",
    embedId: "embedId",
    reportMode: "View", // "Edit"
    permissions: "View", // "All" (when using "Edit" mode)
  }), 3000)
});


const MyReport = ({ accessToken, embedUrl, embedId }) => {
  const reportRef = useRef(null);
  const [report, bootstrap, embed] = useBootstrap();

  const initialReportConfig = {
    embedType: 'report',
    tokenType: 'Embed',
    extraSettings: {
      filterPaneEnabled: false,
      navContentPaneEnabled: false,
    },
  };

  const getMyConfigurationFromServer = () => {
    simulateAjaxCall().then(data => {
      // Embed the report once your configuration is received 
      embed(reportRef, {...initialReportConfig, ...data});
    });
  }

  // important
  useEffect(() => {
    // call inside useEffect so the we have the reportRef (reference available)
    bootstrap(reportRef, initialReportConfig);
  }, []);

  return (
    <div className="report-container">
      <div className="report" ref={reportRef} />
      <button onClick={getMyConfiguraionFromServer}>Get config from AJAX call</button>
    </div>
  );
};

export default MyReport;

Report features and props you can pass into the component

Inside your component where you're using { Report } component.

Constructor:

  ...
  constructor(props) {
    super(props);
    this.report = null; //used to store value of returned report object
  }
  ....

Callback passed to the onLoad or onRender prop

  handleReportLoad = (report) => {
    this.report = report; // get the report object from callback and store it.
  }

  handleReportRender = (report) => {
    this.report = report; // get the report object from callback and store it.
  }
  ...

using the this.report to perform operations

  ...

  setFullscreen = () => {
    if(this.report) this.report.fullscreen();
  }

  printReport = () => {
    if(this.report) this.report.print();
  }

  ...

  //Inside render

  <button onClick={this.setFullscreen}>Fullscreen</button>
  <button onClick={this.printReport}>Print</button>

  ...

For Report Level Filters:

  /*
    Example filter object used in microsoft's demo page:

    const filter = {
        $schema: "http://powerbi.com/product/schema#basic",
        target: {
          table: "Store",
          column: "Chain"
        },
        operator: "In",
        values: ["Lindseys"]
      };
  */
  ...

  setFilter = (filter) => this.report.setFilters([filter]).catch(function (errors) {
        console.log(errors);
    });

  getFilter = () => this.report.getFilters().then(function (filters) {
          console.log(filters);
      }).catch(function (errors) {
          console.log(errors);
      });

  removeFilters = () => this.report.removeFilters()
      .catch(function (errors) {
          console.log(errors);
      });

  ...

Report Page Change

  onPageChange={(data) =>
    console.log(`Page name :{data.newPage.displayName}`)
  }

Report Load

  onLoad={(report) => {
    console.log('Report Loaded!');
    this.report = report;
    }
  }
  onSave={(data) => {
    console.log('Report Saved! Event data: '+data);
    }
  }

Report Render

  onRender={(report) => {
    console.log('Report Rendered!');
    this.report = report;
    }
  }

Report Button Clicked

  onButtonClicked={(data) => {
    console.log(`Button ${data.title} of type ${data.type} Clicked!`);
    }
  }

Report Command Triggered

  onCommandTriggered={(extensionCommand) => {
    console.log('Extension Command Triggered!');
    }
  }

Report Data Element Clicked

  onSelectData={(data) =>
    console.log(`You clicked on chart: ${data.visual.title}`);
  }

Report Handle Errors

  onError={(data) =>
     console.log(`Error: ${data}`);
  }

Use ‘report’ object returned to parent component or from useReport for:

Note: you wouldn't use this if you're using report from useReport hook.

  1. Change Report Mode to View or Edit:
//mode can be "View" or "Edit"

changeMode = (mode) => this.report.switchMode(mode);
  1. Fullscreen
setFullscreen = () => this.report.fullscreen();
  1. Print Report
printReport = () => this.report.print();
  1. Set Filters
    //example filter from microsoft's demo page

    const filter = {
      $schema: "http://powerbi.com/product/schema#basic",
      target: {
        table: "Store",
        column: "Chain"
      },
      operator: "In",
      values: ["Lindseys"]
    };

    // using event handlers

    setFilter = (filter) => this.report.setFilters([filter]).catch(function (errors) {
      console.log(errors);
    });

    // during onload

    onLoad = (report) => {
      report.setFilters([filter]).catch(function (errors) {
        console.log(errors);
      });
      this.report = report;
    }
  }
  1. Get Filters
getFilter = () =>
  this.report
    .getFilters()
    .then(function (filters) {
      console.log(filters);
    })
    .catch(function (errors) {
      console.log(errors);
    });
  1. Remove Filters
removeFilters = () =>
  this.report.removeFilters().catch(function (errors) {
    console.log(errors);
  });
  1. Save edited report when in "Edit" mode

(note: you need to have enough permissions to save the report)

    async saveReport() {
    if (this.report) {
      try{
        await this.report.save();
      } catch (err) {
        console.log("Error saving report", err);
      }
    }
  }
  1. Show / Hide all visual headers:
toggleAllVisualHeaders = (bool) => {
  const newSettings = {
    visualSettings: {
      visualHeaders: [
        {
          settings: {
            visible: bool, // boolean variable
          },
        },
      ],
    },
  };
  this.report
    .updateSettings(newSettings)
    .then(function () {
      console.log('Visual header toggle successful.');
    })
    .catch(function (errors) {
      console.log(errors);
    });
};

Dashboard features and props you can pass into the component

Dashboard Load

  onLoad={(dashboard) => {
    console.log('Report Loaded!');
    this.dashboard = dashboard;
    }
  }

Dashboard Tile Click

onTileClicked = {(data) => {
  console.log('Data from tile', data);
}}

Use dashboard object returned to parent component for:

  1. Fullscreen
setFullscreen = () => this.dashboard.fullscreen();

Tile features and props you can pass into the component

Tile Load

  onLoad={(data) => {
    console.log('Data from tile', data);
  }}

Tile Click

onClick = {(data) => {
    console.log('Data from tile', data);
}}

For playground visit:

http://akshay5995.github.io/powerbi-report-component

You can find out how to generate token for your report using Powershell from this video.

Alternatives

  1. https://github.com/microsoft/powerbi-client-react bundlephobia

powerbi-report-component's People

Contributors

akshay5995 avatar dependabot-preview[bot] avatar muthu1712 avatar saibamen avatar satya-j avatar satya64 avatar talkl avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

powerbi-report-component's Issues

[FEATURE] Refresh Embed Token Before They Expire

Is your feature request related to a problem? Please describe.
After a certain amount of time (about 1 hour) the embed token expires and opening new tabs on a report shows an error (an HTTP 403 error).

Describe the solution you'd like
The PowerBI Client details a way to refresh the token automatically (https://github.com/Microsoft/PowerBI-JavaScript/wiki/Refresh-token-using-JavaScript-SDK-example). It would be nice if this could be added so that the reports will not show an error

Describe alternatives you've considered
I've considered removing this from my project and going directly to the PowerBI Client library for Javascript. I am also looking inside this repository to see if I can find an easy spot to add this functionality myself.

react version supported

I am using quite an old version of React 16.7.0, will the library works in my project.
Because once I add this library and tried to run I am facing below issue ,
"TypeError: React.useState is not a function"

When a 2nd report loaded, error occurs

I have a component which renders a PowerBi report using the powerbi-report-component and the props passed to it containing the reportId and groupId. Code inside the component gets the PBItoken based on the user's access token and adds filters appropriately.

However, when a user selects a new report from the menu (so Route does not change but reportId prop value changes), the new report does not load, even though componentDidUpdate() detects the changed prop and re-runs the request for a PBIToken initially done in componentDidMount (which will not fire again with a change of props) before loading the page.

Is this an error in my technique for applying the code? Or in the code itself?

Power BI Sign-In button does nothing[Question]

When the page comes up the first time comes up with a Power BI Sign-In screen with a Sign-In button. When you click it, nothing happens. Is there a way to have to prompt the user to Sign In or do they need to sign into Power BI outside of this page?

POWER BI Report not refresh the data after the data set refresh.

Sorry to miss info about the previous question.

Stage first-> I render report using the powerbi-report-component, I provided the accessToken, embedUrl, reportId, etc. It is showing report perfectly. fine till now,

Stage Second-> After doing some changes in MSSQL DB. I am Refreshing the PowerBI DataSet report using the DatasetId and GroupId. from the frontend. after 3 second my dataset refreshed, In PowerBi it is affecting. but after rerendering the powerbi-report-component using the shouldComponentUpdate I changes the props and it's rerendering to but not reflecting the actual dataset refresh, and not showing on frontend.

[BUG] Componente re-render always i change any state

Describe the bug
Componente re-render always i change any state. I want re-render specific component in, not powerbi

To Reproduce
Change any state and component re-render

Expected behavior
Not re-render when i change some state

[BUG] Demo - removing config props from fields throwing error

Description:

In the demo page, if we enter embed fields and run, report comes up on the left pane. If we remove one of the entered config value, say Embed Id, it should reset the left pane, but it is causing entire screen to go blank.

Reproduction steps:

Steps to reproduce the behavior:

  1. Go to 'https://akshay5995.github.io/powerbi-report-component/'
  2. Select Embed Type 'report' and embed mode 'view'
  3. Fill in Token, Embed Url, Embed Id and run
  4. Report will appear in the left pane
  5. Next, delete one of the above values from the field, example, remove value Token field
  6. Then the entire screen goes blank

Expected:
It should not go blank. Instead, the right pane should stay same and left pane should reset to default view with "Report will be displayed in this section"

Filters removed when component re-renders

I have embedded a report which requires filters to be set without user interaction.
I am currently setting the filters from the onLoad of the report. Because onLoad is called again once the filter is set I keep within my state whether I have set the filters or not.

However when the component re-renders due to the component being resized the filters are removed.
I cannot use onLoad to set them again as I have already set them.

If I set OnLoad to always set the filters then component gets into an infinate loading/setting filters loop so this is not an option.

I've tried looking at the report object that is passed into onLoad to see if there is a way to identify that I need to re-apply the filters but cannot find a reliable way to do this.

            <Report
              embedType="report"
              tokenType="Embed"
              accessToken={this.state.accessToken}
              embedUrl={this.state.embedUrl}
              embedId={this.state.id}
              extraSettings={this.state.extraSettings}
              permissions="View"
              style={this.state.reportStyle}
              onLoad={this.onReportLoad}
            />


  onReportLoad = (report) => {
    if ((this.state.filter && !this.state.report)) {
      report.setFilters([this.state.filter])
        .then(this.reportFilteringFinished(report))
        .catch((error) => {
          this.setState({ error })
        })
    }
  }

[BUG] Unable to embed tile

I am trying to embed a tile but it doesn't load.

const report2 = ( <Report embedType="dashboard" // or "dashboard" tokenType="Embed" // or "Aad" accessToken={embedTileConfig.embedToken.token} // accessToken goes here embedUrl={embedTileConfig.embedUrl} // embedUrl goes here embedId={embedTileConfig.id} // Report or Dashboard ID goes here dashboardId={embedTileConfig.dashboardId} permissions="View" // or "View" onLoad={this.onEmbedded} /> );

[BUG] Setting the filters get error

Describe the bug
on load report, I'm setting the filters as described in the example but I get the following error:
{message: "undefined property is invalid"}

To Reproduce
Try to set filters on loading report

Here my code:

- setting the filter:

const setFilter = (itemID) => {
        const filter = {
            $schema: "http://powerbi.com/product/schema#basic",
            target: {
                table: table,
                column: column
            },
            operator: "In",
            values: [itemID]
        };


- onLoad:

const handleEmbedded = (report) => {
    report.setFilters([globalFilters]).catch(err => console.error(err))
    setEmbeddedReport(report);
  }

Am I doing anything wrong or could be a bug?
Thanks

handleTileClicked doesn't seem to work for me, how can I troubleshoot?

We have a SPA with sidebar nav, components are imported into the main page so the dashboard div doesn't live precisely at the root div, I was kinda thinking this could be the problem. In any case, I have it set to just console log the data in the dashboard component when the tile is clicked and nothing is happening, Snipped it looks like this:
`
...

handleTileClicked = (data) => {
    console.log('Data from tile', data);
}

render() {
    // const extraSettings = {
    //     filterPaneEnabled: false
    // }
    return (
        <div id="dashboard">
            ...
            <Report
                embedType="dashboard"
                tokenType="Embed"
                accessToken={this.state.embedToken}
                embedUrl={this.state.embedURL}
                embedId={this.state.embedID}
                permissions="All" 
                // extraSettings={extraSettings}
            /> 
        </div>
    )
}

}

`

The parameters are populating correctly, the dashboard works and the report tile we set up is completely interactive. Just not getting any clicks, can't click through to the report.

Component not showing dashboard for secured embedded URL.

Below is the configuration I used for non-secured embedded URL
<Report embedType={${powerbiConfig.EMBED_TYPE}} // or "dashboard" tokenType="Embed" // or "Aad" accessToken={${powerbiConfig.YOUR_EMBED_TOKEN}} // accessToken goes here embedUrl={${powerbiConfig.YOUR_EMBED_URL}} // embedUrl goes here embedId={${powerbiConfig.YOUR_REPORT_ID}} // Report or Dashboard ID goes here permissions="All" // or "View" />
When I use the same settings for secured embedded URL, the rendering fails and shows "This content isn't available" message.

Do I need to modify settings to render both secured and(or) non-secured embedded URL's?

CSP issue on Report component Render

When i try to render my PowerBI Report component on production environment, I face this error:

Refused to frame 'https://app.powerbi.com/' because it violates the following Content Security Policy directive: "default-src 'self'". Note that 'frame-src' was not explicitly set, so 'default-src' is used as a fallback.

[BUG] Remove filters not working

Remove filters not working and not show nothing in the console. But fullscreen it work.
Follow my code

<Button onClick={() => this.report.fullscreen()}>
Full screen
</Button>
<Button onClick={() => this.report.removeFilters().catch(errors => { console.log(errors) }) }>
Clear filters
</Button>
<Report
          embedType="report"
          tokenType="Embed"
          accessToken={myAccessToken}
          embedUrl={myEmbedUrl}
          embedId={myEmbedId}
          extraSettings={{
            filterPaneEnabled: true,
            navContentPaneEnabled: true
          }}
          permissions="All"
          style={}
          onLoad={report => (this.report = report)}
          onRender={report => {
            this.report = report
              this.report.switchMode('edit')
          }}
/>

Datasetbinding in reports

Please add the dynamic dataset binding feature while embedding reports. It is used to connect with different datasets dynamically while having only one report. Below is the URL for refernce.

Here

[FEATURE]Apply theme onload

Is your feature request related to a problem? Please describe.
Currently I wanted to render pbi report with custom theme, whereas I can use after load to customize them on going but it will have a flip between original theme and new theme

Describe the solution you'd like
I checked that we only allowed predefined props being embeded as config, can we add the new feature theme in or you can have a ...extraProps similar to your ...extraSettings so that there is no need to keep updating the new features

Describe alternatives you've considered
A clear and concise description of any alternative solutions or features you've considered.

[BUG] TypeError: Cannot read property 'tid' of undefined

I am repeatedly getting the error TypeError: Cannot read property 'tid' of undefined (detail below). I can't determine why it keeps coming up every time. It also continues to error, like the page is refreshing.

Here is my JS

<Report
              embedType="report"
              tokenType="Embed" // or Embed
              accessToken={accessToken}  //Access token
              embedUrl={embedUrl}
              embedId={reportId}
              extraSettings={extraSettings}
              permissions="All"
              style={reportStyle}
              onLoad={this.handleReportLoad}
              onRender={this.handleReportRender}
          />

reportembed.externals.bundle.min.js:1324 TypeError: Cannot read property 'tid' of undefined
at e.isAADTokenTenantValid (reportEmbed.min.js:1)
at t.isPowerBIAccessTokenValid (reportembed.bundle.min.js:22)
at t.promptForLogin (reportembed.bundle.min.js:22)
at m.scope.promptForLogin (reportembed.bundle.min.js:21)
at fn (eval at compile (reportembed.externals.bundle.min.js:1442), :4:162)
at m.$digest (reportembed.externals.bundle.min.js:1348)
at reportEmbed.min.js:1
at t.r [as _next] (reportEmbed.min.js:1)
at t.__tryOrUnsub (reportEmbed.min.js:1)
at t.next (reportEmbed.min.js:1)
(anonymous) @ reportembed.externals.bundle.min.js:1324
(anonymous) @ reportembed.externals.bundle.min.js:1296
$digest @ reportembed.externals.bundle.min.js:1349
(anonymous) @ reportEmbed.min.js:1
r @ reportEmbed.min.js:1
t.__tryOrUnsub @ reportEmbed.min.js:1
t.next @ reportEmbed.min.js:1
t._next @ reportEmbed.min.js:1
t.next @ reportEmbed.min.js:1
t.next @ reportEmbed.min.js:1
t.emit @ reportEmbed.min.js:1
yy @ reportEmbed.min.js:1
onHasTask @ reportEmbed.min.js:1
t.hasTask @ reportembed.externals.bundle.min.js:1197
t._updateTaskCount @ reportembed.externals.bundle.min.js:1197
e._updateTaskCount @ reportembed.externals.bundle.min.js:1197
e.runTask @ reportembed.externals.bundle.min.js:1197
y @ reportembed.externals.bundle.min.js:1197
e.invokeTask @ reportembed.externals.bundle.min.js:1197
_ @ reportembed.externals.bundle.min.js:1197
b @ reportembed.externals.bundle.min.js:1197

Unable to display dashboard

*Resolved. See comment. *
I am attempting to use the 'Dashboard' component of this repo, however, I am unable to view the dashboard.

I use a backend node server for generating an access token for an "App Owns Data" scenario (service principal authenticationMode, clientSecret, etc) to generate an embed token.

When I attempted to render the report, I can see the component and the styling/image components are displayed properly, but errors are displayed on every visual. I receive

"An unexpected error occurred

An unexpected error occurred. Please try again later."

in the console, i see "ERR_BLOCKED_BY_CLIENT" and the following:
"Could not load content for https://app.powerbi.com/visual.js.map;: HTTP error: status code 404, net::ERR_HTTP_RESPONSE_CODE_FAILURE"

*edit: this particular error was stemming from adblock

DevTools failed to load SourceMap: Could not load content for https://app.powerbi.com/visual.js.map;: HTTP error: status code 404, net::ERR_HTTP_RESPONSE_CODE_FAILURE
DevTools failed to load SourceMap: Could not load content for https://app.powerbi.com/visual.css.map: HTTP error: status code 404, net::ERR_HTTP_RESPONSE_CODE_FAILURE

Originally I had issues viewing the report on my own app, but I was able to reproduce on the sample tool you have made available (super handy for quick testing btw). Additionally, I was able to use the NodeJs sample provided in powerbi-client, and I was able to render the full report there.

Does this package support Service Principal?

Is this related to a possible change in the API from Microsoft?

Page breaks while resizing the window

I am using multiple reports in same page by using pageName property . But on window resize the page breaks with the following error.

powerbi.js:499 Uncaught Error: Attempted to embed using config {"type":"report","tokenType":1,"accessToken":"accestoken","embedUrl":"embedurl","id":"id","pageName":"pageName","permissions":7,"settings":{"filterPaneEnabled":false,"navContentPaneEnabled":false}} on element <div class="report" id="73c79e38-0ace-446c-a5a2-7af4415d4a51" style="height: 100%; border: 0px; width: 100%; overflow: scroll;"><iframe src="uri scrolling="no" allowfullscreen="true" style="width: 100%; height: 100%;"></iframe></div> which already has embedded comopnent associated, but could not find the existing comopnent in the list of active components. This could indicate the embeds list is out of sync with the DOM, or the component is referencing the incorrect HTML element.

Please help me on this.

[Refactor] Docs/ Demo page

Docs component (demo) app has become a gigantic mess with more fields and is not so easy to navigate or use.

Refactor into multiple components.

[FEATURE] typescript support

Is your feature request related to a problem? Please describe.
We using TypeScript in our project. Using this library adds a little inconvenience, because we need to write custom d.ts files, which may not correspond to reality after updating the library.

Describe the solution you'd like
Availability of d.ts files for all components in the library

[BUG] Embed reset function undefined

Describe the bug
If you go to Embed.jsx in the didUpdate() method, you notice that there is no this.reset() method, unless it's from React itself but couldn't find docs. I even tried to force the this.reset before the first if

To Reproduce
Steps to reproduce the behavior:

  1. Go to Embed.jsx
  2. Move this.reset() to first line in the didUpdate method
  3. See error "reset is not a function"

Expected behavior
We should be able to reset the component?

Screenshots
Screen Shot 2020-04-24 at 6 38 58 pm

Is that expected or should have a reset component/report method in place?
Thanks

How to pass a report parameter on call?

I am trying to pass a parameter (currency) into the call to the PBI call. It used to work in the Jquery version, but if I load it into {extraSettings} or as a parameter on the component, it does not pass onto the PBI call.

Is this a bug or am I putting this parameter in the wrong location?

[BUG] ReportVisual datas

Describe the bug
Hi, as we said I am opening an issue regarding the ReportVisual component. Basically, I have a React app that is using two ReportVisual component on the same page. Both of those ReportVisual are rendering the Power Bi visual very well, no problem at all. However, both of the visuals are on the same report on power bi and both have interaction with each other (i.e if I do click on visual A, it does filter the data on the visual B). Unfortunately, it is not working on my test.

Thanks a lot again for your work.

To Reproduce
Steps to reproduce the behavior:

  1. Generate a report on power bi with two visual linked
  2. Use this lib
  3. Create two ReportVisual components with all the attributes (datasetid, reportid, visualid, accesstoken, etc)
  4. Click and see the problem

Here is my code:

return (
      <div className="root">
        <ReportVisual
          tokenType="Aad" // "Aad"
          accessToken="MYACCESSTOKEN" // accessToken goes here
          embedUrl="MYEMBEDURL" // embedUrl goes here
          embedId="MYEMBEDID" // report or dashboard Id goes here
          pageName="ReportSection" // set as current page of the report
          reportMode="View" // open report in a particular mode View/Edit/Create
          datasetId="MYDATASETID" // required for reportMode = "Create" and optional for dynamic databinding in report on View mode
          groupId="MYGROUPID" // optional. Used when reportMode = "Create" and to chose the target workspace when the dataset is shared.
          visualName="MYVISUALNAME_1"
          extraSettings={extraSettings}
          permissions="View" // View, For "Edit" mode permissions should be "All"
          style={reportStyle}
        />
        <ReportVisual
          tokenType="Aad" // "Aad"
          accessToken="MYACCESSTOKEN" // accessToken goes here
          embedUrl="MYEMBEDURL" // embedUrl goes here
          embedId="MYEMBEDID" // report or dashboard Id goes here
          pageName="ReportSection" // set as current page of the report
          reportMode="View" // open report in a particular mode View/Edit/Create
          datasetId="MYDATASETID" // required for reportMode = "Create" and optional for dynamic databinding in report on View mode
          groupId="MYGROUPID" // optional. Used when reportMode = "Create" and to chose the target workspace when the dataset is shared.
          visualName="MYVISUALNAME_2"
          extraSettings={extraSettings}
          permissions="View" // View, For "Edit" mode permissions should be "All"
          style={reportStyle}
        />
      </div>
    );

Report update

Hello good afternoon.
I have another question, I'm looking for the id and embed toke through a request with axios. The request is triggered when I click on the link. The first report loads normally, but if I click on another one it does not update the iframe how can I fix it.

Sem título

import Main from '../template/Main'
import React, { Component } from 'react'
import { Report } from 'powerbi-report-component'
import axios from 'axios'


const headerPros = {
  title: 'Relatorio',
  subtitle: 'Exibição de Relatorios'
}

const baseUrlReports = 'http://localhost:3001/api/v1/groups/'
const baseUrlWorkspace = 'http://localhost:3001/api/v1/usuarios'

export default class Reports extends Component {
  constructor(props) {
    super(props)
    this.state = { 
      idworkspace: '',
      workspaceDb: [],
      values: [],
      report: [] 
    }

    this.getReports = this.getReports.bind(this)
    this.getReport = this.getReport.bind(this)
    this.renderReports = this.renderReports.bind(this)
    this.renderLi = this.renderLi.bind(this)
  }

  getReport(event) {
    event.preventDefault()
    let e = event.target.href

    axios.get(e)
      .then(response => {
        // handle success 
        this.setState({report: response.data})
    })
  }

  getReports(event) {
    let e = event.target.value
    
    this.setState({idworkspace: e})
    
    axios.get(baseUrlReports + e)
      .then(response => {
        // handle success
        this.setState({values: response.data.value})
      })
  }

  renderReports(event) {
    return ( 
      <ul class="m-2">
        {this.renderLi(event)}
      </ul>
    )
  }

  renderLi(event) {
    const lista = {
      listStyle: "none"
    }

    return this.state.values.map(data => {
      return (
        <li key={data.id} style={lista}><a href={"http://localhost:3001/api/v1/groups/" + this.state.idworkspace + "/report/" + data.id} onClick={this.getReport}>{data.name}</a></li>
      )
    })
  }

  componentWillMount() {
    axios(baseUrlWorkspace)
    .then(response => {
      // handle success
      //console.log(response)
      this.setState({workspaceDb: response.data})
    })
  }

  renderWorkspaces() {
    return(
      <select onChange={this.getReports}>
        <option value="oi">Escolha um Worspace</option>
        {this.renderOption()}
      </select>
    )
  }
 
  renderOption() {
    return this.state.workspaceDb.map(data => {
      return (
        <option key={data.idworkspacesusurios} value={data.identworkspace} >{data.workspace}</option>
      )
    })
  }

  render() {
    const reportStyle = {
      // style object for report component
      width: "100%",
      height: "90vh"
    }

    const floatRight = {
      width: "79%",
      marginBottom: "10px"
    }

    const floatLeft = {
      width: "20%"
    }

    return (
      <Main {...headerPros}>
        <div class="float-left" style={floatLeft}>
          <div class="card">
            <div class="card-header">
              <div class="float-left fa fa-bar-chart"></div>
              <div class="leftNavTitle leftNavItem">Grupos de trabalho</div>
            </div>
            {this.renderWorkspaces()}
          </div>
        
          <div class="card">
            <div class="card-header">
              <div class="float-left fa fa-bar-chart"></div>
              <div class="leftNavTitle leftNavItem">Relatorios</div>
            </div>
            {this.renderReports()}
          </div>
        </div>
        <div class="float-right" style={floatRight}>
        { !!this.state.report[0] && !!this.state.report[1] &&
          <Report
            tokenType="Embed" // "Aad"
            accessToken={this.state.report[1].EmbedToken} // accessToken goes here
            embedUrl="https://app.powerbi.com/reportEmbed" // embedUrl goes here
            embedId={this.state.report[0].id} // report or dashboard Id goes here
            pageName="" // set as current page of the report
            reportMode="view" // open report in a particular mode view/edit/create
            permissions="All"
            style={reportStyle}
          />}
          </div>
      </Main>
    );
  }
}

[BUG] onPageChange

Describe the bug
When clicking on the page tabs at the bottom of a PowerBI report, the event onPageChange doesn't fire. I have another event "onSelectData" that does work.

const handleDataSelected = (data) => {
console.log("data selected", data);
}
const handlePageChange = (data) => {
console.log("page changed", data);
}

    <div key={reportId} className={loading !== true ? 'col-sm-12' : 'col-sm-12 loading-delete'}>
      <Report
        className={reportId}
        embedType="report"
        tokenType="Embed"
        pageName={reportId}
        accessToken={config.embedToken}
        embedUrl={config.embedUrl}
        embedId={config.id}
        permissions="All"
        onLoad={onLoadAndSetTokenListener}
        onSelectData={handleDataSelected}
        onTileClicked={handleTileClicked}
        onPageChange={handlePageChange}
        style={{
          height: '90vh',
          width: '100%',
          display: 'block',
          top: '0',
          left: '0',
          position: 'absolute',
          border: '0',
          padding: '20px',
          background: '#fff',
          zIndex: '1',
        }}
      />
    </div>

When I refresh the power bi embed token, the entire report reloads

Hi,
I use a setInterval function to refresh the embed token before the 20 minute expiry that is set in the PowerBI Service. However, in getting the new token, the render() method in React is called and the report is re-rendered, which causes the report to lose its context (e.g. if several PBI report filters are set, the refresh reloads the report as if no filters have been set yet).
Is there a way to refresh the embed token prior to the 20 minute expiry without getting triggering the render() function and causing a reload of the component?

Issue with fullscreen rendering

I'm not able to get the report to render fullscreen, even after adding height 100% to style options, App.css, and index.css. Any idea what could be causing this? Thank you.
Github

How to capture Link clicked event

i need to listen to a Link clicked event from powerbi-report-component. But from the documentation of pbi report component , i could not find any useful explanation on how to do the same.
But in the official documentation i could find the link
Use case is ,i have a power-bi-rpeort with a link to an external report which opens in a new tab.so on click of the button, i need to fetch the report details of the newly opened report.

Does powerbi-report-component have such a event for capture that?

[BUG] Support EditMode in useReport hook

Describe the bug
I can't set "edit mode" when I use PowerBi component with hooks, they just show me report on view mode. When I put reportMode to edit this not works and show me again on view mode. I also can't use onLoad function to use switchMode to edit like I use when not using with hooks.

To Reproduce
const myReportConfig = {
embedType: 'report',
tokenType: 'AccessToken',
permissions: 'All',
accessToken: accessToken,
embedUrl: embedUrl,
embedId: embedId,
extraSettings: {
filterPaneEnabled: false,
navContentPaneEnabled: false,
},
reportMode: 'edit',
};

Expected behavior
show me report on edit mode

Screenshots
If applicable, add screenshots to help explain your problem.
image

Additional context
No have.

Error in set filter

I get an error (undefined property is invalid) when I use report.setFilters. this is my code in onLoad method:

const filterByItemId = {
$schema: "http://powerbi.com/product/schema#advanced",
condition: [
{
operator: "Is",
value: 2,
}
],
filterType: 0,
logicalOperator: "And",
target: {
table: "table_name",
column: "column_name"
},
};

report.setFilters([filterByItemId]).catch(function (errors) {
console.log("error in set filter", errors);
});

[FEATURE] Add 'Report Visual' component

Is your feature request related to a problem? Please describe.
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]

Describe the solution you'd like
There should be another component for Report Visuals. Tiles and Reports don't accept visual name so page visuals can't be rendered

Describe alternatives you've considered
A clear and concise description of any alternative solutions or features you've considered.

[BUG] Change to onLoad event breaks ability to retrieve page data

My embedType is 'report' if that's helpful for context.

In the current version, with the event setup below, I can call await report.getPages() in my onLoad handler and I receive the pages.

      report.on('loaded', () => {
        if (onLoad) onLoad(report);
      });

It appears that the change to onLoad breaks my ability to pull any page data from the report object, as calling await report.getPages() in onLoad now fails silently.

Should this change only apply to embedType === 'dashboard'?

Can you provide any detail on the dashboard bug that this code change addresses?

Gray border coming with report

When Report is loaded, a grey border is coming . How to get rid of this ?

Expectation:
Only report content should be loaded, instead the a gray border of iframe is coming.

[FEATURE] Better docs for settings object

I'm currently trying to implement a mobile view for an embedded report, but I think it's not really clear as to which settings are available on the settings-property of the hooks implementation.

Currently, I'm just struggling with what I can pass to the layoutType property, but I could imagine it would be neat with a reference of which parameters are available, and what they do, both for me and for other developers :)

Otherwise, thanks for a super cool package. Really useful, and love the hooks implementation. Cheers!

[BUG] Error 403 when running application

Good afternoon.
I am trying the following problem. I make a request to an api where I receive the embedtoken and pass the properties. but when i run the application i get a 403 error.

code:
codigo

error:
error

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.