diff --git a/packages/lit-analyzer/src/lib/rules/no-nullable-attribute-binding.ts b/packages/lit-analyzer/src/lib/rules/no-nullable-attribute-binding.ts index 292d3462..4e7e9b7c 100644 --- a/packages/lit-analyzer/src/lib/rules/no-nullable-attribute-binding.ts +++ b/packages/lit-analyzer/src/lib/rules/no-nullable-attribute-binding.ts @@ -22,29 +22,15 @@ const rule: RuleModule = { if (htmlAttr.kind !== HtmlNodeAttrKind.ATTRIBUTE) return; const { typeB } = extractBindingTypes(assignment, context); + const isAssignableToNull = isAssignableToSimpleTypeKind(typeB, "NULL"); - // Test if removing "null" from typeB would work and suggest using "ifDefined(exp === null ? undefined : exp)". - if (isAssignableToSimpleTypeKind(typeB, "NULL")) { + // Test if removing "undefined" or "null" from typeB would work and suggest using "ifDefined". + if (isAssignableToNull || isAssignableToSimpleTypeKind(typeB, "UNDEFINED")) { context.report({ location: rangeFromHtmlNodeAttr(htmlAttr), - message: `This attribute binds the type '${typeToString(typeB)}' which can end up binding the string 'null'.`, - fixMessage: "Use the 'ifDefined' directive and strict null check?", - fix: () => { - const newValue = `ifDefined(${assignment.expression.getText()} === null ? undefined : ${assignment.expression.getText()})`; - - return { - message: `Use '${newValue}'`, - actions: [{ kind: "changeAssignment", assignment, newValue }] - }; - } - }); - } - - // Test if removing "undefined" from typeB would work and suggest using "ifDefined". - else if (isAssignableToSimpleTypeKind(typeB, "UNDEFINED")) { - context.report({ - location: rangeFromHtmlNodeAttr(htmlAttr), - message: `This attribute binds the type '${typeToString(typeB)}' which can end up binding the string 'undefined'.`, + message: `This attribute binds the type '${typeToString(typeB)}' which can end up binding the string '${ + isAssignableToNull ? "null" : "undefined" + }'.`, fixMessage: "Use the 'ifDefined' directive?", fix: () => ({ message: `Use the 'ifDefined' directive.`, diff --git a/packages/lit-analyzer/src/test/rules/no-nullable-attribute-binding.ts b/packages/lit-analyzer/src/test/rules/no-nullable-attribute-binding.ts index 3e788653..1cccbb70 100644 --- a/packages/lit-analyzer/src/test/rules/no-nullable-attribute-binding.ts +++ b/packages/lit-analyzer/src/test/rules/no-nullable-attribute-binding.ts @@ -25,3 +25,17 @@ tsTest("Can assign 'null' in property binding", t => { const { diagnostics } = getDiagnostics('html``'); hasNoDiagnostics(t, diagnostics); }); + +tsTest("Message for 'null' in attribute detects null type correctly", t => { + const { diagnostics } = getDiagnostics('html``'); + hasDiagnostic(t, diagnostics, "no-nullable-attribute-binding"); + + t.true(diagnostics[0].message.includes("can end up binding the string 'null'")); +}); + +tsTest("Message for 'undefined' in attribute detects undefined type correctly", t => { + const { diagnostics } = getDiagnostics('html``'); + hasDiagnostic(t, diagnostics, "no-nullable-attribute-binding"); + + t.true(diagnostics[0].message.includes("can end up binding the string 'undefined'")); +});