Issue Burndown to Power BI
Nightly flow pages through all issues (open + closed) from monitored repos and pushes them to a Dataverse table so Power BI can visualize burndown, label distribution, and assignee load over time.
Provided as-is, without warranty of any kind. Review and test each pattern in a non-production environment before deploying it to live automations. See our Terms.
Overview
Nightly cloud flow that snapshots every issue (open + closed, excluding pull requests) from a configured GitHub repository and writes each one as a row into a dedicated Dataverse table. The table becomes the source-of-truth historical dataset that Power BI reports can bind to for burndown charts, label distribution, assignee workload, and velocity trending.
Ships Off in the Stopped state. Activating it requires only (1) authorizing the GitHub and Dataverse connection references and (2) setting the two environment variables to point at the target org/repo.
Use Case
Product, engineering, and executive stakeholders want historical views of GitHub issue activity that can be sliced over time (burndown, label distribution, assignee load). GitHub's native Insights tab gives point-in-time views; it doesn't support long-range analytical queries or cross-report joins.
This flow creates an append-only snapshot dataset in Dataverse so Power BI can model the data using its own time intelligence and DAX. Each nightly run adds a fresh snapshot row per issue stamped with flowlibs_snapshotdate, which allows burndown-style charts to plot open/closed counts by day, label, or assignee.
The flow is ideal for teams that:
- Product managers tracking issue burndown and velocity trends
- Engineering leaders monitoring assignee workload distribution
- Executives reviewing label distribution and long-range issue activity
- Teams needing historical GitHub data outside the native Insights tab
- Power BI authors building DAX-driven time-intelligence reports
Flow Architecture
Nightly Issue Snapshot Recurrence
RecurrenceFires daily at 02:00 UTC.
Init varGitHubOwner
Initialize variableHydrates owner from the flowlibs_GitHubOwner environment variable.
Init varGitHubRepo
Initialize variableHydrates repo name from the flowlibs_GitHubRepository environment variable.
Init varSnapshotDate
Initialize variableCaptures utcNow() once so every row in this run shares a single timestamp.
Init varRepoFullName
Initialize variableBuilds 'owner/repo' once, reused as the flowlibs_reponame field and in the composite primary key.
Get GitHub Issues All States
GitHub - Get issues (state: all)Returns up to 100 most recent issues; one call = one page. The 100-item cap is acceptable for a nightly demo; add pagination with HttpRequest + page= query for larger repos.
Apply to each Issue
Apply to eachFor each issue returned by Get GitHub Issues All States: evaluates the PR-exclusion check and writes a snapshot row when the item is a true issue.
If Issue Is Not Pull Request
If conditionGitHub's /issues endpoint returns PRs alongside issues. The pull_request object is only present on PRs, so this absence check (coerced to empty string) filters them out.
- Create Issue Snapshot Record — Dataverse Create record on flowlibs_githubissuesnapshots — writes one row per non-PR issue with the composite key, snapshot timestamp, and the serialized labels/assignees arrays.
Environment Variables
| Schema name | Type | Default | Description |
|---|---|---|---|
| flowlibs_GitHubOwner | String | your-org | GitHub organization or user that owns the target repository. |
| flowlibs_GitHubRepository | String | flowlibs-demo | Repository name (without owner) to snapshot each night. |
Connectors & Connections
| Connector | API name | Actions used |
|---|---|---|
| GitHub | shared_github | GetIssues (Returns up to 100 issues per call with state=all) |
| Microsoft Dataverse | shared_commondataserviceforapps | CreateRecord (Inserts a row into flowlibs_githubissuesnapshots) |
Note — All connections are referenced as solution connection references; the flow is portable between environments as long as a connection is mapped at import time.
Customization Guide
Almost every realistic variant of this flow can be implemented by changing environment variable values. A few cases require small edits inside the flow definition — those are called out explicitly below.
- Point at a different repo
- Update the two env var values (flowlibs_GitHubOwner and flowlibs_GitHubRepository) in the solution. No flow changes required.
- Monitor multiple repos
- Replace Init varGitHubOwner and Init varGitHubRepo with a delimited-list env var plus a Select expanded to an array, and wrap the GetIssues call in a parent Apply to each.
- Get beyond 100 issues
- Swap GetIssues for the connector's HttpRequest action with per_page=100 and page=N in a Do until loop (exit when length(body) < 100).
- Filter out triaged issues
- Add a label filter on GetIssues by setting the labels query parameter (comma-delimited list).
- Skip rewriting labels/assignees as JSON
- Replace the string(...) expressions with @{join(select(labels, 'name'), ',')} for a flat CSV instead of a JSON array.
- Change the schedule
- Edit the recurrence block — daily is the minimum meaningful cadence for a burndown curve; hourly produces too much data for Power BI imports.
Key Expressions
The flow is intentionally light on Power Fx / WDL gymnastics — the heaviest expressions are the branch-name concatenation and the approval outcome check. They are listed below in the order they appear in the flow.
EXPR.01Composite primary key (flowlibs_name)
Composite key ensures uniqueness across snapshots of the same issue over time (owner/repo#number@yyyyMMddHHmmss).
EXPR.02PR-exclusion condition
pull_request is only present on PRs. Coercing a missing object to empty string and comparing to '' evaluates true only when the property is absent.
EXPR.03Title truncation (500 chars)
Guards against issues with 500+ char titles overflowing the flowlibs_title column.
EXPR.04Labels / Assignees serialization
Serializes the whole array to JSON so downstream Power BI can split on demand; coalesce(..., json('[]')) avoids null string coercion errors.
Comments
Sign in to join the conversation.
Sign inNo comments yet. Be the first to share your experience with this flow.