PMD Javaルール Multithreadingカテゴリ

PMDのJavaルールについてまとめます。バージョン6.35.0時のルールとなっています。
非推奨となっているルールには「△」を先頭に付与しています。

バージョン6.35.0から6.47.0までのルールの差分については別の記事でまとめています。 olafnosuke.hatenablog.com

Multithreadingカテゴリ

複数の実行スレッドを処理するときに問題にフラグを立てるルールが含まれている。

AvoidSynchronizedAtMethodLevel

メソッドレベルの同期(synchronized)は避ける

// NG
public class Sample {
    synchronized void foo() {
    }
}

// OK
public void doSomething() {
    synchronized (this) {
    }
}

ルール設定例

<rule ref="category/java/multithreading.xml/AvoidSynchronizedAtMethodLevel" />

AvoidThreadGroup

java.lang.ThreadGroupは使用しない スレッドセーフではないメソッドが含まれているため。

// NG
public void doSomething() {
    ThreadGroup tg = new ThreadGroup("My threadgroup");
    tg = new ThreadGroup(tg, "my thread group");
    tg = Thread.currentThread().getThreadGroup();
    tg = System.getSecurityManager().getThreadGroup();
}

ルール設定例

<rule ref="category/java/multithreading.xml/AvoidThreadGroup" />

AvoidUsingVolatile

キーワードvolatileを使用しない

// NG
private volatile String var1;

// OK
private String var2;

ルール設定例

<rule ref="category/java/multithreading.xml/AvoidUsingVolatile" />

DoNotUseThreads

Thread、ExecutorService、Executorsを使用しない java.lang.Thread、java.util.concurrent.ExecutorServiceとその派生クラスをクラスやインターフェースにimplementsやextendsしない。
java.util.concurrent.Executors、java.util.concurrent.ExecutorServiceを使用した処理を書かない。

// NG
public class UsingThread extends Thread {
}
public class Example implements ExecutorService {
}
public class Example extends AbstractExecutorService {
}
public void methodX() {
    ExecutorService executorService = Executors.newFixedThreadPool(5);
}

ルール設定例

<rule ref="category/java/multithreading.xml/DoNotUseThreads" />

DontCallThreadRun

Thread.run()メソッドを明示的に呼び出さない 代わりにThread.start()を使う

// NG
Thread t = new Thread();
t.run(); 

// OK
Thread t = new Thread();
t.start();

ルール設定例

<rule ref="category/java/multithreading.xml/DontCallThreadRun" />

DoubleCheckedLocking

Double-checked lockingを使用しない

// NG
Object obj = null;

Object doSomething() {
    if (obj == null) { 
        synchronized (this) {
            if (obj == null) {
                obj = new Object();
            }
        }
    }
    return obj;
}

ルール設定例

<rule ref="category/java/multithreading.xml/DoubleCheckedLocking" />

NonThreadSafeSingleton

スレッドセーフになっていないシングルトンがないか メソッドを同期させるか、あらかじめインスタンスを初期化しておく。

// NG
private static Book book = null;

public static Book getBook() {
    if (book == null) {
        book = new Book();
    }
    return book;
}

プロパティ

名前 デフォルト値 説明 複数指定
checkNonStaticMethods true staticメソッドを確認する。デフォルトから変えない。 -
checkNonStaticFields false staticフィールドを確認する。デフォルトから変えない。 -

ルール設定例

<!-- プロパティ設定なし -->
<rule ref="category/java/multithreading.xml/NonThreadSafeSingleton" />

<!-- プロパティ設定あり -->
<rule ref="category/java/multithreading.xml/NonThreadSafeSingleton">
    <properties>
        <property name="checkNonStaticMethods" value="true" />
        <property name="checkNonStaticFields" value="false" />
    </properties>
</rule>

△UnsynchronizedStaticDateFormatter

非推奨のため省略


UnsynchronizedStaticFormatter

java.text.Formatのインスタンスは同期されない スレッドごとに別々のフォーマットインスタンスを使用するか、フォーマッタをブロックレベルで同期させる必要がある

// NG
private static final SimpleDateFormat sdf = new SimpleDateFormat();

void doSomething() {
    sdf.format();
}

// OK
private static final SimpleDateFormat sdf = new SimpleDateFormat();

void doSomething() {
    synchronized (sdf) {
        sdf.format();
    }
}

プロパティ

名前 デフォルト値 説明 複数指定
allowMethodLevelSynchronization false trueの場合、メソッドレベルの同期も許可される。 -

ルール設定例

<!-- プロパティ設定なし -->
<rule ref="category/java/multithreading.xml/UnsynchronizedStaticFormatter" />

<!-- プロパティ設定あり -->
<rule ref="category/java/multithreading.xml/UnsynchronizedStaticFormatter">
    <properties>
        <property name="allowMethodLevelSynchronization" value="false" />
    </properties>
</rule>

UseConcurrentHashMap

ConcurrentHashMapを使用する

// NG
Map map = new HashMap();

// OK
Map map = new ConcurrentHashMap(); 

ルール設定例

<rule ref="category/java/multithreading.xml/UseConcurrentHashMap" />

UseNotifyAllInsteadOfNotify

Thread.notify()ではなくThread.notifyAll() を使用する

// NG
Book book = new Book();
book.notify();

// OK
Book book = new Book();
book.notifyAll();

ルール設定例

<rule ref="category/java/multithreading.xml/UseNotifyAllInsteadOfNotify" />

他のカテゴリのルールもまとめています。

Best Practiceカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Code Styleカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Designカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Documentationカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Error Proneカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Performanceカテゴリのまとめはこちら: olafnosuke.hatenablog.com

Securityカテゴリのまとめはこちら: olafnosuke.hatenablog.com