问题描述
我想与您分享编码方面的挑战,希望有人也对此挑战感兴趣,并能提供帮助,因为它需要一些“高级”打字稿技能:) 首先,使用一些基本的Javascript来阐明我要做什么:
// create a custom Task using a custom,configurable creator function
// 'createTask' should be a higher-order function returning the actual task function
const customTask = createTask( /* Some configuration parameters should go here */);
// Now we should be able to execute the task with some custom arguments
const result = customTask( { foo: true} );
挑战在于实现createTask
函数,以便...
- 您可以通过
callback
函数的createTask
参数提供任务的实际执行情况 - 所有自定义参数都应使用custom plugin软件包中的出色api配置
- 如果用错误的参数执行任务,打字稿编译器会警告您
修订1-无需类型检查
现在暂时忽略类型检查问题。
因此,在普通的javascript中,应该是这样的:
function createTask(callback,parameterConfiguration) {
return function(customArgs) {
// Todo: make sure that only valid args are passed to the callback. (using parameterConfiguration)
// execute the task with custom arguments
return callback(customArgs);
};
}
// We should be able to use the yargs api to configure which parameters our task should have:
const parameterConfiguration = require('yargs').option('foo',{ type: 'boolean' });
// Now we create our task with:
const customTaskWithFoo = createTask(callback,parameterConfiguration);
// callback function which does the actual meaningful work
function callback(customArgsWithFoo) {
const { foo } = customArgsWithFoo;
console.log('executing with args:',{ foo });
}
// later we should be able to execute the task with values for all configured parameters:
customTaskWithFoo({ foo: true });
修订2-基本类型检查
现在让我们用打字稿写这个:
import { Argv } from 'yargs'
export type CustomTask<Params,Return> = (args: Params) => Return
export type CustomTaskCallback<Params,Return> = (args: Params) => Return
export function createTask<Params,Return>(callback: CustomTaskCallback<Params,Return>,parameterConfiguration: Argv<Params>): CustomTask<Params,Return> {
return function(customArgs: Params) {
const argsFromYargs = parameterConfiguration.argv
const actualArgs = {
...argsFromYargs,...customArgs
}
return callback(actualArgs)
}
}
const customTaskWithFoo = createTask(callback,require('yargs').option('foo',{ type: 'boolean' }))
// callback function which does the actual meaningful work
function callback(customArgsWithFoo): void {
const { foo } = customArgsWithFoo
console.log('executing with args:',{ foo })
}
// execute the task. Works as expected. No compiler errors
customTaskWithFoo({ foo: false })
// Now this should be permitted by the typescript compiler,// because the `foo` parameter was configured to be a `boolean`
// using the yargs api before with `.option('foo',{ type: 'boolean' })`
// Unfortunately this is actually not rejected by the compiler.
customTaskWithFoo({ foo: 'string-value' })
现在要使这项工作按预期进行,我想我需要使用一些更复杂的打字稿魔术。
修订版3-几乎完美,但具有冗余的类型信息
我想我已经结束了,因为当我为customTask
变量明确提供Type时,它就可以工作了:
// customTask with explicit type:
let customTask: CustomTask< {foo:boolean},void>
customTask = createTask(callback,{ type: 'boolean' }))
// Now this is rejected as expected:
customTask({ foo: 'string-value' })
我对必须在两个地方编写foo
的类型感到不满意:在变量声明let customTask: CustomTask<{**foo:boolean**},void>
中的拳头和在yargs api调用.option( 'foo',{ **type: 'boolean'** } )
中的第二次
我相信有一些高级打字稿功能,允许编译器从yargs的api调用中自动推断customTask
的类型。
我希望有人可以帮助:)
谢谢!
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)