plantain-00 / type-coverage

A CLI tool to check type coverage for typescript code
MIT License
1.26k stars 44 forks source link

A lot of unexpected reports, maybe related to paths #101

Closed JounQin closed 2 years ago

JounQin commented 3 years ago

Version(if relevant): 2.18.2

Environment(if relevant):

Code(if relevant):

// tsconfig.json
{
  "extends": "@1stg/tsconfig/tsconfig",
  "compilerOptions": {
    "baseUrl": ".",
    "jsx": "react-jsx",
    "lib": ["DOM", "ESNext"],
    "noImplicitOverride": true,
    "paths": {
      "*": ["src/*"],
      "lodash": ["lodash-es"],
      "assets/*": ["assets/*"],
      "server": ["server"],
      "shared": ["shared"]
    }
  }
}
// shared/index.ts
export const BAD_REQUEST = 400
export const REDIRECT = 302

export interface ApiErrorOptions<
  R extends string = string,
  E extends object = object,
  T = unknown,
> {
  code: number
  reason: R
  message: string
  extra?: E
  details?: T[]
}

export interface ApiError<
  R extends string = string,
  E extends object = object,
  T = unknown,
> extends ApiErrorOptions<R, E, T>,
    Error {
  // client
  response?: Response
}
import type { ApiError, ApiErrorOptions } from 'shared'
import { REDIRECT, BAD_REQUEST } from 'shared'

export class ResponseError<
    R extends string = string,
    E extends object = object,
    T = unknown,
  >
  extends Error
  implements ApiError<R, E, T>
{
  declare code: number
  declare reason: R
  declare extra: E | undefined
  declare details: T[] | undefined

  constructor(optionsOrMsg: Partial<ApiErrorOptions<R, E, T>> | string) {
    const options =
      typeof optionsOrMsg === 'string'
        ? { message: optionsOrMsg }
        : optionsOrMsg
    super(options.message)
    this.code = options.code || BAD_REQUEST
    this.reason = options.reason || ('Bad Request' as R)
    this.extra = options.extra
    this.details = options.details
  }
}

export class RedirectError extends ResponseError {
  constructor(url: string) {
    super({
      message: url,
      code: REDIRECT,
    })
  }
}

Expected:

No report

Actual:

src/types/shim.ts:2:15: StoreValue
src/types/shim.ts:7:44: value
src/types/shim.ts:7:51: StoreValue
server/utils/errors.ts:17:15: optionsOrMsg
server/utils/errors.ts:18:11: options
server/utils/errors.ts:19:14: optionsOrMsg
server/utils/errors.ts:21:11: optionsOrMsg
server/utils/errors.ts:22:11: options
server/utils/errors.ts:22:19: message
server/utils/errors.ts:23:17: options
server/utils/errors.ts:23:25: code
server/utils/errors.ts:24:19: options
server/utils/errors.ts:24:27: reason
server/utils/errors.ts:25:18: options
server/utils/errors.ts:25:26: extra
server/utils/errors.ts:26:20: options
server/utils/errors.ts:26:28: details
server/utils/proxy.ts:10:7: encoded
server/utils/proxy.ts:17:29: encoded
server/utils/proxy.ts:18:47: encoded
server/middlewares/mock.ts:105:21: body
server/middlewares/mock.ts:109:15: status
server/middlewares/mock.ts:110:13: status
server/middlewares/validate.ts:21:10: name
server/middlewares/validate.ts:21:16: path
server/middlewares/validate.ts:21:27: name
server/middlewares/validate.ts:22:3: name
server/middlewares/validate.ts:23:3: path
server/middlewares/validate.ts:33:17: path
server/middlewares/validate.ts:33:48: path
src/hooks/api.ts:12:3: method
src/hooks/api.ts:215:5: method
src/hooks/api.ts:230:5: method
src/interceptors.ts:15:13: data
src/interceptors.ts:16:31: data
src/plugins/translate/hook.ts:226:35: ignoreNonExist
src/components/StrongPassword/index.tsx:58:5: ev
src/components/StrongPassword/index.tsx:66:5: ev
src/modules/components/Pie.tsx:9:3: dataAll
src/modules/components/Pie.tsx:12:48: dataAll
src/modules/components/Pie.tsx:17:7: value
src/modules/components/Pie.tsx:17:14: dataAll
src/modules/components/Pie.tsx:17:23: open
src/modules/components/Pie.tsx:21:7: value
src/modules/components/Pie.tsx:21:14: dataAll
src/modules/components/Pie.tsx:21:23: solving
src/modules/components/Pie.tsx:25:7: value
src/modules/components/Pie.tsx:25:14: dataAll
src/modules/components/Pie.tsx:25:23: resolved
src/modules/components/Pie.tsx:29:7: value
src/modules/components/Pie.tsx:29:14: dataAll
src/modules/components/Pie.tsx:29:23: closed
src/modules/components/Pie.tsx:75:21: dataAll
src/modules/components/Pie.tsx:75:30: total
src/modules/components/Pie.tsx:97:33: dataAll
src/modules/components/Pie.tsx:97:42: total
src/modules/components/Pie.tsx:98:38: dataAll
src/modules/components/Pie.tsx:98:46: total
src/modules/components/Pie.tsx:127:10: dataAll
src/pages/Home/index.tsx:31:11: data
src/pages/Home/index.tsx:56:49: data
src/pages/Home/index.tsx:56:55: tenantName
src/pages/Home/index.tsx:57:16: data
src/pages/Home/index.tsx:57:22: tenantName
src/pages/Home/index.tsx:61:12: data
src/pages/Home/index.tsx:61:18: currentUser
src/pages/Home/index.tsx:61:30: name
src/pages/Home/index.tsx:74:55: data
src/pages/Home/index.tsx:74:61: serviceCall
src/pages/Home/index.tsx:75:14: data
src/pages/Home/index.tsx:75:20: serviceUsers
src/pages/Home/index.tsx:75:33: map
src/pages/Home/index.tsx:75:38: user
src/pages/Home/index.tsx:75:44: index
src/pages/Home/index.tsx:78:23: user
src/pages/Home/index.tsx:78:28: duty
src/pages/Home/index.tsx:79:24: data
src/pages/Home/index.tsx:79:29: serviceCall
src/pages/Home/index.tsx:80:23: user
src/pages/Home/index.tsx:80:28: name
src/pages/Home/index.tsx:96:21: dataAll
src/pages/Home/index.tsx:96:30: data
src/pages/Home/index.tsx:96:36: issueStatistics
src/pages/Info/Corp.tsx:10:11: data
src/pages/Info/Corp.tsx:21:16: data
src/pages/Info/Corp.tsx:21:22: tenantAccount
src/pages/Info/Corp.tsx:24:16: data
src/pages/Info/Corp.tsx:24:22: tenantName
src/pages/Info/Corp.tsx:27:16: data
src/pages/Info/Corp.tsx:27:22: currentUser
src/pages/Info/Corp.tsx:27:34: name
src/pages/Info/Corp.tsx:30:16: data
src/pages/Info/Corp.tsx:30:22: currentUser
src/pages/Info/Corp.tsx:30:34: role
src/pages/Login/index.tsx:39:27: error
src/pages/Login/index.tsx:46:9: captchaId
src/pages/Login/index.tsx:46:21: error
src/pages/Login/index.tsx:46:28: extra
src/pages/Login/index.tsx:46:35: captchaId
src/pages/Login/index.tsx:47:9: reason
src/pages/Login/index.tsx:47:18: error
src/pages/Login/index.tsx:47:25: reason
src/pages/Login/index.tsx:49:10: pwdPubkey
src/pages/Login/index.tsx:63:14: pwdPubkey
src/pages/Login/index.tsx:64:20: pwdPubkey
src/pages/Login/index.tsx:65:41: _
src/pages/Login/index.tsx:65:59: _
src/pages/Login/index.tsx:67:25: pwdPubkey
src/pages/Login/index.tsx:72:21: captchaId
src/pages/Login/index.tsx:80:20: data
src/pages/Login/index.tsx:81:19: accessToken
src/pages/Login/index.tsx:87:7: captchaId
src/pages/Login/index.tsx:92:7: pwdPubkey
src/pages/Login/index.tsx:119:54: reason
src/pages/Login/index.tsx:123:21: reason
src/pages/Login/index.tsx:124:48: error
src/pages/Login/index.tsx:124:54: message
src/pages/Login/index.tsx:160:18: captchaId
src/pages/Main/Content.tsx:15:28: name
src/pages/Main/Content.tsx:15:45: name
src/pages/Main/Header.tsx:54:14: name
src/pages/Main/Header.tsx:54:63: name
src/pages/Password/Form.tsx:31:27: error
src/pages/Password/Form.tsx:38:9: reason
src/pages/Password/Form.tsx:38:18: error
src/pages/Password/Form.tsx:38:25: reason
src/pages/Password/Form.tsx:40:10: pwdPubkey
src/pages/Password/Form.tsx:53:24: password
src/pages/Password/Form.tsx:53:34: oldPassword
src/pages/Password/Form.tsx:54:14: pwdPubkey
src/pages/Password/Form.tsx:55:20: pwdPubkey
src/pages/Password/Form.tsx:56:41: _
src/pages/Password/Form.tsx:56:59: _
src/pages/Password/Form.tsx:58:25: pwdPubkey
src/pages/Password/Form.tsx:70:44: pwdPubkey
src/pages/Password/Form.tsx:83:37: error
src/pages/Password/Form.tsx:87:13: reason
src/pages/Password/Form.tsx:87:56: error
src/pages/Password/Form.tsx:87:62: message
src/pages/Tickets/TicketCreate.tsx:51:25: body
src/pages/Tickets/TicketCreate.tsx:146:37: k
src/pages/Tickets/index.tsx:181:44: k
src/pages/Tickets/index.tsx:182:51: k
src/pages/Tickets/index.tsx:192:41: k1
src/pages/Tickets/index.tsx:193:52: k1
src/pages/Tickets/index.tsx:194:26: k1
src/pages/Tickets/index.tsx:203:39: item
src/pages/Tickets/index.tsx:206:30: item
server/mocks/api/v1/login.ts:36:9: tenant_type

