OSGi R4服务平台核心规范 :第六章 Framework API(2)

 由  满江红开放技术研究组织 发布

版权说明

本文档版权归原作译者所有。 在免费、且无任何附加条件的前提下,可在网络媒体中自由传播。

如需部分或者全文引用,请事先征求作译者意见。

如果本文对您有些许帮助,表达谢意的最好方式,是将您发现的问题和文档改进意见及时反馈给作者。当然,倘若有时间和能力,能为技术群体无偿贡献自己的所学为最好的回馈。

本文档可从http://www.redsaga.com获取最新更新信息

6.1.4. public interface Bundle

框架中一个已经安装的bundle。

可以通过Bundle对象来对一个已经安装的bundle的生命周期进行控制。

在OSGi框架中安装的每一个bundle都有一个相关的Bundle对象。

bundle必须要有一个惟一标识,这是框架提供的一个长整形数。

在bundle的生命周期期间,这个标识符是不能修改的,即使对bundle进行了更新。而卸载然后重新安装的bundle必须重新分配一个标识符。

bundle具有六种状态:

  • UNINSTALLED[p.125]
  • INSTALLED[p.124]
  • RESOLVED[p.124]
  • STARTING[p.125]
  • STOPPING[p.125]
  • ACTIVE[p.124]
每种状态分配的值是没有规定顺序的;值为位串,可以通过OR操作来获得bundle的有效状态。

只有当bundle的状态是在启动、活动或者是停止时才可以运行代码。处于卸载状态的bundle是不能设置为其他状态的;这种状态只是由于其他地方存在引用而形成的一种僵死状态。

只有框架才能创建Bundle对象,而且只有在创建它们的框架内有效。

6.1.4.1. public static final int ACTIVE = 32

表示bundle正在运行。

当bundle成功启动之后就进入了ACTIVE状态。

ACTIVE状态的值为0x00000020。

6.1.4.2. public static final int INSTALLED = 2

描述bundle已经安装但是还没有解析。

当框架已经安装了bundle但是还不能运行时的状态称为INSTALLED状态。

如果bundle代码的依赖关系还没有解析,这个状态是可见的。框架将尝试解析处于INSTALLED状态的bundle代码依赖关系,并且将bundle转移到RESOLVED状态。

INSTALLED状态的值为0x00000002。

6.1.4.3. public static final int RESOLVED = 4

描述bundle已经解析,而且可以启动。

当框架成功的解析了bundle的依赖关系之后,bundle就处于RESOLVED状态。这些依赖关系包括:

  • 来自于清单文件中Constants.BUNDLE_CLASSPATH描述的bundle类路径。
  • 来自于清单文件中Constants.EXPORT_PACKAGE和Constants.IMPORT_PACKAGE描述的包的依赖关系。
  • 来自于清单文件中Constants.REQUIRE_BUNDLE描述的需要的bundle依赖关系。
  • 来自于清单文件中Constants.FRAGMENT_HOST所描述的片断bundle依赖关系。
需要注意的是此时bundle尚未激活。在启动bundle之前必须将其状态置为RESOLVED。框架可能在任何时候都会尝试对bundle进行解析。

RESOLVED状态的值为0x00000004。

6.1.4.4. public static final int STARTING = 8

描述bundle处于启动过程中。

只有当调用start方法启动bundle之后,bundle进入STARTING状态。

当调用了bundle的BundleActivator.start方法时,bundle必须进入STARTING状态。如果方法成功返回,而没有抛出异常,那么bundle成功启动,并且进入到ACTIVE状态。

STARTING状态的值为0x00000008。

6.1.4.5. public static final int STOPPING = 16

描述bundle处于停止状态。

当调用bundle的stop方法时,bundle进入到STOPPING状态。当调用BundleActivator.stop方法之后,bundle必须要进入这个状态。当方法成功返回而且完全停止了bundle之后,bundle进入到RESOLVED状态。

STOPPING状态的值为0x00000010。

6.1.4.6. public static final int UNINSTALLED = 1

描述卸载bundle之后而且不能再使用的状态。

只有当卸载了bundle之后,bundle的状态才是UNINSTALLED状态;虽然不能再使用bundle,但是对这个Bundle对象的引用还有有效的,可以根据引用来进行自省(introspection)。

UNINSTALLED状态的值为0x00000001。

6.1.4.7. public Enumeration findEntries( String path, String filePattern, boolean recurse )

