// code snippet
function valueOrDefault(a?: string) {
return a || "the default";
}
tslint.json
構成の場合:
{
"defaultSeverity": "error",
"extends": [
"tslint:all"
]
}
2つのエラーのレポートを取得する:
strict-boolean-expressions This type is not allowed in the operand for the '||' operator because it could be undefined. Only booleans are allowed.
strict-boolean-expressions This type is not allowed in the operand for the '||' operator because it is always truthy. Only booleans are allowed.
エラーは報告されていません。 論理||
演算子を使用して、パラメーターのデフォルト値を指定しています(関数パラメーターのデフォルト宣言を使用できることはわかっています。スニペットは、一般的な問題を説明するためのものです)。 式の入力も出力も、どこにもboolean
はありません。
考え? 祈り? どこから/どのように始めるべきかについての提案?
@marcindは、ルールの変更とは異なる動作をする方法の例を提供できますか?
申し訳ありませんが、最初の提出が不明確な部分はどれですか?
私のポイントは、このルールは「ブールコンテキスト」でのみ実行する必要があるということだと思います。次の2つのケースが考えられます。
if
、 while
、またはfor
boolean
として入力された変数に割り当てられます。デフォルト値または短絡評価を提供しようとすると、ルールが実行されないはずです
const a: string = potentiallyUndefinedString || "the default";
const a: string | undefined = potentiallyUndefinedObject && potentiallyUndefinedObject.getString()
@marcind "allow-undefined-union"
オプションを使用すると、前回の投稿の例が機能します。
リクエストの他の部分は、 if
、 for
、 while
、 do ... while
のみをチェックするstrict-boolean-conditions
という名前の別のルールである必要があります。式( x ? y : z
)。
状態全体のタイプのみをチェックし、構成要素はチェックしないと想像できます。
function foo(a: boolean, b?: boolean) {
if (b || a) {} // passes, result is always boolean
if (b && a) {} // fails, result is boolean | undefined
if (a || b) {} // fails, result is boolean | undefined
if (a || !!b) {} // passes
}
たぶん、これは新しいルールではなく、既存のルールのオプションになる可能性があります...
私の意見では、 strict-boolean-expressions
は&&
と||
の左側のオペランドのみをチェックする必要があります。 これらの演算子は(本質的に)三元の砂糖です: a && b
はa ? b : a
に等しく、 a || b
はa ? a : b
等しくなります。 これらの用語で考えると、RHSを無視することは非常に理にかなっており、短絡演算子の動作を3値の動作と一致させることになります。
次に、すべてがif / for / while内にある場合、 strict-boolean-conditions
が機能し、全体的な式を確認できます。 これですべての便利なケースがカバーされると思います。このルールをオンに戻すことができます。
これを私にとって問題としてフラグを立てたコードは、この文書化された一般的なReactパターンでした:
function Foo(props: { showToggle: boolean }) {
return <div>{props.showToggle && <Toggle />}</div>;
}
ERROR: 2:36 strict-boolean-expressions This type is not allowed in the operand for the '&&' operator because it is always truthy. Allowed types are boolean, null-union, undefined-union, string, or number.
@ajafff RHSが一定であるため、ルールのすべてのオプションが有効になっている場合でも、彼のコードはリンターを渡しません。
export function valueOrDefault(a?: string) {
return a || "the default";
}
"strict-boolean-expressions": [true, "allow-null-union", "allow-undefined-union", "allow-string", "allow-number", "allow-mix"]
ERROR: 2:15 strict-boolean-expressions This type is not allowed in the operand for the '||' operator because it is always truthy. Allowed types are boolean, null-union, undefined-union, string, or number.
式の意図はLHSを条件としているので、RHSを無視するという私の提案は彼の問題も解決するでしょう。
&&
と||
のRHSをチェックするのはバグであることに同意します。
また、LHSの&&
、 ||
、およびオペランドの!
のチェックを緩和する傾向があります。 これらは、表現が常に真実であるか、常に偽であるかを確認する必要があります。
これにより、 if
、 for
、 while
、 do ... while
条件と、ブール値(またはその他の構成済みのもの)のみを許可する厳密なチェックの条件式のみが残ります。 )。 @adidahiyaを考えますか?
現在、利用可能な構成オプションを使用してこのルールを有効にすると、コードベースで数日間の作業が必要になります。 :(
number
、 null
またはundefined
からboolean
への暗黙の変換を防ぐことを期待して有効にしました。 例えば:
if (!!array.length) { /* ... */ }
md5-d563d6246c0e981c16f8a2b3d7f53974
md5-430ec08bab82330fa4e519419e9ad014
However I find the following uses acceptable:
md5-70351fc6fdb328ee060919d6974e2cf4
```tsx
md5-036fd2ddd516eac8e1379cdcb9ac2b9a
これは@marcindが示唆していることと一致すると思います。
また、&&のLHSのチェックを緩和する傾向があります|| および!の
@ajafffはこれでif (!!array.length)
またはif (!possiblyNull)
合法化しますか?
@ajafff @adidahiyaここでさらに考えはありますか? 私は@ rhys-vdwとまったく同じ状況にあります。
恥知らずに自分のプロジェクトを宣伝する:
この号の最後の活動以来、私は自分のリンターであるFimbullinterプロジェクトを作成しました。 クイックスタートについては、ドキュメントをお読みください: //github.com/fimbullinter/wotan/blob/master/packages/wotan/README.md
ルールno-useless-predicate
が含まれています。これは、探しているものである可能性があります。 これはTSLintのstrict-type-predicates
とstrict-boolean-expressions
組み合わせですが、いくつかの大きな違いがあります。
TSLintのとは対照的にstrict-type-predicates
もせずに動作します--strictNullChecks
と正しく型パラメータと、空のオブジェクト・タイプを処理します。 (おそらく、この問題を購読している人々にとってはそれほど面白くありません)
TSLintのstrict-boolean-expressions
との主な違いは、すべてがブール値である必要がないことです(暗黙の強制は検出されません)。 それは、すべての条件がおそらく真実で偽物である必要があるだけです。
いくつかの例:
if (0) {} // error, always falsy
if (1) {} // error, always truthy
declare let array: string[];
if (array.length) {} // no error
if (!array.length) {} // no error
if (!!array.length) {} // no error
if (array.length === undefined) {} // error, condition is always false
if (!!false) {} // 2 errors, because of the double negation of an always falsy value
declare let someString: string;
return someString || 'some default string'; // no error, because 'someString' might be falsy
declare const foo: 'bar' | 'baz';
return foo || 'bas'; // error, 'foo' is always truthy
declare let optionalFunction: (() => void) | undefined;
optionalFunction && optionalFunction(); // no error
私の実際のコードから、次のユースケースを紹介したいと思います。
export interface ILoggingRule {
readonly isFinal?: boolean;
readonly loggerNamePattern?: string;
readonly maxLogLevel?: LogLevel;
readonly minLogLevel?: LogLevel;
readonly target: Target;
}
// ...
/**
* Creates an instance of LoggingRule.
* <strong i="6">@param</strong> options Configuration options of the logging rule.
*/
public constructor(options: ILoggingRule) {
// tslint:disable:strict-boolean-expressions
this.isFinal = options.isFinal || false;
this.loggerNamePattern = options.loggerNamePattern || "*";
this.maxLogLevel = options.maxLogLevel || LogLevel.Fatal;
this.minLogLevel = options.minLogLevel || LogLevel.Trace;
this.target = options.target;
// tslint:enable:strict-boolean-expressions
}
ご覧のとおり、LHSが未定義の場合、デフォルト値を示すために||
を使用しています。 tslint
これがstrict-boolean-expressions
準拠していることを理解させる簡潔な方法はありますか? それ以外の場合は、これらの無効化/有効化コマンドを使用する必要があります。 (驚くべきことに、これはタイプチェックが有効になっている場合の問題であり、VSCodeでは問題ではありません。)
この使用法は標準的であり、JavaScriptでは非常に一般的で便利であり、このルールが失敗する原因となることは絶対にありません。
短絡を考慮して、 &&
と||
のRHSをチェックしないでください。 これがデフォルトの動作である必要があります(または、少なくともallow-any-rhs
ようなオプションがあるはずです)。 現在、コードベースに多くの短絡があるため、 strict-boolean-expressions
使用できません。
LHSは危険である可能性があるため、 string
またはnumber
を使用するため、LHSのチェックはそのままIMHOのままにする必要があります。次の例を参照してください。
function foo(x: string | number | null) {
return x || defaultValue;
}
多くの開発者は、 null
だけでなく、 0
と""
によってdefaultValue
が返されることを理解できないため、これは危険です。
""
と0
も誤っていることを開発者が考慮に入れていないため、プロジェクトの主要なバグに対処する必要がありました。 この種のコードを防ぐことは、 strict-boolean-expressions
私の主なユースケースです。
https://github.com/palantir/tslint/pull/4159で修正されましたが、共同編集者からのレビューが必要です。
おっと、私の例の1つが悪かったことを明確にしたかっただけです。
const x = possiblyUndefined || 5;
possiblyUndefined
が0
ある可能性があり、論理エラーである可能性があるため、これは機能しないはずです。 @dobesvのPRはここで機能するようです。
アレイのインクルードはES7の機能です。
ES7またはESNEXTを使用するには、構成を変更する必要があります🦄
よろしく、🚀
@rimitiこんにちは、あなたが何を指しているのか
@dobesvああ、ごめんなさい;)
#4159で修正され、次のリリースで利用可能になります
最も参考になるコメント
私の意見では、
strict-boolean-expressions
は&&
と||
の左側のオペランドのみをチェックする必要があります。 これらの演算子は(本質的に)三元の砂糖です:a && b
はa ? b : a
に等しく、a || b
はa ? a : b
等しくなります。 これらの用語で考えると、RHSを無視することは非常に理にかなっており、短絡演算子の動作を3値の動作と一致させることになります。次に、すべてがif / for / while内にある場合、
strict-boolean-conditions
が機能し、全体的な式を確認できます。 これですべての便利なケースがカバーされると思います。このルールをオンに戻すことができます。これを私にとって問題としてフラグを立てたコードは、この文書化された一般的なReactパターンでした:
@ajafff RHSが一定であるため、ルールのすべてのオプションが有効になっている場合でも、彼のコードはリンターを渡しません。
式の意図はLHSを条件としているので、RHSを無視するという私の提案は彼の問題も解決するでしょう。