Merge pull request 'Varadic args are always last in javascript' (#3) from varadic-and-named into main
Reviewed-on: #3
This commit is contained in:
commit
eb4f103ba3
16
src/vm.ts
16
src/vm.ts
|
|
@ -468,14 +468,6 @@ export class VM {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle variadic parameter (TypeScript rest parameters)
|
|
||||||
// For TypeScript functions with ...rest, we spread the remaining args
|
|
||||||
// rather than wrapping them in an array
|
|
||||||
if (paramInfo.variadic) {
|
|
||||||
const remainingArgs = positionalArgs.slice(nativePositionalArgIndex)
|
|
||||||
nativeArgs.push(...remainingArgs)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Handle named parameter (collect remaining unmatched named args)
|
// Handle named parameter (collect remaining unmatched named args)
|
||||||
// Parameter names matching atXxx pattern (e.g., atOptions, atNamed) collect extra named args
|
// Parameter names matching atXxx pattern (e.g., atOptions, atNamed) collect extra named args
|
||||||
if (paramInfo.named) {
|
if (paramInfo.named) {
|
||||||
|
|
@ -488,6 +480,14 @@ export class VM {
|
||||||
nativeArgs.push(toValue(namedObj))
|
nativeArgs.push(toValue(namedObj))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Handle variadic parameter (TypeScript rest parameters)
|
||||||
|
// For TypeScript functions with ...rest, we spread the remaining args
|
||||||
|
// rather than wrapping them in an array
|
||||||
|
if (paramInfo.variadic) {
|
||||||
|
const remainingArgs = positionalArgs.slice(nativePositionalArgIndex)
|
||||||
|
nativeArgs.push(...remainingArgs)
|
||||||
|
}
|
||||||
|
|
||||||
// Call the native function with bound args
|
// Call the native function with bound args
|
||||||
const result = await fn.fn(...nativeArgs)
|
const result = await fn.fn(...nativeArgs)
|
||||||
this.stack.push(result)
|
this.stack.push(result)
|
||||||
|
|
|
||||||
|
|
@ -534,6 +534,31 @@ test("@named pattern - basic atNamed parameter", async () => {
|
||||||
expect(result).toEqual({ type: 'string', value: 'Hi, Alice! Extra: value' })
|
expect(result).toEqual({ type: 'string', value: 'Hi, Alice! Extra: value' })
|
||||||
})
|
})
|
||||||
|
|
||||||
|
test('@named pattern - atNamed parameters with varadic args', async () => {
|
||||||
|
const bytecode = toBytecode(`
|
||||||
|
TRY_LOAD cmd
|
||||||
|
TRY_LOAD rest1
|
||||||
|
TRY_LOAD rest2
|
||||||
|
PUSH 'named'
|
||||||
|
TRY_LOAD named-value
|
||||||
|
PUSH 2
|
||||||
|
PUSH 1
|
||||||
|
CALL
|
||||||
|
HALT
|
||||||
|
`)
|
||||||
|
|
||||||
|
const vm = new VM(bytecode)
|
||||||
|
vm.registerFunction('cmd', (atNamed: any = {}, ...rest: string[]) => {
|
||||||
|
return { rest, namedArg: atNamed['named'] }
|
||||||
|
})
|
||||||
|
|
||||||
|
const result = await vm.run()
|
||||||
|
expect(result.type).toBe('dict')
|
||||||
|
if (!(result.value instanceof Map)) throw new Error('Expected dict')
|
||||||
|
expect(result.value.get('rest')).toEqual(toValue(['rest1', 'rest2']))
|
||||||
|
expect(result.value.get('namedArg')).toEqual(toValue('named-value'))
|
||||||
|
})
|
||||||
|
|
||||||
test("@named pattern - mixed positional and atOptions", async () => {
|
test("@named pattern - mixed positional and atOptions", async () => {
|
||||||
const bytecode = toBytecode(`
|
const bytecode = toBytecode(`
|
||||||
LOAD configure
|
LOAD configure
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user