path 搜索的路径名称。特殊路径“/”表示bundle根路径。路径和bundle的来源有关,而且必须不能为null值。
filePattern 在指定路径下选择条目(entry)的文件名称模式。只和条目地址的最后单元进行匹配,而且支持子串匹配,如同Filter规范一节中的描述,可以使用通配符“*”。如果filePattern为null值,那么就和“*”的处理一样,匹配所有的文件。
recurse 如果为true,那么递归遍历所有的子目录;如果为false,那么就只会返回当前目录中符合条件的条目。
返回bundle以及它的附加片断中的匹配条目。不使用bundle的类加载器来查找条目。只会搜索bundle以及它附加片断中的内容。如果bundle处于INSTALLED状态,那么在查找之前会尝试对bundle进行解析。

这个方法的意图在于提供从bundle中获取配置、设置、本地化以及其他信息的途径。这个方法考虑到bundle的“目录”中也扩加了片断的信息。这样的一个“bundle 空间”并不是一个惟一成员的命名空间;同样名称的条目可能出现多次。因此这个方法返回的是URL对象的枚举对象。这些URL对象可以是来自不同的JAR文件,但是具有相同的路径名。这个方法既可以指返回指定路径的条目,也可以返回指定路径的子目录下的条目。在解析bundle之后,就可以附加片断,而可能会因此改变了这个方法返回的URL集合。如果还没有解析这个bundle,那么只会返回这个bundle的JAR文件的条目。

例如:

Returns URL对象的枚举对象,其中每一个URL对象是对应于一个匹配条目的。如果不能找到匹配条目,那么返回null值,或者如果Java运行环境支持权限控制而调用这没有适应的管理权限:AdminPermission[this,RESOURCE]。返回条目的URL的排列顺序如下:首先返回bundle片断中条目,而且按照bundle的ID升序排列。如果该bundle是一个片断,那么只会返回这个片断中的匹配结果。
Since 1.3

6.1.4.8. public long getBundleId( )

返回bundle的惟一标识。当在OSGi环境中安装bundle时,框架会给bundle分配一个惟一的标识符。

bundle的标识符具有以下特征:

  • 惟一且持久性
  • 长整型
  • 其他bundle不能再次使用,即使在卸载bundle之后。
  • 当bundle还在安装时不会改变。
  • 当bundle更新时不会改变。
对这个方法的调用将返回bundle的惟一标识符,即使bundle处于UNINSTALLED状态。
Returns 返回bundle的惟一标识符。

6.1.4.9. public URL getEntry( String name )

name 条目名称。参阅java.lang.ClassLoader.getResource来获得关于资源名称的更多描述格式信息。
返回bundle中指定名称的条目URL。不会使用bundle的类加载器来查找指定的条目。只会对bundle的目录来查找指定条目。特殊路径“/”表示bundle根路径。
Returns 指定条目的URL;或者如果没有找到指定条目则返回null;或者如果Java运行环境支持权限控制而调用者没有管理权限:AdminPermission[this, RESOURCE],那么也返回null。
Throws IllegalStateException – 如果bundle已经卸载。
Since 1.3 specified

6.1.4.10. public Enumeration getEntryPaths( String path )

path 返回条目路径的路径名称
返回bunlde中条目的最长子路径和参数提供的路径匹配的所有条目的路径枚举对象。不能使用bundle的类加载器来查找条目。只搜索bundle的目录。特殊路径“/”表示bundle根路径。

以“/”结尾的路径表示是一个子目录,返回的路径都和bundle根路径相关。
Returns 返回条目路径的枚举对象;如果没有找到匹配条目,返回null值;或者如果Java运行环境支持权限控制,而调用者没有合适的管理权限:AdminPermission[this,RESOURCE],也返回null值。
Throws IllegalStateException – 如果bundle已经卸载了
Since 1.3

6.1.4.11. public Dictionary getHeaders( )

返回bundle的清单文件的头标和值对。这个方法返回的是bundle清单文件中主要部分的所有的清单信息,也就是说从第一行到第一个空白行。

清单文件中的头标是不区分大小写的。方法返回的Dictionary对象中对于头标名称的处理也是不区分大小写的。如果头标名称的起始值为“%”,那么必须要使用默认的区域来本地化这个头标。

