demo/typescript.js
function isRelatedTo(source, target, reportErrors, headMessage) {
                var result;
                // both types are the same - covers 'they are the same primitive type or both are Any' or the same type parameter cases
                if (source === target)
                    return -1 /* True */;
                if (relation === identityRelation) {
                    return isIdenticalTo(source, target);
                }
                if (isTypeAny(target))
                    return -1 /* True */;
                if (source === undefinedType)
                    return -1 /* True */;
                if (source === nullType && target !== undefinedType)
                    return -1 /* True */;
                if (source.flags & 128 /* Enum */ && target === numberType)
                    return -1 /* True */;
                if (source.flags & 256 /* StringLiteral */ && target === stringType)
                    return -1 /* True */;
                if (relation === assignableRelation) {
                    if (isTypeAny(source))
                        return -1 /* True */;
                    if (source === numberType && target.flags & 128 /* Enum */)
                        return -1 /* True */;
                }
                if (source.flags & 1048576 /* FreshObjectLiteral */) {
                    if (hasExcessProperties(source, target, reportErrors)) {
                        if (reportErrors) {
                            reportRelationError(headMessage, source, target);
                        }
                        return 0 /* False */;
                    }
                    // Above we check for excess properties with respect to the entire target type. When union
                    // and intersection types are further deconstructed on the target side, we don't want to
                    // make the check again (as it might fail for a partial target type). Therefore we obtain
                    // the regular source type and proceed with that.
                    if (target.flags & 49152 /* UnionOrIntersection */) {
                        source = getRegularTypeOfObjectLiteral(source);
                    }
                }
                var saveErrorInfo = errorInfo;
                // Note that the "each" checks must precede the "some" checks to produce the correct results
                if (source.flags & 16384 /* Union */) {
                    if (result = eachTypeRelatedToType(source, target, reportErrors)) {
                        return result;
                    }
                }
                else if (target.flags & 32768 /* Intersection */) {
                    if (result = typeRelatedToEachType(source, target, reportErrors)) {
                        return result;
                    }
                }
                else {
                    // It is necessary to try "some" checks on both sides because there may be nested "each" checks
                    // on either side that need to be prioritized. For example, A | B = (A | B) & (C | D) or
                    // A & B = (A & B) | (C & D).
                    if (source.flags & 32768 /* Intersection */) {
                        // If target is a union type the following check will report errors so we suppress them here
                        if (result = someTypeRelatedToType(source, target, reportErrors && !(target.flags & 16384 /* Union */))) {
                            return result;
                        }
                    }
                    if (target.flags & 16384 /* Union */) {
                        if (result = typeRelatedToSomeType(source, target, reportErrors)) {
                            return result;
                        }
                    }
                }
                if (source.flags & 512 /* TypeParameter */) {
                    var constraint = getConstraintOfTypeParameter(source);
                    if (!constraint || constraint.flags & 1 /* Any */) {
                        constraint = emptyObjectType;
                    }
                    // Report constraint errors only if the constraint is not the empty object type
                    var reportConstraintErrors = reportErrors && constraint !== emptyObjectType;
                    if (result = isRelatedTo(constraint, target, reportConstraintErrors)) {
                        errorInfo = saveErrorInfo;
                        return result;
                    }
                }
                else {
                    if (source.flags & 4096 /* Reference */ && target.flags & 4096 /* Reference */ && source.target === target.target) {
                        // We have type references to same target type, see if relationship holds for all type arguments
                        if (result = typeArgumentsRelatedTo(source, target, reportErrors)) {
                            return result;
                        }
                    }
                    // Even if relationship doesn't hold for unions, intersections, or generic type references,
                    // it may hold in a structural comparison.
                    var apparentType = getApparentType(source);
                    // In a check of the form X = A & B, we will have previously checked if A relates to X or B relates
                    // to X. Failing both of those we want to check if the aggregation of A and B's members structurally
                    // relates to X. Thus, we include intersection types on the source side here.
                    if (apparentType.flags & (80896 /* ObjectType */ | 32768 /* Intersection */) && target.flags & 80896 /* ObjectType */) {
                        // Report structural errors only if we haven't reported any errors yet
                        var reportStructuralErrors = reportErrors && errorInfo === saveErrorInfo;
                        if (result = objectTypeRelatedTo(apparentType, target, reportStructuralErrors)) {
                            errorInfo = saveErrorInfo;
                            return result;
                        }
                    }
                }
                if (reportErrors) {
                    reportRelationError(headMessage, source, target);
                }
                return 0 /* False */;
            }
