import UnionType from './UnionType' ; import { resolveReferencedType } from '../utils/referenceTypes' ; import { isAssignable } from '../utils/assignable' ; import { normalizeUnion } from '../utils/union' ; import { Annotation , Type } from '@manta-style/core' ; export default class ConditionalType extends Type { private checkType : Type ; private extendsType : Type ; private trueType : Type ; private falseType : Type ; constructor ( checkType , extendsType , trueType , falseType ) { super ( ) ; this . checkType = checkType ; this . extendsType = extendsType ; this . trueType = trueType ; this . falseType = falseType ; } private getResolvedType ( ) { const { checkType : maybeReferencedCheckType , extendsType , trueType : maybeReferencedTrueType , falseType : maybeReferencedFalseType , } = this ; const [ { type : checkType } , { type : trueType } , { type : falseType } ] = [ resolveReferencedType ( maybeReferencedCheckType ) , resolveReferencedType ( maybeReferencedTrueType ) , resolveReferencedType ( maybeReferencedFalseType ) , ] ; if ( checkType instanceof UnionType ) { const resolvedType = normalizeUnion ( new UnionType ( checkType . getTypes ( ) . map ( ( type ) => resolveConditionalType ( type , extendsType , checkType === trueType ? type : trueType , checkType === falseType ? type : falseType ) ) ) ) ; return resolvedType ; } else { const resolvedType = resolveConditionalType ( checkType , extendsType , trueType , falseType ) ; return resolvedType ; } } public deriveLiteral ( annotations ) { const resolvedType = this . getResolvedType ( ) ; return resolvedType . deriveLiteral ( annotations ) ; } public validate ( value ) { const resolvedType = this . getResolvedType ( ) ; return resolvedType . validate ( value ) ; } public format ( value ) { const resolvedType = this . getResolvedType ( ) ; return resolvedType . validate ( value ) ; } } function resolveConditionalType ( checkType , extendsType , trueType , falseType ) { return isAssignable ( checkType , extendsType ) ? trueType : falseType ; }