例如,对于下面的清单头标,如果它们出现在清单文件中,那么它们将出现在返回的Dictionary对象中:

  • Bundle-Name
  • Bundle-Vendor
  • Bundle-Version
  • Bundle-Description
  • Bundle-DocURL
  • Bundle-ContactAddress
如果bundle的状态是UNINSTALLED,那么这个方法依然要返回bundle的清单文件信息。

Returns 返回一个包括了bundle清单头标和值对的Dictionary对象。
Throws SecurityException – 如果Java运行环境支持权限控制,而调用者没有适当的管理权限:AdminPermission[this,METADATA]
See Also Constants.BUNDLE_LOCALIZATION

6.1.4.12. public Dictionary getHeaders( String locale )

locale 头标的值需要进行本地化的区域。如果指定的区域为null,那么使用java.util.Locale.getDefault返回的区域。如果如果指定的区域字符串是空串,那么这个方法将返回所有的以“%”开头的原始的(未本地化的)清单头标。
返回通过指定区域进行本地化的bundle的头标。

这个方法和Bundle.getHeaders()方法的处理是一样的,除了增加区域。如果清单头标的起始值为“%”,那么必须要通过指定区域进行本地化。如果不能找到指定区域,那么那么使用默认的区域的头标的值。如果指定的区域为一个空字符串(””),那么返回没有本地化的值,返回所有的以“%”开始的头标的值。

如果bundle的状态是UNINSTALLED,那么这个方法依然要返回bundle的清单文件信息。但是返回的值只能是原始的值和默认区域的本地化值。

Returns 包含bundle清单头标和值对的Dictionary对象
Throws SecurityException – 如果Java运行环境支持权限控制,而调用者没有适当的管理权限:AdminPermission[this,METADATA]
See Also getHeaders()[p.127] , Constants.BUNDLE_LOCALIZATION[p.154]
Since 1.3

6.1.4.13. public long getLastModified( )

返回bundle上次的最新更新时间。对bundle的修改包括安装、更新和卸载。

时间值为自从1月1日, 1970, 00:00:00 GMT开始的时间。
Returns bundle上次更新的时间
Since 1.3

6.1.4.14. public String getLocation( )

返回bundle区域的标识符。

bundle区域标识符是当安装bundle时,发送给BundleContext.installBundle的区域。只要当bundle还是安装好的,那么bundle的区域标识符就不会改变,即使对bundle进行更新。

如果bundle的状态是UNINSTALLED,那么本方法必须还要能返回bundle的区域标识符。
Returns 描述bundle区域的标识符字符串。
Throws SecurityException – 如果Java运行环境支持权限控制,而调用者没有适当的管理权限:AdminPermission[this,METADATA]

6.1.4.15. public ServiceReference[] getRegisteredServices( )

返回bundle已经注册的所有ServiceReference对象数组,如果bundle没有注册服务,返回null值。

如果Java运行环境支持权限,那么只有当调用者具有ServicePermission来使用至少一个注册的服务类获得服务,才能返回这个ServiceReference对象。

在调用方法时返回的列表是有效的,然则框架是一个动态的环境,服务可能被随时修改或者取消注册。

Returns ServiceReference对象数组或者null值。
Throws IllegalStateException – 如果bundle已经是卸载的。
See Also ServiceRegistration[p.179] , ServiceReference[p.177] , ServicePermission[p.176]

6.1.4.16. public URL getResource( String name )

name 资源名称。参阅java.lang.ClassLoader.getResource关于资源格式的描述。
从bundle中找到指定的资源。通过调用bundle类加载器来查找资源。如果bundle的状态是INSTALLED,那么只会对这个bundle进行搜索,而由于还没有解析bundle,故不会搜索导入包。如果指定bundle是一个片断(fragment),那么返回null值。
Returns 指定资源名称的URL,或者如果不能找到指定资源,或者如果bundle是一个片断,或者如果Java运行环境支持权限而调用者没有管理权限:AdminPermission[this,RESOURCE],那么返回null值。
Throws IllegalStateException – 如果bundle已经是卸载的。
Since 1.1

6.1.4.17. public Enumeration getResources( String name ) throws IOException

name 资源名称。参阅java.lang.ClassLoader.getResource关于资源格式的描述。
从bundle中查找指定资源。在查找过程中调用bundle类加载器。如果bundle状态为INSTALLED,那么只对bundle进行查找。由于bundle还没有解析,所以不查找导入包。如果这是一个片断bundle,那么返回null。
Returns 返回指定名称的资源URL的枚举对象,或者如果不能找到指定资源,或者如果bundle是一个片断,或者如果Java运行环境支持权限而调用者没有管理权限:AdminPermission[this,RESOURCE],那么返回null值。
Throws IllegalStateException – 如果bundle已经是卸载的。

