taler-typescript-core

Wallet core logic and WebUIs for various components
Log | Files | Refs | Submodules | README | LICENSE

commit 221f3e6b2da1f491fc15a88f324fb155227efca6
parent 84976f692f0a6df7b302d69c872ac2d60b09ae2d
Author: Florian Dold <dold@taler.net>
Date:   Tue, 21 Jul 2026 10:56:11 +0200

util: test error responses whose JSON body is null

Diffstat:
Apackages/taler-util/src/http-common.test.ts | 77+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 77 insertions(+), 0 deletions(-)

diff --git a/packages/taler-util/src/http-common.test.ts b/packages/taler-util/src/http-common.test.ts @@ -0,0 +1,77 @@ +/* + This file is part of GNU Taler + (C) 2026 Taler Systems S.A. + + GNU Taler is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3, or (at your option) any later version. + + GNU Taler is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR + A PARTICULAR PURPOSE. See the GNU General Public License for more details. + + You should have received a copy of the GNU General Public License along with + GNU Taler; see the file COPYING. If not, see <http://www.gnu.org/licenses/> + */ + +import assert from "node:assert"; +import { test } from "node:test"; +import { TalerError } from "./errors.js"; +import { + Headers, + HeadersImpl, + HttpResponse, + readTalerErrorResponse, + readUnexpectedResponseDetails, +} from "./http-common.js"; +import { TalerErrorCode } from "./taler-error-codes.js"; + +function jsonResponse(body: string, status = 400): HttpResponse { + const headers = new HeadersImpl(); + headers.set("content-type", "application/json"); + return { + requestUrl: "https://exchange.example/keys", + requestMethod: "GET", + status, + headers: headers as Headers, + async json() { + return JSON.parse(body); + }, + async text() { + return body; + }, + async bytes() { + return new TextEncoder().encode(body); + }, + }; +} + +test("a JSON null error body is reported as a malformed response", async (t) => { + // "null" is valid JSON, so the parse succeeds and the code then reads a + // property off it. That must not escape as a bare TypeError, which carries + // none of the request context. + await assert.rejects( + () => readTalerErrorResponse(jsonResponse("null")), + (e: unknown) => { + assert.ok(e instanceof TalerError, `${e}`); + assert.strictEqual( + e.errorDetail.code, + TalerErrorCode.WALLET_RECEIVED_MALFORMED_RESPONSE, + ); + return true; + }, + ); + const detail = await readUnexpectedResponseDetails(jsonResponse("null")); + assert.strictEqual( + detail.code, + TalerErrorCode.WALLET_RECEIVED_MALFORMED_RESPONSE, + ); +}); + +test("a well-formed error body is returned unchanged", async (t) => { + const detail = await readTalerErrorResponse( + jsonResponse(JSON.stringify({ code: 1234, hint: "nope" })), + ); + assert.strictEqual(detail.code, 1234); + assert.strictEqual(detail.hint, "nope"); +});