SalesforceにおけるWebサービスコールアウトのテスト完全ガイド

Salesforce開発での柔軟なコード設計:Callableで動的メソッドディスパッチを実現


動的メソッドディスパッチとは?

動的メソッドディスパッチとは、クラス名やメソッド名を文字列として指定し、それに基づいて実行する処理を切り替える仕組みです。これにより、事前に確定していない動作を実行時に決定でき、次のような利点があります:

  1. 柔軟性:異なるクラスやメソッドを簡単に切り替え可能。
  2. 拡張性:新たなロジックを既存のコードに影響を与えず追加可能。
  3. 統一性:統一されたインターフェースを提供することでコードの可読性を向上。

コード例

以下は、Callableインターフェースを使用して動的メソッドディスパッチを実現するサンプルコードです。

実行対象クラス:Extension

public class Extension implements Callable {

    // メソッド1:文字列を連結
    String concatStrings(String stringValue) {
        return stringValue + stringValue;
    }

    // メソッド2:数値を掛け算
    Decimal multiplyNumbers(Decimal decimalValue) {
        return decimalValue * decimalValue;
    }

    // 動的メソッドディスパッチの実装
    public Object call(String action, Map<String, Object> args) {
        switch on action {
            when 'concatStrings' {
                return this.concatStrings((String)args.get('stringValue'));
            }
            when 'multiplyNumbers' {
                return this.multiplyNumbers((Decimal)args.get('decimalValue'));
            }
            when else {
                throw new ExtensionMalformedCallException('メソッドが未実装です: ' + action);
            }
        }
    }

    // カスタム例外クラス
    public class ExtensionMalformedCallException extends Exception {}
}

ユニットテスト:ExtensionCaller

@IsTest
private with sharing class ExtensionCaller {

    @IsTest
    private static void givenConfiguredExtensionWhenCalledThenValidResult() {

        // Given: クラス名とメソッド名を動的に指定
        String className = 'Extension';
        String methodName = 'multiplyNumbers';
        Decimal decimalTestValue = 10;

        // When: インスタンスを動的に生成しメソッドを呼び出し
        Callable extension = (Callable) Type.forName(className).newInstance();
        Decimal result = (Decimal) extension.call(methodName, new Map<String, Object> { 'decimalValue' => decimalTestValue });

        // Then: 結果を検証
        System.assertEquals(100, result);
    }
}

使用方法

1. クラスを準備する

上記のExtensionクラスのように、Callableインターフェースを実装します。この中で動的に呼び出したいメソッドを定義し、`call`メソッド内で処理を振り分けます。

2. メソッドを動的に呼び出す

`Type.forName(className).newInstance()`を使用して、クラス名からインスタンスを生成します。その後、`call`メソッドを呼び出し、必要な処理を実行します。

3. ユニットテストで動作を確認

ユニットテストを用いて、指定したメソッドが正しく実行されることを確認します。


応用例

1. プラグインアーキテクチャ

異なる処理ロジックをプラグインとして切り替えられる設計に活用可能。

2. 共通API

異なるクラスに共通のインターフェースを持たせ、動的に切り替えることでAPI設計を効率化。


注意点

  1. 例外処理:実装されていないメソッドが呼び出された場合、適切なエラーメッセージを提供すること。
  2. セキュリティ:外部からクラス名やメソッド名を渡す場合、不正な呼び出しを防ぐ対策が必要。

まとめ

`Callable`インターフェースを利用した動的メソッドディスパッチは、柔軟かつ拡張性の高い設計を可能にします。この手法を活用することで、動的な要件に対応しやすいコードを構築でき、特にプラグインアーキテクチャや共通API設計においてその威力を発揮します。

コメント