IOException – 如果发生I/O错误。
Since 1.3

6.1.4.18. public ServiceReference[] getServicesInUse( )

返回bundle使用的所有服务的ServiceReference对象数组,或者如果bundle没有使用任何服务,那么返回null。如果bundle对一个服务的使用计数大于0,那么就说bundle使用了这个服务。

如果Java运行环境支持权限,那么只有当调用者具有ServicePermission权限来使用至少一个注册时的服务类获得服务,才能返回这个ServiceReference对象。

在调用方法时返回的列表是有效的,然则框架是一个动态的环境,服务可能被随时修改或者取消注册。
Returns An array of ServiceReference objects or null.
Throws IllegalStateException – If this bundle has been uninstalled.
See Also ServiceReference[p.177] , ServicePermission[p.176]

6.1.4.19. public int getState( )

返回bundle当前状态。

bundle在任何时候都只能处于一种状态。
Returns UNINSTALLED,INSTALLED,RESOLVED,STARTING,STOPPING,ACTIVE这六个值中的一个。

6.1.4.20. public String getSymbolicName( )

返回根据Bundle-SymbolicName指定的bundle的符号名称。这个名称是惟一的,推荐通过倒置域名的形式来命名,如同java包的命名一样。

如果没有指定符号名称,那么返回null。

即使bundle的状态是UNINSTALLED,那么本方法依然能返回bundle符号名称。
Returns bundle的符号名称。
Since 1.3

6.1.4.21. public boolean hasPermission( Object permission )

permission 需要检查的权限。
检查bundle是否具有指定权限。

如果Java运行环境不支持权限,那么始终返回true。

permission的类型是Object,这是为了避免直接引用java.security.Permission类。这样,允许框架可以在不支持Java权限的环境下实现。

如果Java运行环境不支持权限,那么bundle和包含在JAR文件中的其他资源是属于同一个java安全域(java.security.ProtectionDomain);也就是说,它们是共享相同的权限集合。
Returns 如果bundle有指定权限或者由bundle分配的权限蕴含了指定权限,那么返回true,否则,如果没有指定权限,或者permission不是instanceofjava.security.Permission的实例。
Throws IllegalStateException – 如果已经卸载了bundle。

6.1.4.22. public Class loadClass( String name ) throws ClassNotFoundException

name 需要加载的类。
使用bundle的;类加载器来加载指定类。

如果bundle为一个片断bundle,那么方法抛出ClassNotFoundException异常。

如果bundle状态为INSTALLED,那么在加载类的时候会尝试解析bundle。

如果不能解析bundle,那么框架发出一个包含BundleException 的FrameworkEvent.ERROR事件,说明bundle不能解析的原因。同时方法抛出ClassNotFoundException异常。

如果bundle状态为UNINSTALLED,那么方法抛出IllegalStateException异常。
Returns 请求类的类对象。
Throws ClassNotFoundException – 如果不能找到指定类,或者是一个片断bundle,或者Java运行环境支持权限,而调用者没有相应的AdminPermission[this, CLASS]权限。

IllegalStateException – 如果bundle已经被卸载。
Since 1.3

6.1.4.23. public void start( ) throws BundleException

启动bundle。

如果框架实现了可选的启动级别服务,而且框架当前的启动级别要小于bundle的启动级别,那么框架必须要持久标记bundle状态为started,延迟到当框架的启动级别大于或者等于bundle的启动级别时,再启动bundle。

否则,按照以下步骤启动bundle:

1. 如果bundle的状态是UNINSTALLED,那么抛出IllegalStateException异常。

2. 如果bundle的状态为STARTING或者STOPPING,那么必须要等到状态改变后再继续执行方法,如果不能在一个有效的时间内继续执行启动,那么方法抛出BundleException表示不能启动bundle。

3. 如果bundle的状态是ACTIVE,那么方法立即返回。

4. 框架持久标记已经启动bundle。当框架重新启动后,必须要自动启动已经启动了的bundle。

5. 如果bundle的状态不是RESOLVED,那么尝试解析bundle的包依赖。如果框架不能解析bundle,抛出BundleException异常。

