microsoft / microsoft/vscode-powerquery-sdk

Invoked Function UI (typed function in leaf Data column) not rendered in the new Power Query "Get Data" experience

Open
#427 1 comment 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
TypeScript
Stars
92
Forks
23
PR merge metrics
No merged PRs in 30d

Description

Environment

Connector type: Custom Power Query connector (.mez), OAuth 2.0 + PKCE, GraphQL backend
Host: Power BI Desktop (new "Get Data" / Navigator experience) vs. classic experience
Pattern: Multi-level navigation table (Project → Folder → Table), where the leaf item exposes a typed function so users can configure filters before data is loaded

Summary

Our connector builds a hierarchical navigation table. For leaf nodes (the selectable 3D model / metadata dataset), instead of placing a table in the Data column, we place a typed function created with Value.ReplaceType(...). The function's parameters are decorated with Documentation.FieldCaption, Documentation.FieldDescription, Documentation.AllowedValues, Documentation.SampleValues, Formatting.IsMultiLine, and Formatting.IsCode.

In the classic experience, this leaf function is rendered as an Invoked Function UI directly inside the Navigator, so the user can pick filter values (Revit Category/Family/Type, property selection, references) and then load.
In the new Power Query experience, the Invoked Function UI is no longer rendered in the Navigator. The user is instead dropped into Transform Data, where the navigation table shows Data=Function. The function can still be invoked manually, but this adds extra steps and degrades the UX.

Technical Details

1. Leaf Data column holds a typed function (not a table)
We return a function whose type is applied via Value.ReplaceType, so Power Query treats it as an invocable, documented function:

DisplayProperty = type function (
    filter as (type text meta [
        Documentation.FieldCaption = "Filter Revit Elements By",
        Documentation.AllowedValues = {"None", "Category", "Family", "Type"}
    ]),
    optional Parameter as (type text meta [
        Documentation.FieldCaption = "Revit Parameter",
        Documentation.SampleValues = {"category:Walls, Floors, Doors|family: Basic Wall"},
        Formatting.IsMultiLine = true,
        Formatting.IsCode = true
    ]),
    optional input as (type list meta [
        Documentation.FieldCaption = "Select Properties",
        Documentation.AllowedValues = <dynamic list from the exchange>
    ]),
    optional reference as (type list meta [
        Documentation.FieldCaption = "Select Revit Reference Properties",
        Documentation.AllowedValues = <dynamic list from the exchange>
    ])
) as table
in
    Value.ReplaceType(DisplayFilteredTable, DisplayProperty)

Note that Documentation.AllowedValues here is computed at runtime from a metadata call to the exchange (the available property/reference names differ per model), which is exactly why we want it surfaced before load.

2. Two navigation-table builders — with and without preview delay
For normal (non-filter) leaves we use the documented helper with Preview.DelayColumn:

newTableType = Type.AddTableKey(tableType, keyColumns, true) meta [
    NavigationTable.NameColumn = nameColumn,
    NavigationTable.DataColumn = dataColumn,
    NavigationTable.ItemKindColumn = itemKindColumn,
    Preview.DelayColumn = itemNameColumn,     // Table.ToNavigationTable
    NavigationTable.IsLeafColumn = isLeafColumn
]

For the filter path (where Data is the typed function) we use a variant that omits Preview.DataColumn, so the function isn't eagerly previewed:

newTableType = Type.AddTableKey(tableType, keyColumns, true) meta [
    NavigationTable.NameColumn = nameColumn,
    NavigationTable.DataColumn = dataColumn,
    NavigationTable.ItemKindColumn = itemKindColumn,
    NavigationTable.IsLeafColumn = isLeafColumn   // Table.ToNavigationTableNoPreviewDelay (no Preview.DelayColumn)
]

The filter leaf is emitted like this (function placed directly in Data, ItemKind = "Table"):

objects = #table(
    {"Name", "Key", "Data", "ItemKind", "ItemName", "IsLeaf"},
    {{ tableName, exchangeName, UI /* typed function */, "Table", "Table", true }}
),
Table.ToNavigationTableNoPreviewDelay(objects, {"Key"}, "Name", "Data", "ItemKind", "ItemName", "IsLeaf")
Image
Questions
  • Is the "typed function in the leaf Data column" pattern still supported in the new Power Query experience? Is it intentionally deprecated?
  • Has the behavior of Preview.DelayColumn / a navigation table without Preview.DelayColumn (our Table.ToNavigationTableNoPreviewDelay) changed in the new experience?
  • Is there a recommended new pattern for collecting user inputs via Documentation.AllowedValues before data load, without pushing the filtering step into Transform Data?
  • If the Invoked Function UI in the Navigator is being deprecated, what is the recommended migration path for connectors that rely on it?

References -

Image

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with the connector's leaf navigation-table construction, the Value.ReplaceType function metadata, and the Preview.DelayColumn or Table.ToNavigationTableNoPreviewDelay variants described in the issue. Review the linked navigation-table, helper-function, and transformation documentation, then compare classic and new Get Data behavior. Done means establishing whether this pattern is supported and documenting the recommended migration path if it is not.

Written by the indexing model from the issue text.

Assessment

Domain
developer-experience, tooling
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.