public class RMIClassLoader extends Object
RMIClassLoader
は、RMI を使用して動的にクラスをロードするための static メソッドから構成されます。このクラスローダーには、ネットワークの場所 (1 つ以上の URL) からクラスをロードするメソッドや、既存のクラスが格納されている場所を取得するメソッドが組み込まれています。これらのメソッドは、リモートメソッド呼び出しの引数や戻り値に含まれるクラスを整列化および非整列化するときに、RMI ランタイムによって使用されます。 また、これらのメソッドをアプリケーションから直接呼び出して、クラスを動的にロードすることもできます。
次の static メソッドの実装は、
loadClass(URL,String)
loadClass(String,String)
loadClass(String,String,ClassLoader)
loadProxyClass(String,String[],ClassLoader)
getClassLoader(String)
getClassAnnotation(Class)
RMIClassLoaderSpi
のインスタンスによって提供されます。このメソッドのいずれかが呼び出されると、その動作がサービスプロバイダインスタンスの対応するメソッドに委譲されます。各メソッドがプロバイダインスタンスに委譲する方法の詳細は、各メソッドのマニュアルを参照してください。
サービスプロバイダインスタンスは次のように選択されます。
java.rmi.server.RMIClassLoaderSpi
が定義されている場合、その値が "default"
のときは、getDefaultProviderInstance()
メソッド呼び出しの戻り値に指定されているプロバイダインスタンスが選択されます。このシステムプロパティーが "default" 以外の値のときは、システムクラスローダー (ClassLoader.getSystemClassLoader()
を参照) がシステムプロパティーに指定されているクラスをロードでき、そのクラスをRMIClassLoaderSpi
に割り当てることができ、引数のない public コンストラクタを持つ場合、プロバイダインスタンス作成時にそのコンストラクタが呼び出されます。このシステムプロパティーが定義されている場合でも、これらの条件が満たされていない場合は、RMIClassLoader
の使用を試みるコードに対して、プロバイダインスタンスの取得に失敗したことを示す、特定できない Error
がスローされます。
META-INF/services/java.rmi.server.RMIClassLoaderSpi
というリソースがシステムクラスローダーから見える場合、そのリソースの内容はプロバイダ構成ファイルとして解釈され、そのファイルの最初に指定されているクラス名がプロバイダクラス名として使用されます。システムクラスローダーがその名前を持つクラスをロードでき、そのクラスを RMIClassLoaderSpi
に割り当てることができ、引数のない public コンストラクタを持つ場合は、プロバイダインスタンス作成時にそのコンストラクタが呼び出されます。そのリソースが見つかっても、記述されているようにプロバイダをインスタンス化できない場合は、RMIClassLoader
の使用を試みるコードに対して、プロバイダインスタンスの取得に失敗したことを示す、不明な Error
がスローされます。
getDefaultProviderInstance()
メソッド呼び出しの戻り値に指定されているプロバイダインスタンスが選択されます。
RMIClassLoaderSpi
修飾子と型 | メソッドと説明 |
---|---|
static String |
getClassAnnotation(Class<?> cl)
クラス定義の位置を示す注釈文字列を返します。RMI はこれを使用して、指定されたクラスのオブジェクトの整列化を行う際に、クラス記述子に注釈を加えます。
|
static ClassLoader |
getClassLoader(String codebase)
指定されたコードベース URL パスからクラスをロードするクラスローダーを返します。
|
static RMIClassLoaderSpi |
getDefaultProviderInstance()
サービスプロバイダインタフェース
RMIClassLoaderSpi のデフォルトプロバイダの正規インスタンスを返します。 |
static Object |
getSecurityContext(ClassLoader loader)
非推奨。
代替はありません。Java 2 プラットフォーム v1.2 以降の RMI では、クラスローダーのセキュリティーコンテキストを取得するためにこのメソッドを使用しません。
|
static Class<?> |
loadClass(String name)
非推奨。
loadClass(String,String) メソッドに置き換えられています |
static Class<?> |
loadClass(String codebase, String name)
指定されたコードベース URL パスからクラスをロードします。
|
static Class<?> |
loadClass(String codebase, String name, ClassLoader defaultLoader)
指定されたコードベース URL パスからクラスをロードします。指定されたローダーを使用することもできます。
|
static Class<?> |
loadClass(URL codebase, String name)
指定されたコードベース URL からクラスをロードします。
|
static Class<?> |
loadProxyClass(String codebase, String[] interfaces, ClassLoader defaultLoader)
指定された名前を持つインタフェース群を実装した動的プロキシクラス (
Proxy を参照) を、指定されたコードベース URL パスからロードします。 |
@Deprecated public static Class<?> loadClass(String name) throws MalformedURLException, ClassNotFoundException
loadClass(String,String)
メソッドに置き換えられました。 name
を名前に持つクラスをロードします。
このメソッドは loadClass(String,String)
に処理を委譲します。このとき、null
が最初の引数として、name
が 2 つめの引数として渡されます。
name
- ロード対象クラスの名前Class
オブジェクトMalformedURLException
- クラスのロード時に使用されたプロバイダ固有の URL が無効である場合ClassNotFoundException
- クラスの定義がコードベースの場所になかった場合loadClass(String,String)
public static Class<?> loadClass(URL codebase, String name) throws MalformedURLException, ClassNotFoundException
codebase
が null
の場合、このメソッドの動作は loadClass(String,String)
に null
の codebase
と所定のクラス名を指定した場合と同じになります。
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.loadClass(String,String,ClassLoader)
メソッドに処理を委譲します。このとき、指定された URL で URL.toString()
を呼び出した結果 (codebase
が null の場合は null
) が最初の引数として、name
が 2 つめの引数として、null
が 3 つめの引数として渡されます。
codebase
- クラスのロード元の URL、または null
name
- ロード対象クラスの名前Class
オブジェクトMalformedURLException
- codebase
が null
で、かつクラスのロード時に使用されたプロバイダ固有の URL が無効である場合ClassNotFoundException
- クラスの定義が指定された URL になかった場合public static Class<?> loadClass(String codebase, String name) throws MalformedURLException, ClassNotFoundException
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.loadClass(String,String,ClassLoader)
メソッドに処理を委譲します。このとき、codebase
が最初の引数として、name
が 2 つめの引数として、null
が 3 つめの引数として渡されます。
codebase
- クラスのロード元の URL のリスト (区切り文字はスペース)、またはnull
name
- ロード対象クラスの名前Class
オブジェクトMalformedURLException
- codebase
が null
以外でかつ無効な URL を含んでいる場合、または codebase
が null
でかつクラスのロード時に使用されたプロバイダ固有 URL が無効である場合ClassNotFoundException
- クラスの定義が指定された場所になかった場合public static Class<?> loadClass(String codebase, String name, ClassLoader defaultLoader) throws MalformedURLException, ClassNotFoundException
defaultLoader
を使用して指定されたクラスの解決を試みたあとで、コードベース URL パスからのクラスの解決を試みます。
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.loadClass(String,String,ClassLoader)
メソッドに処理を委譲します。このとき、codebase
が最初の引数として、name
が 2 つめの引数として、defaultLoader
が 3 つめの引数として渡されます。
codebase
- クラスのロード元の URL のリスト (区切り文字はスペース)、またはnull
name
- ロード対象クラスの名前defaultLoader
- 状況に応じて使用する追加クラスローダー、または null
Class
オブジェクトMalformedURLException
- codebase
が null
以外でかつ無効な URL を含んでいる場合、または codebase
が null
でかつクラスのロード時に使用されたプロバイダ固有 URL が無効である場合ClassNotFoundException
- クラスの定義が指定された場所になかった場合public static Class<?> loadProxyClass(String codebase, String[] interfaces, ClassLoader defaultLoader) throws ClassNotFoundException, MalformedURLException
Proxy
を参照) を、指定されたコードベース URL パスからロードします。
これらのインタフェースの解決は、指定された codebase
を使用して loadClass(String,String)
メソッド経由でロードされるクラスと同様の方法で行われます。
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.loadProxyClass(String,String[],ClassLoader)
メソッドに処理を委譲します。このとき、codebase
が最初の引数として、interfaces
が 2 つめの引数として、defaultLoader
が 3 つめの引数として渡されます。
codebase
- クラスのロード元の URL のリスト (区切り文字はスペース)、またはnull
interfaces
- プロキシクラスが実装するインタフェースの名前defaultLoader
- 状況に応じて使用する追加クラスローダー、または null
MalformedURLException
- codebase
が null
以外でかつ無効な URL を含んでいる場合、または codebase
が null
でかつクラスのロード時に使用されたプロバイダ固有 URL が無効である場合ClassNotFoundException
- 指定されたインタフェースの定義のいずれかが指定された場所に見つからない場合、または動的プロキシクラスの作成に失敗した場合 (Proxy.getProxyClass(ClassLoader,Class[])
が、指定されたインタフェースリストに対して IllegalArgumentException
をスローしたときなど)public static ClassLoader getClassLoader(String codebase) throws MalformedURLException, SecurityException
返されるクラスローダーは、loadClass(String,String)
メソッドが同じ codebase
引数を指定してクラスをロードするときに使用するクラスローダーと同じです。
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.getClassLoader(String)
メソッドに処理を委譲します。このとき、codebase
が引数として渡されます。
セキュリティーマネージャーが存在する場合は、RuntimePermission("getClassLoader")
アクセス権を使用して checkPermission
メソッドが呼び出され、この結果 SecurityException
になることがあります。このメソッドのプロバイダ実装は、呼び出し側コンテキストがコードベース URL パス内のすべての URL に対するアクセス権を持っているかどうかについて、セキュリティーチェックを行うこともあります。
codebase
- 返されるクラスローダーがロードするクラスが格納されている URL のリスト (区切り文字はスペース)、または null
MalformedURLException
- codebase
が null
以外でかつ無効な URL を含んでいる場合、または codebase
が null
でかつクラスローダーの識別に使用されたプロバイダ固有 URL が無効である場合SecurityException
- セキュリティーマネージャーが存在するときに、その checkPermission
メソッドが失敗した場合。または、呼び出し側がコードベース URL パス内のすべての URL に接続するアクセス権を持っていない場合public static String getClassAnnotation(Class<?> cl)
このメソッドは、プロバイダインスタンスの RMIClassLoaderSpi.getClassAnnotation(Class)
メソッドに処理を委譲します。このとき、cl
が引数として渡されます。
cl
- 注釈を取得する対象のクラスnull
NullPointerException
- cl
が null
である場合public static RMIClassLoaderSpi getDefaultProviderInstance()
RMIClassLoaderSpi
のデフォルトプロバイダの正規インスタンスを返します。システムプロパティー java.rmi.server.RMIClassLoaderSpi
が定義されていない場合、次に示す RMIClassLoader
の static メソッドは、
loadClass(URL,String)
loadClass(String,String)
loadClass(String,String,ClassLoader)
loadProxyClass(String,String[],ClassLoader)
getClassLoader(String)
getClassAnnotation(Class)
セキュリティーマネージャーが存在する場合は、RuntimePermission("setFactory")
アクセス権を使用して checkPermission
メソッドが呼び出され、その結果 SecurityException
になることがあります。
デフォルトのサービスプロバイダインスタンスは RMIClassLoaderSpi
を次のように実装します。
getClassAnnotation
メソッドは、指定されたクラス定義のダウンロードにリモート側が使用するコードベース URL パスを表すString
を返します。返される文字列の形式は、空白で区切られた URL のパスです。 返されるコードベースの文字列は、次に示すように、指定されたクラスに定義されているクラスローダーによって異なります。
- 定義されているクラスローダーがシステムクラスローダー (
ClassLoader.getSystemClassLoader()
を参照)、システムクラスローダーの親 (インストール済みの拡張クラスに使用されるローダーなど)、またはブートストラップクラスローダー (null
で表されることもある) の場合、java.rmi.server.codebase
プロパティーの値 (または以前にキャッシュされた値の可能性もある) が返されます。そのプロパティーが設定されていない場合は、null
が返されます。- 定義されているクラスローダーが
URLClassLoader
のインスタンスの場合、そのローダーのgetURLs
メソッド呼び出しから返される、外部形式の URL のリスト (区切り文字はスペース) が返されます。URLClassLoader
がこのプロバイダによって作成され、そのloadClass
またはloadProxyClass
メソッドが使用される場合、関連するコードベース文字列を取得するためのアクセス権は必要ありません。URLClassLoader
インスタンスがこのプロバイダ以外に作成され、セキュリティーマネージャーが存在する場合は、getURLs
メソッドから URL が返されるたびに、openConnection().getPermission()
呼び出しによって返されたアクセス権を使用してセキュリティーマネージャーのcheckPermission
メソッドが呼び出されます。これらの呼び出しのいずれかでSecurityException
またはIOException
がスローされた場合、java.rmi.server.codebase
プロパティーの値 (または以前にキャッシュされた値の可能性もある) が返されます。そのプロパティーが設定されていない場合は、null
が返されます。- 定義されているクラスローダーが
URLClassLoader
のインスタンスではない場合、java.rmi.server.codebase
プロパティーの値 (または以前にキャッシュされた値の可能性もある) が返されます。そのプロパティーが設定されていない場合は、null
が返されます。
codebase
という名前のString
パラメータ (空白で区切られた URL のリスト) を取る、次に説明する各メソッド実装について、メソッドが呼び出されるたびに特定のコードベースローダーが関連付けられます。コードベースローダーは、codebase
引数と現在のスレッドのコンテキストクラスローダー (Thread.getContextClassLoader()
を参照) とを組み合わせて検索されます。セキュリティーマネージャーが存在する場合、このプロバイダは、クラスローダーインスタンスの内部テーブル (少なくともURLClassLoader
のインスタンスを含む) を保持します。このテーブルのキーは、親のクラスローダーとそのコードベース URL パス (URL の順序付きリスト) のペアです。codebase
引数がnull
の場合、コードベース URL パスは、システムプロパティーjava.rmi.server.codebase
の値、以前のキャッシュされた値のいずれかになります。あるコードベース URL パスがある特定のコンテキスト内で次のいずれかのメソッドの呼び出しのcodebase
引数として渡された場合、テーブル内のローダーのうち、パスが指定されたコードベース URL パス、親が現在スレッドのコンテキストクラスローダーであるようなローダーが、コードベースローダーになります。そのようなローダーが存在しない場合は、作成されてテーブルに追加されます。ただし、このテーブルは、到達不可能なローダーとそのローダーに定義されているクラスがガベージコレクトされるように、ローダーへの強参照を保持しません。セキュリティーマネージャーが存在しないときに信頼されないコードが仮想マシンに暗黙的にロードされないようにするために、セキュリティーマネージャーが設定されていない場合は、コードベースローダーは現在のスレッドのコンテキストクラスローダーになります (指定されたコードベース URL パスは無視され、リモートクラスをロードできなくなる)。
getClassLoader
メソッドは、指定されたコードベース URL パスのコードベースローダーを返します。セキュリティーマネージャーが存在する場合、呼び出し側コンテキストにコードベース URL パス内のすべての URL に対するアクセス権がないときは、SecurityException
がスローされます。
loadClass
メソッドは、指定された名前を持つクラスのロードを次の方法で試みます。defaultLoader
引数がnull
でない場合は、まずdefaultLoader
を使用して、指定されたname
のクラスをロードしようとします。たとえば、次のように評価します。Class.forName(name, false, defaultLoader)クラスをdefaultLoader
からロードできた場合は、そのクラスが返されます。ClassNotFoundException
以外の例外がスローされた場合は、その例外が呼び出し側にスローされます。次に、
loadClass
メソッドが、指定されたコードベース URL パスのコードベースローダーを使用して、指定されたname
のクラスのロードを試みます。セキュリティーマネージャーが存在する場合、呼び出し側コンテキストにはコードベース URL パス内のすべての URL に対するアクセス権が必要です。 アクセス権がない場合は、コードベースローダーの代わりに、現在のスレッドのコンテキストクラスローダーが使用されます。
loadProxyClass
メソッドは、次の方法で、指定されたインタフェースの動的プロキシクラスを返そうとします。
defaultLoader
引数がnull
以外で、そのローダーを使用して、指定されたインタフェースをすべて解決できる場合
- 解決されたインタフェースがすべて
public
の場合は、まずProxy.getProxyClass
を使用して、コードベースローダーからそのインタフェースの動的プロキシクラスを取得しようとする。IllegalArgumentException
がスローされた場合は、defaultLoader
からそのインタフェースの動的プロキシクラスを取得しようとする。どちらの場合もIllegalArgumentException
がスローされたときは、ClassNotFoundException
がスローされる。ほかの例外がスローされた場合、その例外は呼び出し側にスローされる- 解決されたインタフェースが
public
以外の場合、それらがすべて同じクラスローダーに定義されているときは、そのローダーからそのインタフェースの動的プロキシクラスを取得しようとする- 上記以外の場合は、
LinkageError
がスローされる (指定されたインタフェースをすべて実装するクラスはいずれのローダーにも定義できないため)指定されたすべてのインタフェースを、コードベースローダーを使用して解決できる場合
- 解決されたインタフェースがすべて
public
の場合は、そのインタフェースの動的プロキシクラスをコードベースローダーから取得しようとする。IllegalArgumentException
がスローされた場合は、ClassNotFoundException
がスローされる。- 解決されたインタフェースが
public
以外の場合、それらがすべて同じクラスローダーに定義されているときは、そのローダーからそのインタフェースの動的プロキシクラスを取得しようとする- 上記以外の場合は、
LinkageError
がスローされる (指定されたインタフェースをすべて実装するクラスはいずれのローダーにも定義できないため)それ以外の場合、解決できなかった指定インタフェースについて、
ClassNotFoundException
がスローされます。
SecurityException
- セキュリティーマネージャーが存在する場合に、その checkPermission
メソッド呼び出しに失敗したとき@Deprecated public static Object getSecurityContext(ClassLoader loader)
loader
- セキュリティーコンテキストの取得元のクラスローダーSecurityManager.getSecurityContext()
バグまたは機能を送信
詳細な API リファレンスおよび開発者ドキュメントについては、Java SE のドキュメントを参照してください。そのドキュメントには、概念的な概要、用語の定義、回避方法、有効なコード例などの、開発者を対象にしたより詳細な説明が含まれています。
Copyright © 1993, 2013, Oracle and/or its affiliates. All rights reserved.