6. 设置bundle状态为STARTING。

7. 发出BundleEvent.STARTING事件。这个事件只发送到bundle同步监听器SynchronousBundleListeners,而不会发送到BundleListeners。

8. 如果指定了一个BundleActivator,那么就调用它的start方法。如果没有指定或者是抛出了异常,那么将bundle状态设置为RESOLVED。
取消注册任何bundle注册的服务。
释放bundle使用的任何服务。
移除bundle注册的任何监听器。
然后抛出bundle异常BundleException。

9. 如果bundle的状态是UNINSTALLED,那么由于在BundleActivator.start运行中卸载了bundle,那么抛出BundleException。

10. 设置bundle状态为ACTIVE。

11. 发出bundle事件BundleEvent.STARTED。

前置条件是:

  • getState() 方法返回值为{INSTALLED},{ RESOLVED}。
如果没有抛出异常, 后置条件:

  • bundle的持久状态标记为活动(active);
  • getState() 方法返回值为{ ACTIVE};
  • 调用了BundleActivator.start()方法,而且没有抛出异常。
如果抛出了异常,后置条件:

  • 依赖于异常抛出的时机,bundle持久状态为活动(active);
  • getState()方法返回值不是{STARTING}或者{ ACTIVE}。
Throws BundleException – 如果不能启动bundle。可能是由于不能解析代码依赖,或者是不能加载指定的启动器(BundleActivator),或者在加载中抛出了异常。

IllegalStateException – 如果已经卸载了bundle或者bundle试图修改自己的状态。

SecurityException – 如果Java运行环境支持权限而调用者没有相应的管理权限:AdminPermission[this,EXECUTE]。

6.1.4.24. public void stop( ) throws BundleException

停止bundle。

按照以下步骤进行:

1. 如果bundle的状态为UNINSTALLED,那么抛出IllegalStateException异常。

2. 如果bundle的状态为STARTING或者STOPPING,那么必须要等到状态改变后再继续执行方法,如果不能在一个有效的时间内继续执行停止方法,那么方法抛出BundleException表示不能停止bundle。

3. 框架持久标记已经停止bundle。当框架重新启动后,必须不能启动这个bundle。

4. 如果bundle的状态不是ACTIVE,那么方法立即返回。

5. 设置bundle状态为STOPPING。

6. 发出BundleEvent.STOPPING事件。这个事件只发送到bundle同步监听器SynchronousBundleListeners,而不会发送到BundleListeners。

7. 如果指定了一个BundleActivator,那么就调用它的stop方法。如果调用这个方法时抛出了异常,那么本方法继续进行停止bundle的过程,而且在执行完剩余代码之后抛出异常:BundleException。

8. 取消注册任何bundle注册的服务。

9. 释放bundle使用的任何服务。

10. 移除bundle注册的任何监听器。

11. 如果bundle的状态是UNINSTALLED,那么由于在BundleActivator. stop运行中卸载了bundle,那么抛出BundleException。v 12. 设置bundle状态为RESOLVED。

13. 发出bundle事件BundleEvent.STOPPED。

前置条件是:

  • getState() 方法返回值为{ACTIVE}。
如果没有抛出异常, 后置条件:

  • bundle的持久状态标记为停止(stopped);
  • getState() 方法返回值不是{ACTIVE, STOPPING};
  • 调用了BundleActivator.stop()方法,而且没有抛出异常。
如果抛出了异常,后置条件:

  • bundle的持久状态标记为停止(stopped);
Throws BundleException – 如果不能加载bundle启动器,或者执行中抛出了异常。

IllegalStateException – 如果已经卸载了bundle或者bundle试图修改自己的状态。

SecurityException – 如果Java运行环境支持权限而调用者没有相应的管理权限:AdminPermission[this,EXECUTE]。

6.1.4.25. public void uninstall( ) throws BundleException

卸载bundle。

这个方法的调用会通知其他bundle已经卸载了这个bundle,而且将bundle的状态设置为UNINSTALLED。框架必须要移除所有可以移除的相关资源。

如果这个bundle已经导出了包,框架必须要保证这些卸载后的bundle的导出包对导入的bundle还是可用的,直到重新启动框架或者是调用了方法PackageAdmin.refreshPackages。

卸载过程步骤如下:

1. 如果bundle状态为UNINSTALLED,那么抛出IllegalStateException 异常。

