import { CallExpression , TypeChecker } from '@tsd/typescript' ; import { Diagnostic } from '../../interfaces' ; import { makeDiagnostic } from '../../utils' ; param checker param nodes return export const isIdentical = ( checker , nodes ) : Diagnostic [ ] => { const diagnostics = [ ] ; if ( ! nodes ) { return diagnostics ; } for ( const node of nodes ) { if ( ! node . typeArguments ) { continue ; } const expectedType = checker . getTypeFromTypeNode ( node . typeArguments [ 0 ] ) ; const argumentType = checker . getTypeAtLocation ( node . arguments [ 0 ] ) ; if ( ! checker . isTypeAssignableTo ( argumentType , expectedType ) ) { continue ; } if ( ! checker . isTypeAssignableTo ( expectedType , argumentType ) ) { /**
             * The expected type is not assignable to the argument type, but the argument type is
             * assignable to the expected type. This means our type is too wide.
             */ diagnostics . push ( makeDiagnostic ( node , `Parameter type \`${ checker . typeToString ( expectedType ) }\` is declared too wide for argument type \`${ checker . typeToString ( argumentType ) }\`.` ) ) ; } else if ( ! checker . isTypeIdenticalTo ( expectedType , argumentType ) ) { /**
             * The expected type and argument type are assignable in both directions. We still have to check
             * if the types are identical. See https://github.com/Microsoft/TypeScript/blob/master/doc/spec.md#3.11.2.
             */ diagnostics . push ( makeDiagnostic ( node , `Parameter type \`${ checker . typeToString ( expectedType ) }\` is not identical to argument type \`${ checker . typeToString ( argumentType ) }\`.` ) ) ; } } return diagnostics ; } ; param checker param nodes return export const isNotIdentical = ( checker , nodes ) : Diagnostic [ ] => { const diagnostics = [ ] ; if ( ! nodes ) { return diagnostics ; } for ( const node of nodes ) { if ( ! node . typeArguments ) { continue ; } const expectedType = checker . getTypeFromTypeNode ( node . typeArguments [ 0 ] ) ; const argumentType = checker . getTypeAtLocation ( node . arguments [ 0 ] ) ; if ( checker . isTypeIdenticalTo ( expectedType , argumentType ) ) { diagnostics . push ( makeDiagnostic ( node , `Parameter type \`${ checker . typeToString ( expectedType ) }\` is identical to argument type \`${ checker . typeToString ( argumentType ) }\`.` ) ) ; } } return diagnostics ; } ;