Skip to content

Commit 82eb85c

Browse files
authored
Merge pull request #284 from cipherstash/searchable-json-integration-tests
Searchable json integration tests
2 parents 7d93d9c + 0b7931e commit 82eb85c

File tree

9 files changed

+2576
-16
lines changed

9 files changed

+2576
-16
lines changed

.github/workflows/tests.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ jobs:
4040
echo "CS_CLIENT_ACCESS_KEY=${{ secrets.CS_CLIENT_ACCESS_KEY }}" >> ./packages/protect/.env
4141
echo "SUPABASE_URL=${{ secrets.SUPABASE_URL }}" >> ./packages/protect/.env
4242
echo "SUPABASE_ANON_KEY=${{ secrets.SUPABASE_ANON_KEY }}" >> ./packages/protect/.env
43+
echo "DATABASE_URL=${{ secrets.DATABASE_URL }}" >> ./packages/protect/.env
4344
echo "CS_ZEROKMS_HOST=https://ap-southeast-2.aws.zerokms.cipherstashmanaged.net" >> ./packages/protect/.env
4445
echo "CS_CTS_HOST=https://ap-southeast-2.aws.cts.cipherstashmanaged.net" >> ./packages/protect/.env
4546

packages/protect/__tests__/encrypt-query-searchable-json.test.ts

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -395,6 +395,79 @@ describe('searchableJson with returnType formatting', () => {
395395
// Format: "(\"json\")" - outer quotes with escaped inner quotes
396396
expect(data[0]).toMatch(/^"\(.*\)"$/)
397397
}, 30000)
398+
399+
describe('single-value returnType', () => {
400+
it('returns composite-literal for selector', async () => {
401+
const result = await protectClient.encryptQuery('$.user.email', {
402+
column: jsonbSchema.metadata,
403+
table: jsonbSchema,
404+
queryType: 'searchableJson',
405+
returnType: 'composite-literal',
406+
})
407+
408+
const data = unwrapResult(result)
409+
expect(typeof data).toBe('string')
410+
expect(data).toMatch(/^\(".*"\)$/)
411+
}, 30000)
412+
413+
it('returns composite-literal for term', async () => {
414+
const result = await protectClient.encryptQuery({ role: 'admin' }, {
415+
column: jsonbSchema.metadata,
416+
table: jsonbSchema,
417+
queryType: 'searchableJson',
418+
returnType: 'composite-literal',
419+
})
420+
421+
const data = unwrapResult(result)
422+
expect(typeof data).toBe('string')
423+
expect(data).toMatch(/^\(".*"\)$/)
424+
}, 30000)
425+
426+
it('returns escaped-composite-literal for selector', async () => {
427+
const result = await protectClient.encryptQuery('$.user.email', {
428+
column: jsonbSchema.metadata,
429+
table: jsonbSchema,
430+
queryType: 'searchableJson',
431+
returnType: 'escaped-composite-literal',
432+
})
433+
434+
const data = unwrapResult(result)
435+
expect(typeof data).toBe('string')
436+
expect(data as string).toMatch(/^"\(.*\)"$/)
437+
// JSON.parse should yield the composite-literal format
438+
const parsed = JSON.parse(data as string)
439+
expect(parsed).toMatch(/^\(.*\)$/)
440+
}, 30000)
441+
442+
it('returns escaped-composite-literal for term', async () => {
443+
const result = await protectClient.encryptQuery({ role: 'admin' }, {
444+
column: jsonbSchema.metadata,
445+
table: jsonbSchema,
446+
queryType: 'searchableJson',
447+
returnType: 'escaped-composite-literal',
448+
})
449+
450+
const data = unwrapResult(result)
451+
expect(typeof data).toBe('string')
452+
expect(data as string).toMatch(/^"\(.*\)"$/)
453+
const parsed = JSON.parse(data as string)
454+
expect(parsed).toMatch(/^\(.*\)$/)
455+
}, 30000)
456+
457+
it('returns Encrypted object when returnType is omitted', async () => {
458+
const result = await protectClient.encryptQuery('$.user.email', {
459+
column: jsonbSchema.metadata,
460+
table: jsonbSchema,
461+
queryType: 'searchableJson',
462+
})
463+
464+
const data = unwrapResult(result) as any
465+
expect(typeof data).toBe('object')
466+
expect(data).toHaveProperty('i')
467+
expect(data.i).toHaveProperty('t')
468+
expect(data.i).toHaveProperty('c')
469+
}, 30000)
470+
})
398471
})
399472

400473
describe('searchableJson with LockContext', () => {

packages/protect/__tests__/encrypt-query.test.ts

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -561,6 +561,84 @@ describe('encryptQuery', () => {
561561
}, 30000)
562562
})
563563

564+
describe('single-value returnType formatting', () => {
565+
it('returns Encrypted by default (no returnType)', async () => {
566+
const result = await protectClient.encryptQuery('test@example.com', {
567+
column: users.email,
568+
table: users,
569+
queryType: 'equality',
570+
})
571+
572+
const data = unwrapResult(result)
573+
574+
expect(data).toMatchObject({
575+
i: { t: 'users', c: 'email' },
576+
v: 2,
577+
})
578+
expect(typeof data).toBe('object')
579+
}, 30000)
580+
581+
it('returns composite-literal format when specified', async () => {
582+
const result = await protectClient.encryptQuery('test@example.com', {
583+
column: users.email,
584+
table: users,
585+
queryType: 'equality',
586+
returnType: 'composite-literal',
587+
})
588+
589+
const data = unwrapResult(result)
590+
591+
expect(typeof data).toBe('string')
592+
// Format: ("json")
593+
expect(data).toMatch(/^\(".*"\)$/)
594+
}, 30000)
595+
596+
it('returns escaped-composite-literal format when specified', async () => {
597+
const result = await protectClient.encryptQuery('test@example.com', {
598+
column: users.email,
599+
table: users,
600+
queryType: 'equality',
601+
returnType: 'escaped-composite-literal',
602+
})
603+
604+
const data = unwrapResult(result)
605+
606+
expect(typeof data).toBe('string')
607+
// Format: "(\"json\")" - outer quotes with escaped inner quotes
608+
expect(data).toMatch(/^"\(.*\)"$/)
609+
}, 30000)
610+
611+
it('returns eql format when explicitly specified', async () => {
612+
const result = await protectClient.encryptQuery('test@example.com', {
613+
column: users.email,
614+
table: users,
615+
queryType: 'equality',
616+
returnType: 'eql',
617+
})
618+
619+
const data = unwrapResult(result)
620+
621+
expect(data).toMatchObject({
622+
i: { t: 'users', c: 'email' },
623+
v: 2,
624+
})
625+
expect(typeof data).toBe('object')
626+
}, 30000)
627+
628+
it('handles null value with composite-literal returnType', async () => {
629+
const result = await protectClient.encryptQuery(null, {
630+
column: users.email,
631+
table: users,
632+
queryType: 'equality',
633+
returnType: 'composite-literal',
634+
})
635+
636+
const data = unwrapResult(result)
637+
638+
expect(data).toBeNull()
639+
}, 30000)
640+
})
641+
564642
describe('LockContext support', () => {
565643
it('single query with LockContext calls getLockContext', async () => {
566644
const mockLockContext = createMockLockContext()

0 commit comments

Comments
 (0)