2. 如果bundle状态为ACTIVE,STARTING或者STOPPING,那么使用Bundle.stop方法来停止bundle。如果stop方法抛出了异常,那么发出包含这个异常的框架事件:FrameworkEvent.ERROR。

3. 设置bundle状态为UNINSTALLED。

4. 发出bundle事件BundleEvent.UNINSTALLED。

5. bundle和其他框架分配给bundle的固定存储区域由框架回收。

前置条件是:

  • getState() 方法返回值不是{UNINSTALLED}。
如果没有抛出异常, 后置条件:

  • getState() 方法返回值是{UNINSTALLED}
  • 已经卸载了bundle。
如果抛出了异常,后置条件:

  • getState() 方法返回值不是{UNINSTALLED}
  • 没有卸载bundle。
Throws BundleException – 如果卸载失败。如果任何线程试图修改bundle状态,但是却没有及时返回会抛出这个异常。

IllegalStateException – 如果已经卸载了bundle或者bundle试图修改自己的状态。

SecurityException – 如果Java运行环境支持权限而调用者没有相应的管理权限:AdminPermission[this, LIFECYCLE]。

6.1.4.26. public void update( ) throws BundleException

更新bundle。

如果bundle状态为ACTIVE,那么必须要停止bundle而且等更新完毕之后再启动bundle。如果更新的bundle导出了包,那么不能对这些导出包进行更新。

直到重新启动框架或者是调用了方法PackageAdmin.refreshPackages,这些导出包都维持原来的版本。

更新过程步骤如下:

1. 如果bundle状态为UNINSTALLED,那么抛出IllegalStateException异常。

2. 如果bundle状态为ACTIVE,STARTING或者STOPPING,那么使用Bundle.stop方法来停止bundle。如果stop方法抛出了异常,那么重新抛出这个异常来终止更新过程。

3. 根据bundle的Constants.BUNDLE_UPDATELOCATION描述的位置信息(如果有提供),或者是bundle的原始位置信息来下载新的版本。

4. 根据框架的实现来翻译位置信息,通常为URL,然后从这个位置获得新的版本。

5. 安装bundle的新版本。如果框架不能安装bundle的新版本,那么保留原来的版本,而且在完成剩下步骤之后抛出BundleException异常。

6. 如果bundle声明了Bundle-RequiredExecutionEnvironment头标,那么将执行环境和列出的执行环境进行比较。如果不是全部匹配,那么保留原来版本,而且在完成剩下步骤之后抛出BundleException异常。

7. 设置bundle状态为INSTALLED。

8. 如果成功安装了bundle的新版本,那么发出BundleEvent.UPDATED bundle事件。

9. 如果bundle最初状态为ACTIVE,那么按照Bundle.start所描述的那样启动bundle。如果Bundle.start方法抛出了异常,那么发出一个包含了异常的框架事件:FrameworkEvent.ERROR。

前置条件是:

  • getState() 方法返回值不在{ UNINSTALLED }中
如果没有抛出异常, 后置条件:

  • getState() 方法返回值在{ INSTALLED, RESOLVED,ACTIVE }中
  • 已经更新了bundle。
如果抛出了异常,后置条件:

  • getState() 方法返回值在{ INSTALLED, RESOLVED,ACTIVE }中
  • 没有更新bundle。
Throws BundleException – 如果更新失败。如果任何线程试图修改bundle状态,但是却没有及时返回会抛出这个异常。

IllegalStateException – 如果已经卸载bundle或者bundle试图修改自己状态。

SecurityException – 如果Java运行环境支持权限而调用者没有对当前bundle和更新后bundle相应的管理权限:AdminPermission[this, LIFECYCLE]。
See Also stop()[p.132] , start()[p.131]

6.1.4.27. public void update( InputStream in ) throws BundleException

in 读入新bundle的输入流(InputStream)
从一个输入流更新bundle。

按照Bundle.update()方法中描述的步骤来进行,除了读取的是从一个提供的输入流而不是URL。方法执行完毕之后一定要关闭输入流,即使执行抛出了异常。
Throws BundleException – 如果更新失败或者是不能读取输入流。

IllegalStateException – 如果已经卸载bundle或者bundle试图修改自己状态。

SecurityException – 如果Java运行环境支持权限而调用者没有对当前bundle和更新后bundle相应的管理权限:AdminPermission[this, LIFECYCLE]。
See Also update()[p.134]
查看评论