diff --git a/lib/online-backup.js b/lib/online-backup.js index 363a0a0..10026d7 100644 --- a/lib/online-backup.js +++ b/lib/online-backup.js @@ -235,9 +235,9 @@ async function deleteOnlineBackup(key, baseUrl = ONLINE_BACKUP_API_URL, options) headers: { 'content-type': 'application/json', accept: 'application/json' }, body: JSON.stringify({ id: parsed.id, deleteSecret }) }, options); - if (response.status !== 204) { - throw new Error(response.status === 404 ? 'Online-Sicherung wurde nicht gefunden' : 'Online-Sicherung konnte nicht gelöscht werden'); - } + if (response.status === 204) return { deleted: true, notFound: false }; + if (response.status === 404) return { deleted: false, notFound: true }; + throw new Error('Online-Sicherung konnte nicht gelöscht werden'); } module.exports = { diff --git a/tests/online-backup.test.js b/tests/online-backup.test.js index 44cc88d..8a7ccbd 100644 --- a/tests/online-backup.test.js +++ b/tests/online-backup.test.js @@ -110,7 +110,7 @@ describe('online backup transport', () => { await uploadOnlineBackup(created.record, baseUrl); const restored = await downloadOnlineBackup(created.key, baseUrl); - await deleteOnlineBackup(created.key, baseUrl); + assert.deepEqual(await deleteOnlineBackup(created.key, baseUrl), { deleted: true, notFound: false }); assert.deepEqual(restored.settings, settings()); assert.equal(JSON.stringify(stored).includes(parseOnlineBackupKey(created.key).masterKey.toString('base64url')), false); @@ -119,6 +119,40 @@ describe('online backup transport', () => { assert.equal(requestedUrls.join(' ').includes(stored.id), false); }); + it('returns an idempotent outcome when the backup is already missing', async () => { + const { createOnlineBackup, deleteOnlineBackup } = require('../lib/online-backup'); + const server = http.createServer((_request, response) => { + response.writeHead(404, { 'content-type': 'application/json' }); + response.end('{"error":"not_found"}'); + }); + servers.push(server); + server.listen(0, '127.0.0.1'); + await once(server, 'listening'); + const missingBaseUrl = `http://127.0.0.1:${server.address().port}`; + const { key } = createOnlineBackup(settings(), '2.0.3'); + + assert.deepEqual(await deleteOnlineBackup(key, missingBaseUrl), { deleted: false, notFound: true }); + }); + + it('uses the generic deletion error without reflecting the server response body', async () => { + const { createOnlineBackup, deleteOnlineBackup } = require('../lib/online-backup'); + const server = http.createServer((_request, response) => { + response.writeHead(500, { 'content-type': 'application/json' }); + response.end('{"leaked":"server-secret-value"}'); + }); + servers.push(server); + server.listen(0, '127.0.0.1'); + await once(server, 'listening'); + const baseUrl = `http://127.0.0.1:${server.address().port}`; + const { key } = createOnlineBackup(settings(), '2.0.3'); + + await assert.rejects( + deleteOnlineBackup(key, baseUrl), + (error) => error.message === 'Online-Sicherung konnte nicht gelöscht werden' + && !error.message.includes('server-secret-value') + ); + }); + it('does not reflect server response bodies into client errors', async () => { const { createOnlineBackup, uploadOnlineBackup } = require('../lib/online-backup'); const server = http.createServer((_request, response) => {