function isRelatedTo(source, target, reportErrors, headMessage) {
                var result;
                // both types are the same - covers 'they are the same primitive type or both are Any' or the same type parameter cases
                if (source === target)
                    return -1 /* True */;
                if (relation === identityRelation) {
                    return isIdenticalTo(source, target);
                }
                if (isTypeAny(target))
                    return -1 /* True */;
                if (source === undefinedType)
                    return -1 /* True */;
                if (source === nullType && target !== undefinedType)
                    return -1 /* True */;
                if (source.flags & 128 /* Enum */ && target === numberType)
                    return -1 /* True */;
                if (source.flags & 256 /* StringLiteral */ && target === stringType)
                    return -1 /* True */;
                if (relation === assignableRelation) {
                    if (isTypeAny(source))
                        return -1 /* True */;
                    if (source === numberType && target.flags & 128 /* Enum */)
                        return -1 /* True */;
                }
                if (source.flags & 1048576 /* FreshObjectLiteral */) {
                    if (hasExcessProperties(source, target, reportErrors)) {
                        if (reportErrors) {
                            reportRelationError(headMessage, source, target);
                        }
                        return 0 /* False */;
                    }
                    // Above we check for excess properties with respect to the entire target type. When union
                    // and intersection types are further deconstructed on the target side, we don't want to
                    // make the check again (as it might fail for a partial target type). Therefore we obtain
                    // the regular source type and proceed with that.
                    if (target.flags & 49152 /* UnionOrIntersection */) {
                        source = getRegularTypeOfObjectLiteral(source);
                    }
                }
                var saveErrorInfo = errorInfo;
                // Note that the "each" checks must precede the "some" checks to produce the correct results
                if (source.flags & 16384 /* Union */) {
                    if (result = eachTypeRelatedToType(source, target, reportErrors)) {
                        return result;
                    }
                }
                else if (target.flags & 32768 /* Intersection */) {
                    if (result = typeRelatedToEachType(source, target, reportErrors)) {
                        return result;
                    }
                }
                else {
                    // It is necessary to try "some" checks on both sides because there may be nested "each" checks
                    // on either side that need to be prioritized. For example, A | B = (A | B) & (C | D) or
                    // A & B = (A & B) | (C & D).
                    if (source.flags & 32768 /* Intersection */) {
                        // If target is a union type the following check will report errors so we suppress them here
                        if (result = someTypeRelatedToType(source, target, reportErrors && !(target.flags & 16384 /* Union */))) {
                            return result;
                        }
                    }
                    if (target.flags & 16384 /* Union */) {
                        if (result = typeRelatedToSomeType(source, target, reportErrors)) {
                            return result;
                        }
                    }
                }
                if (source.flags & 512 /* TypeParameter */) {
                    var constraint = getConstraintOfTypeParameter(source);
                    if (!constraint || constraint.flags & 1 /* Any */) {
                        constraint = emptyObjectType;
                    }
                    // Report constraint errors only if the constraint is not the empty object type
                    var reportConstraintErrors = reportErrors && constraint !== emptyObjectType;
                    if (result = isRelatedTo(constraint, target, reportConstraintErrors)) {
                        errorInfo = saveErrorInfo;
                        return result;
                    }
                }
                else {
                    if (source.flags & 4096 /* Reference */ && target.flags & 4096 /* Reference */ && source.target === target.target) {
                        // We have type references to same target type, see if relationship holds for all type arguments
                        if (result = typeArgumentsRelatedTo(source, target, reportErrors)) {
                            return result;
                        }
                    }
                    // Even if relationship doesn't hold for unions, intersections, or generic type references,
                    // it may hold in a structural comparison.
                    var apparentType = getApparentType(source);
                    // In a check of the form X = A & B, we will have previously checked if A relates to X or B relates
                    // to X. Failing both of those we want to check if the aggregation of A and B's members structurally
                    // relates to X. Thus, we include intersection types on the source side here.
                    if (apparentType.flags & (80896 /* ObjectType */ | 32768 /* Intersection */) && target.flags & 80896 /* ObjectType */) {
                        // Report structural errors only if we haven't reported any errors yet
                        var reportStructuralErrors = reportErrors && errorInfo === saveErrorInfo;
                        if (result = objectTypeRelatedTo(apparentType, target, reportStructuralErrors)) {
                            errorInfo = saveErrorInfo;
                            return result;
                        }
                    }
                }
                if (reportErrors) {
                    reportRelationError(headMessage, source, target);
                }
                return 0 /* False */;
            }
