JPCERT コーディネーションセンター

EXP06-J. アサーションを行う式で副作用を発生させない

EXP06-J. アサーションを行う式で副作用を発生させない

assert文はコードに診断テストを組み込むための便利な機能である。assert文は実行時の設定に従って動作する。有効にすると引数の式を評価し、評価結果がfalseの場合はAssertionErrorを投げる。無効にするとassert文は何もしない、つまりアサーションを行う式に起因する副作用は発生しない。したがって、標準のassert文で使用する式は副作用を発生させてはならない。

違反コード

以下の違反コード例では、アサーションの中でリストからすべてのnullを削除しようとしている。しかし、アサーションが無効にされると、boolean式は評価されなくなる。

private ArrayList<String> names;

void process(int index) {
  assert names.remove(null); // 副作用
  // ...
}

適合コード

アサーションの中で副作用が発生する可能性を避けるためには、boolean式をアサーションとは別の式にするとよい。

private ArrayList<String> names;

void process(int index) {
  boolean nullsRemoved = names.remove(null);
  assert nullsRemoved; // 副作用はない
  // ...
}

リスク評価

アサーションに副作用が存在すると、プログラムの動作がアサーションが有効であるか無効であるかに依存してしまう。

ルール

深刻度

可能性

自動検出

自動修正

優先度

レベル

EXP06-J

P3

L3

自動検出

副作用の発生がローカルなスコープから見えるアサート式を検出するのは容易である。場合によっては、どのメソッドが副作用を持たないかをプログラマがツールに知らせてやる必要がある。

ツール バージョン チェッカー 説明
CodeSonar 9.0p0

JAVA.STRUCT.SE.ASSERT

Assertion contains side effects

Parasoft Jtest 2024.2 CERT.EXP06.EASE Expressions used in assertions must not produce side effects
PVS-Studio

7.38

V6055
SonarQube

9.9

S3346 Expressions used in "assert" should not produce side effects
関連ガイドライン

SEI CERT C コーディングスタンダード

PRE31-C. 安全でないマクロの引数では副作用を避ける

実装の詳細 (Android)

assert文はDalvik VMでサポートされているが、デフォルトの設定では無視される。adb shell setprop debug.assert 1を実行するか、コマンドライン引数で--enable-assertをDalvik VMに渡すことで、debug.assertシステムプロパティが設定され、アサーションを有効にできる。

参考文献

[Java Tutorials]

Programming With Assertions

[Seacord 2015] Image result for video icon IDS17-J. Prevent XML External Entity Attacks LiveLesson
翻訳元

これは以下のページを翻訳したものです。

EXP06-J. Expressions used in assertions must not produce side effects (revision 119)

Top へ

Topへ
最新情報(RSSメーリングリストTwitter