この章では、Solaris WBEM SDK とクライアント API (javax.wbem.client) を使ってクライアントプログラムを作成する方法について説明します。この章の内容は、次のとおりです。
WBEM クライアント API (javax.wbem.client) の詳細については、/usr/sadm/lib/wbem/doc/index.html を参照してください。
WBEM クライアントアプリケーションは、javax.wbem.client API を使用して CIM オブジェクトを操作します。クライアントアプリケーションは、CIM API を使ってオブジェクトを構築したあと、そのオブジェクトのインスタンスを作成します。こうしたオブジェクトには、クラス、インスタンス、名前空間などがあります。アプリケーションは、クライアント API を使ってオブジェクトを CIM オブジェクトマネージャ に渡し、WBEM 操作を要求します。たとえば、CIM クラスの作成、インスタンスの作成、名前空間の作成といった操作があります。
クライアントアプリケーションは通常、次の手順で処理を行います。
CIMClient を使って CIMOM に接続します。クライアントアプリケーションは、WBEM 操作を実行する必要があるとき、毎回 CIMOM に接続します。WBEM 操作には、CIM クラスの作成、CIM インスタンスの更新などがあります。詳細は、「クライアント接続の開始と終了」を参照してください。
クライアント API を使用して、操作の要求およびプログラミング作業を実行します。アプリケーションの機能セットは、どの処理を要求すべきかを決定します。次に、ほとんどのプログラムが実行する一般的な処理を示します。
インスタンスの作成、削除、更新
オブジェクトの列挙
メソッドの呼び出し
クラス定義の取得
エラー処理
クラスの作成と削除、名前空間の作成と削除、および修飾子の使用は、クライアントプログラムからも実行できます。詳細は、「基本的なクライアント操作の実行」を参照してください。
CIMClient を使用して CIM オブジェクトマネージャへのクライアント接続を閉じて、クライアントセッションが使用しているリソースをすべて解放します。詳細は、「クライアント接続の開始と終了」を参照してください。
クライアントが WBEM 操作を実行するためには、まずアプリケーションから CIMOM への接続を確立する必要があります。たとえば、CIM クラス、CIM インスタンス、CIM 修飾子型などを追加、変更、または削除する WBEM 作業があります。クライアントアプリケーションと CIM オブジェクトマネージャは、同一のホスト上でも、別のホスト上でも実行可能です。また、複数のクライアントが 1 つの CIM オブジェクトマネージャに接続を確立することもできます。
アプリケーションが CIMOM への接続を確立する場合、名前空間への接続も行う必要があります。後続の操作はすべてこの名前空間上で行われます。名前空間は、ディレクトリに似た構造を持ち、内部にクラス、インスタンス、および修飾子型を含みます。名前空間内のオブジェクト名は、すべて一意にする必要があります。Solaris WBEM SDK をインストールすると、次の 4 つの名前空間が作成されます。
root\cimv2 – デフォルトの名前空間。Solaris WBEM ソフトウェアがインストールされたシステムのオブジェクトを表す CIM クラスが含まれる。
root\snmp – SNMP アダプタクラスが含まれる。
root\system – CIM オブジェクトマネージャ を管理するクラスが含まれる。
クライアント接続を開始する場合、CIMClient クラスを使用して CIM オブジェクトマネージャに接続します。CIMClient クラスは、次の 4 つの引数を取ります。
名前 – 必須。クライアント接続に使用されるホストおよび名前空間の名前を含む CIMNameSpace オブジェクトのインスタンス。デフォルト値は、ローカルホスト上の root\cimv2 です。ローカルホストとは、クライアントアプリケーションを実行しているホストです。クライアントから CIMOM への接続が確立されたあと、後続の CIMClient 操作はすべて指定された名前空間内で行われます。
principal – 必須。有効な Solaris OS ユーザーアカウント名を含む UserPrincipal オブジェクトのインスタンス。CIMOM は、ユーザー名からそのアクセス特権を確認し、CIM オブジェクトに許可されたアクセスの種類を決定します。
credential – 必須。UserPrincipal Solaris OS アカウントの有効なパスワードを含む PasswordCredential オブジェクトのインスタンス。
protocol – 任意 (文字列)。CIMOM へのメッセージ送信に使用するプロトコル。有効な値は、RMI (デフォルト値) または HTTP です。
次の例では、アプリケーションは、デフォルトの名前空間のローカルホストで稼働する CIM オブジェクトマネージャ に接続します。アプリケーションは、デフォルトの名前空間のすべての CIM オブジェクトに読み取り権および書き込み権を持つ、ルートアカウント用 UserPrincipal オブジェクトを作成します。
{ ... /* デフォルトのホスト (ローカルホスト) とデフォルトの名前 空間 (root\cimv2) を示す 2 つの NULL 文字列で初期化された名前空間オブジェクトを作成する */ CIMNameSpace cns = new CIMNameSpace("", ""); UserPrincipal up = new UserPrincipal("root"); PasswordCredential pc = new PasswordCredential("root-password"); /* root ユーザーとして root パスワードを使って名前空間に接続する */ CIMClient cc = new CIMClient(cns, up, pc); ... }
次の例では、アプリケーションは、最初に CIMNameSpace、UserPrincipal、および PasswordCredential オブジェクトのインスタンスを作成します。次に、CIMOM への接続を確立するため、CIMClient クラスを使って、資格情報 (ホスト名、名前空間、ユーザー名、およびパスワード) を渡します。
{ ... /* ホスト happy 上の名前空間 A で初期化された名前空間オブジェクトを 作成する */ CIMNameSpace cns = new CIMNameSpace("happy", "A"); UserPrincipal up = new UserPrincipal("Mary"); PasswordCredential pc = new PasswordCredential("marys-password"); CIMClient cc = new CIMClient(cns, up, pc); ... }
SolarisUserPrincipal および SolarisPasswordCredential クラスを使用して、ユーザーの役割 ID を認証します。次の例では、Mary の役割を Admin として認証します。
{ ... CIMNameSpaceRole cns = new CIMNameSpace("happy", "A"); SolarisUserPrincipal sup = new SolarisUserRolePrincipal("Mary", "Admin"); SolarisPswdCredential spc = new SolarisPswdCredential("marys-password", "admins-password"); CIMClient cc = new CIMClient(cns, sup, spc);
CIMClient クラスの close メソッドを使用して、クライアント接続を閉じ、セッションが使用したサーバーリソースを解放します。
次の例では、クライアント接続を閉じます。インスタンス変数 cc は、クライアント接続を表します。
... cc.close(); ...
この節では、javax.wbem.client API を使った操作の要求方法と、一般的なプログラミング作業の実行方法について説明します。
既存のクラスのインスタンスを作成するには、 newInstance メソッドを使用します。既存のクラスがキープロパティを保持する場合、アプリケーションはそのプロパティを一意の値に設定する必要があります。インスタンスは、必要に応じてそのクラスに定義されていない別の修飾子を定義することもできます。これらの修飾子は、インスタンス、またはそのインスタンスの特定のプロパティに対して定義できます。クラス宣言内に修飾子を記述する必要はありません。
アプリケーションは、クラスに定義されている一連の修飾子を getQualifiers メソッドを使用して取得できます。
次の例では、 newInstance メソッドを使用して、CIM インスタンスを表す Java クラスを作成します。たとえば、 Solaris_Package クラスから Solaris パッケージを作成します。
... { /* ローカルホスト上の名前空間 root\cimv2 で CIM オブジェクトマネージャに接続する root\cimv2 にオブジェクトへの書き込み権を 持つアカウントのユーザー名とパスワードを指定する */ UserPrincipal up = new UserPrincipal("root"); PasswordCredential pc = new PasswordCredential("root-password"); /* root ユーザーとして root パスワードを使用して名前空間に接続 する */ CIMClient cc = new CIMClient(cns, up, pc); ... // Solaris_Package クラスを取得 cimclass = cc.getClass(new CIMObjectPath("Solaris_Package"), true, true, true, null); /* プロパティのデフォルト値で生成された Solaris_Package クラスの新しいインスタンスを作成する。 クラスのプロバイダがデフォルト値を指定していない場合、 プロパティの値は NULL になるため、明示的に設定する 必要がある */ CIMInstance ci = cc.createInstance (new CIMObjectPath("Solaris_Package"), ci); } ...
インスタンスの削除には、deleteInstance メソッドを使用します。
クライアントアプリケーションを CIMOM に接続する
CIMObjectPath を使って、削除されるオブジェクトの CIM オブジェクトパスを含むオブジェクトを構築する
enumerateInstance を呼び出して、指定のインスタンスとそのサブクラスのすべてのインスタンスを取得する
deleteInstance を呼び出して各インスタンスを削除する
import java.rmi.*; import java.util.Enumeration; import javax.wbem.cim.CIMClass; import javax.wbem.cim.CIMException; import javax.wbem.cim.CIMInstance; import javax.wbem.cim.CIMNameSpace; import javax.wbem.cim.CIMObjectPath; import javax.wbem.client.CIMClient; import javax.wbem.client.PasswordCredential; import javax.wbem.client.UserPrincipal; /** * 指定のクラスのインスタンスをすべて返す。 * この例は、ホスト名 (args[0])、ユーザー名 (args[1])、 * パスワード (args[2])、名前空間 (args[3])、およびクラス名 (args[4]) という * 5 つの引数を取る。指定のクラス名のインスタンスをすべて削除する。 * 指定のユーザー名は、指定の名前空間に対する書き込み権を持つ必要 * がある */ public class DeleteInstances { public static void main(String args[]) throws CIMException { CIMClient cc = null; // 5 つの引数が指定されない場合は使用法を表示して終了する if (args.length != 5) { System.out.println("Usage: DeleteInstances host username " + "password namespace classname "); System.exit(1); } try { // args[0] にはホスト名、args[3] には名前空間が含まれる。 // 指定のホスト上の指定の名前空間を指す CIMNameSpace (cns) // を作成する CIMNameSpace cns = new CIMNameSpace(args[0], args[3]); // args[1] と args[2] にはユーザー名とパスワードが含まれる。 // このユーザー名で UserPrincipal (up) を作成し、 // このパスワードで PasswordCredential を作成する UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); // CIM オブジェクトマネージャに接続し、 // 作成した CIMNameSpace、UserPrincipal、および // PasswordCredential のオブジェクトを渡す cc = new CIMClient(cns, up, pc); // クラス名 (args[4]) を取得し CIMObjectPath を作成する CIMObjectPath cop = new CIMObjectPath(args[4]); // クラスとその全サブクラスのインスタンスオブジェクトパスの // 列挙を取得する。インスタンスオブジェクトパスは、 // CIM オブジェクトマネージャがインスタンスを検索する // ときに使用する参照 Enumeration e = cc.enumerateInstanceNames(cop); // インスタンスオブジェクトパスの列挙を繰り返し処理する。 // オブジェクトを構築し、列挙された各インスタンスの // オブジェクトパスを格納し、このインスタンスを出力 // して、削除する while (e.hasMoreElements()) { CIMObjectPath op = (CIMObjectPath)e.nextElement(); System.out.println(op); cc.deleteInstance(op); } // while の終了 } catch (Exception e) { // 例外が発生した場合はそれを出力する System.out.println("Exception: "+e); } // catch の終了 // セッションの終了 if (cc != null) { cc.close(); } } }
クライアントアプリケーションは、一般に getInstance メソッドを使って CIMOM から CIM インスタンスを取得します。クラスのインスタンスが作成されると、クラスはクラス階層内のすべての親クラスのプロパティを継承します。getInstance メソッドは、ブール値引数 localOnly を受け取ります。
localOnly が true の場合、getInstance メソッドは指定されたインスタンスの非継承プロパティだけを返します。非継承プロパティは、インスタンス内で定義されます。
localOnly が false の場合、クラス内のすべてのプロパティが返されます。たとえば、インスタンス内で定義されたプロパティや、クラス階層内のすべての親クラスから継承されたすべてのプロパティが返されます。
既存のインスタンスを更新する場合は、setInstance メソッドを使用します。
この例は次のことを行います。
列挙内のオブジェクトパスのインスタンスを取得する
各インスタンス内の b のプロパティ値を 10 に更新する
更新されたインスタンスを CIMOM に渡す
... { // オブジェクトパス、myclass というCIM 名を含むオブジェクト // を作成する CIMObjectPath cop = new CIMObjectPath("myclass"); /* 列挙内の各インスタンスオブジェクトパスに対するインスタンスを 取得し、各インスタンスの b のプロパティ値を 10 に更新し、更新した インスタンスを CIM オブジェクトマネージャに渡す */ while(e.hasMoreElements()) { CIMInstance ci = cc.getInstance((CIMObjectPath) (e.nextElement()),true, true, true, null); ci.setProperty("b", new CIMValue(new Integer(10))); cc.setInstance(new CIMObjectPath(),ci); } } ...
CIM プロパティは、CIM クラスの特性を記述する値です。プロパティは、1 組の関数と見なすことができます。一方の関数はプロパティ値を「取得」し、もう一方の関数はプロパティ値を「設定」します。
次の例は、enumerateInstanceNames を使って Solaris プラットフォームプロセッサのすべてのインスタンスの名前を返します。この例は、getProperty を使って各インスタンスの現在のクロック速度の値を取得し、println を使ってこの値を出力します。
... { /* オブジェクト (CIMObjectPath) を作成して、 Solaris_Processor クラスの名前を格納する */ CIMObjectPath cop = new CIMObjectPath("Solaris_Processor"); /* CIM オブジェクトマネージャは、Solaris_Processor クラスの インスタンス名を含む列挙を返す */ Enumeration e = cc.enumerateInstanceNames(cop); /* インスタンスオブジェクトパスの列挙を繰り返し処理する。 getProperty メソッドを使用して、Solaris プロセッサごとの 現在のクロック速度の値を取得する */ while(e.hasMoreElements()) { CIMValue cv = cc.getProperty(e.nextElement(CIMObjectPath), "CurrentClockSpeed"); System.out.println(cv); } ... }
次の例では、すべての Solaris_UserTemplate インスタンスの初期シェル値を設定します。このコードセグメントは、enumerateInstanceNames を使って Solaris_UserTemplate のすべてのインスタンスの名前を取得します。また、setProperty を使って各インスタンスの初期シェルの値を設定します。
... { /* オブジェクト (CIMObjectPath) を作成して Solaris_Processor クラスの名前を格納する */ CIMObjectPath cop = new CIMObjectPath("Solaris_UserTemplate"); /* CIM オブジェクトマネージャは、 Solaris_UserTemplate クラスおよび そのサブクラスすべてのインスタンス名を含む列挙を返す */ Enumeration e = cc.enumerateInstanceNames(cop); /* インスタンスオブジェクトパスの列挙を繰り返し処理する。 setProperty メソッドを使用して、初期シェル値を Solaris_UserTemplate のインスタンスごとに /usr/bin/sh に設定する */ for (; e.hasMoreElements(); cc.setProperty(e.nextElement(), "/usr/bin/sh", new CIMValue(new Integer(500)))); }
列挙とは一度にオブジェクトを 1 つずつ取り出すことができるオブジェクトの集合です。クラス、クラス名、インスタンス、インスタンス名、および名前空間を列挙できます。次の表に示すように、列挙の結果は使用するメソッドや引数によって異なります。
ソート方法 |
引数なし |
deep |
localOnly |
---|---|---|---|
enumerateClasses |
path に指定されたクラスの内容を返す |
true の場合: 指定されたクラスのサブクラスの内容を返す。ただし、指定されたクラス自体は返さない |
true の場合: 指定されたクラスの継承されないプロパティおよびメソッドのみを返す |
false の場合: 指定されたクラスの直接のサブクラスの内容を返す |
false の場合: 指定されたクラスのプロパティをすべて返す |
||
enumerateInstances |
path に指定されたクラスのインスタンスを返す |
true の場合: 指定されたクラスおよびそのサブクラスのインスタンスを返す |
true の場合: 指定されたクラスのインスタンスの継承されないプロパティのみを返す |
false の場合: 指定されたクラスおよびそのサブクラスのインスタンスを返す。サブクラスのプロパティは、フィルタ処理される |
false の場合: 指定されたクラスのインスタンスのプロパティをすべて返す |
||
enumerateClassNames |
path に指定されたクラスの名前を返す |
true の場合: 指定されたクラスから派生したすべてのクラスの名前を返す |
なし |
false の場合:指定されたクラスの第 1 レベルの子の名前のみを返す |
なし |
||
enumerateInstanceNames |
path に指定されたクラスのインスタンスの名前を返す |
なし |
なし |
enumNameSpace |
path に指定された名前空間内の名前空間のリストを返す |
true の場合: 指定された名前空間内の名前空間階層全体を返す |
なし |
false の場合: 指定された名前空間の第 1 レベルの子のみを返す |
なし |
次のプログラム例は、クラスおよびそのサブクラスの内容を返します。
... { /* CIMObjectPath オブジェクトを作成し、列挙される CIM クラスの 名前 (myclass) で初期化する */ CIMObjectPath cop = new CIMObjectPath(myclass); /* この列挙には、列挙されたクラス内のクラスとサブクラスが 含まれる (deep=true)。 この列挙は、各クラスおよびサブクラスの 継承されないメソッドおよびプロパティだけを返す (localOnly が true) */ Enumeration e = cc.enumerateClasses(cop, true, true); } ...
次のプログラム例は、クラスおよびインスタンスの列挙で deep および shallow (deep=false) が指定された場合の動作を示します。localOnly フラグは、クラスおよびインスタンスの名前ではなく、クラスおよびインスタンスの内容を返します。
import java.rmi.*; import java.util.Enumeration; import javax.wbem.client.CIMClient; import javax.wbem.cim.CIMClass; import javax.wbem.cim.CIMException; import javax.wbem.cim.CIMInstance; import javax.wbem.cim.CIMNameSpace; import javax.wbem.cim.CIMObjectPath; import javax.wbem.client.UserPrincipal; import javax.wbem.client.PasswordCredential; /** * この例は、クラスとインスタンスを列挙する。コマンド行から * 渡されるクラス上で deep 列挙と shallow 列挙を行う */ public class ClientEnum { public static void main(String args[]) throws CIMException { CIMClient cc = null; CIMObjectPath cop = null; if (args.length < 4) { System.out.println("Usage: ClientEnum host user passwd " + "classname"); System.exit(1); } try { CIMNameSpace cns = new CIMNameSpace(args[0]); UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); cc = new CIMClient(cns, up, pc); // コマンド行からクラス名を取得 cop = new CIMObjectPath(args[3]); // クラスの deep 列挙を実行 Enumeration e = cc.enumerateClasses(cop, true, true, true, true); // クラスのサブクラスをすべて出力 while (e.hasMoreElements()) { System.out.println(e.nextElement()); } System.out.println("+++++"); // クラスの shallow 列挙を実行 e = cc.enumerateClasses(cop, false, true, true, true); // 第 1 レベルのサブクラスを出力 while (e.hasMoreElements()) { System.out.println(e.nextElement()); } System.out.println("+++++"); // クラスのインスタンスの deep 列挙を実行 e = cc.enumerateInstances(cop, false, true, true, true, null); // クラスおよびそのサブクラスのインスタンスをすべて出力 while (e.hasMoreElements()) { System.out.println(e.nextElement()); } System.out.println("+++++"); // クラスのインスタンスの shallow 列挙を実行 e = cc.enumerateInstances(cop, false, false, true, true, null); // クラスのインスタンスをすべて出力 while (e.hasMoreElements()) { System.out.println(e.nextElement()); } System.out.println("+++++"); e = cc.enumerateInstanceNames(cop); while (e.hasMoreElements()) { System.out.println(e.nextElement()); } System.out.println("+++++"); e = cc.enumerateInstanceNames(cop); while (e.hasMoreElements()) { CIMObjectPath opInstance = (CIMObjectPath)e.nextElement(); CIMInstance ci = cc.getInstance(opInstance, false, true, true, null); System.out.println(ci); } System.out.println("+++++"); } catch (Exception e) { System.out.println("Exception: "+e); } // セッションの終了 if (cc != null) { cc.close(); } } }
次のプログラム例は、クラス名およびサブクラス名のリストを返します。
... { /* CIMObjectPath オブジェクトを作成し、列挙する CIM クラスの 名前 (myclass) を使用して初期化する */ CIMObjectPath cop = new CIMObjectPath(myclass); /* この列挙には、列挙されたクラス内の クラスおよびサブクラスの名前が含まれる */ Enumeration e = cc.enumerateClassNames(cop, true); } ...
このプログラム例は、CIMClient クラスの enumNameSpace メソッドを使用して、名前空間とその中に含まれるすべての名前空間の名前を出力します。
import java.rmi.*; import java.util.Enumeration; import javax.wbem.cim.CIMClass; import javax.wbem.cim.CIMException; import javax.wbem.cim.CIMInstance; import javax.wbem.cim.CIMNameSpace; import javax.wbem.cim.CIMObjectPath; import javax.wbem.client.CIMClient; import javax.wbem.client.PasswordCredential; import javax.wbem.client.UserPrincipal; /** * */ public class EnumNameSpace { public static void main(String args[]) throws CIMException { CIMClient cc = null; // 4 つの引数が指定されない場合、使用法を表示して終了する if (args.length < 4) { System.out.println("Usage: EnumNameSpace host username " + "password namespace"); System.exit(1); } try { // args[0] にはホスト名が含まれる。指定されたホスト上の // 指定された名前空間を指す CIMNameSpace (cns) を作成する CIMNameSpace cns = new CIMNameSpace(args[0], ""); // args[1] と args[2] にはユーザー名およびパスワードが含まれる。 // ユーザー名を使用して UserPrincipal (up) を、 // パスワードを使用して PasswordCredential を作成する UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); // CIM オブジェクトマネージャに接続して、作成した CIMNameSpace、 // UserPrincipal、 およびPasswordCredential オブジェクトを渡す cc = new CIMClient(cns, up, pc); // 名前空間 (args[3]) を使用して CIMObjectPath を作成する CIMObjectPath cop = new CIMObjectPath("", args[3]); // 名前空間を列挙する Enumeration e = cc.enumNameSpace(cop); while (e.hasMoreElements()) { System.out.println((CIMObjectPath)e.nextElement()); } // while の終了 } catch (Exception e) { // 例外が発生した場合はそれを出力する System.out.println("Exception: "+ e); } // catch の終了 // セッションの終了 if (cc != null) { cc.close(); } } }
関連とは、コンピュータやそのハードディスクなどの管理される複数のリソース間の関係を表したものです。この関係は、関連修飾子を含む特殊なクラス型である関連クラス内で抽象化されます。実際のオブジェクトに影響を与えることなく、関連クラスを追加または変更できます。
前出の図には、Teacher と Student という 2 つのクラスが示されています。両方のクラスは、TeacherStudent 関連によってリンクされています。TeacherStudent 関連には、次の 2 つの参照が存在します。
Teaches は、Teacher クラスのインスタンスを参照するプロパティ
TaughtBy は、Student クラスのインスタンスを参照するプロパティ
CIMClient 内の関連メソッドは、クライアントとインスタンス間の関連 (関係) に関する情報を返します。次の表では、これらのメソッドについて説明します。
表 4–2 関連メソッド
ソート方法 |
説明 |
---|---|
associators |
指定された CIM クラスやインスタンスに関連付けられている CIM クラスやインスタンスを取得する |
associatorNames |
指定された CIM クラスやインスタンスに関連付けられている CIM クラスやインスタンスの名前を取得する |
references |
指定された CIM クラスやインスタンスを参照する関連クラスやインスタンスを取得する |
referenceNames |
指定された CIM クラスやインスタンスを参照する関連クラスやインスタンスの名前を取得する |
これらのメソッドは、単一の必須引数 CIMObjectPath を取ります。CIMObjectPath は、検索する関連、関連付けられたクラス、またはインスタンスを持つソースの CIM クラスまたは CIM インスタンスの名前です。CIMOM は、関連、関連付けられたクラス、またはインスタンスを検出できない場合、何も返しません。
CIMObjectpath がクラスの場合、このメソッドは関連付けられたクラスとそのクラスのサブクラスを返します。
CIMObjectpath がインスタンスの場合、このメソッドは関連付けされたクラスとそのサブクラスのインスタンスを返します。
前出の図の associators および associatorNames メソッドは、Teacher および Student クラスに関連付けられたクラスの情報を返します。references および referenceNames メソッドは、Teacher および Student クラス間の関連に関する情報を返します。
表 4–3 TeacherStudent メソッド
例 |
出力 |
説明 |
---|---|---|
associators(Teacher, null, null, null, null, false, false, null) |
Student クラス |
関連付けられているクラスを返す。Student は、TeacherStudent 関連によって Teacher とリンクされている |
associators(MathTeacher, null, null, null, null,false, false, null) |
Student |
関連付けられているクラスを返す。Teacher は、TeacherStudent 関連によって Student とリンクされている。MathTeacher と ArtTeacher は、Teacher から TeacherStudent 関連を継承する |
associatorNames(Teacher, null, null, null, null) |
Student クラスの名前 |
関連付けられているクラスの名前を返す。Student は、TeacherStudent 関連によって Teacher とリンクされている |
references(Student, null, null, false, false, null) |
TeacherStudent |
Student が関与している関連を返す |
references(Teacher, null, null, false, false, null) |
TeacherStudent |
Teacher が関与している関連の名前を返す |
references(Teacher, null, null, false, false, null) |
TeacherStudent |
Teacher が関与している関連の名前を返す |
referenceNames(Teacher, null, null) |
TeacherStudent クラスの名前 |
Teacher が関与している関連の名前を返す |
referenceNames(Teacher, null, null) |
TeacherStudent クラスの名前 |
Teacher が関与している関連の名前を返す |
associatorNames および referenceNames メソッドは、引数 includeQualifiers、includeClassOrigin および propertyList を取りません。これらの引数は、インスタンスまたはクラスの名前だけを返し、その内容を返さないメソッドには不必要です。
クラス名を指定する場合、そのモデルパスを指定します。モデルパスには、クラスの名前空間、クラス名、およびキーが含まれます。キーは、管理対象リソースを一意に識別するプロパティまたはプロパティのセットです。キープロパティは、key 修飾子によって示されます。次に、サンプルモデルパスを示します。
\\myserver\\root\cimv2\Solaris_ComputerSystem.Name= mycomputer: CreationClassName=Solaris_ComputerSystem
このモデルパスは、次の値を指定します。
\\myserver\root\cimv2 – ホスト myserver 上のデフォルトの CIM 名前空間
Solaris_ComputerSystem – インスタンスの派生元クラスの名前
Name=mycomputer、CreationClassName=Solaris_ComputerSystem – 2 つのキープロパティ (key property=value 形式)
enumerateInstances メソッドを使用して、所定のクラスのすべてのインスタンスを返し、ループ構造を使用して各インスタンスを処理します。ループでは、各インスタンスを関連メソッドに渡すことができます。
この例は、op クラスとそのサブクラスのインスタンスを列挙します。while ループを使って個々のインスタンスを CIMObjectPath (op) にキャストし、各インスタンスを associators メソッドの第 1 引数として渡します。
{ ... Enumeration e = cc.enumerateInstances(op, true); while (e.hasMoreElements()) { op = (CIMObjectPath)e.nextElement(); Enumeration e1 = cc.associators(op, null, null, null, null, false, false, null); ... }
関連メソッドでオプション引数を使用して、返されるクラスやインスタンスをフィルタ処理できます。すべてのパラメータが処理されるまで、オプションの各パラメータ値は、その結果をフィルタ処理のために次のパラメータに渡します。
任意の 1 つのオプションパラメータ、またはその組み合わせた値を渡すことができます。各パラメータには値または null を指定する必要があります。最初の 4 つのパラメータは、返されるクラスおよびインスタンスをフィルタします。
assocClass
resultClass
resultRole
role
これらの引数を使用すると、これらのパラメータに指定された値と一致するクラスやインスタンスだけが返されます。返されるクラスやインスタンスに含まれている情報をフィルタ処理するパラメータには、includeQualifiers、includeClassOrigin、propertyList があります。
プロバイダによってサポートされるクラス内のメソッドを呼び出すには、invokeMethod インタフェースを使用します。メソッドのシグニチャーを取得するには、最初にそのメソッドが属するクラスの定義を取得する必要があります。invokeMethod メソッドは CIMValue を返します。呼び出したメソッドが戻り値を定義していない場合には、戻り値は null です。
invokeMethod インタフェースは、次の表に示す 4 つの引数を受け取ります。
表 4–4 invokeMethod パラメータ
パラメータ |
データ型 |
説明 |
---|---|---|
name |
CIMObjectPath |
インスタンス名。このインスタンスでメソッドを呼び出す |
methodName |
String |
呼び出すメソッド名 |
inParams |
Vector |
メソッドに渡す入力パラメータ |
outParams |
Vector |
メソッドから受け取る出力パラメータ |
この例では、CIM_Service クラスのインスタンスを取得します。これらのインスタンスは、デバイスやソフトウェアの機能を管理するサービスを表します。invokeMethod メソッドを使って、各サービスを停止します。
{ ... /* CIM_Service クラスの CIM オブジェクトパスを CIM オブジェクトマネージャに渡す。このクラスで定義されたメソッドを 呼び出す */ CIMObjectPath op = new CIMObjectPath("CIM_Service"); /* CIM オブジェクトマネージャは、インスタンスオブジェクトパスの 列挙、CIM_Service クラスのインスタンス 名を返す */ Enumeration e = cc.enumerateInstanceNames (op, true); /* インスタンスオブジェクトパスの列挙を繰り返し処理する*/ while(e.hasMoreElements()) { // インスタンスを取得する CIMObjectPath op = (CIMObjectPath) e.nextElement(); // Stop Service メソッドを呼び出して CIM サービスを停止する cc.invokeMethod("StopService", null, null); } }
CIM クラスを取得するには getClass メソッドを使用します。クラスが作成されると、そのクラスは、クラス階層内のすべての親クラスのメソッドとプロパティを継承します。getClass メソッドは、ブール値引数 localOnly を受け取ります。
localOnly が true の場合、getClass は継承されていないプロパティおよびメソッドを返す
localOnly が false の場合、getClass はクラス内のすべてのプロパティを返す
このプログラム例は、次のメソッドを使用してクラス定義を取得します。
CIMNameSpace – 新しい名前空間を作成する
CIMClient – CIM オブジェクトマネージャへの新しいクライアント接続を作成する
CIMObjectPath – オブジェクトパス (取得するクラス名を含むオブジェクト) を作成する
getClass – CIM オブジェクトマネージャからクラスを取得する
import java.rmi.*; import javax.wbem.client.CIMClient; import javax.wbem.cim.CIMInstance; import javax.wbem.cim.CIMValue; import javax.wbem.cim.CIMProperty; import javax.wbem.cim.CIMNameSpace; import javax.wbem.cim.CIMObjectPath; import javax.wbem.cim.CIMClass; import javax.wbem.cim.CIMException; import java.util.Enumeration; /** * コマンド行で指定されたクラスを取得する。作業をデフォルトの名前空間 * root\cimv2 で行う */ public class GetClass { public static void main(String args[]) throws CIMException { CIMClient cc = null; try { CIMNameSpace cns = new CIMNameSpace(args[0]); UserPrincipal up = new UserPrincipal("root"); PasswordCredential pc = new PasswordCredential("root_password"); cc = new CIMClient(cns); CIMObjectPath cop = new CIMObjectPath(args[1]); // 指定されたクラスに対してローカルなメソッド // とプロパティのみを返す // (localOnly は true) cc.getClass(cop, true); } catch (Exception e) { System.out.println("Exception: "+e); } if(cc != null) { cc.close(); } } }
各 CIMClient メソッドは、CIMException、つまりエラー状態をスローします。CIMOM は、Java の例外処理により、WBEM 固有の例外の階層を作成します。CIMException クラスは、CIM 例外の基底クラスです。CIMException 以外の CIM 例外クラスは、CIMException クラスのサブクラスです。
CIM 例外の各クラスは、API コードが処理する特定のエラー状態を定義します。CIMException は、エラーコードおよび例外に関連したパラメータを取得するメソッドを保持します。CIMException クラスの詳細は、/usr/sadm/lib/wbem/doc/index.html を参照してください。
Solaris OS は、標準の CIM MOF (Managed Object Format) ファイルをコンパイルしてデフォルトの名前空間を生成します。新しい名前空間を作成する場合は、先に適切な CIM .mof ファイルを新しい名前空間にコンパイルしてから、その名前空間にオブジェクトを作成する必要があります。たとえば、標準の CIM 要素を使用するクラスを作成する場合は、名前空間に CIM コアスキーマをコンパイルします。CIM アプリケーションスキーマを拡張するクラスを作成する場合は、名前空間に CIM アプリケーションをコンパイルします。
次の例では、2 段階の処理を実行して、既存の名前空間内に名前空間を作成します。
名前空間の作成時に、CIMNameSpace メソッドが CIM オブジェクトマネージャ に渡すパラメータを含む名前空間オブジェクトを作成します。
CIMClient クラスは、 CIM オブジェクトマネージャ に接続して名前空間オブジェクトを渡します。CIM オブジェクトマネージャ は、名前空間オブジェクトに含まれるパラメータを使用して名前空間を作成します。
{ ... /* クライアント上で名前空間オブジェクトを作成し、 コマンド行から渡されるパラメータを格納する。args[0] にはホスト名 (たとえば myhost) が、args[1] には親の名前空間 (たとえば 最上位 ディレクトリ) が含まれる。 */ CIMNameSpace cns = new CIMNameSpace (args[0], args[1]); UserPrincipal up = new UserPrincipal("root"); PasswordCredential pc = new PasswordCredential("root_password"); /* CIM オブジェクトマネージャに接続し、3 つのパラメータを渡す。 3 つのパラメータとは、ホスト名 (args[0]) および親の名前空間名 (args[1]) を含む名前空間オブジェクト (cns)、ユーザー名文字列 (args[3])、およびパスワード文字列 (args[4]) を指す */ CIMClient cc = new CIMClient (cns, up, pc); /* CIM オブジェクトマネージャに、NULL 文字列 (ホスト名) と args[2] の子名前空間の名前 (たとえば secondlevel) を含む別の 名前空間オブジェクトを渡す */ CIMNameSpace cop = new CIMNameSpace("", args[2]); /* myhost の最上位の名前空間に、args[2] を介して渡された名前で、 新しい名前空間を作成する./* cc.createNameSpace(cop); ... }
名前空間を削除するには、 deleteNameSpace メソッドを使用します。
MOF 言語を使用して基底クラスを作成することもできます。MOF 構文に慣れている場合は、テキストエディタで MOF ファイルを作成します。次に、MOF コンパイラでファイルをコンパイルし、Java クラスを生成します。詳細は、第 7 章「MOF コンパイラを使用した JavaBeans 構成要素の作成」を参照してください。
CIM クラスを表す Java クラスを作成するには、 CIMClass クラスを使用します。ほとんどの基底クラスは、クラス名およびキープロパティまたは abstract (抽象) 修飾子を指定するだけで宣言できます。ただし、ほとんどのクラスには、クラスのデータを表すプロパティが含まれます。プロパティを宣言するには、プロパティのデータ型、名前、およびオプションのデフォルト値を含めます。プロパティのデータ型は、CIMDataType のインスタンスである必要があります。
プロパティには、キープロパティであることを示すキー修飾子を指定できます。キープロパティは、クラスのインスタンスを個別に定義します。インスタンスを持てるのは、キーが指定されたクラスだけです。そのため、キープロパティが定義されないクラスは、abstract (抽象) クラスとしてしか使用できません。新しい名前空間内でクラスにキープロパティを定義する場合は、最初にコア MOF ファイルをその名前空間にコンパイルする必要があります。コア MOF ファイルには、標準の CIM 修飾子 (キー修飾子など) の宣言が含まれます。
クラス定義は、別名、修飾子、修飾子フレーバなどの MOF 機能が含まれることにより複雑化します。
クラスを削除するには、CIMClient の deleteClass メソッドを使用します。このメソッドは、クラスを削除し、CIMException をスローします。
基底クラスを削除する場合、最初に既存のサブクラスまたはインスタンスをすべて削除しておく必要があります。
このプログラム例は、deleteClass メソッドを使用して、デフォルトの名前空間 root\cimv2 にあるクラスを削除します。このプログラムは、次の 4 つの必須文字列引数を取ります。
hostname
classname
username
password
このプログラムを実行するユーザーは、root\cimv2 名前空間への書き込み権を持つアカウントのユーザー名とパスワードを指定する必要があります。
import javax.wbem.cim.CIMClass; import javax.wbem.cim.CIMException; import javax.wbem.cim.CIMNameSpace; import javax.wbem.cim.CIMObjectPath; import javax.wbem.client.CIMClient; import javax.wbem.client.UserPrincipal; import javax.wbem.client.PasswordCredential; import java.rmi.*; import java.util.Enumeration; /** * コマンド行で指定されたクラスを削除する。デフォルトの名前空間 * root\cimv2 で作業を行う */ public class DeleteClass { public static void main(String args[]) throws CIMException { CIMClient cc = null; // 4 つの引数が指定されていない場合、使用法を表示して終了する if (args.length != 4) { System.out.println("Usage: DeleteClass host className " + "username password"); System.exit(1); } try { // args[0] にはホスト名が含まれる。指定されたホスト上の // デフォルトの名前空間を指す CIMNameSpace を作成する CIMNameSpace cns = new CIMNameSpace(args[0]); // args[2] と args[3] には、ユーザー名およびパスワードが // 含まれる。 // ユーザー名を使用して UserPrincipal (up) を、 // パスワードを使用して PasswordCredential を作成する UserPrincipal up = new UserPrincipal(args[2]); PasswordCredential pc = new PasswordCredential(args[3]); cc = new CIMClient(cns, up, pc); // クラス名 (args[4]) を取得し、CIMObjectPath を作成する CIMObjectPath cop = new CIMObjectPath(args[1]); // クラスを削除する cc.deleteClass(cop); } catch (Exception e) { System.out.println("Exception: "+e); } if (cc != null) { cc.close(); } } }
ユーザーまたは名前空間ごとに、アクセス制御を設定できます。次のアクセス制御クラスは、root\security 名前空間に格納されます。
Solaris_Acl – Solaris OS アクセス制御リスト (ACL) の基底クラス。このクラスは、文字列プロパティ capability を定義し、そのデフォルト値を r (読み取り専用) に設定する
Solaris_UserAcl – 指定の名前空間内の CIM オブジェクトに対するユーザーのアクセス制御を示す
Solaris_NamespaceAcl – 名前空間に対するアクセス制御を示す
名前空間内の CIM オブジェクトに対するアクセス制御は、ユーザーごとに設定できます。Solaris_UserACL クラスのインスタンスを作成し、そのアクセス権を変更します。同様に、Solaris_NameSpaceACL クラスのインスタンスを作成し、createInstance メソッドを使用してそのインスタンスへのアクセス権を設定することにより、名前空間へのアクセス制御を設定できます。
Solaris_NameSpaceACL クラスを使ってこの 2 つのクラスの使用方法を組み合わせ、まず、名前空間内のオブジェクトに対するすべてのユーザーのアクセスを制限します。次に、Solaris_UserACL クラスを使用して、選択したユーザーに名前空間へのアクセスを許可します。
Solaris_UserAcl クラスは、Solaris_Acl 基底クラスを拡張したクラスです。Solaris_UserAcl クラスは、Solaris_Acl 基底クラスから文字列プロパティ capability をデフォルト値 r (読み取り専用) で継承します。capability プロパティには、次の表に示すアクセス特権の値を設定できます。
アクセス権 |
説明 |
---|---|
r |
読み取り |
rw |
読み取りおよび書き込み |
w |
書き込み |
なし |
アクセス権なし |
次の表に、Solaris_UserAcl クラスが定義するキープロパティを示します。名前空間内には、名前空間とユーザー名 ACL のペアのインスタンスを 1 つだけ入れることができます。
プロパティ |
データ型 |
目的 |
---|---|---|
nspace |
string |
ACL を適用する名前空間を示す |
username |
string |
ACL を適用するユーザーを示す |
Solaris_UserAcl クラスのインスタンスを作成します。
... /* ローカルホスト上に root\security (名前空間の名前) で初期化した名前空間オブジェクトを作成する */ CIMNameSpace cns = new CIMNameSpace("", "root\security"); // root ユーザーとして root\security 名前空間に接続する cc = new CIMClient(cns, user, user_passwd); // Solaris_UserAcl クラスを取得する cimclass = cc.getClass(new CIMObjectPath("Solaris_UserAcl"); // Solaris_UserAcl の新しいインスタンスを作成する class ci = cimclass.newInstance(); ...
capability プロパティを目的のアクセス権に設定します。
... /* root\molly 名前空間内のオブジェクトに対するユーザー Guest の アクセス権 (capability) を読み取りおよび書き込みに変更する */ ci.setProperty("capability", new CIMValue(new String("rw")); ci.setProperty("nspace", new CIMValue(new String("root\molly")); ci.setProperty("username", new CIMValue(new String("guest")); ...
インスタンスを更新します。
... // 更新されたインスタンスを CIM オブジェクトマネージャに渡す cc.createInstance(new CIMObjectPath(), ci); ...
Solaris_NamespaceAcl クラスは、 Solaris_Acl 基底クラスを拡張したクラスであり、文字列プロパティ capability をデフォルト値 r (すべてのユーザーに対し読み取り専用) で継承します。Solaris_NamespaceAcl クラスは、次のキープロパティを定義します。
プロパティ |
データ型 |
目的 |
---|---|---|
nspace |
string |
アクセス制御リストを適用する名前空間を示す。名前空間内には、名前空間 ACL のインスタンスを 1 つだけ指定できる |
Solaris_namespaceAcl クラスのインスタンスを作成します。
... /* ローカルホスト上に root\security (名前空間の名前) で初期化した名前空間オブジェクトを作成する */ CIMNameSpace cns = new CIMNameSpace("", "root\security"); // root ユーザーとして root\security 名前空間に接続する cc = new CIMClient(cns, user, user_passwd); // Solaris_namespaceAcl クラスを取得する cimclass = cc.getClass(new CIMObjectPath("Solaris_namespaceAcl"); // Solaris_namespaceAcl の新しいインスタンスを作成する class ci = cimclass.newInstance(); ...
capability プロパティを目的のアクセス権に設定します。
... /* root\molly 名前空間のアクセス権 (capability) を読み取り/書き込みに変更する */ ci.setProperty("capability", new CIMValue(new String("rw")); ci.setProperty("nspace", new CIMValue(new String("root\molly")); ...
インスタンスを更新します。
// 更新されたインスタンスを CIM オブジェクトマネージャに渡す cc.createInstance(new CIMObjectPath(), ci);
CIM 修飾子は、CIM クラス、インスタンス、プロパティ、メソッド、パラメータのいずれかの特性を示す要素です。修飾子の属性は、次のとおりです。
型
値
名前
MOF 構文では、各 CIM 修飾子は、定義された CIM 修飾子データ型を 1 つ持ちます。修飾子には、その修飾子を使用可能な CIM 要素を示すスコープ属性はありません。スコープを定義できるのは、修飾子のデータ型宣言内だけです。修飾子内でスコープを変更することはできません。
次に、CIM 修飾子のデータ型を宣言する MOF 構文を示します。この文は、 key という名前のブール型の修飾子を定義します。デフォルト値は false です。この修飾子で説明できるのは、プロパティとオブジェクトへの参照だけです。DisableOverride フレーバは、このキー修飾子がそれらの値を変更できないことを意味します。
Qualifier Key : boolean = false, Scope(property, reference), Flavor(DisableOverride);
次のコード例は、CIM 修飾子の MOF 構文を示します。このサンプル MOF ファイルでは、key と説明は、プロパティ a の修飾子です。プロパティのデータ型は、プロパティ名 a を持つ整数です。
{ [key, Description("test")] int a; };
修飾子フレーバは、修飾子の使用を制御するフラグです。フレーバは、修飾子を派生クラスおよびインスタンスに継承できるかどうかを指定する規則について説明します。派生クラスやインスタンスが修飾子の元の値をオーバーライドできるかどうかを規則で決定することもできます。
次のコード例は、新しいクラスの CIM 修飾子のリストをそのスーパークラス内の修飾子に設定します。
{ try { cimSuperClass = cimClient.getClass(new CIMObjectPath(scName)); Vector v = new Vector(); for (Enumeration e = cimSuperClass.getQualifiers().elements(); e.hasMoreElements();) { CIMQualifier qual = (CIMQualifier) ((CIMQualifier)e.nextElement()).clone(); v.addElement(qual); } cimClass.setQualifiers(v); } catch (CIMException exc) { return; } } ...
複数の CIMClient API 呼び出しを単一のリモート呼び出しとしてバッチ処理することにより、複数のリモートメッセージ交換による遅延を軽減できます。BatchCIMClient クラスのインスタンスを使用して、バッチ要求内で実行する操作のリストを作成できます。次に、CIMClient クラスの performBatchOperations メソッドを使用して、CIM オブジェクトマネージャに操作のリストを送信します。
バッチ操作は、単一のトランザクションを意味するわけではありません。バッチ内の個々の操作間に依存関係はありません。前の操作の成功または失敗が、後続の操作に影響を及ぼすことはありません。
BatchCIMClient クラスには、非バッチモードと同じ CIM 操作を実行できるメソッドが含まれます。これらのメソッドは、CIMClient メソッドとよく似ています。ただし、BatchCIMClient メソッドによって返される型は、CIMClient クラス内の同等のメソッドが返す型とは異なります。これは、バッチ操作の完了後に、リストとして値が返されるからです。このメソッドは、整数の操作 ID を返します。この ID を使用して、操作の結果をあとで取得できます。BatchCIMClient のメソッドが呼び出されると、BatchCIMClient オブジェクトは、後で実行される CIMOperation オブジェクトのリストを作成します。
クライアントは、CIMClient の performBatchOperations メソッドを呼び出すことにより、バッチ操作を実行します。バッチ操作の結果は、BatchResult オブジェクト内に返されます。次に、クライアントは、操作 ID を BatchResult クラスの getResult メソッドに渡して、操作の結果を取得します。リスト内の操作により例外が発生すると、BatchResult オブジェクトに例外オブジェクトが埋め込まれます。失敗した操作 ID を使用する getResult メソッドを起動すると、getResult メソッドにより例外がスローされます。
次の例は、バッチ処理 API を使用して、1 つのリモート呼び出し内で複数の操作を実行する方法を示します。3 つの操作を単一のバッチ操作として実行します。3 つの操作の内容は、enumerateInstanceNames、getClass、enumerateInstances です。
import java.util.Enumeration; import java.util.ArrayList; import java.util.Vector; import java.lang.String; import javax.wbem.cim.*; import javax.wbem.client.*; import javax.wbem.client.UserPrincipal; import javax.wbem.client.PasswordCredential; public class TestBatch { public static void main(String args[]) throws CIMException { CIMClient cc = null; CIMObjectPath cop = null; String protocol = CIMClient.CIM_RMI; if (args.length < 4) { System.out.println("Usage: TestBatch host user passwd classname " + "[rmi|http]"); System.exit(1); } try { CIMNameSpace cns = new CIMNameSpace(args[0]); UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); if (args.length == 5 && args[4].equalsIgnoreCase("http")) { protocol = CIMClient.CIM_XML; } cc = new CIMClient(cns, up, pc, protocol); CIMObjectPath op = new CIMObjectPath(args[3]); BatchCIMClient bc = new BatchCIMClient(); int[] ids = new int[3]; ids[0] = bc.enumerateInstanceNames(op); ids[1] = bc.getClass(op, false, true, true, null); ids[2] = bc.enumerateInstances(op, true, false, false, false, null); BatchResult br = cc.performBatchOperations(bc); Enumeration instanceNames = (Enumeration)br.getResult (ids[0]); CIMClass cl = (CIMClass)br.getResult(ids[1]); Enumeration instances = (Enumeration)br.getResult(ids[2]); while (instanceNames.hasMoreElements()) { System.out.println((CIMObjectPath)instanceNames. nextElement()); } System.out.println(cl.toMOF()); while (instances.hasMoreElements()) { System.out.println((CIMInstance)instances. nextElement()); } } catch (Exception e) { e.printStackTrace(); System.out.println("Exception: "+e); } // セッションの終了 if (cc != null) { cc.close(); } } }
CIM インジケーション、および CIM インジケーションを使用してイベントの発生を通知する方法については、http://www.dmtf.org/education/whitepapers.php の「CIM Schema White Papers」を参照してください。
「イベント」とは、1 つの発生した事象です。「インジケーション」とは、イベントの発生通知です。CIM では、発行されるのはインジケーションであり、イベントではありません。イベントの発生時に、プロバイダはインジケーションを生成します。
インジケーションは、状態の変化を認識する 0 以上の「トリガー」を保持します。WBEM は、トリガーを表す明示的なオブジェクトを保持しません。その代わり、トリガーは以下のアクションにより暗黙的に示されます。
システムの基本オブジェクトに対する操作。クラスの作成、削除、変更、クラスへのアクセスなどを実行できます。インスタンスの変更、インスタンスへのアクセスも可能です。
管理された環境内で発生するイベント
たとえば、サービスの終了によってトリガーが作動したとき、このイベントは、サービスが終了したことを通知するインジケーションになります。
Solaris WBEM サービススキーマ内の関連するCIM イベントクラスは、/usr/sadm/lib/wbem/doc/mofhtml/index.html で確認できます。次の表に、クラスの構造を示します。
表 4–5 CIM_Indication クラス構造
ルートクラス |
スーパークラス |
サブクラス |
---|---|---|
CIM_Indication |
CIM_ClassIndication |
CIM_ClassCreation, CIM_ClassDeletion, CIM_ClassModification |
CIM_InstIndication |
CIM_InstCreation、CIM_InstDeletion、CIM_InstMethodCall、CIM_InstModification、CIM_InstRead |
|
CIM_ProcessIndication |
CIM_AlertIndication, CIM_AlertInstIndication, CIM_ThresholdIndication, CIM_SNMPTrapIndication |
CIM イベントは、ライフサイクルまたはプロセスとして分類できます。「ライフサイクルイベント」は、データ内の特定の変更によって発生する組み込み型の CIM イベントです。ライフサイクルイベントをトリガーする変更には、次のものがあります。
クラスの作成、変更、または削除
クラスインスタンスの作成、変更、削除、読み取り、またはメソッド呼び出し
「プロセスイベント」は、ライフサイクルイベントに含まれないユーザー定義のイベントです。
イベントプロバイダは、CIMOM により作成された要求に応答してインジケーションを生成します。CIMOM は、予約要求を分析します。CIMOM は、EventProvider または CIMIndicationProvider インタフェースを使ってプロバイダと通信を行い、適切なインジケーションを生成するように要求します。プロバイダがインジケーションを生成すると、CIMOM は CIM_IndicationHandler インスタンスにより指定された宛先にインジケーションを配信します。これらのインスタンスは、予約者により作成されます。
イベントプロバイダは、インスタンスプロバイダと同じ方法で検出されます。CIM_InstIndication のサブクラスなど、インスタンスのライフサイクルインジケーションに属する予約の場合、CIMOM は、特定の手順に従います。CIMOM は、予約の有効範囲内のクラスを判別すると、これらのクラスのインスタンスプロバイダと通信します。プロセスインジケーションの場合、CIMOM は Provider 修飾子を使用して、適切なプロバイダと通信を行います。
CIM オブジェクトマネージャおよび CIM オブジェクトマネージャリポジトリは、次の条件下でインジケーションを処理します。
プロバイダがインジケーションをサポートしない場合、またはプロバイダによって CIMOM からのポーリングが禁じられている場合、CIMOM は次のイベントを処理します。
CIM_InstMethodCall
CIM_InstModification
CIM_InstDeletion
CIM_InstCreation
CIM オブジェクトマネージャリポジトリは、プロバイダを保持しないクラスインジケーションおよびライフサイクルインジケーションをすべて処理します。次のクラスがあります。
CIM_ClassCreation
CIM_ClassDeletion
CIM_ClassModification
CIM_InstCreation
CIM_InstModification
CIM_InstDeletion
CIM_InstRead
上記の場合、プロバイダはインジケーションを生成しないか、EventProvider インタフェースを実装します。また、プロバイダは、イベントの生成機能を CIM オブジェクトマネージャに委託することもできます。CIM オブジェクトマネージャ は、プロバイダ上の enumerateInstances を呼び出します。CIMOM は、以前の状態のスナップショットと現在の状態のスナップショットを比較して、インスタンスの作成、変更、または削除が行われたかどうかを特定します。
ポーリングを使用すると大幅なオーバーヘッドが発生するため、ほとんどの場合、プロバイダが独自のインジケーションを処理する必要があります。インジケーションを生成する場合は、プロバイダがポーリングを行う必要があります。このとき、プロバイダはタスクを CIMOM に委託できます。
プロバイダが EventProvider インタフェースを実装する場合、CIMOM はインタフェース内のメソッドを呼び出し、その応答に応じて操作を実行します。特定のプロバイダが予約要求に参加する必要があると CIMOM が判断すると、次の順序でメソッドが呼び出されます。
mustPoll – CIM オブジェクトマネージャ によるポーリングをプロバイダが望んでいるかどうかを判断するため、CIM オブジェクトマネージャ により、CIM_InstCreation、CIM_InstDeletion、および CIM_InstModification に対して呼び出されます。プロバイダが EventProvider インタフェースを実装していない場合、CIM オブジェクトマネージャ はデフォルトでポーリングを実行するとみなします。
authorizeFilter – プロバイダが Authorizable インタフェースを実装する場合、予約が承認されるかどうかを判断するため、CIMOM により、このメソッドが呼び出されます。プロバイダは、インジケーションハンドラの所有者 (インジケーションの受信者) のユーザー ID か、予約を作成したユーザーのユーザー ID に基づいて決定を行うことができます。
プロバイダが Authorizable インタフェースを実装しない場合、CIM オブジェクトマネージャは、名前空間に対してデフォルトの読み取り承認検査を実行します。
プロバイダが EventProvider インタフェースを実装せず、CIMOM がポーリングを試みる場合、プロバイダに対する enumerateInstances が正常終了すると、承認が正しく行われます。
activateFilter– 承認が正しく行われ、プロバイダがポーリングを要求しない場合に、CIMOM により呼び出されます。
deActivateFilter– 予約者または CIMOM によって予約が削除された場合に呼び出されます。たとえば、宛先ハンドラが正しく機能しない場合などです。
クライアントアプリケーションでは、CIM イベントが通知されるように予約することができます。「予約」は、1 つまたは複数の一連のインジケーションを宣言することによって行います。現在は、プロバイダがイベントインジケーションを予約することはできません。
CIM イベントのインジケーションを予約するアプリケーションは、次の情報を提供します。
アプリケーションが予約するインジケーション
CIMOM がインジケーションを送信するハンドラ
イベントの発生は、CIM_Indication クラスのいずれかのサブクラスのインスタンスとして表されます。インジケーションは、そのイベントがクライアントによって予約されているときだけ生成されます。
アプリケーションは、1 つまたは複数のイベントフィルタと 1 つまたは複数のイベントハンドラを作成できます。イベントインジケーションは、アプリケーションがイベントの予約を作成するまで送信されません。
CIM_Listener のインスタンスを作成します。詳細は、「CIM リスナーの追加」を参照してください。
CIM_IndicationFilter のインスタンスを作成します。詳細は、「イベント フィルタの作成」を参照してください。
CIM_IndicationHandler のインスタンスを作成します。詳細は、「イベントハ ンドラの作成」を参照してください。
CIM_IndicationFilter を CIM_IndicationHandler にバインドします。詳細は、「イベントフィルタとイベントハンドラのバインド」を参照してください。
CIM イベントのインジケーションを受信するには、最初に CIMClient に対して addCIMListener メソッドを呼び出して、CIMListener のインスタンスを CIMClient に追加します。
CIMListener インタフェースは、indicationOccured メソッドを実装する必要があります。このメソッドは、引数として CIMEvent を取ります。インジケーションが送信可能な場合、このメソッドが呼び出されます。
// CIM オブジェクトマネージャに接続する cc = new CIMClient(); // CIM リスナーを登録する cc.addCIMListener( new CIMListener() { public void indicationOccured(CIMEvent e) { } });
イベントフィルタでは、送信するイベントの種類と、どのような条件下で送信するかを指定します。CIM_IndicationFilter クラスのインスタンスを作成し、そのプロパティの値を定義することによって、イベントフィルタを作成します。各イベントフィルタは、そのフィルタが属する名前空間に属するイベントに対してのみ有効です。
CIM_IndicationFilter クラスは文字列型のプロパティを持ちます。これらのプロパティの設定により、フィルタを一意に識別したり、照会文字列を指定したり、照会文字列の構文解析を行う照会言語を指定したりできます。現在は、WQL (WBEM Query Language) だけがサポートされます。
表 4–6 CIM_IndicationFilter プロパティ
プロパティ |
説明 |
必須/任意 |
---|---|---|
SystemCreationClassName |
このフィルタを作成するクラスがあるシステム名、またはこのクラスが適用されるシステム名 |
任意。値は、CIM オブジェクトマネージャにより決定される |
SystemName |
このフィルタがあるシステム名、またはこのフィルタが適用されるシステム名 |
任意。このキープロパティのデフォルトは、CIM オブジェクトマネージャが動作しているシステム名 |
CreationClassName |
このフィルタの作成に使用するクラス名またはサブクラス名 |
任意。CIM オブジェクトマネージャは、このキープロパティのデフォルトとして CIM_IndicationFilter を割り当てる |
Name |
フィルタの固有名 |
任意。CIM オブジェクトマネージャは一意の名前を割り当てる |
SourceNamespace |
CIM インジケーション生成元であるローカル名前空間へのパス |
任意。デフォルトは null |
Query |
インジケーションをどのような条件のときに生成するかを定義する照会式。現在は、Level 1 の WQL 式だけがサポートされる。WQL 照会式の詳細は、第 5 章「WBEM 照会の作成」を参照 |
必須。 |
QueryLanguage |
照会を表現する言語 |
必須。デフォルトは WQL |
CIM_IndicationFilter クラスのインスタンスを作成します。
CIMClass cimfilter = cc.getClass (new CIMObjectPath "CIM_IndicationFilter"), true, true, true, null); CIMInstance ci = cimfilter.newInstance(); |
イベントフィルタ名を指定します。
Name = "filter_all_new_solarisdiskdrive" |
WQL 文字列を作成し、返されるイベントインジケーションを指定します。
String filterString = "SELECT * FROM CIM_InstCreation WHERE sourceInstance ISA Solaris_DiskDrive"; |
cimfilter インスタンス内にプロパティ値を設定して、次の情報を識別できるようにします。
フィルタ名
CIM イベントを選択するフィルタ文字列
照会文字列の構文解析を行う照会言語 (WQL)
ci.setProperty("Name", new CIMValue("filter_all_new_solarisdiskdrives")); ci.setProperty("Query", new CIMValue(filterString)); ci.setProperty("QueryLanguage", new CIMValue("WQL");)
cimfilter インスタンス (filter) を作成します。このインスタンスを CIM オブジェクトマネージャリポジトリに格納します。
CIMObjectPath filter = cc.createInstance(new CIMObjectPath(), ci); |
CIMClass cimfilter = cc.getClass(new CIMObjectPath ("CIM_IndicationFilter"), true); CIMInstance ci = cimfilter.newInstance(); // 名前空間に test_a クラスが存在するものとする String filterString = "select * from CIM_InstCreation where sourceInstance isa test_a" ci.setProperty("query", new CIMValue(filterString)); CIMObjectPath filter = cc.createInstance(newCIMObjectPath(), ci);
イベントハンドラは、CIM_IndicationHandler クラスのインスタンスです。CIM_IndicationHandler クラスのインスタンス内でプロパティを設定して、ハンドラに一意の名前を付け、その所有者の UID を示します。CIM イベント MOF には、HTTP プロトコルを使ってクライアントアプリケーションに送信されるインジケーションの宛先を指定する CIM_IndicationHandlerCIMXML クラスが定義されています。Solaris_Event.mof は、Solaris_JAVAXRMIDelivery クラスを作成することにより、CIM_IndicationHandler クラスを拡張します。 このサブクラスは、RMI プロトコルを使用するクライアントアプリケーションに、CIM イベントのインジケーションを送信します。RMI クライアントは、RMI 送信の場所を設定するために Solaris_JAVAXRMIDelivery クラスのインスタンスを作成する必要があります。
表 4–7 CIM_IndicationHandler プロパティ
プロパティ |
説明 |
必須/任意 |
---|---|---|
SystemCreationClassName |
このハンドラを作成するクラスがあるシステム名、またはこのクラスが適用されるシステム名 |
任意。CIM オブジェクトマネージャにより指定される |
SystemName |
このハンドラがあるシステム名、またはこのハンドラが適用されるシステム名 |
任意。このキープロパティのデフォルト値は、CIM オブジェクトマネージャが動作しているシステム名 |
CreationClassName |
このハンドラの作成に使用するクラスまたはサブクラス |
任意。CIM オブジェクトマネージャは、適切なクラス名をこのキープロパティのデフォルトとして割り当てる |
Name |
このハンドラの固有名 |
任意。クライアントアプリケーションは固有名を指定する必要がある |
Owner |
このハンドラを作成した、または保持するエンティティ名。プロバイダは、この値を検査して、インジケーションの受信をハンドラに承認するかどうかを判断できる |
任意。デフォルトは、このインスタンスを作成するユーザーの Solaris ユーザー名 |
// Solaris_JAVAXRMIDelivery クラスのインスタンスを作成するか、 // ハンドラの適切なインスタンスを取得する CIMInstance ci = cc.getIndicationHandler(null); // 新しいインスタンス (delivery) を // rmidelivery インスタンスから作成する CIMObjectPath delivery = cc.createInstance(new CIMObjectPath(), ci);
CIM_IndicationSubscription クラスのインスタンスを作成することにより、イベントフィルタとイベントハンドラをバインドします。このクラスのインジケーションを作成すると、イベントフィルタにより指定されたイベントのインジケーションが送信されます。
次の例では、予約 (filterdelivery) を作成し、 filter プロパティの値として 「イベントフィルタの作成」で作成した filter オブジェクトパスを指定します。また、handler プロパティの値として、例 4–23 で作成した delivery オブジェクトパスを指定します。
CIMClass filterdelivery = cc.getClass(new CIMObjectPath("CIM_IndicationSubscription"), true, true, true, null); ci = filterdelivery.newInstance(): // filter インスタンスを参照する filter プロパティを作成 ci.setProperty("filter", new CIMValue(filter)); // delivery インスタンスを参照する handler プロパティを作成 ci.setProperty("handler", new CIMValue(delivery)); CIMObjectPath indsub = cc.createInstance(new CIMObjectPath(), ci);
Solaris MOF ファイルには、ログクラスが含まれます。クライアントは、これらのクラスを使用してエラー、警告、および情報メッセージをログに記録し、読み取ることができます。たとえば、ログメッセージから次のような状態を読み取ることができます。
システムがシリアルポートにアクセスできない
システムが正常にファイルシステムをマウントしている
システム上で許可されている数より多くのプロセスが実行されている
ログクラスの基盤となるプロバイダは、ログ要求を syslog デーモン (Solaris オペレーティング環境のデフォルトログシステム) に転送できます。詳細は、syslogd(1M) のマニュアルページを参照してください。
WBEM ログメッセージは、/var/sadm/wbem/log ディレクトリ内の個々のログファイルに格納されます。Solaris_LogServiceProperties クラスの singleton インスタンスでは、次のプロパティを操作できます。
ログファイル名
ログファイルが格納されているディレクトリ
ログファイルのサイズの制限
格納できるログファイル数
メッセージを syslogd(1M) に転送するかどうか
各ログエントリの形式は、CIM_LogRecord のサブクラスである Solaris_LogEntry クラスによって定義されます。Solaris_LogEntry は Solaris_Device.mof 内に、CIM_LogRecord は CIM_Device26.mof 内に存在します。
ログメッセージには、次の要素が含まれます。
表 4–8 ログメッセージの要素
要素 |
説明 |
---|---|
Category |
メッセージの種類 – アプリケーション、システム、またはセキュリティ |
Severity |
状況の重大性 – 警告またはエラー |
Application |
ログメッセージを書き込んだアプリケーション (またはプロバイダ) の名前 |
User |
ログメッセージの生成時にアプリケーションを使用していたユーザー名 |
Client Machine |
ログメッセージの生成時にユーザーが使用していたシステム名および IP アドレス |
Server Machine |
ログメッセージの原因となったイベントが発生したシステム名 |
Summary Message |
イベントの概要説明 |
Detailed Message |
イベントの詳細説明 |
Data |
イベントをより把握するための状況説明 |
SyslogFlag |
メッセージを syslogd(1M) に送信するかどうかを指定するブール値のフラグ |
次の例では、ログを作成し、その内容を表示します。
このプログラム例では、Solaris_LogEntry のインスタンスを作成し、そのインスタンスを設定します。
public class CreateLog { public static void main(String args[]) throws CIMException { // 渡されたコマンド行引数が不足している場合、 // 使用法を表示する if (args.length < 3) { System.out.println("Usage: CreateLog host username password " + "[rmi|http]"); System.exit(1); } String protocol = CIMClient.CIM_RMI; CIMClient cc = null; CIMObjectPath cop = null; BufferedReader d = new BufferedReader(new InputStreamReader (System.in)); String input_line = ""; // 作成するレコード数をユーザーに問い合わせる System.out.print("How many log records do you want to write? "); int num_recs = 0; try { num_recs = Integer.parseInt(d.readLine()); } catch (Exception ex) { ex.printStackTrace(); System.exit(1); } // try-catch ブロックのオーバーアーチ try { CIMNameSpace cns = new CIMNameSpace(args[0]); UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); // トランスポートプロトコルをデフォルトの RMI に設定する if (args.length == 4 && args[3].equalsIgnoreCase("http")) { protocol = CIMClient.CIM_XML; } cc = new CIMClient(cns, up, pc, protocol); Vector keys = new Vector(); CIMProperty logsvcKey = null; // ログ記録の作成に必要な関連情報の入力を // ユーザーに求める System.out.println("Please enter the record Category: "); System.out.println("\t(0)application, (1)security, (2)system"); logsvcKey = new CIMProperty("category"); input_line = d.readLine(); logsvcKey.setValue(new CIMValue(Integer.valueOf (input_line))); keys.addElement(logsvcKey); System.out.println("Please enter the record Severity:"); System.out.println("\t(0)Informational, (1)Warning, (2)Error"); logsvcKey = new CIMProperty("severity"); input_line = d.readLine(); logsvcKey.setValue(new CIMValue(Integer.valueOf (input_line))); keys.addElement(logsvcKey); logsvcKey = new CIMProperty("Source"); System.out.println("Please enter Application Name:"); logsvcKey.setValue(new CIMValue(d.readLine())); keys.addElement(logsvcKey); logsvcKey = new CIMProperty("SummaryMessage"); System.out.println("Please enter a summary message:"); logsvcKey.setValue(new CIMValue(d.readLine())); keys.addElement(logsvcKey); logsvcKey = new CIMProperty("DetailedMessage"); System.out.println("Please enter a detailed message:"); logsvcKey.setValue(new CIMValue(d.readLine())); keys.addElement(logsvcKey); logsvcKey = new CIMProperty("RecordData"); logsvcKey.setValue( new CIMValue("0xfe 0x45 0xae 0xda random data")); keys.addElement(logsvcKey); logsvcKey = new CIMProperty("SyslogFlag"); logsvcKey.setValue(new CIMValue(new Boolean(true))); keys.addElement(logsvcKey); CIMObjectPath logreccop = new CIMObjectPath("Solaris_LogEntry", keys); CIMClass logClass = cc.getClass(logreccop); CIMInstance ci = logClass.newInstance(); ci.setClassName("Solaris_LogEntry"); ci.setProperties(keys); // System.out.println(ci.toString()); // 要求された数のレコードインスタンスを作成する for (int i = 0; i < num_recs; i++) { cc.createInstance(logreccop, ci); } } catch (Exception e) { System.out.println("Exception: "+e); e.printStackTrace(); } // セッションの終了 if (cc != null) { cc.close(); } } }
このプログラム例では、ログ記録のリストを表示します。
public class ReadLog { public static void main(String args[]) throws CIMException { String protocol = CIMClient.CIM_RMI; // 渡されたコマンド行引数が不足している場合、 // 使用法を表示する if (args.length < 3) { System.out.println("Usage: ReadLog host username password " + "[rmi|http]"); System.exit(1); } CIMClient cc = null; CIMObjectPath cop = null; CIMObjectPath serviceObjPath = null; Vector inVec = new Vector(); Vector outVec = new Vector(); // try-catch ブロックのオーバーアーチ try { CIMNameSpace cns = new CIMNameSpace(args[0]); UserPrincipal up = new UserPrincipal(args[1]); PasswordCredential pc = new PasswordCredential(args[2]); // トランスポートプロトコルをデフォルトの RMI に設定する if (args.length == 4 && args[3].equalsIgnoreCase("http")) { protocol = CIMClient.CIM_XML; } cc = new CIMClient(cns, up, pc, protocol); cop = new CIMObjectPath("Solaris_LogEntry"); // Solaris_LogEntry クラスのインスタンスリストを列挙する Enumeration e = cc.enumerateInstances(cop, true, false, false, false, null); // リストを繰り返し処理して、各プロパティを出力する for (; e.hasMoreElements(); ) { System.out.println("---------------------------------"); CIMInstance ci = (CIMInstance)e.nextElement(); System.out.println("Log filename : " + ((String)ci.getProperty("LogName").getValue(). getValue())); int categ = (((Integer)ci.getProperty("Category").getValue().getValue()). intValue()); if (categ == 0) System.out.println("Category : Application Log"); else if (categ == 1) System.out.println("Category : Security Log"); else if (categ == 2) System.out.println("Category : System Log"); int severity = (((Integer)ci.getProperty("Severity").getValue().getValue()). intValue()); if (severity == 0) System.out.println("Severity : Informational"); else if (severity == 1) System.out.println("Severity : Warning Log!"); else if (severity == 2) System.out.println("Severity : Error!!"); System.out.println("Log Record written by :" + ((String)ci.getProperty("Source").getValue().getValue())); System.out.println("User : " + ((String)ci.getProperty("UserName").getValue().getValue())); System.out.println("Client Machine : " + ((String)ci.getProperty("ClientMachineName").getValue().getValue())); System.out.println("Server Machine : " + ((String)ci.getProperty("ServerMachineName").getValue().getValue())); System.out.println("Summary Message : " + ((String)ci.getProperty("SummaryMessage").getValue().getValue())); System.out.println("Detailed Message : " + ((String)ci.getProperty("DetailedMessage").getValue().getValue())); System.out.println("Additional data : " + ((String)ci.getProperty("RecordData").getValue().getValue())); boolean syslogflag = ((Boolean)ci.getProperty("SyslogFlag").getValue().getValue()). booleanValue(); if (syslogflag == true) { System.out.println("Record was written to syslog"); } else { System.out.println("Record was not written to syslog"); } System.out.println("---------------------------------"); } } catch (Exception e) { System.out.println("Exception: "+e); e.printStackTrace(); } // セッションの終了 if (cc != null) { cc.close(); } } }