62 lines
2.0 KiB
JavaScript
62 lines
2.0 KiB
JavaScript
export const enforceCatchType = {
|
||
meta: {
|
||
type: "problem",
|
||
docs: {
|
||
description:
|
||
"强制 catch 子句使用 e: unknown,并用 instanceof Error 提取错误信息;空的 catch 块应添加注释说明原因",
|
||
},
|
||
messages: {
|
||
missingTypeAnnotation:
|
||
"catch 子句缺少类型注解。请使用 catch (e: unknown),然后用 e instanceof Error ? e.message : String(e) 提取错误信息。",
|
||
nonUnknownType:
|
||
"catch 的类型注解应为 unknown,切勿使用 any。请改为 catch (e: unknown),然后用 e instanceof Error ? e.message : String(e) 提取错误信息。",
|
||
emptyCatchNoComment:
|
||
"空的 catch 块应添加注释说明为什么忽略此异常。如果确有理由静默吞掉错误,请在该 catch body 内添加注释。",
|
||
},
|
||
schema: [],
|
||
},
|
||
|
||
create(context) {
|
||
const sourceCode = context.sourceCode ?? context.getSourceCode();
|
||
|
||
function isUnknownType(typeAnnotation) {
|
||
if (!typeAnnotation) return false;
|
||
const type = typeAnnotation.typeAnnotation;
|
||
if (type?.type === "TSTypeReference") {
|
||
return type.typeName?.name === "unknown";
|
||
}
|
||
return false;
|
||
}
|
||
|
||
function hasCommentsInBody(body) {
|
||
if (!body) return false;
|
||
return sourceCode.getCommentsInside(body).length > 0;
|
||
}
|
||
|
||
function check(node) {
|
||
const { param, body } = node;
|
||
|
||
if (param) {
|
||
const typeAnnotation = param.typeAnnotation;
|
||
if (!typeAnnotation) {
|
||
context.report({ node: param, messageId: "missingTypeAnnotation" });
|
||
} else if (!isUnknownType(typeAnnotation)) {
|
||
context.report({ node: typeAnnotation, messageId: "nonUnknownType" });
|
||
}
|
||
}
|
||
|
||
if (
|
||
body &&
|
||
body.type === "BlockStatement" &&
|
||
body.body.length === 0 &&
|
||
!hasCommentsInBody(body)
|
||
) {
|
||
context.report({ node: body, messageId: "emptyCatchNoComment" });
|
||
}
|
||
}
|
||
|
||
return {
|
||
CatchClause: check,
|
||
};
|
||
},
|
||
}; |