0N/A/*
2362N/A * Copyright (c) 1996, 2009, Oracle and/or its affiliates. All rights reserved.
0N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
0N/A *
0N/A * This code is free software; you can redistribute it and/or modify it
0N/A * under the terms of the GNU General Public License version 2 only, as
2362N/A * published by the Free Software Foundation. Oracle designates this
0N/A * particular file as subject to the "Classpath" exception as provided
2362N/A * by Oracle in the LICENSE file that accompanied this code.
0N/A *
0N/A * This code is distributed in the hope that it will be useful, but WITHOUT
0N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
0N/A * version 2 for more details (a copy is included in the LICENSE file that
0N/A * accompanied this code).
0N/A *
0N/A * You should have received a copy of the GNU General Public License version
0N/A * 2 along with this work; if not, write to the Free Software Foundation,
0N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
0N/A *
2362N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
2362N/A * or visit www.oracle.com if you need additional information or have any
2362N/A * questions.
0N/A */
0N/A
0N/Apackage java.beans;
0N/A
0N/Aimport com.sun.beans.finder.ClassFinder;
0N/A
1077N/Aimport java.applet.Applet;
1077N/Aimport java.applet.AppletContext;
1077N/Aimport java.applet.AppletStub;
1077N/Aimport java.applet.AudioClip;
0N/A
1077N/Aimport java.awt.Image;
0N/A
0N/Aimport java.beans.beancontext.BeanContext;
0N/A
1077N/Aimport java.io.IOException;
1077N/Aimport java.io.InputStream;
1077N/Aimport java.io.ObjectInputStream;
1077N/Aimport java.io.ObjectStreamClass;
1077N/Aimport java.io.StreamCorruptedException;
0N/A
0N/Aimport java.net.URL;
1077N/A
1077N/Aimport java.security.AccessController;
1077N/Aimport java.security.PrivilegedAction;
1077N/A
1077N/Aimport java.util.Enumeration;
1077N/Aimport java.util.Hashtable;
1077N/Aimport java.util.Iterator;
1077N/Aimport java.util.Vector;
1077N/A
0N/A/**
0N/A * This class provides some general purpose beans control methods.
0N/A */
0N/A
0N/Apublic class Beans {
0N/A
0N/A /**
0N/A * <p>
0N/A * Instantiate a JavaBean.
0N/A * </p>
0N/A *
0N/A * @param cls the class-loader from which we should create
0N/A * the bean. If this is null, then the system
0N/A * class-loader is used.
0N/A * @param beanName the name of the bean within the class-loader.
0N/A * For example "sun.beanbox.foobah"
0N/A *
1077N/A * @exception ClassNotFoundException if the class of a serialized
0N/A * object could not be found.
1077N/A * @exception IOException if an I/O error occurs.
0N/A */
0N/A
1077N/A public static Object instantiate(ClassLoader cls, String beanName) throws IOException, ClassNotFoundException {
0N/A return Beans.instantiate(cls, beanName, null, null);
0N/A }
0N/A
0N/A /**
0N/A * <p>
0N/A * Instantiate a JavaBean.
0N/A * </p>
0N/A *
0N/A * @param cls the class-loader from which we should create
0N/A * the bean. If this is null, then the system
0N/A * class-loader is used.
0N/A * @param beanName the name of the bean within the class-loader.
0N/A * For example "sun.beanbox.foobah"
0N/A * @param beanContext The BeanContext in which to nest the new bean
0N/A *
1077N/A * @exception ClassNotFoundException if the class of a serialized
0N/A * object could not be found.
1077N/A * @exception IOException if an I/O error occurs.
0N/A */
0N/A
1077N/A public static Object instantiate(ClassLoader cls, String beanName, BeanContext beanContext) throws IOException, ClassNotFoundException {
0N/A return Beans.instantiate(cls, beanName, beanContext, null);
0N/A }
0N/A
0N/A /**
0N/A * Instantiate a bean.
0N/A * <p>
0N/A * The bean is created based on a name relative to a class-loader.
0N/A * This name should be a dot-separated name such as "a.b.c".
0N/A * <p>
0N/A * In Beans 1.0 the given name can indicate either a serialized object
0N/A * or a class. Other mechanisms may be added in the future. In
0N/A * beans 1.0 we first try to treat the beanName as a serialized object
0N/A * name then as a class name.
0N/A * <p>
0N/A * When using the beanName as a serialized object name we convert the
0N/A * given beanName to a resource pathname and add a trailing ".ser" suffix.
0N/A * We then try to load a serialized object from that resource.
0N/A * <p>
0N/A * For example, given a beanName of "x.y", Beans.instantiate would first
0N/A * try to read a serialized object from the resource "x/y.ser" and if
0N/A * that failed it would try to load the class "x.y" and create an
0N/A * instance of that class.
0N/A * <p>
0N/A * If the bean is a subtype of java.applet.Applet, then it is given
0N/A * some special initialization. First, it is supplied with a default
0N/A * AppletStub and AppletContext. Second, if it was instantiated from
0N/A * a classname the applet's "init" method is called. (If the bean was
0N/A * deserialized this step is skipped.)
0N/A * <p>
0N/A * Note that for beans which are applets, it is the caller's responsiblity
0N/A * to call "start" on the applet. For correct behaviour, this should be done
0N/A * after the applet has been added into a visible AWT container.
0N/A * <p>
0N/A * Note that applets created via beans.instantiate run in a slightly
0N/A * different environment than applets running inside browsers. In
0N/A * particular, bean applets have no access to "parameters", so they may
0N/A * wish to provide property get/set methods to set parameter values. We
0N/A * advise bean-applet developers to test their bean-applets against both
0N/A * the JDK appletviewer (for a reference browser environment) and the
0N/A * BDK BeanBox (for a reference bean container).
0N/A *
0N/A * @param cls the class-loader from which we should create
0N/A * the bean. If this is null, then the system
0N/A * class-loader is used.
0N/A * @param beanName the name of the bean within the class-loader.
0N/A * For example "sun.beanbox.foobah"
0N/A * @param beanContext The BeanContext in which to nest the new bean
0N/A * @param initializer The AppletInitializer for the new bean
0N/A *
1077N/A * @exception ClassNotFoundException if the class of a serialized
0N/A * object could not be found.
1077N/A * @exception IOException if an I/O error occurs.
0N/A */
0N/A
0N/A public static Object instantiate(ClassLoader cls, String beanName, BeanContext beanContext, AppletInitializer initializer)
1077N/A throws IOException, ClassNotFoundException {
0N/A
1077N/A InputStream ins;
1077N/A ObjectInputStream oins = null;
0N/A Object result = null;
0N/A boolean serialized = false;
1077N/A IOException serex = null;
0N/A
0N/A // If the given classloader is null, we check if an
0N/A // system classloader is available and (if so)
0N/A // use that instead.
0N/A // Note that calls on the system class loader will
0N/A // look in the bootstrap class loader first.
0N/A if (cls == null) {
0N/A try {
0N/A cls = ClassLoader.getSystemClassLoader();
0N/A } catch (SecurityException ex) {
0N/A // We're not allowed to access the system class loader.
0N/A // Drop through.
0N/A }
0N/A }
0N/A
0N/A // Try to find a serialized object with this name
0N/A final String serName = beanName.replace('.','/').concat(".ser");
0N/A final ClassLoader loader = cls;
1077N/A ins = (InputStream)AccessController.doPrivileged
1077N/A (new PrivilegedAction() {
0N/A public Object run() {
0N/A if (loader == null)
0N/A return ClassLoader.getSystemResourceAsStream(serName);
0N/A else
0N/A return loader.getResourceAsStream(serName);
0N/A }
0N/A });
0N/A if (ins != null) {
0N/A try {
0N/A if (cls == null) {
0N/A oins = new ObjectInputStream(ins);
0N/A } else {
0N/A oins = new ObjectInputStreamWithLoader(ins, cls);
0N/A }
0N/A result = oins.readObject();
0N/A serialized = true;
0N/A oins.close();
1077N/A } catch (IOException ex) {
0N/A ins.close();
0N/A // Drop through and try opening the class. But remember
0N/A // the exception in case we can't find the class either.
0N/A serex = ex;
0N/A } catch (ClassNotFoundException ex) {
0N/A ins.close();
0N/A throw ex;
0N/A }
0N/A }
0N/A
0N/A if (result == null) {
0N/A // No serialized object, try just instantiating the class
0N/A Class cl;
0N/A
0N/A try {
0N/A cl = ClassFinder.findClass(beanName, cls);
0N/A } catch (ClassNotFoundException ex) {
0N/A // There is no appropriate class. If we earlier tried to
0N/A // deserialize an object and got an IO exception, throw that,
0N/A // otherwise rethrow the ClassNotFoundException.
0N/A if (serex != null) {
0N/A throw serex;
0N/A }
0N/A throw ex;
0N/A }
0N/A
0N/A /*
0N/A * Try to instantiate the class.
0N/A */
0N/A
0N/A try {
0N/A result = cl.newInstance();
0N/A } catch (Exception ex) {
0N/A // We have to remap the exception to one in our signature.
0N/A // But we pass extra information in the detail message.
0N/A throw new ClassNotFoundException("" + cl + " : " + ex, ex);
0N/A }
0N/A }
0N/A
0N/A if (result != null) {
0N/A
0N/A // Ok, if the result is an applet initialize it.
0N/A
0N/A AppletStub stub = null;
0N/A
0N/A if (result instanceof Applet) {
0N/A Applet applet = (Applet) result;
0N/A boolean needDummies = initializer == null;
0N/A
0N/A if (needDummies) {
0N/A
0N/A // Figure our the codebase and docbase URLs. We do this
0N/A // by locating the URL for a known resource, and then
0N/A // massaging the URL.
0N/A
0N/A // First find the "resource name" corresponding to the bean
0N/A // itself. So a serialzied bean "a.b.c" would imply a
0N/A // resource name of "a/b/c.ser" and a classname of "x.y"
0N/A // would imply a resource name of "x/y.class".
0N/A
0N/A final String resourceName;
0N/A
0N/A if (serialized) {
0N/A // Serialized bean
0N/A resourceName = beanName.replace('.','/').concat(".ser");
0N/A } else {
0N/A // Regular class
0N/A resourceName = beanName.replace('.','/').concat(".class");
0N/A }
0N/A
0N/A URL objectUrl = null;
0N/A URL codeBase = null;
0N/A URL docBase = null;
0N/A
0N/A // Now get the URL correponding to the resource name.
0N/A
0N/A final ClassLoader cloader = cls;
0N/A objectUrl = (URL)
1077N/A AccessController.doPrivileged
1077N/A (new PrivilegedAction() {
0N/A public Object run() {
0N/A if (cloader == null)
0N/A return ClassLoader.getSystemResource
0N/A (resourceName);
0N/A else
0N/A return cloader.getResource(resourceName);
0N/A }
0N/A });
0N/A
0N/A // If we found a URL, we try to locate the docbase by taking
0N/A // of the final path name component, and the code base by taking
0N/A // of the complete resourceName.
0N/A // So if we had a resourceName of "a/b/c.class" and we got an
0N/A // objectURL of "file://bert/classes/a/b/c.class" then we would
0N/A // want to set the codebase to "file://bert/classes/" and the
0N/A // docbase to "file://bert/classes/a/b/"
0N/A
0N/A if (objectUrl != null) {
0N/A String s = objectUrl.toExternalForm();
0N/A
0N/A if (s.endsWith(resourceName)) {
0N/A int ix = s.length() - resourceName.length();
0N/A codeBase = new URL(s.substring(0,ix));
0N/A docBase = codeBase;
0N/A
0N/A ix = s.lastIndexOf('/');
0N/A
0N/A if (ix >= 0) {
0N/A docBase = new URL(s.substring(0,ix+1));
0N/A }
0N/A }
0N/A }
0N/A
0N/A // Setup a default context and stub.
0N/A BeansAppletContext context = new BeansAppletContext(applet);
0N/A
0N/A stub = (AppletStub)new BeansAppletStub(applet, context, codeBase, docBase);
0N/A applet.setStub(stub);
0N/A } else {
0N/A initializer.initialize(applet, beanContext);
0N/A }
0N/A
0N/A // now, if there is a BeanContext, add the bean, if applicable.
0N/A
0N/A if (beanContext != null) {
0N/A beanContext.add(result);
0N/A }
0N/A
0N/A // If it was deserialized then it was already init-ed.
0N/A // Otherwise we need to initialize it.
0N/A
0N/A if (!serialized) {
0N/A // We need to set a reasonable initial size, as many
0N/A // applets are unhappy if they are started without
0N/A // having been explicitly sized.
0N/A applet.setSize(100,100);
0N/A applet.init();
0N/A }
0N/A
0N/A if (needDummies) {
0N/A ((BeansAppletStub)stub).active = true;
0N/A } else initializer.activate(applet);
0N/A
0N/A } else if (beanContext != null) beanContext.add(result);
0N/A }
0N/A
0N/A return result;
0N/A }
0N/A
0N/A
0N/A /**
0N/A * From a given bean, obtain an object representing a specified
0N/A * type view of that source object.
0N/A * <p>
0N/A * The result may be the same object or a different object. If
0N/A * the requested target view isn't available then the given
0N/A * bean is returned.
0N/A * <p>
0N/A * This method is provided in Beans 1.0 as a hook to allow the
0N/A * addition of more flexible bean behaviour in the future.
0N/A *
0N/A * @param bean Object from which we want to obtain a view.
0N/A * @param targetType The type of view we'd like to get.
0N/A *
0N/A */
0N/A public static Object getInstanceOf(Object bean, Class<?> targetType) {
0N/A return bean;
0N/A }
0N/A
0N/A /**
0N/A * Check if a bean can be viewed as a given target type.
0N/A * The result will be true if the Beans.getInstanceof method
0N/A * can be used on the given bean to obtain an object that
0N/A * represents the specified targetType type view.
0N/A *
0N/A * @param bean Bean from which we want to obtain a view.
0N/A * @param targetType The type of view we'd like to get.
0N/A * @return "true" if the given bean supports the given targetType.
0N/A *
0N/A */
0N/A public static boolean isInstanceOf(Object bean, Class<?> targetType) {
0N/A return Introspector.isSubclass(bean.getClass(), targetType);
0N/A }
0N/A
0N/A
0N/A /**
0N/A * Test if we are in design-mode.
0N/A *
0N/A * @return True if we are running in an application construction
0N/A * environment.
0N/A *
1077N/A * @see DesignMode
0N/A */
0N/A public static boolean isDesignTime() {
4373N/A return ThreadGroupContext.getContext().isDesignTime();
0N/A }
0N/A
0N/A /**
0N/A * Determines whether beans can assume a GUI is available.
0N/A *
0N/A * @return True if we are running in an environment where beans
0N/A * can assume that an interactive GUI is available, so they
0N/A * can pop up dialog boxes, etc. This will normally return
0N/A * true in a windowing environment, and will normally return
0N/A * false in a server environment or if an application is
0N/A * running as part of a batch job.
0N/A *
1077N/A * @see Visibility
0N/A *
0N/A */
0N/A public static boolean isGuiAvailable() {
4373N/A return ThreadGroupContext.getContext().isGuiAvailable();
0N/A }
0N/A
0N/A /**
0N/A * Used to indicate whether of not we are running in an application
0N/A * builder environment.
0N/A *
0N/A * <p>Note that this method is security checked
0N/A * and is not available to (for example) untrusted applets.
0N/A * More specifically, if there is a security manager,
0N/A * its <code>checkPropertiesAccess</code>
0N/A * method is called. This could result in a SecurityException.
0N/A *
0N/A * @param isDesignTime True if we're in an application builder tool.
0N/A * @exception SecurityException if a security manager exists and its
0N/A * <code>checkPropertiesAccess</code> method doesn't allow setting
0N/A * of system properties.
0N/A * @see SecurityManager#checkPropertiesAccess
0N/A */
0N/A
0N/A public static void setDesignTime(boolean isDesignTime)
0N/A throws SecurityException {
0N/A SecurityManager sm = System.getSecurityManager();
0N/A if (sm != null) {
0N/A sm.checkPropertiesAccess();
0N/A }
4373N/A ThreadGroupContext.getContext().setDesignTime(isDesignTime);
0N/A }
0N/A
0N/A /**
0N/A * Used to indicate whether of not we are running in an environment
0N/A * where GUI interaction is available.
0N/A *
0N/A * <p>Note that this method is security checked
0N/A * and is not available to (for example) untrusted applets.
0N/A * More specifically, if there is a security manager,
0N/A * its <code>checkPropertiesAccess</code>
0N/A * method is called. This could result in a SecurityException.
0N/A *
0N/A * @param isGuiAvailable True if GUI interaction is available.
0N/A * @exception SecurityException if a security manager exists and its
0N/A * <code>checkPropertiesAccess</code> method doesn't allow setting
0N/A * of system properties.
0N/A * @see SecurityManager#checkPropertiesAccess
0N/A */
0N/A
0N/A public static void setGuiAvailable(boolean isGuiAvailable)
0N/A throws SecurityException {
0N/A SecurityManager sm = System.getSecurityManager();
0N/A if (sm != null) {
0N/A sm.checkPropertiesAccess();
0N/A }
4373N/A ThreadGroupContext.getContext().setGuiAvailable(isGuiAvailable);
0N/A }
0N/A}
0N/A
0N/A/**
0N/A * This subclass of ObjectInputStream delegates loading of classes to
0N/A * an existing ClassLoader.
0N/A */
0N/A
0N/Aclass ObjectInputStreamWithLoader extends ObjectInputStream
0N/A{
0N/A private ClassLoader loader;
0N/A
0N/A /**
0N/A * Loader must be non-null;
0N/A */
0N/A
0N/A public ObjectInputStreamWithLoader(InputStream in, ClassLoader loader)
0N/A throws IOException, StreamCorruptedException {
0N/A
0N/A super(in);
0N/A if (loader == null) {
0N/A throw new IllegalArgumentException("Illegal null argument to ObjectInputStreamWithLoader");
0N/A }
0N/A this.loader = loader;
0N/A }
0N/A
0N/A /**
0N/A * Use the given ClassLoader rather than using the system class
0N/A */
0N/A protected Class resolveClass(ObjectStreamClass classDesc)
0N/A throws IOException, ClassNotFoundException {
0N/A
0N/A String cname = classDesc.getName();
0N/A return ClassFinder.resolveClass(cname, this.loader);
0N/A }
0N/A}
0N/A
0N/A/**
0N/A * Package private support class. This provides a default AppletContext
0N/A * for beans which are applets.
0N/A */
0N/A
0N/Aclass BeansAppletContext implements AppletContext {
0N/A Applet target;
1077N/A Hashtable imageCache = new Hashtable();
0N/A
0N/A BeansAppletContext(Applet target) {
0N/A this.target = target;
0N/A }
0N/A
0N/A public AudioClip getAudioClip(URL url) {
0N/A // We don't currently support audio clips in the Beans.instantiate
0N/A // applet context, unless by some luck there exists a URL content
0N/A // class that can generate an AudioClip from the audio URL.
0N/A try {
0N/A return (AudioClip) url.getContent();
0N/A } catch (Exception ex) {
0N/A return null;
0N/A }
0N/A }
0N/A
0N/A public synchronized Image getImage(URL url) {
0N/A Object o = imageCache.get(url);
0N/A if (o != null) {
0N/A return (Image)o;
0N/A }
0N/A try {
0N/A o = url.getContent();
0N/A if (o == null) {
0N/A return null;
0N/A }
0N/A if (o instanceof Image) {
0N/A imageCache.put(url, o);
0N/A return (Image) o;
0N/A }
0N/A // Otherwise it must be an ImageProducer.
0N/A Image img = target.createImage((java.awt.image.ImageProducer)o);
0N/A imageCache.put(url, img);
0N/A return img;
0N/A
0N/A } catch (Exception ex) {
0N/A return null;
0N/A }
0N/A }
0N/A
0N/A public Applet getApplet(String name) {
0N/A return null;
0N/A }
0N/A
1077N/A public Enumeration getApplets() {
1077N/A Vector applets = new Vector();
0N/A applets.addElement(target);
0N/A return applets.elements();
0N/A }
0N/A
0N/A public void showDocument(URL url) {
0N/A // We do nothing.
0N/A }
0N/A
0N/A public void showDocument(URL url, String target) {
0N/A // We do nothing.
0N/A }
0N/A
0N/A public void showStatus(String status) {
0N/A // We do nothing.
0N/A }
0N/A
0N/A public void setStream(String key, InputStream stream)throws IOException{
0N/A // We do nothing.
0N/A }
0N/A
0N/A public InputStream getStream(String key){
0N/A // We do nothing.
0N/A return null;
0N/A }
0N/A
1077N/A public Iterator getStreamKeys(){
0N/A // We do nothing.
0N/A return null;
0N/A }
0N/A}
0N/A
0N/A/**
0N/A * Package private support class. This provides an AppletStub
0N/A * for beans which are applets.
0N/A */
0N/Aclass BeansAppletStub implements AppletStub {
0N/A transient boolean active;
0N/A transient Applet target;
0N/A transient AppletContext context;
0N/A transient URL codeBase;
0N/A transient URL docBase;
0N/A
0N/A BeansAppletStub(Applet target,
0N/A AppletContext context, URL codeBase,
0N/A URL docBase) {
0N/A this.target = target;
0N/A this.context = context;
0N/A this.codeBase = codeBase;
0N/A this.docBase = docBase;
0N/A }
0N/A
0N/A public boolean isActive() {
0N/A return active;
0N/A }
0N/A
0N/A public URL getDocumentBase() {
0N/A // use the root directory of the applet's class-loader
0N/A return docBase;
0N/A }
0N/A
0N/A public URL getCodeBase() {
0N/A // use the directory where we found the class or serialized object.
0N/A return codeBase;
0N/A }
0N/A
0N/A public String getParameter(String name) {
0N/A return null;
0N/A }
0N/A
0N/A public AppletContext getAppletContext() {
0N/A return context;
0N/A }
0N/A
0N/A public void appletResize(int width, int height) {
0N/A // we do nothing.
0N/A }
0N/A}