function isRelatedTo ( source , target , reportErrors , headMessage ) { var result ; // both types are the same - covers 'they are the same primitive type or both are Any' or the same type parameter cases if ( source === target ) return - 1 /* True */ ; if ( relation === identityRelation ) { return isIdenticalTo ( source , target ) ; } if ( isTypeAny ( target ) ) return - 1 /* True */ ; if ( source === undefinedType ) return - 1 /* True */ ; if ( source === nullType && target !== undefinedType ) return - 1 /* True */ ; if ( source . flags & 128 /* Enum */ && target === numberType ) return - 1 /* True */ ; if ( source . flags & 256 /* StringLiteral */ && target === stringType ) return - 1 /* True */ ; if ( relation === assignableRelation ) { if ( isTypeAny ( source ) ) return - 1 /* True */ ; if ( source === numberType && target . flags & 128 /* Enum */ ) return - 1 /* True */ ; } if ( source . flags & 1048576 /* FreshObjectLiteral */ ) { if ( hasExcessProperties ( source , target , reportErrors ) ) { if ( reportErrors ) { reportRelationError ( headMessage , source , target ) ; } return 0 /* False */ ; } // Above we check for excess properties with respect to the entire target type. When union // and intersection types are further deconstructed on the target side, we don't want to // make the check again (as it might fail for a partial target type). Therefore we obtain // the regular source type and proceed with that. if ( target . flags & 49152 /* UnionOrIntersection */ ) { source = getRegularTypeOfObjectLiteral ( source ) ; } } var saveErrorInfo = errorInfo ; // Note that the "each" checks must precede the "some" checks to produce the correct results if ( source . flags & 16384 /* Union */ ) { if ( result = eachTypeRelatedToType ( source , target , reportErrors ) ) { return result ; } } else if ( target . flags & 32768 /* Intersection */ ) { if ( result = typeRelatedToEachType ( source , target , reportErrors ) ) { return result ; } } else { // It is necessary to try "some" checks on both sides because there may be nested "each" checks // on either side that need to be prioritized. For example, A | B = (A | B) & (C | D) or // A & B = (A & B) | (C & D). if ( source . flags & 32768 /* Intersection */ ) { // If target is a union type the following check will report errors so we suppress them here if ( result = someTypeRelatedToType ( source , target , reportErrors && ! ( target . flags & 16384 /* Union */ ) ) ) { return result ; } } if ( target . flags & 16384 /* Union */ ) { if ( result = typeRelatedToSomeType ( source , target , reportErrors ) ) { return result ; } } } if ( source . flags & 512 /* TypeParameter */ ) { var constraint = getConstraintOfTypeParameter ( source ) ; if ( ! constraint || constraint . flags & 1 /* Any */ ) { constraint = emptyObjectType ; } // Report constraint errors only if the constraint is not the empty object type var reportConstraintErrors = reportErrors && constraint !== emptyObjectType ; if ( result = isRelatedTo ( constraint , target , reportConstraintErrors ) ) { errorInfo = saveErrorInfo ; return result ; } } else { if ( source . flags & 4096 /* Reference */ && target . flags & 4096 /* Reference */ && source . target === target . target ) { // We have type references to same target type, see if relationship holds for all type arguments if ( result = typeArgumentsRelatedTo ( source , target , reportErrors ) ) { return result ; } } // Even if relationship doesn't hold for unions, intersections, or generic type references, // it may hold in a structural comparison. var apparentType = getApparentType ( source ) ; // In a check of the form X = A & B, we will have previously checked if A relates to X or B relates // to X. Failing both of those we want to check if the aggregation of A and B's members structurally // relates to X. Thus, we include intersection types on the source side here. if ( apparentType . flags & ( 80896 /* ObjectType */ | 32768 /* Intersection */ ) && target . flags & 80896 /* ObjectType */ ) { // Report structural errors only if we haven't reported any errors yet var reportStructuralErrors = reportErrors && errorInfo === saveErrorInfo ; if ( result = objectTypeRelatedTo ( apparentType , target , reportStructuralErrors ) ) { errorInfo = saveErrorInfo ; return result ; } } } if ( reportErrors ) { reportRelationError ( headMessage , source , target ) ; } return 0 /* False */ ; }
Compare two types and return Ternary.True if they are related with no assumptions, Ternary.Maybe if they are related with assumptions of other relationships, or Ternary.False if they are not related.
Compare two types and return Ternary . True if they are related with no assumptions Ternary . Maybe if they are related with assumptions of other relationships or Ternary . False if they are not related .