/**
* test/complex_test.ets
*
* Comprehensive tests for complex features:
* - Map fields (string->string, string->int32, string->message, int32->string)
* - Oneof fields
* - Nested messages
* - Repeated messages
* - All scalar types
* - Enums
*/
import { ComplexMessage } from '../test-output/test/messages/ComplexMessage'
import { Metadata } from '../test-output/test/messages/Metadata'
import { NestedData } from '../test-output/test/messages/NestedData'
import { Status } from '../test-output/test/enums/Status'
console.log('=== Complex Features Test Suite ===\n')
// Test 1: Map fields
console.log('Test 1: Map Fields')
const msg1 = ComplexMessage.create({
id: 'test-001',
properties: new Map([
['env', 'production'],
['region', 'us-west-1'],
['version', '2.0.0']
]),
counters: new Map([
['requests', 1000],
['errors', 5],
['success', 995]
]),
metadataMap: new Map([
['meta1', Metadata.create({ key: 'k1', value: 'v1', timestamp: 1234567890n })],
['meta2', Metadata.create({ key: 'k2', value: 'v2', timestamp: 9876543210n })]
]),
idToName: new Map([
[1, 'Alice'],
[2, 'Bob'],
[3, 'Charlie']
])
})
console.log(' properties.size:', msg1.properties.size)
console.log(' counters.size:', msg1.counters.size)
console.log(' metadataMap.size:', msg1.metadataMap.size)
console.log(' idToName.size:', msg1.idToName.size)
const binary1 = msg1.toBinary()
console.log(' Binary length:', binary1.length)
const decoded1 = ComplexMessage.fromBinary(binary1)
console.log(' Decoded properties.size:', decoded1.properties.size)
console.log(' Decoded counters.get("requests"):', decoded1.counters.get('requests'))
console.log(' Decoded metadataMap.get("meta1").key:', decoded1.metadataMap.get('meta1')?.key)
console.log(' Decoded idToName.get(2):', decoded1.idToName.get(2))
console.log(' ✅ Map fields work!\n')
// Test 2: Oneof fields
console.log('Test 2: Oneof Fields')
const msg2a = ComplexMessage.create({
id: 'test-002a',
payload: { kind: 'textPayload', textPayload: 'Hello World' }
})
console.log(' Text payload:', msg2a.payload?.kind === 'textPayload' ? msg2a.payload.textPayload : 'N/A')
const binary2a = msg2a.toBinary()
const decoded2a = ComplexMessage.fromBinary(binary2a)
console.log(' Decoded payload kind:', decoded2a.payload?.kind)
console.log(' Decoded payload value:', decoded2a.payload?.kind === 'textPayload' ? decoded2a.payload.textPayload : 'N/A')
const msg2b = ComplexMessage.create({
id: 'test-002b',
payload: { kind: 'numericPayload', numericPayload: 42 }
})
const binary2b = msg2b.toBinary()
const decoded2b = ComplexMessage.fromBinary(binary2b)
console.log(' Numeric payload:', decoded2b.payload?.kind === 'numericPayload' ? decoded2b.payload.numericPayload : 'N/A')
const msg2c = ComplexMessage.create({
id: 'test-002c',
payload: { kind: 'binaryPayload', binaryPayload: new Uint8Array([0x01, 0x02, 0x03, 0xFF]) }
})
const binary2c = msg2c.toBinary()
const decoded2c = ComplexMessage.fromBinary(binary2c)
console.log(' Binary payload length:', decoded2c.payload?.kind === 'binaryPayload' ? decoded2c.payload.binaryPayload.length : 0)
console.log(' ✅ Oneof fields work!\n')
// Test 3: Nested messages
console.log('Test 3: Nested Messages')
const msg3 = ComplexMessage.create({
id: 'test-003',
nested: NestedData.create({ name: 'nested-1', value: 100 }),
metadataList: [
Metadata.create({ key: 'k1', value: 'v1', timestamp: 111n }),
Metadata.create({ key: 'k2', value: 'v2', timestamp: 222n }),
Metadata.create({ key: 'k3', value: 'v3', timestamp: 333n })
]
})
console.log(' nested.name:', msg3.nested?.name)
console.log(' metadataList.length:', msg3.metadataList.length)
const binary3 = msg3.toBinary()
const decoded3 = ComplexMessage.fromBinary(binary3)
console.log(' Decoded nested.name:', decoded3.nested?.name)
console.log(' Decoded nested.value:', decoded3.nested?.value)
console.log(' Decoded metadataList[1].key:', decoded3.metadataList[1]?.key)
console.log(' ✅ Nested messages work!\n')
// Test 4: Recursive messages (deep nesting)
console.log('Test 4: Recursive Messages')
const msg4 = ComplexMessage.create({
id: 'parent',
count: 1,
child: ComplexMessage.create({
id: 'child-1',
count: 2,
child: ComplexMessage.create({
id: 'child-2',
count: 3,
child: ComplexMessage.create({
id: 'child-3',
count: 4
})
})
})
})
console.log(' Root id:', msg4.id)
console.log(' Child id:', msg4.child?.id)
console.log(' Grandchild id:', msg4.child?.child?.id)
console.log(' Great-grandchild id:', msg4.child?.child?.child?.id)
const binary4 = msg4.toBinary()
console.log(' Binary length:', binary4.length)
const decoded4 = ComplexMessage.fromBinary(binary4)
console.log(' Decoded root id:', decoded4.id)
console.log(' Decoded child id:', decoded4.child?.id)
console.log(' Decoded grandchild id:', decoded4.child?.child?.id)
console.log(' Decoded great-grandchild id:', decoded4.child?.child?.child?.id)
console.log(' ✅ Recursive messages work!\n')
// Test 5: All scalar types
console.log('Test 5: All Scalar Types')
const msg5 = ComplexMessage.create({
id: 'scalar-test',
count: 42,
bigNumber: 9223372036854775807n, // Max int64
price: 99.99,
active: true,
data: new Uint8Array([0xDE, 0xAD, 0xBE, 0xEF]),
status: Status.ACTIVE,
tags: ['tag1', 'tag2', 'tag3'],
numbers: [1, 2, 3, 4, 5]
})
console.log(' id:', msg5.id)
console.log(' count:', msg5.count)
console.log(' bigNumber:', msg5.bigNumber)
console.log(' price:', msg5.price)
console.log(' active:', msg5.active)
console.log(' data.length:', msg5.data.length)
console.log(' status:', Status[msg5.status as number])
console.log(' tags.length:', msg5.tags.length)
console.log(' numbers.length:', msg5.numbers.length)
const binary5 = msg5.toBinary()
console.log(' Binary length:', binary5.length)
const decoded5 = ComplexMessage.fromBinary(binary5)
console.log(' Decoded count:', decoded5.count)
console.log(' Decoded bigNumber:', decoded5.bigNumber)
console.log(' Decoded price:', decoded5.price)
console.log(' Decoded active:', decoded5.active)
console.log(' Decoded data:', Array.from(decoded5.data).map(b => '0x' + b.toString(16).toUpperCase()).join(' '))
console.log(' Decoded status:', Status[decoded5.status as number])
console.log(' ✅ All scalar types work!\n')
// Test 6: Validation
console.log('Test 6: Validation')
const validMsg = ComplexMessage.create({
id: 'valid-001',
nested: NestedData.create({ name: 'test', value: 1 }),
metadataList: [
Metadata.create({ key: 'k1', value: 'v1', timestamp: 123n })
]
})
const validationResult = validMsg.validate()
console.log(' Validation result:', validationResult === null ? 'PASS' : validationResult)
console.log(' ✅ Validation works!\n')
// Test 7: Clear and isEmpty
console.log('Test 7: Clear and isEmpty')
const msg7 = ComplexMessage.create({
id: 'test-007',
count: 100,
tags: ['a', 'b'],
properties: new Map([['key', 'value']])
})
console.log(' Before clear - isEmpty:', msg7.isEmpty())
console.log(' Before clear - id:', msg7.id)
console.log(' Before clear - count:', msg7.count)
msg7.clear()
console.log(' After clear - isEmpty:', msg7.isEmpty())
console.log(' After clear - id:', msg7.id)
console.log(' After clear - count:', msg7.count)
console.log(' After clear - tags.length:', msg7.tags.length)
console.log(' After clear - properties.size:', msg7.properties.size)
console.log(' ✅ Clear and isEmpty work!\n')
// Test 8: Clone and equals
console.log('Test 8: Clone and Equals')
const msg8 = ComplexMessage.create({
id: 'test-008',
count: 500,
properties: new Map([['env', 'test']]),
nested: NestedData.create({ name: 'nested', value: 99 })
})
const cloned8 = msg8.clone()
console.log(' Original id:', msg8.id)
console.log(' Cloned id:', cloned8.id)
console.log(' Are equal:', msg8.equals(cloned8))
cloned8.count = 999
console.log(' After modification - Original count:', msg8.count)
console.log(' After modification - Cloned count:', cloned8.count)
console.log(' After modification - Are equal:', msg8.equals(cloned8))
console.log(' ✅ Clone and equals work!\n')
console.log('=== All Complex Features Tests Passed! ✅ ===')