@@ -5,6 +5,7 @@ import type { EncryptionClient } from '@/encryption'
55import { EncryptionErrorTypes } from '@/errors'
66import { Encryption } from '@/index'
77import { encryptedColumn , encryptedTable } from '@/schema'
8+ import type { BulkDecryptPayload } from '@/types'
89
910/** FFI tests require longer timeout due to client initialization */
1011const FFI_TEST_TIMEOUT = 30_000
@@ -246,26 +247,30 @@ describe('FFI Error Code Preservation', () => {
246247
247248 describe ( 'bulkDecrypt error codes' , ( ) => {
248249 it (
249- 'returns undefined code for malformed ciphertexts (non-FFI validation) ' ,
250+ 'returns per-item errors for malformed ciphertexts' ,
250251 async ( ) => {
251- // bulkDecrypt uses the "fallible" FFI API (decryptBulkFallible) which normally:
252- // - Succeeds at the operation level
253- // - Returns per-item results with either { data } or { error }
254- //
255- // However, malformed ciphertexts cause parsing errors BEFORE the fallible API,
256- // which throws and triggers a top-level failure (not per-item errors).
257- // These pre-FFI errors don't have structured FFI error codes.
252+ // bulkDecrypt uses the fallible FFI API, so malformed items are
253+ // reported per item instead of failing the whole operation.
258254 const invalidCiphertexts = [
259255 { data : { i : { t : 'test_table' , c : 'email' } , v : 2 , c : 'invalid1' } } ,
260256 { data : { i : { t : 'test_table' , c : 'email' } , v : 2 , c : 'invalid2' } } ,
261- ]
257+ ] as unknown as BulkDecryptPayload
262258
263259 const result = await protectClient . bulkDecrypt ( invalidCiphertexts )
264260
265- expect ( result . failure ) . toBeDefined ( )
266- expect ( result . failure ?. type ) . toBe ( EncryptionErrorTypes . DecryptionError )
267- // FFI parsing errors don't have structured error codes
268- expect ( result . failure ?. code ) . toBeUndefined ( )
261+ if ( result . failure ) {
262+ throw new Error (
263+ `Expected per-item errors, got ${ result . failure . type } ` ,
264+ )
265+ }
266+
267+ expect ( result . data ) . toHaveLength ( 2 )
268+ expect ( result . data . every ( ( item ) => 'error' in item ) ) . toBe ( true )
269+
270+ for ( const item of result . data ) {
271+ expect ( item . error ) . toBeDefined ( )
272+ expect ( 'code' in item ) . toBe ( false )
273+ }
269274 } ,
270275 FFI_TEST_TIMEOUT ,
271276 )
0 commit comments