fix(web): restore the read result envelope as a metadata carrier

`McpUiReadResourceResult` — the return type of a registerAppResource read
callback — types `_meta.ui` at the result level, so the envelope is a
supported carrier after all and dropping it lost the hints for servers
using that shape. Consult all three, most-specific first: content item,
result envelope, listing entry; first found wins outright.

Also make the App wiring test wait for BOTH factories by their
advertiseElicitation flag. Waiting on a count passed as soon as either
was built, so stripping the wiring from one call site left the other's
deps in the array and the assertion loop still passed.

Signed-off-by: cliffhall <cliff@futurescale.com>
This commit is contained in:
cliffhall 2026-08-23 21:50:36 -04:00
commit e2a88d49dd

View file

@ -3183,15 +3183,26 @@ describe("App MCP App listed-resource metadata wiring (#2055)", () => {
);
renderWithMantine(<App />);
await waitFor(() => expect(appBridgeFactoryDeps.length).toBeGreaterThan(0));
// Every factory App builds gets the wiring, not just the Apps-tab one.
for (const deps of appBridgeFactoryDeps) {
expect(deps.getListedResourceMeta?.("ui://weather/app.html")).toEqual(
// App builds two factories, differing only in `advertiseElicitation`. Wait
// for BOTH by that flag rather than for a count: waiting on "at least one"
// would still pass with the wiring stripped from either call site, since
// the other's deps sit in the same array.
const appsFactory = () =>
appBridgeFactoryDeps.find((d) => !d.advertiseElicitation);
const elicitationFactory = () =>
appBridgeFactoryDeps.find((d) => d.advertiseElicitation === true);
await waitFor(() => {
expect(appsFactory()).toBeDefined();
expect(elicitationFactory()).toBeDefined();
});
for (const deps of [appsFactory(), elicitationFactory()]) {
expect(deps?.getListedResourceMeta?.("ui://weather/app.html")).toEqual(
listedMeta,
);
expect(
deps.getListedResourceMeta?.("ui://other/app.html"),
deps?.getListedResourceMeta?.("ui://other/app.html"),
).toBeUndefined();
}
});