Environment
@microsoft/power-apps SDK: 1.1.3
- App type: Power Apps Code App (React + Vite, runs in a cross-origin iframe served via
storageproxy)
- Failure surface: Published / native Power Apps player only (web and mobile). Never reproduces in a standalone browser at
localhost or via npx power-apps run.
- Backend: a Power Automate cloud flow invoked through the generated connector service (
<FlowService>.Run, i.e. IDataSource.executeAsync).
Summary
When a Power Automate flow returns a JSON payload that contains multibyte UTF-8 characters (e.g. Chinese / CJK), the SDK data channel in the published app delivers a corrupted / truncated payload to the client. JSON.parse then throws:
JSON Parse error: Unterminated string
(Unterminated string is the JavaScriptCore / WebKit wording for a string that was cut off — i.e. the byte stream was broken mid-character.)
The same flow, same input, same client code works correctly:
- in a desktop / mobile browser (non-published), and
- in the Power Automate run history — the flow itself always returns HTTP 200 with a complete, valid JSON body.
So the defect is not in the flow and not in the application JSON. It is in the SDK's response-decoding path for published apps.
Where it throws (SDK internals)
Call chain for the flow invocation:
executeAsync
-> retrieveDataAsync // carries the "Retrieve operation failure" prefix
-> _executeRequest // reads response as arraybuffer
-> _decodeArrayBuffer // TextDecoder over the bytes
-> JSON.parse(text) // <- throws "Unterminated string"
File: @microsoft/power-apps/dist/internal/data/core/runtimeClient/runtimeDataClient.js.
The browser's TextDecoder decodes the multibyte bytes correctly, which is why the browser path never fails. In the published app the bytes reaching this point are already damaged.
Why we believe it is a multibyte / transport-integrity issue
This matches existing reports against the same channel:
Reproduction
- Build a Code App that calls a Power Automate flow via the generated connector (
executeAsync).
- Have the flow return a JSON object whose string values contain multibyte characters (e.g. any Chinese text). Length is irrelevant — it reproduces even at ~600 characters.
- Run in a browser -> parses fine.
- Publish, run in the native Power Apps player (web or mobile) ->
JSON Parse error: Unterminated string.
Isolation test that confirms the root cause
We changed only the content encoding of the flow's response, holding everything else constant (same flow, same client code path, same Chinese input message):
- Variable isolated: presence of multibyte / non-ASCII characters in the response body.
- Method: forced the producer to emit ASCII-only JSON (translate / romanize all string values), so the response carried zero multibyte characters. No change to request, transport, payload size, or call path.
- Result:
- Multibyte response (Chinese) -> fails in published app (
Unterminated string), works in browser.
- ASCII-only response -> succeeds in published app.
A single-variable flip (multibyte <-> ASCII) toggles the failure on/off, while the browser path is unaffected either way. This isolates the defect to multibyte-payload corruption in the SDK / storageproxy response channel for published apps.
Impact
Any Code App that returns non-ASCII content (CJK, accented Latin, emoji, etc.) from a connector / flow via executeAsync is unusable once published. ASCII-only is not an acceptable constraint for localized apps.
Workaround being evaluated
Base64-encode the payload on the flow side (a Compose action before Respond to a PowerApp or flow) and Base64-decode on the client, bypassing the multibyte-sensitive decode path. We are requesting a proper SDK-side fix so this workaround is not required.
Environment
@microsoft/power-appsSDK: 1.1.3storageproxy)localhostor vianpx power-apps run.<FlowService>.Run, i.e.IDataSource.executeAsync).Summary
When a Power Automate flow returns a JSON payload that contains multibyte UTF-8 characters (e.g. Chinese / CJK), the SDK data channel in the published app delivers a corrupted / truncated payload to the client.
JSON.parsethen throws:(
Unterminated stringis the JavaScriptCore / WebKit wording for a string that was cut off — i.e. the byte stream was broken mid-character.)The same flow, same input, same client code works correctly:
So the defect is not in the flow and not in the application JSON. It is in the SDK's response-decoding path for published apps.
Where it throws (SDK internals)
Call chain for the flow invocation:
File:
@microsoft/power-apps/dist/internal/data/core/runtimeClient/runtimeDataClient.js.The browser's
TextDecoderdecodes the multibyte bytes correctly, which is why the browser path never fails. In the published app the bytes reaching this point are already damaged.Why we believe it is a multibyte / transport-integrity issue
This matches existing reports against the same channel:
format: "binary"body parameters upload corrupted files. #230 — Known Issue: connectorexecuteAsyncmishandles payloads ("works in Power Automate flows but not viaexecuteAsync"); blanketJSON.stringifyin_buildOperationBodyParam(). Partially addressed in 1.1.3.storageproxyafter deployment (the published-app proxy corrupts byte payloads).Reproduction
executeAsync).JSON Parse error: Unterminated string.Isolation test that confirms the root cause
We changed only the content encoding of the flow's response, holding everything else constant (same flow, same client code path, same Chinese input message):
Unterminated string), works in browser.A single-variable flip (multibyte <-> ASCII) toggles the failure on/off, while the browser path is unaffected either way. This isolates the defect to multibyte-payload corruption in the SDK /
storageproxyresponse channel for published apps.Impact
Any Code App that returns non-ASCII content (CJK, accented Latin, emoji, etc.) from a connector / flow via
executeAsyncis unusable once published. ASCII-only is not an acceptable constraint for localized apps.Workaround being evaluated
Base64-encode the payload on the flow side (a Compose action before Respond to a PowerApp or flow) and Base64-decode on the client, bypassing the multibyte-sensitive decode path. We are requesting a proper SDK-side fix so this workaround is not required.