Most of these symbols are well typed...

JounQin commented 3 years ago

My config

{
  "typeCoverage": {
    "atLeast": 98.52,
    "cache": true,
    "detail": true,
    "ignoreAsAssertion": true,
    "ignoreNested": true,
    "ignoreNonNullAssertion": true,
    "showRelativePath": true,
    "strict": true,
    "update": true
  }
}
plantain-00 commented 3 years ago

tsc doesn't work: error TS2307: Cannot find module 'shared' or its corresponding type declarations. Still not producible:

$ tsc -p src
✨  Done in 1.85s.
$ type-coverage -p src
83 / 83 100.00%
type-coverage success.
JounQin commented 3 years ago

Wired again, can you provide an email so that I can send you the whole internal project for reproduction?

tqn-treezor commented 2 years ago

@JounQin Did you find a solution to that? I seem to have a similar issue, which is even more important on AWS CodeBuild

JounQin commented 2 years ago

@plantain-00 I made a runnable reproduction at https://github.com/rx-ts/react-app-boilerplate, you can run pnpm i && pnpm typecov to reproduce.

plantain-00 commented 2 years ago

v2.21.1 should fix this.

JounQin commented 2 years ago

@plantain-00 Thanks for fixing this!

Although there is a last exception:

server/middlewares/mock.ts:101:21: body

I'm not sure why body is not type covered(I've enabled ignoreAsAssertion option).

plantain-00 commented 2 years ago

req.body is any, ignoreAsAssertion ignores req.body as T

JounQin commented 2 years ago

req.body is any, ignoreAsAssertion ignores req.body as T

@plantain-00 Then what does the output server/middlewares/mock.ts:101:21: body mean? How can I fix it?

plantain-00 commented 2 years ago

It means body(from file server/middlewares/mock.ts at row 101 column 21) is any, it comes from express, fix it by improving @types/express