@@ -201,6 +201,35 @@ let SideloadedTag = {
201201 } ,
202202} ;
203203
204+ type ConfigBaseType = {
205+ publicInput ?: ProvableType ;
206+ publicOutput ?: ProvableType ;
207+ methods : {
208+ [ I in string ] : {
209+ privateInputs : Tuple < PrivateInput > ;
210+ auxiliaryOutput ?: ProvableType ;
211+ } ;
212+ } ;
213+ } ;
214+
215+ type InferMethodSignatures < Config extends ConfigBaseType > = Config [ 'methods' ] ;
216+ type InferPrivateInput < Config extends ConfigBaseType > = {
217+ [ I in keyof Config [ 'methods' ] ] : Config [ 'methods' ] [ I ] [ 'privateInputs' ] ;
218+ } ;
219+ type InferAuxiliaryOutputs < Config extends ConfigBaseType > = {
220+ [ I in keyof InferMethodSignatures < Config > ] : Get <
221+ InferMethodSignatures < Config > [ I ] ,
222+ 'auxiliaryOutput'
223+ > ;
224+ } ;
225+ type InferMethodType < Config extends ConfigBaseType > = {
226+ [ I in keyof Config [ 'methods' ] ] : Method <
227+ InferProvableOrUndefined < Get < Config , 'publicInput' > > ,
228+ InferProvableOrVoid < Get < Config , 'publicOutput' > > ,
229+ Config [ 'methods' ] [ I ]
230+ > ;
231+ } ;
232+
204233/**
205234 * Wraps config + provable code into a program capable of producing {@link Proof}s.
206235 *
@@ -229,40 +258,13 @@ let SideloadedTag = {
229258 * @returns an object that can be used to compile, prove, and verify the program.
230259 */
231260function ZkProgram <
232- Config extends {
233- publicInput ?: ProvableType ;
234- publicOutput ?: ProvableType ;
235- methods : {
236- [ I in string ] : {
237- privateInputs : Tuple < PrivateInput > ;
238- auxiliaryOutput ?: ProvableType ;
239- } ;
240- } ;
241- } ,
242- Methods extends {
243- [ I in keyof Config [ 'methods' ] ] : Method <
244- InferProvableOrUndefined < Get < Config , 'publicInput' > > ,
245- InferProvableOrVoid < Get < Config , 'publicOutput' > > ,
246- Config [ 'methods' ] [ I ]
247- > ;
248- } ,
249- // derived types for convenience
250- MethodSignatures extends Config [ 'methods' ] = Config [ 'methods' ] ,
251- PrivateInputs extends {
252- [ I in keyof Config [ 'methods' ] ] : Config [ 'methods' ] [ I ] [ 'privateInputs' ] ;
253- } = {
254- [ I in keyof Config [ 'methods' ] ] : Config [ 'methods' ] [ I ] [ 'privateInputs' ] ;
255- } ,
256- AuxiliaryOutputs extends {
257- [ I in keyof MethodSignatures ] : Get < MethodSignatures [ I ] , 'auxiliaryOutput' > ;
258- } = {
259- [ I in keyof MethodSignatures ] : Get < MethodSignatures [ I ] , 'auxiliaryOutput' > ;
260- }
261+ Config extends ConfigBaseType ,
262+ _ extends unknown = unknown // weird hack that makes methods infer correctly when their inputs are not annotated
261263> (
262264 config : Config & {
263265 name : string ;
264266 methods : {
265- [ I in keyof Config [ 'methods' ] ] : Methods [ I ] ;
267+ [ I in keyof Config [ 'methods' ] ] : InferMethodType < Config > [ I ] ;
266268 } ;
267269 overrideWrapDomain ?: 0 | 1 | 2 ;
268270 }
@@ -292,10 +294,10 @@ function ZkProgram<
292294
293295 publicInputType : ProvableOrUndefined < Get < Config , 'publicInput' > > ;
294296 publicOutputType : ProvableOrVoid < Get < Config , 'publicOutput' > > ;
295- privateInputTypes : PrivateInputs ;
296- auxiliaryOutputTypes : AuxiliaryOutputs ;
297+ privateInputTypes : InferPrivateInput < Config > ;
298+ auxiliaryOutputTypes : InferAuxiliaryOutputs < Config > ;
297299 rawMethods : {
298- [ I in keyof Config [ 'methods' ] ] : Methods [ I ] [ 'method' ] ;
300+ [ I in keyof Config [ 'methods' ] ] : InferMethodType < Config > [ I ] [ 'method' ] ;
299301 } ;
300302
301303 Proof : typeof Proof <
@@ -309,10 +311,15 @@ function ZkProgram<
309311 [ I in keyof Config [ 'methods' ] ] : Prover <
310312 InferProvableOrUndefined < Get < Config , 'publicInput' > > ,
311313 InferProvableOrVoid < Get < Config , 'publicOutput' > > ,
312- PrivateInputs [ I ] ,
313- InferProvableOrUndefined < AuxiliaryOutputs [ I ] >
314+ InferPrivateInput < Config > [ I ] ,
315+ InferProvableOrUndefined < InferAuxiliaryOutputs < Config > [ I ] >
314316 > ;
315317} {
318+ // derived types for convenience
319+ type Methods = InferMethodSignatures < Config > ;
320+ type PrivateInputs = InferPrivateInput < Config > ;
321+ type AuxiliaryOutputs = InferAuxiliaryOutputs < Config > ;
322+
316323 let doProving = true ;
317324
318325 let methods = config . methods ;
@@ -626,15 +633,8 @@ type ZkProgram<
626633 auxiliaryOutput ?: ProvableType ;
627634 } ;
628635 } ;
629- } ,
630- Methods extends {
631- [ I in keyof Config [ 'methods' ] ] : Method <
632- InferProvableOrUndefined < Get < Config , 'publicInput' > > ,
633- InferProvableOrVoid < Get < Config , 'publicOutput' > > ,
634- Config [ 'methods' ] [ I ]
635- > ;
636636 }
637- > = ReturnType < typeof ZkProgram < Config , Methods > > ;
637+ > = ReturnType < typeof ZkProgram < Config > > ;
638638
639639/**
640640 * A class representing the type of Proof produced by the {@link ZkProgram} in which it is used.
0 commit comments